Mixer SVG et JavaScript

La programmation d’animations avec canvas est assez lourde. Les possibilités d’animation en SVG pur avec les balises animate et animateMotion sont assez limitées. Donc on est a priori dans une impasse. Mais heureusement on peut coupler SVG avec toute la puissance du langage de programmation de JavaScript et alors on peut réaliser facilement des animations voire des jeux !

En effet les objets SVG sont des "noeuds" du DOM donc on peut les manipuler avec Javascript en particulier on peut modifier les attributs d’un objet SVG avec la méthode setAttribute et on peut récupérer les valeurs des attributs avec la méthode getAttribute.

Dans la page ci-dessous on crée en SVG deux voitures et on anime l’une des deux : elle se déplace le long d’une diagonale. On peut arrêter cette animation automatique en cliquant sur un bouton de commande.

Même si vous modifiez les dimensions de la zone de dessin SVG vous n’avez pas à modifier le code JavaScript puisque dans ce code on récupère ces dimensions avec la méthode getAttribute. Pratique !

Notez l’emploi de la fonction JS clearInterval() pour arrêter  la fonction animate ; l’astuce est d’identifier la fonction d’animation avec une variable (ici boucle)  et de produire l’instruction clearInterval(boucle). Facile, non ?

Extrait du code de la page :

<script>
window.onload = function ()
{
var auto = document.querySelector(‘#auto’);
var bouton = document.querySelector(‘button’) ;
var svg = document.querySelector(‘svg’);
var X = svg.getAttribute(‘width’) ;
var Y =svg.getAttribute(‘height’);
var x = 0 ; var y = 0 ;
var delta = 1;
var boucle = setInterval(animate,100) ;
function animate()
{
if (x >=X-40) delta = -1 ;
if (x <= 0) delta = 1 ;
x = x + (delta * 6) ;
y = y + (delta * 4) ;
auto.setAttribute(‘x’,x) ;
auto.setAttribute(‘y’,y) ; 
}
bouton.onclick = function()
{ clearInterval(boucle) ; alert(‘fin animation’) ; }
} // fin fonction anonyme
</script></head>
<body>
<h1>Animation automatique d’un groupe de forme</h1>
<svg width="600" height="400" style =’background : lime ; box-shadow : 5px 5px 5px grey; ‘>
<defs>
<g id = ‘voiture’>
<path d= ‘M 0,20 v-10 h10 v-10 h 20 v 10 h 10 v 10 z’ fill = ‘yellow’ />
<rect x = ’14’ y =’2′ width =’14’ height =’8′ fill = ‘grey’ />
<circle cx = ’10’ cy=’20’ r = ‘5’ fill = ‘silver’ />
<circle cx = ’30’ cy=’20’ r = ‘5’ fill = ‘silver’ />
</g>
</defs>
<use xlink:href="#voiture" x="0" y="0" id =’auto’ />
<use xlink:href="#voiture" x="90%" y="10%" id =’auto2′ />
</svg>
<button type = ‘button’>Arrêter animation </button>

Démonstration : voir mon site

Publié dans HTML 5, SVG | Poster un commentaire

Embarquer une police de caractères

Vous avez réalisé en local un site superbe en particulier grâce à l’emploi d’une police exotique. Mais au moment de l’hébergement de ce site vous vous dites : "c’est idiot, cette police exotique ne sera probablement pas installée sur le PC du visiteur … ".

Rassurez vous grâce à CSS 3 il est désormais possible dans une page d’embarquer une police de caractères c’est à dire de la mettre à disposition de l’internaute le temps de sa visite du site … Sympa, non ?

Extrait du code de la page :

<style>
@font-face{font-family : "ecole"; src:url(../polices/ecole.ttf) ; }
.special {font-family : ecole ; font-size : 12pt ; }
</style> </head>
<body>
<h1> Une police importée</h2>
<h2 class = ‘special’> Ce titre et le texte ci-dessous doit apparaître avec une police téléchargée</h2>
<p class =’special’> La troisième République veut que l’école élémentaire dispense non seulement l’instruction de base mais aussi fasse des petits français des patriotes prêts à se battre pour leur pays ; et à venger l’affront de mil huit cent soixante dix ; à reprendre l’Alsace et la Lorraine aux "boches". </p>

Commentaire du code :

Regarder attentivement la feuille de style !
La première règle de style (sélecteur @font-face) permet au client d’embarquer un fichier de police sous le nom ecole.
Il suffit ensuite de préciser que tout texte affecté de la classe special sera mis en forme avec la police dénommée ecole.

Démonstration

Publié dans CSS 3, HTML 5 | Poster un commentaire

SVG – la balise PATH

SVG – la balise PATH

Dans l’article sur les formes de base en SVG nous avons vu les balises rect, circle, ellipse, line, polygon et polyline.
Mais si vous voulez dessiner un escalier ou une courbe quadratique ou encore une courbe de Bézier alors vous devez utiliser la balise PATH.
Le grand intérêt de PATH par rapport à POLYGON ou POLYLINE c’est que vous pouvez exprimer les coordonnées des points en relatif (c’est à dire par rapport au point précédent) et ça c’est très très pratique …
La balise PATH sert aussi beaucoup pour les animations basée sur le déplacement d’un objet (une forme ou d’un groupe de formes ou une image voire un groupe d’images). En effet la balise animateMotion permet le déplacement d’un objet le long d’un PATH.

Exemple 1 : deux triangles dessinés avec la balise PATH

Le code de la page (extraits) :

<style>
path{ stroke:darkviolet; fill:yellow; stroke-width : 2px ; }
</style></head>
<body>

<svg width="400px" height="300px">
<!– path non fermé : pas de Z à la fin–>
<path d="M 40,40 L 150,100 L 100,280"/>
<!– path fermé : Z à la fin –>
<path d="M 240,40 L 350,100 L 300,280 Z"/>
</svg>

démonstration

Exemple 2 : deux carrés dessinés avec la balise PATH

Vous allez dire c’est idiot puisque l’on dispose de la balise rect. Mais il s’agit ici de vous monter qu’il y a deux raccourcis pour tracer des lignes horizontales ou verticales: les Lineto horizontaux (commande H) et les Lineto verticaux (commande V).
Le code de la page (extrait) :

< style>
path {fill : none ; stroke : purple ; stroke-width : 2px ; }

< svg width="400px" height="400px">
< !–Deux formes fermées dans le même path –>
< path d="M 100,100 H 200 V 200 H 100 Z M 200,200 H 300 V 300 H 200 Z"/>
< /svg>

Remarquez ici que les deux formes sont dessinées dans un Path unique mais contenant deux fois la commande M

Démonstration

Exemple 3 : un escalier et un zigzag

Le code de la page (extrait) :
< style>
path{ stroke:green; stroke-width:6px; fill:none; }

< svg width="400px" height="300px" >
< path d="M 10,10 h 20 v 20 h 20 v 20 h 20 v 20 h 20 v 20 h 20 v 20 h 20 v 20 h 20 v 20 h 20 v 20 h 20 v 20 h 20 v 20 z"/>
< path d="M 10,280 l 20,-20 l 20,20 l 20, -20 l 20,20 l 20, -20 l 20,20 l 20, -20 l 20,20 l 20, -20 l 20,20 l 20, -20 l 20,20 l 20"/>
< /svg>

Remarquez ici que les commandes H V et L sont écrites en minuscules. Donc les coordonnées qui suivent ces lettres minuscules sont des coordonnées relatives c’est à dire par rapport au point précédent. Donc c’est très pratique car c’est beaucoup plus facile de concevoir les coordonnées relatives d’un point que les coordonnées absolues. Attention les coordonnées du premier point doivent être exprimées en absolu.

Démonstration

Publié dans SVG | Tagué | Poster un commentaire

Incorporer des images dans SVG

Incorporer des images dans la zone de dessin SVG

Description de l’animation

Nous allons réaliser une animation très amusante en quelques lignes de code : un plongeur est poursuivi par un requin avec en décor un jardin de corail.
SVG est une balise block et donc il est possible via le CSS de lui attribuer une image de fond qui fera fonction de décor à notre scène.
Ensuite nous créons un motif composé de deux gifs animmés : un requin et un plongeur
Le motif est intégré dans un rectangle.
Nous créons un chemin invisible (PATH) et nous demandons au rectangle de se déplacer le long du chemin.
Nous demandons que cette animation soit répétée à l’infini.

Le code de la page (extrait)

<svg width="500" height="200" style = ‘background : url(../images/fond1.jpg) repeat-x;’>
<defs>
<pattern id="poursuite" patternUnits="userSpaceOnUse" x="0" y="0" width="200" height="100" >
<image x="0" y="0" width="100" height="100" xlink:href="../images/requin.gif" />
<image x="100" y="0" width="100" height="100" xlink:href="../images/plongeur2.gif" />
</pattern>
</defs>
<path id="trajectoire" d="M 0,50 h 500 " fill = ‘none’ />
<rect x="0" y="0" width="200" height="100" fill = "url(#poursuite)" >
<animateMotion begin="0s" dur="30s" repeatCount="indefinite">
<mpath xlink:href="#trajectoire"/>
</animateMotion>
</rect>
</svg>

démonstration

Publié dans SVG | Poster un commentaire

Animation avec CANVAS – principes

Principes de l’animation avec l’API CANVAS

Dans cet article nous allons expliquer au travers de deux exemples le principe de l’animation dans CANVAS Une animation CANVAS repose toujours selon les mêmes principes. Il faut appeler régulièrement la fonction d’animation grâce à la fonction JavaScript setInterval().
Dans le cadre de la fonction d’animation il faut :

  • effacer l’ancien dessin grâce à la fonction clearRect()
  • produire un nouveau dessin avec de nouveaux paramètres

Remarques sur mes habitudes de programmation : Dans mes exemples la variable canevas est une variable objet qui  référence la zone de dessin. Les variables  X et Y représentent respectivement la largeur et la hauteur de la zone de dessin

Premier exemple

Il s’agit d’un exemple simple. Nous voulons qu’un rond d’abord tout petit devienne très grand jusqu’à occuper tout la zone de dessin puis rapetisse pour retrouver sa taille initiale. Et ce cycle doit se répéter à l’infini.
Le code de la page est le suivant (extrait) :

<script>
window.onload = function()
{
var canevas = document.querySelector(‘canvas’);
var contexte = canevas.getContext(‘2d’);
var X = canevas.width ;
var Y = canevas.height;
var maxi = X/2;
var rayon = 10;
var variation = 1 ;
setInterval(animate,100);
function animate()
{
contexte.clearRect(0,0, X,Y) ;
contexte.beginPath();
contexte.arc(X/2, Y/2,rayon, 0, Math.PI*2);
contexte.fillStyle =’orange';
contexte.fill();
if (rayon == maxi) variation = -1 ;
if (rayon == 10) variation = 1 ;
rayon = rayon + variation ;
} // fin fonction animate
} // fin fonction anonyme
</script>
</head>
<body>
<h1>Extension puis réduction d’un rond</h1>
<canvas width = ‘300’ height =’300′></canvas>

Rappels

Le code Javascript doit être contenu dans la partie head de la page est plus précisément dans le conteneur script. Le code Javascript contient une fonction anonyme qui est est appelée sur chargement de la page La fonction anonyme contient l’instruction setInterval(animate,100) qui veut dire : appel de la fonction animate toutes les 100 millisecondes (donc 10 fois par seconde) La fonction animate contient l’instruction contexte.clearRect(0,0, X,Y) qui veut dire : effacement de toute la zone de dessin. Ensuite dans la fonction animate on crée un nouveau dessin : un rond avec fond orange avec une nouvelle valeur pour le rayon. La nouvelle valeur du rayon est égal à l’ancienne plus ou moins 1 pixel selon la variable variation vaut 1 ou -1

Démonstration

Deuxième exemple

Nous voulons qu’un carré d’abord tout petit devienne très grand jusqu’à occuper toute la zone de dessin puis rapetisse pour retrouver sa taille initiale. Et ce cycle doit se répéter à l’infini. Le carré doit toujours être centré horizontalement et verticalement dans la zone de dessin.
Le code de la page (extrait) est le suivant :
… <script>
window.onload = function()
{
var canevas = document.querySelector(‘canvas’);
var contexte = canevas.getContext(‘2d’);
var X = canevas.width ; var Y = canevas.height;
var cote = 10; // valeur initiale du cote du carré noir
var variation = 1 ; // valeur initiale de sens de variation
var x = (X-cote)/2 ; var y = (Y-cote)/2;
// coordonnées initiales de l’arête supérieure gauche du carré
setInterval(animate, 100);
function animate()
{
contexte.clearRect(0, 0, X, Y); // effacement ancien carré
contexte.fillStyle =’olive';
contexte.fillRect(x, y, cote, cote);
// dessiner carré de fond olive
if (cote == X) variation = -1 ;
if (cote == 10) variation = 1 ;
cote = cote + variation ; //nouvelle cote du carré
x = (X-cote)/2 ;
y = (Y-cote)/2 ;
// nouvelles coordonnées de l’arête supérieure gauche du carré
} // fin fonction animate
} // fin fonction anonyme
</script> </head>
<body>
<h1>Extension puis réduction d’un carré qui est toujours centré dans CANVAS</h1> <canvas width = ‘300’ height =’300′ style = ‘background : lime’></canvas>

Démonstration

Publié dans canvas | Poster un commentaire

SVG – principes de l’animation

Une animation en SVG

Dans cet article nous allons expliquer au travers de deux exemples le principe de l’animation automatique dans l’API SVG.

Premier exemple

Il s’agit d’un exemple simple. Nous voulons qu’un rond d’abord tout petit devienne très grand jusqu’à occuper tout la boîte SVG puis rapetisse pour retrouver sa taille initiale. Et ce cycle doit se répéter à l’infini.
Le code du conteneur SVG est le suivant :
<svg width="400px" height="400px" >
<circle cx="50%" cy="50%" r = ‘1px’ fill = ‘red’>
<animate attributeName="r" attributeType="XML" values = "1;200;1"
begin ="0s" dur="30s" repeatCount="indefinite"/>
</circle>
</svg>

Nous observons que la balise circle est désormais une balise double (un conteneur) et qu’elle contient la balise simple animate

La balise ANIMATE contient de nombreux attributs :

  • attributeName = "r" : ici on modifie le rayon du cercle
  • attributeType prend la valeur XML ou CSS selon que l’on modifie un attribut de la balise ou une propriété CSS de la balise
  • values = "1;200;1" : le rayon passe de 1px à 200 puis retombe à 1
  • begin = ‘0s’ :l’animation démarre dès le chargement de la page
  • dur : "30s" : l’animation (extension et contraction) dure 30 secondes
  • repeatCount="indefinite" : l’animation se répète à l’infini (autre valeur possible de cet attribut : un entier > à 1)

Deuxième exemple

Nous voulons qu’une boule se déplace le long d’une diagonale. Il faut donc inclure dans le conteneur circle deux animations car il faut modifier non seulement le cx mais aussi le cy du cercle.
Le code du conteneur SVG est alors le suivant :
<svg width="500px" height="500px" style = ‘background : green’>
<circle cx =’10’ cy =’10’ r= ’10’ fill = ‘red’>
<animate attributeName="cx" attributeType="XML" values = "10;490;10" begin ="0s" dur="15s" repeatCount="indefinite" />
<animate attributeName="cy" attributeType="XML" values = "10;490;10"
begin = ‘0s’ dur ="15s" repeatCount="indefinite" />
</circle>
</svg>

Démonstrations

Publié dans SVG | Poster un commentaire

SVG – les formes de base

Les rectangles

<svg height="200px" width="400px">
<rect x="25px" y="25px" width="100px" height="100px"
fill="orange" fill-opacity="0.5" stroke-width="5" stroke="olive" />
<rect x="150" y="75" width="100" height="100"
style = "fill : yellow ; fill-opacity : 0.5 ; stroke-width : 5 ;stroke : purple" />
</svg>
La balise rect a besoin au minimum de quatre attributs :

  • coordonnées x et y de l’arête supérieure gauche
  • largeur et hauteur du rectangle

Il y aussi les attributs de mise en forme :

  • stroke : couleur du contour
  • fill : couleur de remplissage
  • stroke-opacity : opacité du contour (de 0 à 1)
  • fill-opacity : opacité du remplissage (de 0 à 1)
  • stroke-with : épaisseur du contour

Notez le formatage du premier rectangle est fait avec des attributs de mise en forme et que celui du deuxième rectangle est réalisé  avec l’attribut style reprenant les mêmes mots comme propriétés CSS.

Les cercles

<svg height="200" width="400" >
< circle cx="100" cy="100" r="80" fill="olive" />
< circle cx="150" cy="100" r="80" fill="aqua" fill-opacity="0.5" />
< circle cx="300" cy="100" r="40" stroke="navy" stroke-width="20" fill="none"
stroke- opacity="0.5" />
< circle cx="340" cy="100" r="40" stroke="navy" stroke-width="10" fill="none" />
< /svg>
On utilise la balise circle dans SVG pour créer un cercle avec coordonnées du centre (attributs cx et cy) et rayon (attribut r)

Les ellipses

< svg height = "200px" width = "400px" >
< ellipse cx="200px" cy="100px" rx="200px" ry="100px" fill="lightgreen" stroke="red" stroke-width="2"/>
< /svg>
Pour définir une ellipse il faut quatre attributs :

  • coordonnées du centre de l’ellipse (cx et cy)
  • rx est le rayon horizontal de l’ellipse
  • ry le rayon vertical de l’ellipse

On peut définir les coordonnées et rayons en pixels (valeur par défaut) ou en pourcentage ; cx et rx en pourcentage de la largeur de SVG et cy et ry en pourcentage de la hauteur de SVG.
Donc nous aurions pu écrire :
<svg height = "200px" width = "400px" >
<ellipse cx="50%" cy="50%" rx="50%" ry="50%" fill="lightgreen" stroke="red"
stroke-width="2"/>
</svg>

Les lignes

<svg height="200" width="400">
<line x1="50" y1="50" x2="150" y2="150" stroke="black" />
<line x1="100" y1="50" x2="200" y2="150"
style = ‘stroke : red ; stroke-width : 5px ; stroke-opacity : 0.5 ;’ />
<line x1="150" y1="50" x2="250" y2="150"
stroke = ‘blue’ stroke-width = ’10px’ stroke-linecap = ’round’ />
<line x1="200" y1="50" x2="300" y2="150"
stroke = ‘blue’ stroke-width = ’10px’ stroke-dasharray =’5 5′ />
</svg>
Pour dessiner un ligne, on utilise la balise line qui a besoin de quatre attributs :

  • x1 renseigne l’abscisse du point de départ
  • y1 l’ordonnée du point de départ
  • x2 l’abscisse du point d’arrivé
  • y2 l’ordonnée du point d’arrivé

L’attribut stroke-linecap avec la valeur round permet d’avoir des extrémités arrondies et l’attribut stroke-dasharray avec la valeur 5 5 permet d’avoir des lignes pointillées : 5 pixels coloriés puis un intervalle de 5 pixels
Notez que tantôt le formatage de la droite est faite avec des attributs et tantôt avec une règle de style reprenant les mêmes mots comme propriétés CSS.

Les balises polygon et polyline

On emploie ici la balise polygon pour dessiner des formes fermées (ici deux triangles) en effet avec cette balise un segment est ajouté entre le dernier et le premier point et la balise polyline pour dessiner une forme ouverte.
Dans les deux balises il suffit de préciser les coordonnées x et y des angles de la forme.
La feuille de style :
< style>
polygon, polyline{ fill:none; stroke-width : 10px ; }
< /style>
Le code de la partie body :
< svg width="400px" height="300px">
< polygon points="50,50 50,100 150,50" stroke = ‘navy’ stroke-linejoin = ’round’ />
< polygon points="100,100 100,200 250,100" stroke = ‘olive’ stroke-linejoin = ‘miter’ />
< polyline points="200,200 200,280 300,200" stroke = ‘purple’stroke-linejoin = ‘bevel’ />
< /svg>

Notez l’emploi de l’attribut (ou propriété CSS) stroke-linejoin pour préciser le style des angles

Les valeurs possibles de l’attribut ( ou propriété CSS) stroke-linejoin :

  • round : angle arrondi
  • miter : c’est la valeur par défaut
  • bevel : angle tronqué

Démonstrations : voir mon site sur SVG et CANVAS

Publié dans SVG