Inscrit le: 12 Sep 2009 Messages: 801 Sujets: 64 Spécialité en worldedit: Ne pas.
Posté le: 08/07/11 21:17 Sujet du message: Problème de loop
Je vois que j'ai beaucoup de problèmes de déclo en ce moment :p
J'ai ce déclencheur, ainsi qu'un autre, qui ne font leur loop qu'une fois...
Voici les déclencheurs responsables :
Secret:
Gui:
Trigger:
TotemExplode
Evénements
Temps - Every 0.10 seconds of game time
Conditions
Actions
Custom script: local unit udg_Lunit_caster Set Lunit_Caster = unit_Caster
Groupe unité - Pick every unit in grpUnit_TotemsMortel and do (Actions)
Boucle - Actions
Set r_TpsTotem = (Load 0 of (Key (Picked unit)) from HashTable_HashTableTotem)
If (All Conditions are True) then do (Then Actions) else do (Else Actions)
Si - Conditions
r_TpsTotem Supérieur ou égal à 5.00
Alors - Actions
Set point_tmpPointTotem = (Position of (Load 0 of (Key (Picked unit)) in HashTable_HashTableTotem)) Set grpUnit_UnitInExplosionTotem = (Units within 400.00 of point_tmpPointTotem matching (((Matching unit) belongs to an enemy of (Owner of (Picked unit))) Egal à TRUE)) Partie - Display to (All players) the text: (String((Number of units in grpUnit_UnitInExplosionTotem))) Effet spécial - Create a special effect at point_tmpPointTotem using ObjectsSpawnmodelsHumanHCancelDeathHCancelDeath.mdl Effet spécial - Destroy (Last created special effect) Set tmpInt = (Number of units in grpUnit_UnitInExplosionTotem) Partie - Display to (All players) the text: (String(tmpInt))
For each (Integer A) from 1 to tmpInt, do (Actions)
Boucle - Actions
Partie - Display to (All players) the text: (String((Integer A))) Set unit_RndUnitInExplosion = (Random unit from grpUnit_UnitInExplosionTotem) Set point_tmpPointTotem = (Position of unit_RndUnitInExplosion) Effet spécial - Create a special effect at point_tmpPointTotem using ObjectsSpawnmodelsOrcOrcLargeDeathExplodeOrcLargeDeathExplode.mdl Effet spécial - Destroy (Last created special effect)
Groupe unité - Pick every unit in grpUnit_TotemsMortelCaster and do (Actions)
Boucle - Actions
Set r_dmgTotem = (Load 1 of (Key (Picked unit)) from HashTable_HashTableTotem)
Unité - Cause Lunit_Caster to damage unit_RndUnitInExplosion, dealing r_dmgTotem damage of attack type Chaos and damage type Normal Texte flottant - Create floating text that reads ((String((Integer(r_dmgTotem)))) + !) at point_tmpPointTotem with Z offset 0.00, using font size 10.00, color (100.00%, 0.00%, 0.00%), and 20.00% transparency Texte flottant - Set the velocity of (Last created floating text) to 80.00 towards 80.00 degrees Texte flottant - Change (Last created floating text): Désactiver permanence Texte flottant - Change the lifespan of (Last created floating text) to 3.00 seconds Groupe unité - Remove unit_RndUnitInExplosion from grpUnit_UnitInExplosionTotem
Groupe unité - Remove Lunit_Caster from grpUnit_TotemsMortelCaster Groupe unité - Remove (Load 0 of (Key (Picked unit)) in HashTable_HashTableTotem) from grpUnit_TotemsMortel Unité - Remove (Load 0 of (Key (Picked unit)) in HashTable_HashTableTotem) from the game Custom script: call RemoveLocation( udg_point_tmpPointTotem ) Table de hachage - Clear all child hashtables of child (Key (Picked unit)) in HashTable_HashTableTotem
Sinon - Actions
Table de hachage - Save (r_TpsTotem + 0.10) as 0 of (Key (Picked unit)) in HashTable_HashTableTotem
Et son initialisation :
Gui:
Trigger:
TotemCast
Evénements
Unité - A unit Initie l'effet d'une compétence
Conditions
(Ability being cast) Egal à Totem Mortel
Actions
Set r_TotemMortelLvlMultiplier = 0.50 Set r_TotemMortelIntelMultiplier = 0.80 Set point_tmpPointTotem = (Target point of ability being cast) Unité - Create 1 Balise de soins for (Owner of (Triggering unit)) at point_tmpPointTotem facing Orientation bâtiment par défaut degrees Table de hachage - Save Handle Of(Last created unit) as 0 of (Key (Last created unit)) in HashTable_HashTableTotem Table de hachage - Save Handle Of(Triggering unit) as (Key (Triggering unit)) of 1 in HashTable_HashTableTotem Groupe unité - Add (Triggering unit) to grpUnit_TotemsMortelCaster Groupe unité - Add (Last created unit) to grpUnit_TotemsMortel Set unit_Caster = (Triggering unit) Set r_dmgTotem = (((Real((Hero level of (Triggering unit)))) x r_TotemMortelLvlMultiplier) x ((Real((Intelligence of (Triggering unit) (Inclure bonuses)))) x r_TotemMortelIntelMultiplier)) Table de hachage - Save r_dmgTotem as 1 of (Key (Triggering unit)) in HashTable_HashTableTotem Custom script: call RemoveLocation( udg_point_tmpPointTotem )
J'ai mis des messages de debug, et on peut lire en partie, quand on y lance sur 10 unités :
10
10
1
Alors que, avec la loop, on devrait obtenir (normalement) :
10
10
1
2
3
4
5
6
7
8
9
10
Je tiens à préciser que c'est spécifique à cette carte, et que ça ne bug qu'après avoir ajouté un (des?) déclencheur(s), mais je ne sais plus lesquels...
Un gros poutoux ainsi qu'un gros merci à celui qui trouve une solution à ce problème... _________________
Inscrit le: 23 Aoû 2007 Messages: 7143 Sujets: 147 Spécialité en worldedit: le troll, le flood, la vulgarité, mon coeur balance Médailles: 2 (En savoir plus...)
Posté le: 09/07/11 18:15 Sujet du message:
Avant d'aller plus loin, le "shadowing" de variable n'est plus autorisé depuis plusieurs patchs.
Autrement dit il n'est plus possible d'utiliser le même nom pour une variable locale et globale (l'astuce du local udg_... n'est plus valable).
Je ne me suis pas intéressé à la question de ce qui se passe désormais quand on nomme une variable locale du même nom qu'une variable globale, peut être est ce une histoire de priorité.
Il me semble que jasshelper permet en quelque sorte le shadowing si on spécifie une option dans jasshelper.conf, il renomme les variables pour avoir le comportement attendu (mais c'est déconseillé, car de toute façon utiliser une variable locale en GUI est incroyablement limité, du fait de la nature d'une variable locale qui n'a d'existence que dans le bloc de code où elle a été déclarée et de la tendance du gui à diviser le code en série de fonctions)
Et de toute façon ici une variable locale est tout à fait inutile car tu n'utilises pas de wait. _________________
Inscrit le: 23 Aoû 2007 Messages: 7143 Sujets: 147 Spécialité en worldedit: le troll, le flood, la vulgarité, mon coeur balance Médailles: 2 (En savoir plus...)
Posté le: 09/07/11 21:10 Sujet du message:
EDIT : Je ne t'avais pas quoté avant ton edit, mais bon tu comprends le sens de ma réponse.
Lunit_Caster != Lunit_caster
Ah oui en effet, mais ça ne change rien pour l'inutilité de la variable locale.
Par contre c'est une très mauvaise pratique de "codage", il faut utiliser la casse à bon escient.
Je regarderais à nouveau le trigger modifié si tu as toujours le problème. _________________
Inscrit le: 12 Sep 2009 Messages: 801 Sujets: 64 Spécialité en worldedit: Ne pas.
Posté le: 09/07/11 21:41 Sujet du message:
Bein maintenant il est en jass, il me déclare des erreurs de compilation que je comprends pas vraiment o_O'
Voici le déclo :
Secret:
Jass:
function TM takes nothing returns nothing
local unit uC = GetTriggerUnit()
local unit uDD = null
local real rDmg
local location lC = GetUnitLoc(uC)
local group uG = null
//====
if ( not (GetSpellAbilityId() != 'A002' ) ) then
call CreateNUnitsAtLoc(1, 'o002',GetOwningPlayer(uC), lC,180.0)
set uDD = GetLastCreatedUnit()
call UnitApplyTimedLife( 5, 'BTLF', uDD )
call TriggerSleepAction(5.0)
call AddSpecialEffectLocBJ(uDD, "Objects\\Spawnmodels\\Human\\HCancelDeath\\HCancelDeath.mdl")
call DestroyEffect(GetLastCreatedEffectBJ())
set uG = GetUnitsInRangeOfLocMatching(400.00, lC, Condition(IsUnitEnemy(GetFilterUnit, GetOwningPlayer(uC)) == true and IsUnitAliveBJ(GetFilterUnit)))
call ApplyDamages(rDmg, uG, uC)
endfunction
function ApplyDamages takes real r, group g, unit u returns nothing
local group uG
local unit rU
local unit uC
local real rD
local integer i
local integer i2
local location l
set i2 = CountUnitsInGroup(uG)
set rDmg = r
set uC = u
set uG = g
loop
exitwhen (i > i2)
//====
set rU = GroupPickRandomUnit(uG)
set l = GetUnitLoc(rU)
call UnitDamageTarget(uC, rU, rD, ATTACK_TYPE_NORMAL, DAMAGE_TYPE_NORMAL)
call GroupRemoveUnitSimple(rU, uG)
call AddSpecialEffectBJ(l, "Objects\\Spawnmodels\\Orc\\OrcLargeDeathExplode\\OrcLargeDeathExplode.mdl")
call DestroyEffect(GetLastCreatedEffectBJ())
set i = i + 1
//====
endloop
//===========================================================================
function InitTrig_Totem_Mortel takes nothing returns nothing
set gg_trg_Totem_Mortel = CreateTrigger( )
call TriggerRegisterAnyUnitEventBJ( gg_trg_Totem_Mortel, EVENT_PLAYER_UNIT_SPELL_EFFECT )
call TriggerAddAction( gg_trg_Totem_Mortel, function TM, ApplyDamages )
endfunction
Pour les erreurs de compilation, y'en a 28 chez moi :/ _________________
Inscrit le: 12 Sep 2009 Messages: 801 Sujets: 64 Spécialité en worldedit: Ne pas.
Posté le: 09/07/11 21:53 Sujet du message:
call TriggerAddAction( gg_trg_Totem_Mortel, function TM, ApplyDamages ) remplacé par call TriggerAddAction( gg_trg_Totem_Mortel, function TM )
(J'ai juste?)
Toujours 27 (une de moins, ouf.) erreurs de compilations :/
EDIT :
J'ai éradiqué 20 erreurs de compil d'un coup en remplaçant set uG = GetUnitsInRangeOfLocMatching(400.00, lC, Condition(IsUnitEnemy(GetFilterUnit, GetOwningPlayer(uC)) == true and IsUnitAliveBJ(GetFilterUnit))) par set uG = GetUnitsInRangeOfLocMatching(400.00, lC, Condition(IsUnitEnemy(GetFilterUnit, GetOwningPlayer(uC))) == true and IsUnitAliveBJ(GetFilterUnit)) _________________
Inscrit le: 23 Aoû 2007 Messages: 7143 Sujets: 147 Spécialité en worldedit: le troll, le flood, la vulgarité, mon coeur balance Médailles: 2 (En savoir plus...)
Posté le: 09/07/11 22:01 Sujet du message:
ouep.
En jass pour appeller une fonction il faut qu'elle ait déjà été definie, donc inverse l'order de TM et ApplyDamages.
Autre chose : set uG = GetUnitsInRangeOfLocMatching(400.00, lC, Condition(IsUnitEnemy(GetFilterUnit, GetOwningPlayer(uC)) == true
Y'a pas de fonction anonyme en jass, il te faut utiliser un filtre intermédiaire via une fonction, puis dans le Get... Filter(function NomDeTonFiltre).
Et pour l'amour de toi même, choisi des noms explicites, au moins tu comprendras ton code si tu y reviens plus tard ...
Sinon toutes les BJ (fonctions en violets) que tu utilises sont useless (hormis TriggerRegisterAnyUnitEventBJ), mais vérifie que tu utilises le bon type d'argument et dans le bon ordre. _________________
Inscrit le: 23 Aoû 2007 Messages: 7143 Sujets: 147 Spécialité en worldedit: le troll, le flood, la vulgarité, mon coeur balance Médailles: 2 (En savoir plus...)
Posté le: 09/07/11 22:25 Sujet du message:
Nan mais c'est pas aussi simple, il ne suffit pas de remove le BJ, premièrement parce que la fonction native n'existe pas forcément sous ce nom, puis l'ordre des paramètres est souvent différent, voir la nature.
Je te conseille d'utiliser jasscraft, dispo sur wc3c.net (fonctionne correctement avec wine)
A partir des BJ tu retrouveras les fonctions natives.
En partant du principe que ton code est bon
function MonFiltre takes nothing returns boolean
return IsUnitEnemy(GetFilterUnit(), GetOwningPlayer(uC)) and IsUnitAliveBJ(GetFilterUnit())
endfunction
set uG = GetUnitsInRangeOfLocMatching(400.00, lC, Filter(function MonFiltre))
Jasshelper te permet dans certains cas d'utiliser implicitement Filter() (ou Condition() ), c'est à dire que s'il le faut le code jass compilé est modifié pour que cela soit ajouté, mais d'après mes souvenirs ça ne fonctionne pas pour tout. _________________
Maintenant cela prend les variables globales avant les locales, donc déclarer une variable locale avec le même nom qu'une globale ne sert pas. _________________
Vous ne pouvez pas poster de nouveaux sujets dans ce forum Vous ne pouvez pas répondre aux sujets dans ce forum Vous ne pouvez pas éditer vos messages dans ce forum Vous ne pouvez pas supprimer vos messages dans ce forum Vous ne pouvez pas voter dans les sondages de ce forum