• 🏆 Texturing Contest #33 is OPEN! Contestants must re-texture a SD unit model found in-game (Warcraft 3 Classic), recreating the unit into a peaceful NPC version. 🔗Click here to enter!
  • 🏆 Hive's 6th HD Modeling Contest: Mechanical is now open! Design and model a mechanical creature, mechanized animal, a futuristic robotic being, or anything else your imagination can tinker with! 📅 Submissions close on June 30, 2024. Don't miss this opportunity to let your creativity shine! Enter now and show us your mechanical masterpiece! 🔗 Click here to enter!

Coding Style Question

Status
Not open for further replies.

EdgeOfChaos

E

EdgeOfChaos

Me and another coder have a disagreement about how to use variables, and want your opinion on the hive.

The other coder thinks it's not safe to use the same variable in more than one trigger (like temp variables) and you should make new variables for everything. For example, if you're going to make two locations and then nullify them in two triggers:
Set MyLoc1 = Position of Casting Unit
....Actions
call RemoveLocation(udg_MyLoc1)
Set MyLoc2 = Position of Triggering Unit
....Actions
call RemoveLocation(udg_MyLoc2)

I think it's better to use the same variable if you will set and then remove it immediately.
Set TempPoint = Position of Casting Unit
....Actions
call RemoveLocation(udg_TempPoint)
Set TempPoint = Position of Triggering Unit
....Actions
call RemoveLocation(udg_TempPoint)

Which is a better method, and which is safer to do? And why?
 
Level 8
Joined
Feb 3, 2013
Messages
277
well I'm not a professional coder by any means but in my experience of jass and esp in GUI,
making variables is a waste of time. If you can do what's required with the fewest amount possible without losing readability/comfort, then do it.

As for your simple scenario, both examples are safe - but the second only uses one variable - less resources/time used, thus I think the second is better.

edit: now that i think about it, in vjass i dont really use public globals outside a trigger unless i can't pass data to a certain function. But for spells and such in GUI I think it's safe to have different variables.
 
Last edited:
It is generally safer to use separate variables. Sharing variables is OK, but you have to be extra careful.

Take this as a simple example:
  • Spell Cast
    • Events
      • Unit - A unit starts the effect of an ability
    • Conditions
    • Actions
      • Set TempPoint = (Position of (Triggering unit))
      • Unit - Create 1 Dummy at TempPoint facing 270.00 degrees
      • Special Effect - Create a special effect at TempPoint using <SPELL_MODEL>
      • Custom script: call RemoveLocation(udg_TempPoint)
  • Enter Map
    • Events
      • Unit - A unit enters (Playable map area)
    • Conditions
    • Actions
      • Set TempPoint = (Position of (Triggering unit))
      • Special Effect - Create a special effect at TempPoint using <ENTER_MODEL>
      • Custom script: call RemoveLocation(udg_TempPoint)
This looks fine and dandy, right? Sadly, it isn't. It is problematic due to the way Wc3 runs triggers.

When a spell is cast, it will run these actions:
  • Set TempPoint = (Position of (Triggering unit))
  • Unit - Create 1 Dummy at TempPoint facing 270.00 degrees
As such, TempPoint = Position of Caster

Then it will create a dummy. This fires the "unit enters (playable map area)" event. The question is, does it fire the "Enter Map" trigger, or does it finish the "Spell Cast" trigger first? (note: they can't run at the "same time"--wc3 is single threaded)

You would probably assume it finishes the "spell cast" trigger first. After all, there must be an infinitely small delay when firing the event, right? Turns out, Wc3 will pause the actions, fire the event and all of its triggers, before resuming the trigger. This can cause globals to change their values.

A quick quiz:
  • Where will the effect, SPELL_MODEL, be created?
  • Where will the effect, ENTER_MODEL, be created?

ENTER_MODEL will be created first, that means TempPoint will be reassigned to the dummy's position (a.k.a. the 'entering unit'). But the location is then removed, so now TempPoint doesn't point to a valid location.

When it returns to create SPELL_MODEL, it will be passed a destroyed handle. By default, Wc3 will place the effect at the coordinates (0, 0).

------

In the end, this is sort of rare. Usually triggers will have all sorts of conditions and whatnot, so this sort of problem only happens under rare circumstances. But it is 100% possible, and it is sometimes difficult to track down. It is up to you whether you want to use the same globals. Using shared globals is pretty convenient, it just means you have to be extra careful.
 
Level 12
Joined
Feb 22, 2010
Messages
1,115
The enter region event is delayed.


Once I was trying something like this,


  • Trigger 1
  • Events
    • something happens
  • Conditions
  • Actions
    • Unit - Create 1 footman at the center of region RRR
  • Trigger 2
  • Events
    • A unit enters region RRR
  • Conditions
    • Unit type of triggering unit equal to footman
  • Actions
    • Unit - order triggering unit to attack move somewhere

but this wasn't working for some reason, I changed second trigger to

  • Trigger 2
  • Events
    • A unit enters region RRR
  • Conditions
    • Unit type of triggering unit equal to footman
  • Actions
    • Wait 0.01 seconds (i know 0.00 is cooler)
    • Unit - order triggering unit to attack move somewhere
and it started to work, I am not sure maybe I remember something wrong.Weird.
 
Status
Not open for further replies.
Top