Night.png);">
Apprendre


Vous êtes
nouveau sur
Oniromancie?

Visite guidée
du site


Découvrir
RPG Maker


Apprendre
RPG Maker

Tutoriels
Guides
Making-of

Dans le
Forum

Section Entraide

Jeux: puie z / Jeux: Citymaime - Chapitre 1 / Jeux: Mer, îles et fous / News: Du neuf dans le making / News: Muma|Rope est disponible en (...) / Chat

Bienvenue
visiteur !




publicité RPG Maker!

Statistiques

Liste des
membres


Contact

Mentions légales

394 connectés actuellement

30734253 visiteurs
depuis l'ouverture

1218 visiteurs
aujourd'hui



Barre de séparation

Partenaires

Indiexpo

Akademiya RPG Maker

Blog Alioune Fall

Fairy Tail Constellations

Tashiroworld

Leo-Games

RPG Maker - La Communauté

ConsoleFun

Tous nos partenaires

Devenir
partenaire



Cosinus et Sinus, avec (+ - * /)

Approximer les fonctions trigonométriques cosinus et sinus en utilisant les opérations de base, idéal pour faire tourner des pictures autour de points.

Ecrit par Anton_ le 23/06/2013


❤ 2

PARTIE I : Présentation du problème

Prenons un exemple simple qui nous suivra tout au long de ce tutoriel : j'ai nommé, l'horloge.

L'horloge, comme chacun le sait, possède des compteurs qui tournent autour du cadran, mais voilà, qui voudrait mémoriser 60 positions différentes X et Y, avec autant de conditions chiantes et répétitives ? personne ! (à part les imbéciles)
oui, mais certains iront plutôt mettre des pictures d'aiguilles dans diverses positions, ce qui est plus adapté si on veut des aiguilles dans une horloge (c'est compréhensible)
Ici, on va se contenter d'une petite boule qui tourne autour d'un centre

on va définir l'angle de rotation de l'horloge en fonction d'une variable "secondes" qui incrémente quand le temps passe.
Et le Cos et le Sin seront définis par le modulo 360 de cet angle (on est en degrés, pas en radians...)
Les variables cos/sin finales seront comprises entre -1000 et 1000 au lieu de -1 et 1 (c'est mieux pour des valeurs entières)

1 seconde correspond à 1/60e de tour, soit 6°.
Sur le cercle trigonométrique, la position 0 de l'horloge correspond à +90° et elle tourne dans le sens -

angle_horloge = 90 - 6 * "secondes"

soit X = modulo 360 de cet angle.


Maintenant, observons les courbes des fonctions Cos et Sin, ça promet d'être passionnant
[mode Matheux ON]


PARTIE II : Des fonctions complexes...

la première fois qu'on voit les courbes de Cos et Sin, on se dit : "tiens, mais ça ressemble à des paraboles qu'on colle les uns après les autres"

C'est évidemment une fausse illusion, mais c'est également une bonne piste pour faire des approximations.

1) Un trinôme ?

on va décomposer les courbes en morceaux de paraboles entre 0 et 360 :

COS : [ (0-90) , maximum en 0 ] , [ (90-270) , minimum en 180 ] , [ (270-360) , maximum en 360 ]
SIN : [ (0-180) , maximum en 90 ] , [ (180-360) , minimum en 270 ]


Faites roulez les conditions !

exemple : on fait l'approximation de sin entre 0 et 180 :
Y = (A) *(X-90)² + 1000

avec A = -10/81


Notez plusieurs choses :
La parabole a son maximum en 90, si c'est un minimum, il faut multiplier le tout par -1
On soustrait aussi X de la position du sommet. (super important)

le coefficient A est le même pour tous les bouts de trinôme, il faut juste penser à son orientation !
(visualisez vos courbes sur excel si vous n'êtes pas sûrs)

Enfin bon, ça, c'est la méthode facile, légère en calcul, et rapide, mais elle a une grande marge d'erreur...
on obtient une erreur maximale de 6%, que qui fait un pixel à coté tous les 16.4 pixels de distance.

"oouuh remboursez, c'est pas ce qu'il y avait d'écrit sur la description !"

Tout juste, voici un polynôme plus précis.

2) Polynôme de Degré 4

Si on soustrait notre "mauvaise" fonction avec la vraie courbe de Cosinus ou Sinus, on voit une sorte de polynôme de Degré 4.

On modifie alors la fonction principale :
Y = A*(X-sommet) ^ 4 + B*(X-sommet) ^ 2 + 1000

j'ai tâtonné pendant des heures pour trouver les meilleurs coefficients, les voici !

A = (1/540)²
B = (7/18)²


N'oubliez pas l'orientation du polynôme !! (Si le sommet est en bas, multipliez tout par -1)

Et voilà, notre fonction est-elle prête à l'emploi ?

NON !
Le terme en X^4 est à manipuler avec précaution !

comme vous le voyez, (X-sommet) est toujours compris entre -90 et 90
Seulement voilà, 90^4 = 65 610 000
nombre trop grand pour être intégré à une variable RMesque, dont la limite est de 9 999 999

Il faut donc appliquer DANS L'ORDRE :

Terme_en_X4 = (X-sommet)^3
/36
*(X-sommet)
/8100


et voilà, plus de problèmes.

On observe la marge d'erreur par rapport aux vraies courbes ... 0.2% !! Soit 1 pixel de raté tous les 500 pixels !
Sur une résolution de 640x480, qui pourra faire la différence ?

3) résultats

Nous avons donc en entrée la variable "angle"
réservez 5 ou 6 variables pour le calcul intermédiaire
Et 2 variables sont en Sortie, COS et SIN.

4) Le code svp !

Voici le code ligne par ligne (simplifié pour une meilleure lecture)

INPUT : Angle, n'importe quel nombre entier, sera tranformé en un nombre entre 0 et 360 selon le modulo 360 du nombre initial.
L'angle suit le cercle trigonométrique : donc 0 c'est à l'Est, 90 au Nord, 180 à l'Ouest, et 270 au sud.

OUTPUT : outputCos, et outputSin, entre -1000 et +1000. représentent au mieux le cos et le sin de l'angle d'input donné en entrée.

Portion de code : Tout sélectionner

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
 
Angle %= 360 
If : Angle < 0
   Angle += 360 
  
End If
// set sommet/signe of parabole for COS
If : Angle < 90
    sommet = 0 
    signe = 1 
  
 Else
  If : Angle < 270
      sommet = 180 
      signe = -1 
    
   Else
      sommet = 360 
      signe = 1 
    
  End If
End If
 
// GET Y of Parabole
// get x
  x = Angle
  x -= sommet
// get x^4 with the positive coeff (warning, 90^4 overflows)
  x4 = x
  x4 *= x
  x4 *= x
  x4 /= 36 
  x4 *= x
  x4 /= 8100 
// get x² with the negative coeff
  x2 = x
  x2 *= x
  x2 *= 49 
  x2 /= 324 
// add up everything
  x = x4
  x -= x2
  x += 1000 
// apply sign
  x *= signe
// tadam !
outputCos = x
 
// set sommet/signe of parabole for SIN
If : Angle < 180
    sommet = 90 
    signe = 1 
  
 Else
    sommet = 270 
    signe = -1 
  
End If
// GET Y of Parabole (same stuff)
// get x
  x = Angle
  x -= sommet
// get x^4 with the positive coeff (warning, 90^4 overflows)
  x4 = x
  x4 *= x
  x4 *= x
  x4 /= 36 
  x4 *= x
  x4 /= 8100 
// get x² with the negative coeff
  x2 = x
  x2 *= x
  x2 *= 49 
  x2 /= 324 
// add up everything
  x = x4
  x -= x2
  x += 1000 
// apply sign
  x *= signe
// tadam !
outputSin = x




PARTIE III : Applications

Nous avons donc COS et SIN , deux variables comprises entre -1000 et 1000

"C'est bien beau tout ça, mais comment on s'en sert ?"

C'est simple ... Il faut encore des variables !

Reprenons notre horloge :
Elle tourne dans un coin de l'écran. On définit son centre de rotation en un point dont on choisit les coordonnées : Cx et Cy
Il faut aussi la distance par rapport au centre : le rayon, R.
la position de la petite boule qui tourne autour est donc
X_final = Cx + (COS * R)/1000
Y_final = Cy + (SIN * R)/1000


Pourquoi je divise par 1000 ? C'est dans le but de définir COS et SIN entre -1 et 1
(appliquez la multiplication avant la division par 1000 !)


Et voilà, amusez vous bien !

BONUS : vous pouvez faire varier les entrées !!
Cx , Cy , R , angle , vitesse d'avance de l'angle


image

Mis à jour le 30 septembre 2020.



Autres articles similaires :

- Tassle, "Cosinus et Sinus, avec */+", Oniromancie, le 30 septembre 2020, https://www.rpg-maker.fr/index.php?page=tutos&id=499



verehn - posté le 23/06/2013 à 19:07:04 (9058 messages postés) - honor

❤ 0

Vhehrhehn

J'ai mis quelques passages en couleur, Anton. Si tu n'aimes pas je les enlèverai ;)

Eldrao ~ PakuPaku ~ Winged Light ~ Ruin ~ Ma galerie ~ LTDAD ~ Don de graphismes plateforme 2D


Anton_ - posté le 23/06/2013 à 19:23:06 (1535 messages postés)

❤ 0

c'est impeccable, on fait super bien la différence avec ce qui est calcul et ce qui n'en est pas :sourit

edit importante :
Dans RM 2003 (et les autres, peut être), le modulo d'un nombre négatif donne un résultat négatif. (pourquoi ? je ne sais pas)
Alors qu'ici dans la fonction utilisée après, il nous faut un nombre entre 0 et 360.

Il faut rajouter ces deux lignes suivantes après X = Angle modulo 360

Si X < 0
{
X ajouter 360
}


Raetribution | Megamike || tutos : 1 2 || Une bonne dose de maths pour la route


Joke - posté le 23/06/2013 à 19:34:10 (5090 messages postés)

❤ 1

Bilouteux fou

Tutoriel très intéressant, ça veut dire qu'on peut faire de faux cosinus et faux sinus sous RM2003, et donc faire parcourir des coordonnées sur des cercles ou ellipses... Cool : )

biloumaster.fr, mon joli site ouèb tout bô tout frai !


Grade - posté le 23/06/2013 à 20:36:26 (905 messages postés)

❤ 0

Sympa !
Je m'en souvienderai définitivement la prochaine fois que je fais un projet RPG Maker.

Ça me donne envie d'écrire des tutos sur l'algorithmique ça.

MMORPG 2D Amateur | http://www.shinsekaionline.com


Maelstorm - posté le 23/06/2013 à 22:31:29 (3984 messages postés)

❤ 0

Une chance sur un million

Citation:

la première fois qu'on voit les courbes de Cos et Sin, on se dit : "tiens, mais ça ressemble à des paraboles qu'on colle les uns après les autres"


euh ... ouais ?

peut etre un peut abrupt pour les néophytes ton tuto ...


Ixsuixwzone - posté le 24/06/2013 à 10:26:45 (2453 messages postés)

❤ 0

Hey ! Mais c'est carrément utile ça 0.o
Merci Anton, c'est bien pensé. Ça risque de me servir plus tard.

| Âmes Bannies - Demo 0.2 |


Anton_ - posté le 27/09/2013 à 11:51:39 (1535 messages postés)

❤ 0

Je signale un détail sur l'angle et son modulo (oui oui, trois mois après !! :F)

Dans RM 2003 (et les autres, peut être), le modulo d'un nombre négatif donne un résultat négatif. (pourquoi ? je ne sais pas)
Alors qu'ici dans la fonction utilisée après, il nous faut un nombre entre 0 et 360.

Il faut rajouter ces deux lignes suivantes après X = Angle modulo 360

Si X < 0
{
X ajouter 360
}


Raetribution | Megamike || tutos : 1 2 || Une bonne dose de maths pour la route


Anton_ - posté le 14/07/2017 à 02:40:53 (1535 messages postés)

❤ 1

Je suis revenu ici pour réutiliser dans un projet le cos et le sin. Et quelle fut ma surprise de voir que ce tuto est TRES MAL EXPLIQUE SCROGNEUGNEU !!

Donc pour me faire pardonner, voici le code ligne par ligne (simplifié pour une meilleure lecture)

INPUT : Angle, n'importe quel nombre entier, sera tranformé en un nombre entre 0 et 360 selon le modulo 360 du nombre initial.
L'angle suit le cercle trigonométrique : donc 0 c'est à l'Est, 90 au Nord, 180 à l'Ouest, et 270 au sud.

OUTPUT : outputCos, et outputSin, entre -1000 et +1000. représentent au mieux le cos et le sin de l'angle d'input donné en entrée.

Bon copinage.

Portion de code : Tout sélectionner

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
 
Angle %= 360 
If : Angle < 0
   Angle += 360 
  
End If
// set sommet/signe of parabole for COS
If : Angle < 90
    sommet = 0 
    signe = 1 
  
 Else
  If : Angle < 270
      sommet = 180 
      signe = -1 
    
   Else
      sommet = 360 
      signe = 1 
    
  End If
End If
 
// GET Y of Parabole
// get x
  x = Angle
  x -= sommet
// get x^4 with the positive coeff (warning, 90^4 overflows)
  x4 = x
  x4 *= x
  x4 *= x
  x4 /= 36 
  x4 *= x
  x4 /= 8100 
// get x² with the negative coeff
  x2 = x
  x2 *= x
  x2 *= 49 
  x2 /= 324 
// add up everything
  x = x4
  x -= x2
  x += 1000 
// apply sign
  x *= signe
// tadam !
outputCos = x
 
// set sommet/signe of parabole for SIN
If : Angle < 180
    sommet = 90 
    signe = 1 
  
 Else
    sommet = 270 
    signe = -1 
  
End If
// GET Y of Parabole (same stuff)
// get x
  x = Angle
  x -= sommet
// get x^4 with the positive coeff (warning, 90^4 overflows)
  x4 = x
  x4 *= x
  x4 *= x
  x4 /= 36 
  x4 *= x
  x4 /= 8100 
// get x² with the negative coeff
  x2 = x
  x2 *= x
  x2 *= 49 
  x2 /= 324 
// add up everything
  x = x4
  x -= x2
  x += 1000 
// apply sign
  x *= signe
// tadam !
outputSin = x
 



Raetribution | Megamike || tutos : 1 2 || Une bonne dose de maths pour la route


Tassle - posté le 01/12/2021 à 17:18:07 (5274 messages postés)

❤ 2

Disciple de Pythagolf

J'ai expérimenté un peu et j'ai trouvé une meilleure méthode:

Spoiler (cliquez pour afficher)


La vitesse est exactement la même que pour la méthode d'Anton (si on supprime ses commentaires, parce que oui chaque commentaire coûte quasi autant de temps que tout autre instruction) mais l'erreur max est de 1.35 (au lieu de 1.91 avec la méthode d'Anton).

Si a1 et a2 sont des variables d'id consécutives, de même que b1 et b2, sign1 et sign2, outputCos et outputSin, on peut améliorer très légerement la vitesse d'execution en utilisant le fait que RM2k3 permet de modifier plusieurs variables en même temps (ce qui est aussi rapide que de modifier une seule variable):

Spoiler (cliquez pour afficher)


(ce code est environ 11% plus rapide que le précédent, mais on utilise plus de variables différentes)

Edit: Pour ceux que ça intéresse, j'utilise une approximation par une fonction rationnelle plutôt que polynomiale. En gros cos(x) ~ 994*(8097-x^2)/((32151+x^2)/4) pour x entre -90 et 90 (avec des divisions entières). On pourrait enlever le /4 et remplacer 994 par 4*994 (= 3976) mais après les valeurs des variables pourraient dépasser le max de RM2k3.

~~

Suite à de nombreux abus, le post en invités a été désactivé. Veuillez vous inscrire si vous souhaitez participer à la conversation.

Haut de page

Merci de ne pas reproduire le contenu de ce site sans autorisation.
Contacter l'équipe - Mentions légales

Plan du site

Communauté: Accueil | Forum | Chat | Commentaires | News | Flash-news | Screen de la semaine | Sorties | Tests | Gaming-Live | Interviews | Galerie | OST | Blogs | Recherche
Apprendre: Visite guidée | RPG Maker 95 | RPG Maker 2003 | RPG Maker XP | RPG Maker VX | RPG Maker MV | Tutoriels | Guides | Making-of
Télécharger: Programmes | Scripts/Plugins | Ressources graphiques / sonores | Packs de ressources | Midis | Eléments séparés | Sprites
Jeux: Au hasard | Notre sélection | Sélection des membres | Tous les jeux | Jeux complets | Le cimetière | RPG Maker 95 | RPG Maker 2000 | RPG Maker 2003 | RPG Maker XP | RPG Maker VX | RPG Maker VX Ace | RPG Maker MV | Autres | Proposer
Ressources RPG Maker 2000/2003: Chipsets | Charsets | Panoramas | Backdrops | Facesets | Battle anims | Battle charsets | Monstres | Systems | Templates
Ressources RPG Maker XP: Tilesets | Autotiles | Characters | Battlers | Window skins | Icônes | Transitions | Fogs | Templates
Ressources RPG Maker VX: Tilesets | Charsets | Facesets | Systèmes
Ressources RPG Maker MV: Tilesets | Characters | Faces | Systèmes | Title | Battlebacks | Animations | SV/Ennemis
Archives: Palmarès | L'Annuaire | Livre d'or | Le Wiki | Divers