Flash - Tutoriel : Horloge (AS1)

Voici un tutoriel pas forcement très adapté pour les néophytes en Flash et en Action Script. Je vais m’efforcer d’être le plus clair et donner un maximum d’explications.

1. L'OBJET HORLOGE

On commence par créer l’objet Horloge qui contiendra l’ensemble de ce que nous allons faire. Ce qui permettra de l’insérer plus facilement dans un autre script si besoin est. Le niveau choisi est 1. Attention qu’il n’y ait rien au même niveau, il serait écrasé. Pour éviter d’avoir à répéter que nous appelons Horloge, nous passerons par la fonction with qui englobera le reste du script.

createEmptyMovieClip("Horloge", 1);
with (Horloge) {
}

Ensuite on va créer les aiguilles de l’horloge. Elle sera composée de 3 aiguilles de 3 tailles différentes avec des épaisseurs différentes.

2. LES AIGUILLES

On commence par créer l’aiguille des secondes que l’on va appeler Aiguille1. Le niveau choisi sera assez élevé, 21, pour pouvoir placer d’autres objets en dessous (les points). On utilise with pour la même raison précédemment citée.

createEmptyMovieClip("Aiguille1", 21);
with (Aiguille1) {
}

Dans cet objet, on lui donne le type de ligne à tracer avec lineStyle. On prend une épaisseur de 1

lineStyle(1);

On lui dit ensuite de commencer à dessiner avec beginFill.

beginFill();

On choisit le point de départ avec moveto aux coordonnées (0, 0) dans l’objet Aiguille1 (ce qui correspond aussi à (0, 0) dans Horloge).

moveto(0, 0);

On peut maintenant dessiner cette fameuse aiguille avec lineto. On lui donne les coordonnées d’arrivée de cette ligne. On va la faire d’une longueur de 100, mais étant donné que les coordonnées y sont inverses par rapport à un repère « standard », il faut lui donner les coordonnées (x, y)=( 0, -100) pour avoir une ligne verticale pointant comme pour 0 seconde à l’horloge (cela à son importance pour facilité les calculs par la suite).

lineto(0, -100);

Et on ferme le tracé.

endFill();

Pour cette première aiguille, nous avons donc ceci :

createEmptyMovieClip("Aiguille1", 21);
    with (Aiguille1) {
    lineStyle(1);
    beginFill();
    moveto(0, 0);
    lineto(0, -100);
    endFill();
}

L’aiguille des minutes et des heures se font sur le même modèle. Pour les minutes, on prend une épaisseur de 1,5 et une longueur de 75 au niveau 22. Pour les heures, une épaisseur de 2 et une longueur de 50 au niveau 23.

createEmptyMovieClip("Aiguille2", 22);
    with (Aiguille2) {
    lineStyle(1.5);
    beginFill();
    moveto(0, 0);
    lineto(0, -75);
    endFill();
}
createEmptyMovieClip("Aiguille3", 23);
    with (Aiguille3) {
    lineStyle(2);
    beginFill();
    moveto(0, 0);
    lineto(0, -50);
    endFill();
}

On a nos aiguilles et on pourrait s’en contenter. Cependant ce n’est pas super niveau lecture. On va donc ajouter les points des heures pour rendre cette horloge un peu plus claire.

3. LES POINTS DES HEURES

On a besoin de 12 points, donc une boucle est nécessaire.

for (i=1; i<=12; i++) {
}

On va rentrer le nom des points dans une variable nom.

nom = "Point"+i;

Ensuite, on lui dit de créer l’objet point. Cette opération se répète 12 fois, il était donc nécessaire d’avoir 12 noms différents à 12 niveaux différents (i). On se sert d’eval pour transformer le contenu de la chaîne nom en nom de variable.

createEmptyMovieClip(nom, i);
with (eval(nom)) {
}

C’est maintenant que cela se complique un peu. On va lui dire de dessiner des points, et ce n’est pas vraiment ce qu’il y a de plus simple niveau dessin dans Flash. A la main, il n’y a aucun mal à dessiner un cercle parfait, en programmation c’est plus compliqué. D’ailleurs si on regarde de très près ce n’est pas vraiment circulaire, mais c’est suffisant pour ce que l’on fait.
Pour simplifier la gestion de coordonnées, on rentre les coordonnées de départ dans 2 variables :

x = -5;
y = -100;

Cela place le départ de l'objet assez haut pour effectuer des rotations très simples.

Pour le style de ligne, on n’en veut pas donc on ne met rien. ^^

lineStyle();

Par contre le remplissage nous intéresse. On met donc la couleur 0xA0D0FE (un bleu ciel, mais vous pouvez le changer si elle ne vous plaît pas).

beginFill(0xA0D0FE);

Les coordonnées de départ sont x et y :

moveTo(x, y);

On lui dit ensuite de dessiner ce « cercle » 

curveTo(x-5, y+5, x+0, y+10);
curveTo(x+5, y+15, x+10, y+10);
curveTo(x+15, y+5, x+10, y+0);
curveTo(x+5, y-5, x+0, y+0);

Note : J'admets que pour comprendre comment on dessine des courbes, ce n'est pas simple. D'ailleurs, je n'ai pas vraiment trouvé comment expliquer. Essayer avec l'aide si vous voulez vraiment le faire, mais je n'ai pas vraiment compris celle-ci. J'ai fait par tâtonnement jusqu'à comprendre le système. J'essaierai de faire une explication plus claire quand j'aurai le temps.

On le ferme :

endFill();

Et on lui attribue une valeur de rotation (en degrés, pas en radians) pour le faire pivoter et ainsi placer les douze points en fonction de i

_rotation = valeur+(360/12)*i;

On a donc cela pour créer les points  :

for (i=1; i<=12; i++) {
    nom = "Point"+i;
    createEmptyMovieClip(nom, i);
    with (eval(nom)) {
        x = -5;
        y = -100;
        lineStyle();
        beginFill(0xA0D0FE);
        moveTo(x, y);
        curveTo(x-5, y+5, x+0, y+10);
        curveTo(x+5, y+15, x+10, y+10);
        curveTo(x+15, y+5, x+10, y+0);
        curveTo(x+5, y-5, x+0, y+0);
        endFill();
        _rotation = (360/12)*i;
    }
}

4. L'AFFICHAGE DE L'HEURE

Maintenant, il s'agit de faire fonctionner tout cela et que l'heure s'affiche correctement :
On crée une fonction que l'on place sur l'une des aiguilles (par exemple) qui aura pour but de tourner en permanence donc : onEnterFrame

Aiguille1.onEnterFrame = function() {
}

On récupère la date dans un variable :

ladate = new Date();

On applique à l'Aiguille1 les secondes grâce à getSeconds() :

Aiguille1._rotation = ladate.getSeconds()/60*360;

Si vous voulez que l'aiguille des secondes ne se déplace pas par à-coup :

Aiguille1._rotation = (ladate.getSeconds()+ladate.getMilliseconds()/1000)/60*360;

On applique à l'Aiguille2 les minutes grâce à getSeconds() :

Aiguille2._rotation = ladate.getMinutes()/60*360;

Et les heures à l'Aiguille3 grâce à getHours() mais pour avoir comme sur les vraies montres un avancement de l'aiguille en fonction du temps on ajoute getMinutes() dans le calcule :

Aiguille3._rotation = (ladate.getHours()%12+(ladate.getMinutes()/60))/12*360;

Avant de fermer with (Horloge), on décale l'objet Horloge pour qu'il soit visible

_x = 120;
_y = 120;

J'espère que vous avez suivi. Pour les calculs mathématiques, je n'ai pas expliqué. C'est suffisamment simple pour être compris sans aide.

5. RESULTAT ET SCRIPT

Après compilation, vous devriez avoir un truc du genre :) Si ce n'est pas le cas, le code complet est à la fin pour vous aider.


Voici tout le script de mon horlogecreateEmptyMovieClip("Horloge", 1);
with (Horloge) {
    createEmptyMovieClip("Aiguille1", 21);
    with (Aiguille1) {
        lineStyle(1);
        beginFill();
        moveto(0, 0);
    lineto(0, -100);
    endFill();
    }
    createEmptyMovieClip("Aiguille2", 22);
    with (Aiguille2) {
        lineStyle(1.5);
        beginFill();
        moveto(0, 0);
        lineto(0, -75);
        endFill();
    }
    createEmptyMovieClip("Aiguille3", 23);
    with (Aiguille3) {
        lineStyle(2);
        beginFill();
        moveto(0, 0);
        lineto(0, -50);
        endFill();
    }
    for (i=1; i<=12; i++) {
        nom = "Point"+i;
        createEmptyMovieClip(nom, i);
        with (eval(nom)) {
            x = -5;
            y = -100;
            lineStyle();
            beginFill(0xA0D0FE);
            moveTo(x, y);
            curveTo(x-5, y+5, x+0, y+10);
            curveTo(x+5, y+15, x+10, y+10);
            curveTo(x+15, y+5, x+10, y+0);
            curveTo(x+5, y-5, x+0, y+0);
            endFill();
            _rotation = (360/12)*i;
        }
    }
    Aiguille1.onEnterFrame = function() {
        ladate = new Date();
        Aiguille1._rotation = (ladate.getSeconds()+ladate.getMilliseconds()/1000)/60*360;
        Aiguille2._rotation = ladate.getMinutes()/60*360;
        Aiguille3._rotation = (ladate.getHours()%12+(ladate.getMinutes()/60))/12*360;
    };
    _x = 120;
    _y = 120;
}

2 commentaires déposés

Par jean-michel, le 20/02/2009 à 09:10:58
Avatar
Membre

super merci pour les debutants comme moi ça aide

Par Zéfling, le 20/02/2009 à 18:46:55
Avatar
Webmaster

Je pourrais le refaire en Haxe, ça serait mieux. ^_^'

Compared to French grammar, nothing is hard. (Rasmus Lerdorf)

Écrire un commentaire