My first attempt at JASS scripting

Hatebreeder

So many apples
Reaction score
381
Hey all,
Since someone inspired me of learning JASS, I thought, that I might give it a try.
The following Trigger is supposed to be a One Target Omni Slash. The caster moves to Target 5 times at 5 different angles.
This is what I've got so far:
JASS:
function Trig_Condition takes nothing returns boolean
    return GetSpellAbilityId() == 'A000'
endfunction
function Trig_Actions takes nothing returns nothing
    set local unit U = GetTriggerUnit
    set local unit T = GetSpellTargetUnit
    loop
    endif I >= 5
    set local I = (I + 1)
    set local real Angle = 360 / I
    set local location UL = GetLocationX(U),GetLocationY(U)
    set local location TL = GetLocationX(T),GetLocationY(T)
    // Do Actions here
    set local location UL = null
    set local location TL = null
    call RemoveLocation(UL)
    call RemoveLocation(TL)
    call PolledWait(0.35) 
    endloop
    endfunction

What must I write to move the Caster U, to the location of the unit T?
 

Rheias

New Helper (I got over 2000 posts)
Reaction score
232
Firstly, you must create all locals in the top of the function. When setting, there is no need to put the "local" so, it should look like this:

JASS:
function Trig_Actions takes nothing returns nothing
    set local unit U = GetTriggerUnit() // When calling a function you must put (<arguements>)
    set local unit T = GetSpellTargetUnit() // Same thing
    local location UL = Location(GetUnitX(U),GetUnitY(U)) // Got it a bit wrong <img src="data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7" class="smilie smilie--sprite smilie--sprite2" alt=";)" title="Wink    ;)" loading="lazy" data-shortname=";)" />
    local location TL = Location(GetUnitX(T),GetUnitY(T))
    local integer I = 0
    local real Angle
    
    loop
    exitwhen I &gt;= 5 // exitwhen, not endif
    set Angle = 360 / I
    // Do Actions here
    call RemoveLocation(UL) // Before the nulling
    call RemoveLocation(TL)
    setUL = null
    set TL = null
    call PolledWait(0.35) 
    endloop
endfunction
 

Trollvottel

never aging title
Reaction score
262
JASS:
 local location UL = Location(GetUnitX(U),GetUnitY(U)) // Got it a bit wrong <img src="data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7" class="smilie smilie--sprite smilie--sprite2" alt=";)" title="Wink    ;)" loading="lazy" data-shortname=";)" />
  local location TL = Location(GetUnitX(T),GetUnitY(T))


use

JASS:
   local location UL =GetUnitLoc(U)
   local location TL =GetUnitLoc(X)


instead, would be much shorter to do it like this.
JASS:
    set local unit U = GetTriggerUnit() // When calling a function you must put (&lt;arguements&gt;)
    set local unit T = GetSpellTargetUnit() // Same thing


this is wrong too it should be

JASS:
    local unit U = GetTriggerUnit() // When calling a function you must put (&lt;arguements&gt;)
    local unit T = GetSpellTargetUnit() // Same thing
 

Hatebreeder

So many apples
Reaction score
381
Firstly, you must create all locals in the top of the function. When setting, there is no need to put the "local" so, it should look like this:

JASS:
function Trig_Actions takes nothing returns nothing
    set local unit U = GetTriggerUnit() // When calling a function you must put (&lt;arguements&gt;)
    set local unit T = GetSpellTargetUnit() // Same thing
    local location UL = Location(GetUnitX(U),GetUnitY(U)) // Got it a bit wrong <img src="data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7" class="smilie smilie--sprite smilie--sprite2" alt=";)" title="Wink    ;)" loading="lazy" data-shortname=";)" />
    local location TL = Location(GetUnitX(T),GetUnitY(T))
    local integer I = 0
    local real Angle
    
    loop
    exitwhen I &gt;= 5 // exitwhen, not endif
    set Angle = 360 / I
    // Do Actions here
    call RemoveLocation(UL) // Before the nulling
    call RemoveLocation(TL)
    set UL = null
    set TL = null
    call PolledWait(0.35) 
    endloop
endfunction

Ahhhh... Ok, I get it now!
And, can you only set locals in the beginning of the Trigger, or at anytime your start a new function?
 

Trollvottel

never aging title
Reaction score
262
Angle is a real, look at
JASS:
    local real Angle


but then youll have to do it like this:

JASS:
set Angle = 360 / I2R(I) // Real to integer

because you cant divide reals with integers


you can set and declare locals at the beginning of the function
but later you can only set them to new values
 
Reaction score
333
Angle is a real, look at
JASS:

    local real Angle


but then youll have to do it like this:

JASS:

set Angle = 360 / I2R(I) // Real to integer

because you cant divide reals with integers


you can set and declare locals at the beginning of the function
but later you can only set them to new values

Fairly sure you can perform arithmetic on reals and integers without conversion.
 

Hatebreeder

So many apples
Reaction score
381
Nice, thanks.
I was thinking, wouldn't the loop be infinite, if I didn't do I = (I + 1)?
And, why can you set variables, without defining them?
local real Angle
for example.
 

Trollvottel

never aging title
Reaction score
262
oh yes thats right, i didnt even see it :)

Fairly sure you can perform arithmetic on reals and integers without conversion.

i dont think so, in gui you have to convert it too, and if you set a real value to X * GetUnitAbilityLevel(y,z) youll have to convert it, too.
 

SFilip

Gone but not forgotten
Reaction score
634
Rheias the first two lines should be just local and not set local also ;)

> And, can you only set locals in the beginning of the Trigger, or at anytime your start a new function?
You can set them at any point in the function, but can only define them on the top.

It is possible to perform arithmetics on reals and integers without converting. I2R and R2I have limited purpose in Jass.
 

Hatebreeder

So many apples
Reaction score
381
Rheias the first two lines should be just local and not set local too ;)

> What type of Variable is Angle?
It's a real, that's the way he defined it (local real Angle a couple of lines above).

> And, can you only set locals in the beginning of the Trigger, or at anytime your start a new function?
You can set them at any time, but can only define them on the top.

I see.
But, if I move the caster to target unit, wouldn't he move around 1 location, instead of moving after the target? Because, I didn't set any location in the loop...
 

SerraAvenger

Cuz I can
Reaction score
234
well... First of all, you need to first declarise ( = create ) the local variables in your code, and then you can use them without the local TYPE prefix.

Code:
function Trig_Actions takes nothing returns nothing
    local unit U
    local unit T
    local location UL
    local location TL[COLOR="DarkOrange"]
    local integer I[/COLOR]
    local real angle[COLOR="Cyan"]
    set local unit U = GetTriggerUnit
    set local unit T = GetSpellTargetUnit[/COLOR]
    loop[COLOR="YellowGreen"]
        endif I >= 5[/COLOR]
        set  I [COLOR="PaleTurquoise"]== [/COLOR](I + 1)
        set Angle = 360 / I[COLOR="Olive"]
        set UL = GetLocationX(U),GetLocationY(U)
        set TL = GetLocationX(T),GetLocationY(T)[/COLOR]
[COLOR="Navy"]        set UL = null
        set TL = null
        call RemoveLocation(UL)
        call RemoveLocation(TL)[/COLOR]
        call PolledWait(0.35) 
    endloop
endfunction

Then You made some other mistakes.
First of all, GetLocationX() takes a location, not a unit. For a unit, Use GetUnitX ( Same for Y ). Then, you want to get a location, not two reals, so you use Location( real X , real Y ) thus
JASS:
Location( GetUnitX( T ) , GetUnitY( T ) )


then you forgot the () at two functions: GetTriggerUnit and GetSpellUnit. IT has to be GetTriggerUnit() and GetSpellUnit(). If there are no arguments, you still need those ()!


The Codeword to exit a loop is exitwhen! endif simply indicates the end of an if-block. Instead use exitwhen I > 5.


Another point is that your I is not initialised. Anything you want to increase has to have a value to be increased. You cannot increase nothing to something. Thus in the declarisation you need an: local integer I = 0

Here you used the wrong symbol. == is for a comparision, equals to. The thing you need here is a =, set to.


You should not first set it to null and then Remove the location, as then you would remove the "null" location which actually means no location. You should only null the variable once it's content has been destroyed.


The most important thing for debuggers / codereaders is that you have the variable names actually mean something. Instead of UL for Unit location, use trigUnitLocation. For T as Triggering Unit, use trigUnit or triggerUnit. Instead of SU for Unit that is the target of a spell, use spellTargetUnit. It really saves you and your mates time when reading the code, and is almost no work. Saving the time of a few seconds for typing the 9 additional letters really is no comparision to the comprehebility of the code.
It is a matter of style how you actualy capitalise the letters,
however you should have a global standart.
My deal is:
Global Variables: First letter of each word capitalised ( KilledUnit )
Local Variables: All but the first word have their first letter capitalised ( killedUnit )
Functions: Same as globals
Function Parameters: Same as locals
This helps Determining wether the variable I just read is a global one or a local one.

So in the end, your code should look like this:
JASS:

function Trig_Actions takes nothing returns nothing
    local unit triggerUnit = GetTriggerUnit()
    local unit spellTarget = GetSpellTargetUnit()
    local location triggerUnitLocation
    local location spellTargetLocation
    local integer loopIndicator = 1
    local real angle
    loop
        exitwhen loopIndicator &gt;= 5
        set angle = 360 / loopIndicator
        set triggerUnitLocation = Location( GetUnitX(triggerUnit) , GetUnitY(triggerUnit) )
        set spellTargetLocation = Location( GetUnitX(spellTarget) , GetUnitY(spellTarget) )
        
        call RemoveLocation(triggerUnitLocation)
        call RemoveLocation(spellTargetLocation)
        
        call PolledWait(0.35)
                                                       
        set  loopIndicator =  loopIndicator + 1
    endloop
    set triggerUnitLocation = null
    set spellTargetLocation = null
    set angle = 0
    set loopIndicator =  0
    set triggerUnit = null
    set spellTarget = null
endfunction


Now with a single glance, you can see what the code does. And it actually does what it should. However now I'm tired so ask someone else how to do what you want. Hope that helped at least a bit, Cpt.DaveyJones.

PS: Perhaps you should look at the JASS tutorials here on TH, they should help you alot. I have actually never looked at them, so I cannot tell you how good they are... Sorry.

PPS: Try to get JassCraft, can make your life easier while coding...

Greetings, DaveyJones

EDIT: Sorry that I said some things others have allready done, but I started typing while there were no other posts there ; )
 

Hatebreeder

So many apples
Reaction score
381
Ok, I have added some stuff, and re-worked out the variable diffinitio, so everybody knows what I'm talking about.
JASS:
function Trig_Condition takes nothing returns boolean
    return GetSpellAbilityId() == &#039;A000&#039;
endfunction
function Trig_Actions takes nothing returns nothing
    local unit Caster = GetTriggerUnit()
    local unit Target = GetSpellTargetUnit()
    local location CasterLocation
    local location TargetLocation
    local integer Integer
    local real Angle
    local location PolarProjection
    
    loop
    exitwhen Integer &gt;= 5
    // Define Locals    
    set Angle = 360.00 / I2R(Integer)
    set CasterLocation = Location( GetUnitX(Caster),GetUnitY(Caster))
    set TargetLocation = Location( GetUnitX(Target),GetUnitY(Target))
    set PolarProjection = PolarProjectionBJ(TargetLocation,50.00,Angle * R2I([GetForLoopIndexA]))
    // Actions
    call UnitDamageTarget(Caster,Target,2.55 * GetHeroStr(Caster),true,false,ATTACK_TYPE_HERO,DAMAGE_TYPE_NORMAL,WEAPON_TYPE_WHOKNOWS)
    call SetUnitPositionLoc(Caster,PolarProjection)
    call AddSpecialEffectLoc(&quot;Abilities\Spells\Orc\WarStomp\WarStompCaster.mdl&quot;,TargetLocation)
    call DestroyEffect(GetLastCreatedEffectBJ)
    // End Actions, Clear up leaks
    call RemoveLocation(CasterLocation)
    call RemoveLocation(TargetLocation)
    call PolledWait(0.35)
    set Integer = ( Integer + 1 ) 
    endloop
    
set Caster = null
set Target = null    
set CasterLocation = null
set TargetLocation = null
set Angle = 0
set Integer = 0    
endfunction

//===========================================================================
function InitTrig_OneTargetOmniSlash takes nothing returns nothing
    set gg_trg_OneTargetOmniSlash = CreateTrigger(  )
    call TriggerAddAction( gg_trg_OneTargetOmniSlash, function Trig_Actions )
endfunction


I get some really weird Errors here and there, could someone help me out on this?
 

0zaru

Learning vJASS ;)
Reaction score
60
Mean to post errors please?

You don't need to set Angle and Integer to 0

Also i doubt that you are destroying those effects since AddSpecialEffectLoc don't set the variable bj_lastCreatedEffect.

You need a event for the trigger also.
 

SFilip

Gone but not forgotten
Reaction score
634
Code:
    set CasterLocation = Location( GetUnitX(Caster),GetUnitY(Caster))
    set TargetLocation = Location( GetUnitX(Target),GetUnitY(Target))
can be simply
Code:
    set CasterLocation = GetUnitLoc(Caster)
    set TargetLocation = GetUnitLoc(Target)

Code:
    call AddSpecialEffectLoc("Abilities\Spells\Orc\WarStomp\WarStompCaster.mdl",TargetLocation)
    call DestroyEffect(GetLastCreatedEffectBJ)
can (and should, because GetLastCreatedEffectBJ doesn't work with AddSpecialEffectLoc) be
Code:
    call DestroyEffect(AddSpecialEffectLoc("Abilities\Spells\Orc\WarStomp\WarStompCaster.mdl",TargetLocation))
This is also where your error is coming from as GetLastCreatedEffectBJ needs () after it.
 

Hatebreeder

So many apples
Reaction score
381
These are the Errors I get, when Parsing.
Syntax Error: Line 19
Not enough Arguments passed on: line 21
Invalid escape character sequence: lines 23 and 24
line 42: undeclared Varible: gg_Trig_OneTargetOmniSlash
 
Reaction score
456
Line 21 error:

JASS:


GetHeroStr takes another value, boolean.

JASS:
native          GetHeroStr          takes unit whichHero, boolean includeBonuses returns integer


Line 19 error:

In my previous post.

Line 23 and 24 error:

JASS:
    call AddSpecialEffectLoc(&quot;Abilities\Spells\Orc\WarStomp\WarStompCaster.mdl&quot;,TargetLocation)


Remember double slashes when using path strings. "\\"

Line 42:

Obvious.
 
General chit-chat
Help Users
  • No one is chatting at the moment.

      The Helper Discord

      Members online

      No members online now.

      Affiliates

      Hive Workshop NUON Dome World Editor Tutorials

      Network Sponsors

      Apex Steel Pipe - Buys and sells Steel Pipe.
      Top