[JASS] How to program this 2 Systems

Status
Not open for further replies.
Level 4
Joined
Aug 3, 2008
Messages
80
Hey all

2 Questions about creating 2 Systems:

1) How is it possible to program a fullscreen inventory save/load system in Jass?
It should save all carried items and a variables from the inventory (itemstats, itemabilitys, ....and so on)

2) How to create a Shield system in Jass like the shield spell from wow (power word: shield)
It should protect the hero from damage without hp reg or other stuff, just for example: shield has 500 hp so it protects the hero from 500 damage.

thx almii*
 
Level 18
Joined
Jan 21, 2006
Messages
2,552
1) How is it possible to program a fullscreen inventory save/load system in Jass?
It should save all carried items and a variables from the inventory (itemstats, itemabilitys, ....and so on)

There are already ones that exist. Go look. I believe Anachron's inventory system is full-screen but believe me its not going to be as easy as making Kraft Dinner. For the most part it involves images and trackables. The images give the system an interface while the trackables provide click-functionality.

2) How to create a Shield system in Jass like the shield spell from wow (power word: shield)
It should protect the hero from damage without hp reg or other stuff, just for example: shield has 500 hp so it protects the hero from 500 damage.

I believe there is an easy way to do this using the Banshee spell Anti-magic Shell - play around with this spell's field values (such as Shield Life) and see if you can't get something to work for you; if not then post back here.
 
Level 14
Joined
Jul 26, 2008
Messages
1,009
For Inventory like maybe TKoK has, it is not easy at all and yes, you're better of Downloading your own and tweaking it to your preference. Some are simpler than others. But most who make them are skilled in the upper levels of vJASS.

Here is my own spell like you have suggested. It requires TimerUtils and AutoIndex. This is really about as simple but efficient as I can make it without using DamageDetection or DamageModifying system. Also it cannot stop fatal damage (I.E. 300 damage when you only have 150 life left. That requires a BonusMod type setup.)

JASS:
scope Wall initializer InitTrig_Wall

globals
//"Abilities\\Spells\\Items\\StaffOfSanctuary\\Staff_Sanctuary_Target.mdl"
    private constant integer SPELLID    = 'Wall'
    private constant string mdl         = "Abilities\\Spells\\Orc\\SpiritLink\\SpiritLinkZapTarget.mdl"
    private real array Wall
    private trigger array EventTrigger
    private effect array WallFX
endglobals

private struct Data

    unit c
    unit t
    real dur
    real wall

    static method Timer takes nothing returns nothing
     local timer tim = GetExpiredTimer()
     local Data D = Data(GetTimerData(tim))
        call DestroyEffect(WallFX[GetUnitId(D.t)])
        call ReleaseTimer(tim)
        set Wall[GetUnitId(D.t)] = 0
        call DestroyTrigger(EventTrigger[GetUnitId(D.t)])
        set EventTrigger[GetUnitId(D.t)] = null
        set D.c = null
        set WallFX[GetUnitId(D.t)] = null
        set D.t = null
        call D.destroy()
    endmethod

    static method Conditions takes nothing returns boolean
     local integer lvl = GetUnitAbilityLevel(GetEventDamageSource(), SPELLID)
     local texttag tag = CreateTextTag()
            if GetRandomInt(1,3) == 3 then
                call DestroyEffect(AddSpecialEffectTarget("Abilities\\Spells\\Human\\Defend\\DefendCaster.mdl", GetTriggerUnit(), "head"))
            endif
            call SetWidgetLife(GetTriggerUnit(), GetWidgetLife(GetTriggerUnit()) + GetEventDamage())
            set Wall[GetUnitId(GetTriggerUnit())] = Wall[GetUnitId(GetTriggerUnit())] - GetEventDamage()
            call SetTextTagText(tag, I2S(R2I(Wall[GetUnitId(GetTriggerUnit())]))+"HP", 0.024)
            call SetTextTagPos(tag, GetUnitX(GetTriggerUnit()), GetUnitY(GetTriggerUnit()), 0.00)
            call SetTextTagColor(tag, 0, 0, 255, 255)
            call SetTextTagVelocity(tag, 0, 0.03)
            call SetTextTagVisibility(tag, true)
            call SetTextTagFadepoint(tag, 0.75)
            call SetTextTagLifespan(tag, 1.5)
            call SetTextTagPermanent(tag, false)
            if Wall[GetUnitId(GetTriggerUnit())] < 1 or GetUnitAbilityLevel(GetTriggerUnit(), 'B00B') < 1 then
                call UnitRemoveAbility(GetTriggerUnit(), 'B00B')
                call DestroyEffect(WallFX[GetUnitId(GetTriggerUnit())])
                call DestroyTrigger(EventTrigger[GetUnitId(GetTriggerUnit())])
                set EventTrigger[GetUnitId(GetTriggerUnit())] = null
                set WallFX[GetUnitId(GetTriggerUnit())] = null
                call DestroyTextTag(tag)
                set tag = null
            endif
     return false
    endmethod

    static method create takes unit caster, unit target, integer lvl returns Data
     local xecast xc = xecast.createA()
     local Data D = Data.allocate()
     local timer tim = NewTimer()
        set D.c = caster
        set D.t = target
        set D.dur = 0
        set D.wall = 50+(50*lvl*lvl)*(0.7+0.1*lvl)+SpellStat(D.c, true)*(lvl*0.35+0.75)

        set xc.abilityid    = 'duwa' 
        set xc.level = GetUnitAbilityLevel(caster, SPELLID)
        set xc.orderstring  = "bloodlust"
        set xc.owningplayer = GetOwningPlayer(caster)
        call xc.castOnTarget( target )
        
        if EventTrigger[GetUnitId(D.t)] == null then
            set EventTrigger[GetUnitId(D.t)] = CreateTrigger()
            call TriggerRegisterUnitEvent(EventTrigger[GetUnitId(D.t)], D.t, EVENT_UNIT_DAMAGED)
            call TriggerAddCondition(EventTrigger[GetUnitId(D.t)], function Data.Conditions)
        endif

        if WallFX[GetUnitId(D.t)] == null then
            set WallFX[GetUnitId(D.t)] = AddSpecialEffectTarget(mdl, D.t, "chest")
        endif

        set Wall[GetUnitId(D.t)] = D.wall

        call SetTimerData(tim,D)
        call TimerStart(tim, 35+10*lvl, false, function Data.Timer)

     return D
    endmethod
    
endstruct

private function Conditions takes nothing returns boolean
    if GetSpellAbilityId() == SPELLID then
        call Data.create(GetTriggerUnit(), GetSpellTargetUnit(), GetUnitAbilityLevel(GetTriggerUnit(), SPELLID))
    endif
 return false
endfunction

//===========================================================================
public function InitTrig_Wall takes nothing returns nothing
 local trigger t = CreateTrigger()
    call TriggerRegisterAnyUnitEventBJ( t, EVENT_PLAYER_UNIT_SPELL_EFFECT )
    call TriggerAddCondition( t, function Conditions )
    call XE_PreloadAbility(SPELLID)
 set t = null
endfunction

endscope
 
Level 18
Joined
Jan 21, 2006
Messages
2,552
I am pretty sure that Anti-magic Shell can be modified to negate a specified amount of damage before dissipating. I think that this is how Abaddon's Aphotic Shield is setup, at least in older versions of DotA anyway.
 
Level 13
Joined
May 11, 2008
Messages
1,198
for your first request...not sure what you mean, but anyway i don't have an interest for such a thing.

for your second request...i think someone already made a system for it. attached is the scope that i edited to suit my purposes. if you need the original, you can probably do a search for it. there's probably enough information intact though that you may not need to.

Code:
scope Barrier initializer I

// The_Witcher's Shield System
//
// This is an easy to use shield system.
// it allows you to add shield points to a unit
// the shield works like in the game halo:
// the attacked unit doesn't receive any dmg, the shield gets it
// when the shield is down the unit is damaged
// the shield can reload constantly or after some seconds of not beeing attacked
//
// to give a unit shield points just use
//
//  call AddShield( yourunit, shieldHP, shieldreg per second, shielddamagefactor, show the bar, colorcode, time till reg starts, destroy when shieldhp = 0 )
//                    unit       real                real               real            boolean      string          real               boolean
//
// you can check whether a unit has already a shield with (it will return a boolean)
//  UnitHasShield( yourunit)
//                  unit
//
// to implement this system, just copy this trigger in your map
// it requires jngp to be edited/saved
//
// To get rid of a shield just use
//   call DestroyShield( which unit's)
//                         unit
//
// to show or hide the shield bar use
//   call ShowShield( WhichUnits, Show? )
//                      unit     boolean
//
// to get information about an existing shield use:
//    HP:           GetShieldHp(  unit  )
//    maxHP:        GetShieldMaxHp(  unit  )
//    percentHP:    GetShieldHpPercent(  unit  )
//    regeneration: GetShieldReg(  unit  ) 
//    TimeTillReg:  GetShieldTimeTillReg(  unit  )
//    DamageFactor: GetShieldDamageFactor(  unit  )
//
// to change the values of an existing shield use:
//    HP:           SetShieldHp(  unit, NewValue  )
//    maxHP:        SetShieldMaxHp(  unit, NewValue  )
//    percentHP:    SetShieldHpPercent(  unit, NewValue  )
//    regeneration: SetShieldReg(  unit, NewValue  )
//    TimeTillReg:  SetShieldTimeTillReg(  unit, NewValue  )
//    DamageFactor: SetShieldDamageFactor(  unit, NewValue  )
//
// have fun^^
// The (very small^^) Setup part
globals
private constant integer CloudStrifeShield = 'A09J'//Cloud's Barrier AbilityId
    private constant real size = 0.01  // the shieldbar's size (should be 0.01 for best result)
    private constant integer lifeabi = 'A001'  // A ability which gives a high instant life bonus
    private constant real interval = 0.01  // the timer interval (should be 0.01 but if laggy then just change it)
endglobals
// end of Setup!!
private struct shield
unit u
real hp
real fullhp
real reg
real f
string code
texttag t
real r
timer time
boolean kill 
integer i
real damage = 0
boolean show
endstruct

globals
    private trigger trg = CreateTrigger()
    private group g = CreateGroup()
    private hashtable h = InitHashtable()
    private integer total = 0
    private unit array units
    private timer tim = CreateTimer()
endglobals

function UnitHasShield takes unit u returns boolean
    return LoadInteger(h,GetHandleId(u),0) != 0
endfunction

function DestroyShield takes unit whichunits returns nothing
    local shield dat = LoadInteger(h,GetHandleId(whichunits),0)
    local shield dat2 = LoadInteger(h,GetHandleId(units[total-1]),0)
    if dat != 0 then
        call DestroyTextTag(dat.t)
        call DestroyTimer(dat.time)
        call FlushChildHashtable(h,GetHandleId(whichunits))
        set total = total - 1
        set units[dat.i] = units[total]
        set dat2.i = dat.i
        call dat.destroy()
    endif
    if total == 0 then
        call PauseTimer(tim)
    endif
endfunction

private function regeneration takes nothing returns nothing
    local shield dat
    local string s = "||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||"
    local integer k
    local integer i = 0
    loop
        exitwhen i >= total
        set dat = LoadInteger(h,GetHandleId(units[i]),0)
        if TimerGetRemaining(dat.time) == 0 then
            if dat.hp < dat.fullhp then
                set dat.hp = dat.hp + dat.reg
            else
                set dat.hp = dat.fullhp
            endif
        endif
        set k = IMinBJ(R2I(100 * dat.hp / dat.fullhp),100)
        call SetTextTagText(dat.t, dat.code + SubString(s,0, k ) + "'|r"  + SubString(s,k + 1,StringLength(s)) , size)
        call SetTextTagPos(dat.t,GetUnitX(dat.u) -40, GetUnitY(dat.u),-100)
        if dat.damage != 0 then
            if dat.hp > (dat.damage * dat.f) then
                set dat.hp = dat.hp - (dat.damage * dat.f)
                call SetWidgetLife( dat.u,GetWidgetLife(dat.u) + dat.damage)
            else
                call SetWidgetLife( dat.u,GetWidgetLife(dat.u) + dat.hp)
                set dat.hp = 0
            endif
            set dat.damage = 0
        endif
        call UnitRemoveAbility(dat.u,lifeabi)
        if dat.hp <= 0 and dat.kill == true then
            call DestroyShield(dat.u)
            set i = i - 1
        endif
        set i = i + 1
    endloop
    set s = null
endfunction

private function attack takes nothing returns nothing
    local shield dat = LoadInteger(h,GetHandleId(GetTriggerUnit()),0)
    local timer t 
    if dat != 0 then
        if dat.hp > 0 then
            set dat.damage = dat.damage + GetEventDamage()
        endif     
        call TimerStart(dat.time,dat.r,false,null)
    endif
endfunction

function AddShield takes unit towhich, real hp, real RegPerSec, real TimeTillReg, real dmgfactor, string colorcode, boolean destroy, boolean ShowBar returns nothing
    local shield dat
    if LoadInteger(h,GetHandleId(towhich),0) != 0 then
        call DestroyShield(towhich)
    endif
    set dat = shield.create()
    set dat.u = towhich
    set dat.fullhp = hp
    set dat.hp = hp
    set dat.reg = RegPerSec / 100
    set dat.f = dmgfactor
    set dat.code = colorcode
    set dat.r = TimeTillReg
    set dat.kill = destroy
    set dat.time = CreateTimer()
    set dat.t = CreateTextTag()
    set dat.show = ShowBar
    call SetTextTagVisibility(dat.t,ShowBar)
    set dat.i = total
    if not IsUnitInGroup(dat.u,g) then
        call GroupAddUnit(g,dat.u)
        call TriggerRegisterUnitEvent( trg, towhich, EVENT_UNIT_DAMAGED )
    endif
    set units[total] = dat.u
    set total = total + 1
    call SaveInteger(h,GetHandleId(dat.u),0,dat)
    if total == 1 then
        call TimerStart(tim,interval,true,function regeneration)
    endif
endfunction

private function kill takes nothing returns nothing
    call DestroyShield(GetTriggerUnit())
endfunction

function ShowShield takes unit u, boolean flag returns nothing
    local shield dat = LoadInteger(h,GetHandleId(u),0)
    if dat != 0 then
        set dat.show = flag
        call SetTextTagVisibility(dat.t,flag)
    endif
endfunction

function GetShieldHpPercent takes unit u returns real
    local shield dat = LoadInteger(h,GetHandleId(u),0)
    if dat != 0 then
        return dat.hp / dat.fullhp * 100.0
    endif
    return .0
endfunction

function GetShieldHp takes unit u returns real
    local shield dat = LoadInteger(h,GetHandleId(u),0)
    if dat != 0 then
        return dat.hp
    endif
    return .0
endfunction

function GetShieldMaxHp takes unit u returns real
    local shield dat = LoadInteger(h,GetHandleId(u),0)
    if dat != 0 then
        return dat.fullhp
    endif
    return .0
endfunction

function GetShieldReg takes unit u returns real
    local shield dat = LoadInteger(h,GetHandleId(u),0)
    if dat != 0 then
        return dat.reg*100
    endif
    return .0
endfunction

function GetShieldTimeTillReg takes unit u returns real
    local shield dat = LoadInteger(h,GetHandleId(u),0)
    if dat != 0 then
        return dat.r
    endif
    return .0
endfunction

function GetShieldDamageFactor takes unit u returns real
    local shield dat = LoadInteger(h,GetHandleId(u),0)
    if dat != 0 then
        return dat.f
    endif
    return .0
endfunction

function SetShieldHpPercent takes unit u, real new returns nothing
    local shield dat = LoadInteger(h,GetHandleId(u),0)
    if dat != 0 then
        set dat.hp = dat.fullhp * new
        if dat.fullhp < dat.hp then
            set dat.hp = dat.fullhp
        endif
    endif
endfunction

function SetShieldHp takes unit u, real new returns nothing
    local shield dat = LoadInteger(h,GetHandleId(u),0)
    if dat != 0 then
        set dat.hp = new
        if dat.fullhp < dat.hp then
            set dat.hp = dat.fullhp
        endif
    endif
endfunction

function SetShieldMaxHp takes unit u, real new returns nothing
    local shield dat = LoadInteger(h,GetHandleId(u),0)
    if dat != 0 then
        set dat.fullhp = new
        if dat.fullhp < dat.hp then
            set dat.hp = dat.fullhp
        endif
    endif
endfunction

function SetShieldReg takes unit u, real new returns nothing
    local shield dat = LoadInteger(h,GetHandleId(u),0)
    if dat != 0 then
        set dat.reg = new/100
    endif
endfunction
                                                                            
function SetShieldTimeTillReg takes unit u, real new returns nothing
    local shield dat = LoadInteger(h,GetHandleId(u),0)
    if dat != 0 then
        set dat.r = new
        call TimerStart(dat.time,dat.r,false,null)
    endif
endfunction

function SetShieldDamageFactor takes unit u, real new returns nothing
    local shield dat = LoadInteger(h,GetHandleId(u),0)
    if dat != 0 then
        set dat.f = new
    endif
endfunction
//thought about modifying the shield to the below...haven't really used it though...
function AddShieldTAF takes unit u, real realhp, real realregen returns nothing
        if UnitHasShield(u) then
            call DestroyShield(u)
            endif
call AddShield(u, realhp,realregen,1.0,1.0,"|cff0000ff",true,false)
//function AddShield takes unit towhich, real hp, real RegPerSec, real TimeTillReg, real dmgfactor, string colorcode, boolean destroy, boolean ShowBar returns nothing
endfunction


//modified the shield to be like ff7 barrier spell like you see below
function AddShieldCloudStrife takes unit u, real realwidgetlifehp, real realnegativedecimalregen returns nothing
        if UnitHasShield(u) then
            call DestroyShield(u)
            endif
call AddShield(u, realwidgetlifehp,realwidgetlifehp * realnegativedecimalregen,3.0,1.0,"|cff0000ff",true,false)
//function AddShield takes unit towhich, real hp, real RegPerSec, real TimeTillReg, real dmgfactor, string colorcode, boolean destroy, boolean ShowBar returns nothing
endfunction

private function f takes nothing returns boolean
local unit tu = GetSpellTargetUnit()
local unit ut = GetTriggerUnit()
local integer lvl = GetUnitAbilityLevel(ut,CloudStrifeShield)
local real lifehp = GetWidgetLife(tu)
call AddShieldCloudStrife(tu,lifehp*(0.40+(0.20*lvl)),-1.00/(-5.00 +(15.00*lvl)))
//DESCRIPTION:
//FIRST OF ALL NOTICE THAT THE SHOW BAR FUNCTION SEEMS TO NOT WORK
//SO DON'T USE TRUE IN THAT FIELD
//THE ONLY OTHER BOOLEAN YOU NEED TO WORRY ABOUT IS WHETHER THE SHIELD IS LIKE
//A ONE TIME CAST OR IF IT IS A PASSIVE SHIELD FOR GENERAL COMBAT LIKE PROTOSS SHIELDS
//IN THIS ABILITY'S CASE IT IS THE FORMER, A ONE TIME CAST OF A SHIELD, CALLED BARRIER
//
//AT EACH LEVEL NONCOMBAT (DELAY OF 3 SECONDS) DEGENERATION OF SHIELD
//REGENERATION IS... NEGATIVE 1 DIVIDED BY NEGATIVE 5 PLUS 15 TIMES LEVEL OF THE ABILITY
//SO... LEVEL 1, REGENERATION OF -1 DIVIDED BY TEN, OR 1/10 DEGENERATION
//LEVEL 2, REGENERATION OF -1 DIVIDED BY TWENTY FIVE, OR 1/25 DEGENERATION
//LEVEL 3, REGENERATION OF -1 DIVIDED BY TWENTY FIVE, OR 1/40 DEGENERATION
//LEVEL 4, REGENERATION OF -1 DIVIDED BY TWENTY FIVE, OR 1/55 DEGENERATION
//IN OTHER WORDS...IF NO DAMAGE IS TAKEN, THE SHIELD DISSIPATES IN...
//LEVEL 1: 10 SECONDS
//LEVEL 2: 25 SECONDS
//LEVEL 3: 40 SECONDS
//LEVEL 4: 55 SECONDS
//IF DAMAGE IS TAKEN EVERY LESS THAN 3 SECONDS THE SHIELD WILL NOT REGENERATE NEGATIVELY
//TO EDIT DURATION OF SHIELD CHANGE: -5.00+(15.00*lvl
//LEVEL 1: SHIELD STRENGTH EQUAL TO 60 PERCENT OF CURRENT LIFE
//LEVEL 2: SHIELD STRENGTH EQUAL TO 80 PERCENT OF CURRENT LIFE
//LEVEL 3: SHIELD STRENGTH EQUAL TO 100 PERCENT OF CURRENT LIFE
//LEVEL 4: SHIELD STRENGTH EQUAL TO 120 PERCENT OF CURRENT LIFE
//TO EDIT SHIELD STRENGTH ACCORDING TO THE CURRENT LIFE CHANGE: 0.40+(0.20*lvl

set ut=null
set tu=null
return false
endfunction
private function I takes nothing returns nothing
    local trigger tt = CreateTrigger()
    call TriggerAddAction(tt, function kill)
    call TriggerRegisterAnyUnitEventBJ( tt, EVENT_PLAYER_UNIT_DEATH )    
    
    call TriggerAddAction(trg, function attack)    
call GT_AddStartsEffectAction(function f, CloudStrifeShield)
endfunction
endscope
 
Level 4
Joined
Aug 3, 2008
Messages
80
thank you for your answers!

Berb: i know anachron made a fullscreen inventory and i think there is a save/ load system in it (but i'm not sure). but it's coded in vJass and i made a fullscreen inventory by my self and i need a save/load system for it also in Jass. And of course i would made it by my self but the problem is i don't can make a save/load system because i don't know how to code it or how it works :S

and for the shield system the Anti-magic Shell only blocks magic damage or all kind of damage?

Titanhex: i have created a own inventory system (like that in TkoK) and so i need for my inventory a save/load system....is it possibly to create save/load system for that in Jass or only with vJass?

thx for the spell rep+ but one question if the shield has only 200 hp left und the next hit will have 300 damage did the shield "die" and the hero will lose 100 hp or 300 hp?

SanKakU: thx i have already seen this system and maby i will use this i'm just searching for an system like that in jass and maby easier^^
 
Level 4
Joined
Aug 3, 2008
Messages
80
@ Bribe: i don't use anachron's system because i can't save my mape with his system, don't now why. I using NewGen 5.d but when i save the map with his system i get an error. So i'm working on my own inventory system (in Jass) it's not as good as anachrons but it works for my mape^^. So i need a save and load system for my inventory to save all things!
and it's ok for me in vJass but better in Jass, because maby i'll use it for a Campaign and than vJass won't work. But for my map now it would be ok in vJass
 
Level 13
Joined
May 11, 2008
Messages
1,198
thank you for your answers!

Berb: i know anachron made a fullscreen inventory and i think there is a save/ load system in it (but i'm not sure). but it's coded in vJass and i made a fullscreen inventory by my self and i need a save/load system for it also in Jass. And of course i would made it by my self but the problem is i don't can make a save/load system because i don't know how to code it or how it works :S

and for the shield system the Anti-magic Shell only blocks magic damage or all kind of damage?

Titanhex: i have created a own inventory system (like that in TkoK) and so i need for my inventory a save/load system....is it possibly to create save/load system for that in Jass or only with vJass?

thx for the spell rep+ but one question if the shield has only 200 hp left und the next hit will have 300 damage did the shield "die" and the hero will lose 100 hp or 300 hp?

SanKakU: thx i have already seen this system and maby i will use this i'm just searching for an system like that in jass and maby easier^^

well,as you can see i edited the system and made it easier... notice the all caps section? i wrote that.
you can just write your own lines where my system uses systems for spell casting and spell loading(GT and xe lines) if you don't use those.
 
Level 13
Joined
May 11, 2008
Messages
1,198
@ Bribe: i don't use anachron's system because i can't save my mape with his system, don't now why. I using NewGen 5.d but when i save the map with his system i get an error.

i think your vjass isn't working because you are notupdating your jasshelper to the latest version. there have been many jasshelper updates since newgen 5.d and the official downloads for newgen 5.d do not include the latest jasshelper. also, i don't understand why there isn't just a newgen new version released with latest version of jasshelper, but that's just the way it is.
 
Level 4
Joined
Aug 3, 2008
Messages
80
how to update it? Cause I have downloaded the newest version of JassHelper and overwrite the old data but it doesn't work....

Bribe: can you maby explain me how to create a save/load system for fullscreen systems or just how it works and how i can save veriables?

SanKakU: i also don't understand why there is no new version auf NewGen :S
 
Level 14
Joined
Jul 26, 2008
Messages
1,009
Personally I'd rather just use JassHelper stand-alone but I don't understand how to make it stand-alone.

For my Wall spell it doesn't take 300 damage on a 200 shield and deal 100 damage to the barer. That was an oversight on my part.

It can easily be remedied by putting:
JASS:
if Wall[GetUnitId(GetTriggerUnit())] < 1 then
      call UnitDamageTarget(GetTriggerUnit(),GetEventDamageSource(), Wall[GetUnitId(GetTriggerUnit())]*1, true, false, ATTACK_TYPE_MAGIC, DAMAGE_TYPE_NORMAL, null)
endif

Somewhere past
JASS:
            set Wall[GetUnitId(GetTriggerUnit())] = Wall[GetUnitId(GetTriggerUnit())] - GetEventDamage()
 
Last edited:
Level 4
Joined
Aug 3, 2008
Messages
80
Personally I'd rather just use JassHelper stand-alone but I don't understand how to make it stand-alone.

For my Wall spell it doesn't take 300 damage on a 200 shield and deal 100 damage to the barer. That was an oversight on my part.

It can easily be remedied by putting:
JASS:
if Wall[GetUnitId(GetTriggerUnit())] < 1 then
      call UnitDamageTarget(GetTriggerUnit(),GetEventDamageSource(), Wall[GetUnitId(GetTriggerUnit())]*1, true, false, ATTACK_TYPE_MAGIC, DAMAGE_TYPE_NORMAL, null)
endif

Somewhere past
JASS:
            set Wall[GetUnitId(GetTriggerUnit())] = Wall[GetUnitId(GetTriggerUnit())] - GetEventDamage()

witch part i have to replace? thank you again for the spell ;)
 
Level 14
Joined
Jul 26, 2008
Messages
1,009
You don't have to replace anything. Just put the first JASS code somewhere past the line shown in the second JASS code.

JASS:
scope Wall initializer InitTrig_Wall

globals
//"Abilities\\Spells\\Items\\StaffOfSanctuary\\Staff_Sanctuary_Target.mdl"
    private constant integer SPELLID    = 'Wall'
    private constant string mdl         = "Abilities\\Spells\\Orc\\SpiritLink\\SpiritLinkZapTarget.mdl"
    private real array Wall
    private trigger array EventTrigger
    private effect array WallFX
endglobals

private struct Data

    unit c
    unit t
    real dur
    real wall

    static method Timer takes nothing returns nothing
     local timer tim = GetExpiredTimer()
     local Data D = Data(GetTimerData(tim))
        call DestroyEffect(WallFX[GetUnitId(D.t)])
        call ReleaseTimer(tim)
        set Wall[GetUnitId(D.t)] = 0
        call DestroyTrigger(EventTrigger[GetUnitId(D.t)])
        set EventTrigger[GetUnitId(D.t)] = null
        set D.c = null
        set WallFX[GetUnitId(D.t)] = null
        set D.t = null
        call D.destroy()
    endmethod

    static method Conditions takes nothing returns boolean
     local integer lvl = GetUnitAbilityLevel(GetEventDamageSource(), SPELLID)
     local texttag tag = CreateTextTag()
            if GetRandomInt(1,3) == 3 then
                call DestroyEffect(AddSpecialEffectTarget("Abilities\\Spells\\Human\\Defend\\DefendCaster.mdl", GetTriggerUnit(), "head"))
            endif
            call SetWidgetLife(GetTriggerUnit(), GetWidgetLife(GetTriggerUnit()) + GetEventDamage())
            set Wall[GetUnitId(GetTriggerUnit())] = Wall[GetUnitId(GetTriggerUnit())] - GetEventDamage()
            call SetTextTagText(tag, I2S(R2I(Wall[GetUnitId(GetTriggerUnit())]))+"HP", 0.024)
            call SetTextTagPos(tag, GetUnitX(GetTriggerUnit()), GetUnitY(GetTriggerUnit()), 0.00)
            call SetTextTagColor(tag, 0, 0, 255, 255)
            call SetTextTagVelocity(tag, 0, 0.03)
            call SetTextTagVisibility(tag, true)
            call SetTextTagFadepoint(tag, 0.75)
            call SetTextTagLifespan(tag, 1.5)
            call SetTextTagPermanent(tag, false)
            //<< Put it here.
            if Wall[GetUnitId(GetTriggerUnit())] < 1 or GetUnitAbilityLevel(GetTriggerUnit(), 'B00B') < 1 then
                call UnitRemoveAbility(GetTriggerUnit(), 'B00B')
                call DestroyEffect(WallFX[GetUnitId(GetTriggerUnit())])
                call DestroyTrigger(EventTrigger[GetUnitId(GetTriggerUnit())])
                set EventTrigger[GetUnitId(GetTriggerUnit())] = null
                set WallFX[GetUnitId(GetTriggerUnit())] = null
                call DestroyTextTag(tag)
                set tag = null
            endif
     return false
    endmethod

    static method create takes unit caster, unit target, integer lvl returns Data
     local xecast xc = xecast.createA()
     local Data D = Data.allocate()
     local timer tim = NewTimer()
        set D.c = caster
        set D.t = target
        set D.dur = 0
        set D.wall = 50+(50*lvl*lvl)*(0.7+0.1*lvl)+SpellStat(D.c, true)*(lvl*0.35+0.75)

        set xc.abilityid    = 'duwa' 
        set xc.level = GetUnitAbilityLevel(caster, SPELLID)
        set xc.orderstring  = "bloodlust"
        set xc.owningplayer = GetOwningPlayer(caster)
        call xc.castOnTarget( target )
        
        if EventTrigger[GetUnitId(D.t)] == null then
            set EventTrigger[GetUnitId(D.t)] = CreateTrigger()
            call TriggerRegisterUnitEvent(EventTrigger[GetUnitId(D.t)], D.t, EVENT_UNIT_DAMAGED)
            call TriggerAddCondition(EventTrigger[GetUnitId(D.t)], function Data.Conditions)
        endif

        if WallFX[GetUnitId(D.t)] == null then
            set WallFX[GetUnitId(D.t)] = AddSpecialEffectTarget(mdl, D.t, "chest")
        endif

        set Wall[GetUnitId(D.t)] = D.wall

        call SetTimerData(tim,D)
        call TimerStart(tim, 35+10*lvl, false, function Data.Timer)

     return D
    endmethod
    
endstruct

private function Conditions takes nothing returns boolean
    if GetSpellAbilityId() == SPELLID then
        call Data.create(GetTriggerUnit(), GetSpellTargetUnit(), GetUnitAbilityLevel(GetTriggerUnit(), SPELLID))
    endif
 return false
endfunction

//===========================================================================
public function InitTrig_Wall takes nothing returns nothing
 local trigger t = CreateTrigger()
    call TriggerRegisterAnyUnitEventBJ( t, EVENT_PLAYER_UNIT_SPELL_EFFECT )
    call TriggerAddCondition( t, function Conditions )
    call XE_PreloadAbility(SPELLID)
 set t = null
endfunction

endscope
 
Status
Not open for further replies.
Top