Worldedit
  Worldedit
Le site sur l'éditeur de warcraft 3 !
 
  FAQFAQ   RechercherRechercher   Liste des MembresListe des Membres    Groupes d'utilisateursGroupes d'utilisateurs   medals.php?sid=25f102dfa9952f99fba37dd13525bb6aMédailles   S'enregistrerS'enregistrer 
 ProfilProfil   Se connecter pour vérifier ses messages privésSe connecter pour vérifier ses messages privés   ConnexionConnexion 
  FAQFAQ World Editor   UploadUploader une map ou une image    UploadAjouter sa map à l'annuaire   UploadConsulter l'annuaire

[vJass] Mouvement avec arc

 
Poster un nouveau sujet   Répondre au sujet    Worldedit Index du Forum -> Fonction Jass
Voir le sujet précédent :: Voir le sujet suivant  
Auteur Message
 Sapeur-Goblin
Floodeur prématuré


Inscrit le: 14 Oct 2009
Messages: 719
Sujets: 40
Spécialité en worldedit: Les bugs
Médailles: 1 (En savoir plus...)
Créateur d'unité (Quantité : 1)

MessagePosté le: 03/03/12 18:55    Sujet du message: [vJass] Mouvement avec arc Citer

Nom de la fonction : CreateProjectile
Créateur : Plein de gens je pense
Fonctions requises : Aucune. Il faut cependant utiliser un modèle d'unité pouvant s'incliner que vous pourrez trouver ici pour que ça marche correctement.
Code :
Secret:

Jass:
library CreateProjectile

globals
    private constant integer DummyId = 'dumm' //Référence du dummy
    private constant real Interval = 0.01 //Interval de temps pour le timer
endglobals

private function interface ImpactProjectile takes unit u, unit c returns nothing

private struct Projectile
    unit u
    real x
    real y
    real h
    unit c
    real speed
    real arc
    real aarc
    unit dum
    effect fx
    ImpactProjectile func
endstruct

globals
    private timer TimProjectile = CreateTimer()
    private Projectile array Ar
    private integer Total = 0
endglobals

private function Move takes nothing returns nothing
    local Projectile ap
    local real xc
    local real yc
    local real xdum
    local real ydum
    local real hc
    local real hdum
    local real d
    local real dm
    local real dp
    local real a
    local real adum
    local real h
    local real r
    local real x
    local real y
    local integer i = 0
   
    loop
        exitwhen i >= Total
        set ap = Ar[i]
       
        set xc = GetUnitX(ap.c)
        set yc = GetUnitY(ap.c)
       
        set xdum = GetUnitX(ap.dum)
        set ydum = GetUnitY(ap.dum)
       
        set a = Atan2(yc-ydum, xc-xdum)
       
        set hc = GetUnitFlyHeight(ap.c) + 50
        set hdum = GetUnitFlyHeight(ap.dum)
       
        set d = SquareRoot((xdum-ap.x)*(xdum-ap.x)+(ydum-ap.y)*(ydum-ap.y)+(hdum-ap.h)*(hdum-ap.h))
        set dm = SquareRoot((xc-ap.x)*(xc-ap.x)+(yc-ap.y)*(yc-ap.y)+(hc-ap.h)*(hc-ap.h))
        set dp = d/dm
       
        set h = ap.h + (GetUnitFlyHeight(ap.c)+50-ap.h) * dp + ap.arc * dm * Sin(dp*bj_PI)
        set r = 90 + Atan((h-GetUnitFlyHeight(ap.dum))/ap.speed) * bj_RADTODEG
   
        set x = xdum + ap.speed * Cos(a)
        set y = ydum + ap.speed * Sin(a)
       
        set adum = Atan2(y-ydum, x-xdum)*bj_RADTODEG
       
        call SetUnitFlyHeight(ap.dum, h, 0)
        call SetUnitFacing(ap.dum, adum)
        call SetUnitAnimationByIndex(ap.dum, R2I(r))
   
        if dm-d >= 0 then
            call SetUnitX(ap.dum, x)
            call SetUnitY(ap.dum, y)
        else
            call SetUnitX(ap.dum, xc)
            call SetUnitY(ap.dum, yc)
           
            call DestroyEffect(ap.fx)
            call KillUnit(ap.dum)
           
            call ap.func.execute(ap.u, ap.c)
           
            set ap.u = null
            set ap.c = null
            set ap.dum = null
            set ap.fx = null
           
            set Ar[i] = Ar[Total - 1]
            set Total = Total - 1
            call ap.destroy()
           
            set i = i - 1
        endif
       
        set i = i + 1
    endloop
   
    if Total == 0 then
        call PauseTimer(TimProjectile)
    endif
endfunction

function CreateProjectile takes unit u, unit c, string fx, real size, real speed, real arc, real aarc, ImpactProjectile func returns nothing
    local Projectile ap = Projectile.create()
    local real xs = GetUnitX(u)
    local real ys = GetUnitY(u)
    local real xc = GetUnitX(c)
    local real yc = GetUnitY(c)
    local real a = Atan2(yc-ys, xc-xs) * bj_RADTODEG
   
    set ap.u = u
    set ap.x = xs
    set ap.y = ys
    set ap.h = GetUnitFlyHeight(u) + 50
    set ap.c = c
    set ap.speed = speed * Interval
    set ap.arc = arc
    set ap.aarc = aarc
    set ap.dum = CreateUnit(GetOwningPlayer(u), DummyId, xs, ys, a)
    set ap.fx = AddSpecialEffectTarget(fx, ap.dum, "origin")
    set ap.func = func
   
    call SetUnitScale(ap.dum, size, size, size)
    call SetUnitFlyHeight(ap.dum, ap.h, 0)
   
    if Total == 0 then
        call TimerStart(TimProjectile, Interval, true, function Move)
    endif
   
    set Ar[Total] = ap
    set Total = Total + 1
   
    set u = null
    set c = null
endfunction

endlibrary

Utilisation :

Voici un petit exemple d'utilisation :
Jass:
function ImpactProjectile takes unit u, unit c returns nothing
    call UnitDamageTarget(u, c, 50, false, true, ATTACK_TYPE_NORMAL, DAMAGE_TYPE_FIRE, WEAPON_TYPE_WHOKNOWS)
    set u = null
    set c = null
endfunction

function Action takes nothing returns nothing
    call CreateProjectile(GetTriggerUnit(), GetSpellTargetUnit(), "Abilities\\Weapons\\FireBallMissile\\FireBallMissile.mdl", 1, 1200, 0.15, ImpactProjectile)
endfunction



Ce qui va envoyer un projectile sur la cible et lui infliger 50 pts de dégâts à la collision.

Juste pour que tout soit clair :
GetTriggerUnit() : L'unité lanceuse du projectile (ah bon?)
GetSpellTargetUnit() : L'unité cible
"Abilities\\Weapons\\FireBallMissile\\FireBallMissile.mdl" : Le modèle attaché au projectile
1 : La taille du projectile
1200 : La vitesse du projectile
0.15 : L'arc (correspond au même que celui dans l'éditeur d'objet, donc allez-y lentement sur les valeur Wink. Au-delà de 2, on voit à peine le projectile).
ImpactProjectile : Fonction appelée quand le projectile touche sa cible. Elle doit prendre pour arguments deux unités ; la première est l'unité lanceuse, la deuxième la cible.

Copyright : Libre
Remarques : Ca fait des jolies courbes comme les projectiles faits par l'éditeur de donnée. Le modèle tiré du système détaillé plus haut permet d'incliner l'unité vers le haut/bas, donc rend le mouvement réaliste.
_________________


Dernière édition par Sapeur-Goblin le 08/03/12 17:57; édité 16 fois
Revenir en haut
Voir le profil de l'utilisateur Envoyer un message privé
 Tirlititi



Inscrit le: 21 Fév 2010
Messages: 1785
Sujets: 22
Spécialité en worldedit: La modestie
Médailles: 1 (En savoir plus...)
Grand mage créateur de sort (Quantité : 1)

MessagePosté le: 03/03/12 19:43    Sujet du message: Citer

Petite review vite faite :
- Il faut mettre un exemple dans son ensemble : avec la fonction d'initialisation et la récupération des xs/xc/speed/etc à chaque étape.
- Ce serait bien de mettre un lien direct vers le dummy (en voilà un).
- Tu devrais utiliser "bj_PI" et "bj_RADTODEG", ce sera plus lisible et je n'pense pas que ça ait une influence sur la vitesse d'exécution (à priori, ça a juste une influence insignifiante sur le temps de chargement de la map).
- Tu devrais garder une cohérence dans les noms de tes variables : je vois pas pourquoi SPEED, HEIGHT_MIN et ARC sont en majuscule.

Au niveau du système en lui-même, j'ai pas testé, mais je pense qu'il y a quelques erreurs :
- La direction "a" est calculé selon la source et la destination, il serait plus judicieux de la calculer selon la position du projectile et la destination.
- "if dm-d >= SPEED then" à transformer en "if dm-d >= 0 then" (parce que tu rajoutes déjà SPEED dans d). C'pas une grosse différence mais voilà quoi.
- J'ai plusieurs remarques mais qui dépendent de la façon selon laquelle est obtenue la position source et la position ciblée à chaque instant.

Sinon, ça pourrait se révéler intéressant.
_________________
Warcraft III, c'était mieux avant. Y'avait des purs chefs-d'oeuvres du mapping !
Road Of Glory (par moi)
Casse-briques (par moi)
Temple de Glace (par moi)
Revenir en haut
Voir le profil de l'utilisateur Envoyer un message privé
 Sapeur-Goblin
Floodeur prématuré


Inscrit le: 14 Oct 2009
Messages: 719
Sujets: 40
Spécialité en worldedit: Les bugs
Médailles: 1 (En savoir plus...)
Créateur d'unité (Quantité : 1)

MessagePosté le: 03/03/12 22:54    Sujet du message: Citer

Voilà, j'ai corrigé les erreurs.
J'améliorerais d'ici peu la fonction pour qu'elle puisse supporter des unités aériennes. Parce que là, si l'unité cible est aérienne, il n'y a aucun moyen d'élever le projectile.

Edit : Si on utilise un arc assez grand, 0.5 par exemple, des effets bizarres apparaissent lors de la mort du projectile. On dirait qu'il est téléporté quelque part autours de la cible. Je ne vois pas d'où ça peut venir...

Deuxième édit : C'est bon, les unités aériennes sont gérées. Par contre il y a toujours ce petit soucis d'effet à la mort du projectile :/. En fait plus l'intervalle du timer est petit, plus ces effets sont présents.
_________________
Revenir en haut
Voir le profil de l'utilisateur Envoyer un message privé
 Troll-Brain
Ri1kamoua


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...)
Grand mage créateur de sort (Quantité : 1) Rédacteur de tuto #3 (Quantité : 1)

MessagePosté le: 04/03/12 19:06    Sujet du message: Citer

En général on privilégie la langue de Shakespeare à la langue de Molière pour la programmation.

Mais au delà de cela, "Mouvement" est un nom bien trop générique.

Tu pourrais utiliser par ex "ArcMouv"
_________________
Revenir en haut
Voir le profil de l'utilisateur Envoyer un message privé
 Sapeur-Goblin
Floodeur prématuré


Inscrit le: 14 Oct 2009
Messages: 719
Sujets: 40
Spécialité en worldedit: Les bugs
Médailles: 1 (En savoir plus...)
Créateur d'unité (Quantité : 1)

MessagePosté le: 05/03/12 17:10    Sujet du message: Citer

J'ai édité mon poste, j'ai fait un système beaucoup plus simple d'utilisation, il gère tout.
Si vous (je pense particulièrement à Troll-Brain Rolling Eyes) avez des recommandations quant à l'amélioration, allez-y, lâchez tout Smile.

Ps : Il y a toujours ce problème atterrissage pas très net de temps en temps. Ca le fait chez tout le monde ou j'ai un problème? Si oui, qu'est-ce qui pourrait en être la cause?
_________________
Revenir en haut
Voir le profil de l'utilisateur Envoyer un message privé
 Tirlititi



Inscrit le: 21 Fév 2010
Messages: 1785
Sujets: 22
Spécialité en worldedit: La modestie
Médailles: 1 (En savoir plus...)
Grand mage créateur de sort (Quantité : 1)

MessagePosté le: 05/03/12 18:30    Sujet du message: Citer

Ça le fait sans aucun doute à tout le monde, mais je testerai un autre jour. Pour l'optimisation, on verra ça un autre jour aussi, mais il doit y avoir moyen de ^^.

Juste une remarque en passant : tu devrais mettre un argument "speed" exprimé en distance/seconde, et pas distance/interval. Tu as juste à mettre "set ap.speed = speed * Interval" et l'argument speed correspondra à celui qu'on met dans l'éditeur d'objet.
_________________
Warcraft III, c'était mieux avant. Y'avait des purs chefs-d'oeuvres du mapping !
Road Of Glory (par moi)
Casse-briques (par moi)
Temple de Glace (par moi)
Revenir en haut
Voir le profil de l'utilisateur Envoyer un message privé
 Sapeur-Goblin
Floodeur prématuré


Inscrit le: 14 Oct 2009
Messages: 719
Sujets: 40
Spécialité en worldedit: Les bugs
Médailles: 1 (En savoir plus...)
Créateur d'unité (Quantité : 1)

MessagePosté le: 07/03/12 15:32    Sujet du message: Citer

C'est bon pour le speed.

Sinon j'ai mis à jour le code à cause d'un petit défaut qu'il avait : il calculait la distance en deux dimensions et non en 3, ce qui pouvait causer des problèmes avec les unités aériennes.

Le problème de atterrissage semble venir de SetUnitX/Y : j'ai essayé avec SetUnitPositionLoc et il a disparu...

Edit : Ce problème vient du fait que la fonction Atan2 renvoie des angles improbables vers la fin...

Second edit : Cet éditeur est une blague. J'ai créé ma propre fonction pour calculer des angles : résultat, quand je calcule un angle mais que je ne le réutilise pas après, il correspond au bon angle. Quand je le réutilise, il change -.-'. J'ai sérieusement l'impression d'avoir un problème avec mon pc Evil or Very Mad.
_________________
Revenir en haut
Voir le profil de l'utilisateur Envoyer un message privé
 Sapeur-Goblin
Floodeur prématuré


Inscrit le: 14 Oct 2009
Messages: 719
Sujets: 40
Spécialité en worldedit: Les bugs
Médailles: 1 (En savoir plus...)
Créateur d'unité (Quantité : 1)

MessagePosté le: 08/03/12 17:56    Sujet du message: Citer

Désolé pour ce double poste mais éditer l'autre aurait été un peu de trop Very Happy. C'était juste pour dire que j'ai réussi à enlever le bug d'atterrissage, c'était plus un bug qu'autre chose.
_________________
Revenir en haut
Voir le profil de l'utilisateur Envoyer un message privé
 Troll-Brain
Ri1kamoua


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...)
Grand mage créateur de sort (Quantité : 1) Rédacteur de tuto #3 (Quantité : 1)

MessagePosté le: 09/03/12 21:12    Sujet du message: Citer

Les noms courts non explicites sont à bannir, du style "local real a".

Tout simplement parce que ça rend le code plus difficile à lire, et donc sources d'erreurs possible.
Evidemment il existe quelques exceptions tel que "i,j,k" pour les variables d'incrémentation de loop, "n" pour un indice de tableau, etc.

A la limite c'est "acceptable" pour le code que l'utilisateur n'est pas censé modifié, mais ça ne l'est pas pour les en tête des API (les arguments des fonctions fournies pour l'utilisateur)
_________________
Revenir en haut
Voir le profil de l'utilisateur Envoyer un message privé
Montrer les messages depuis:   
Poster un nouveau sujet   Répondre au sujet    Worldedit Index du Forum -> Fonction Jass Toutes les heures sont au format GMT + 1 Heure
Page 1 sur 1

 
Sauter vers:  
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


Powered by phpBB © 2001, 2005 phpBB Group
Traduction par : phpBB-fr.com