Wèèèèèsh lecteurtrice !! Bien ou bien ?
T’as lu mon article précédent et t’as grave kiffé au taquet de ouf’ ? Sois jouasse, en rev’là une gorgée !
Avant qu’on s’y remette, j’espère que t’as fait tes devoirs, ou que t’as au moins essayé.
Si ce n’est pas le cas, ce n’est pas grave, je vais simplement prévenir mes robots correcteurs. Ils te jetteront du sable fin sur les sourcils, puis te pendront par les pieds et te fouetteront jusqu’à ce que tes larmes aient entièrement nettoyé tes sourcils.
Voici la solution du devoir, avec plein de commentaires qui expliquent comment c’est gaulay.
Un diamant
Let’s go sur un truc simple pour commencer. Retourne dans Trinket, ton bel environnement de dev, enlève le programme initial et ajoute les deux lignes habituelles au début : « import turtle », « turtle.speed(0) ». On va commencer simple, tu vas me dessiner un diam’s.

♫ C’est le python qui va dicter ton code. ♪ Génération Oui-Oui. ♬♪
Un diamant, c’est quatre quarts de cercle. Sauf qu’après chaque quart, la tortue fait demi-tour, pour changer le sens de tracé du quart suivant.
On n’est pas des prolos et on veut un gros diam, alors tu me fais des quart de cercles de 100 pixels de rayon. Tu as le droit de le réaliser d’abord à la crade, c’est à dire en copiant-collant 4 fois le même morceau de programme. Mais ensuite, tu me met ça sous forme d’une boucle.
Tu devrais réussir à bling-blinguer un diamant cossu comme ça :
Lien vers la réponse si tu as du mal à te remettre dans la vibe.
Laissez-moi vos coordonnées
Si tu as fait quelques années d’école, lecteurtrice, tu as sûrement placé des points sur une feuille, pour faire un graphique ou pour tracer une droite. Tu utilisais alors des coordonnées : un nombre en X, un autre en Y.
Si tu es Muriel Robin, lecteurtrice, tu pourrais faire la blague « laissez-moi vos cordonniers, je vous rappellerais », et tu aurais été super drôle, pour l’époque.
La tortue se déplace dans un espace défini par des coordonnées. Cet espace est orienté de la même manière qu’en cours de maths :
- La coordonnée (0, 0) correspond au milieu de la zone de dessin.
- Lorsqu’on va vers la droite, la première valeur (le X) augmente, elle diminue lorsqu’on va vers la gauche.
- Lorsqu’on va vers le haut, la deuxième valeur (le Y) augmente, elle diminue lorsqu’on va vers le bas.
C’est pas du tout orienté selon les conventions habituelles en informatique. On va pas s’attarder là-dessus pour l’instant, sinon je vais encore traiter les matheux de ringards.
La fonction « turtle.setpos » permet de positionner la tortue à des coordonnées données (Wesh, lecteurtrice ! « coordonnées données » ça fait une répétition lolilol !).
Voici un lien vers la doc de la fonction.
Au début de ton programme, ajoute un setpos pour positionner la tortue aux coordonnées X = -40, Y = +30.
Le déplacement va dessiner un trait moche. On réglera ça au chapitre suivant.
Mais avant, tu vas mettre ces coordonnées dans deux variables, intitulées « pos_x » et « pos_y ». Tu te souviens de ce qu’est une variable ?
Au début du programme, tu définis la variable « pos_x » à -40 et la variable « pos_y » à 30.
Ensuite, dans l’instruction « turtle.setpos », tu n’utilises plus directement les valeurs -40 et 30, mais les deux variables que tu viens de définir.
Pour l’instant, ces variables servent à R (Wesh lecteurtrice, langage de jeune !!), mais ce sera utile très bientôt.
Lien vers le code, si t’en chie.
Attention, les majuscules-minuscules sont importantes. « pos_x » et « Pos_x », ce n’est pas la même chose.
Les conventions de codage en python conseillent d’écrire les noms de variables tout en minuscules. Lorsqu’un nom est composé de plusieurs mots, on les sépare par des « _ » (le tiret bas). Un jour, jeune programmeurtrice dont les poils n’ont pas encore poussés, je te parlerai plus en détail de la notion de « convention de codage » et du PEP-8.
Si t’as envie d’appeler tes variables « posx » et « posy », t’as le droit, tu fais tout qu’est-ce que tu veux, c’est ta création, c’est bonheur. Il faudra juste que tu t’en rappelles, parce que dans la suite de l’article je continue de les appeler « pos_x » et « pos_y ».
Up and Down
C’est trognon ces variables, mais ça règle pas le problème du trait dégueubeurk que fait le setpos.
Je te donne juste le nom des deux fonctions permettant de régler le problème : « turtle.penup », « turtle.pendown ». Tu te débrouilles pour savoir ce que ça fait, comment ça marche, est-ce que ces fonctions ont besoin de paramètres, où les appeler, etc. Peut-être que tu peux commencer par les taper dans un moteur de recherche.
Tu regardes des docs et des exemples de code, tu testes dans ton programme, si ça fait des trucs pétés, tu testes autre chose. Azy lecteur, fais pas ta tafiolle, azy lectrice, fait pas ton tafiot (Wesh lecteurtrice, t’as vuuuu ? Écriture inclusive sur le mot « tafiolle » !)
Quand tu auras réussi, ça fera le même diam’s qu’au tout début, mais sans le trait moche.
Lien vers la réponse, si t’es au bout de ta vie.
Tout ça pour ça ? Je t’entends penser d’ici : « you you foutay de magl, ou bien ? ».
Ne brûle pas cet article tout de suite lecteurtrice, la suite est plus intéressante.

lofteurs.up() and lofteurs.down()
Pléthore de diam’s
Ce serait le top de la bling-bling-itude de pouvoir dessiner des diamants où on veut. Mais pas en copiant-collant le code, sinon ce serait le top de la cra-cra-itude. Alors on va créer une fonction.
Tu ne sais pas ce qu’est une fonction ? Eh bien si. Tu en utilises depuis le début : « print », « turtle.circle », « turtle.penup », … Maintenant, tu vas en créer une nouvelle qui sera rien qu’à toi.
Lorsqu’on crée une fonction, on lui associe un bloc de code, qu’on appelle le corps de la fonction. Comme tu as bien retenu la leçon précédente, tu sais déjà que ce bloc peut éventuellement contenir des sous-blocs, sous-sous-blocs, etc.
Ensuite on exécute la fonction (on peut aussi dire « appeler la fonction »), ce qui revient à exécuter son corps. Ça fait très bizarre de dire « exécuter son corps », alors dites-le uniquement dans votre tête, d’à-corps ?
Tu vas donc me créer une fonction, sans paramètre, intitulée « dessiner_diams ». Dans le corps, tu mets ce que tu as déjà écrit, depuis « turtle.penup » jusqu’à la boucle dessinant les quarts de cercle. Tu n’y mets pas l’initialisation des variables pos_x et pos_y, c’est fait exprès.
Voilà un lien de doc qui pourra t’aider : https://courspython.com/fonctions.html, à lire jusqu’au chapitre « Fonction avec paramètre ». Cela dit, les chapitres d’après peuvent t’aider pour la suite, et c’est assez bien expliqué. Y’a juste pas de fun, contrairement à mes articles qui regorgent d’espiègleries toutes pailletées de saveurs foisonnantes prestige t’as vu wesh ?
Seulement voilà. Si t’exécutes ton code là maintenant, t’auras queud’. Zéro diams. Retour à l’âge de prolétaire.
C’est normal, il faut appeler la fonction que tu as créée. À la fin du programme, ajoute « dessiner_diams() », et re-bling-bling !
Si tu appelles plusieurs fois de suite la fonction, ça ne changera pas le dessin final, car tu dessines plusieurs fois au même endroit.
Or, la fonction utilise les variables pos_x et pos_y pour se positionner avant de dessiner. Il suffit donc de les modifier puis de re-appeler la fonction.
Tant qu’on y est, tu vas ranger un peu ton code. En général on met les imports au début, puis la définition des fonctions, puis le code principal. Ça va donc donner un truc comme ça :
import turtle # Cette ligne, y'a qu'à la laisser au tout début. turtle.speed(0) # Ici, il y a la définition de la fonction "dessiner_diams" # Ensuite, la définition des variables pos_x et pos_y, # avec les mêmes valeurs qu'avant : -40 et +30 # Appel de la fonction. dessiner_diams() # On redéfinit les variables pos_x et pos_y, # avec, disons : pos_x = 10 et pos_y = 60 # Re-fonction. dessiner_diams()
Et ça devrait donner deux diamants, à deux endroits différents :
Lien vers la réponse, si t’es en PLS.
Avec des paramètres
On a fait un truc bizarre dans le chapitre précédent. On a utilisé les variables pos_x et pos_y à l’intérieur d’une fonction, alors qu’on ne les a pas définies dans la fonction elle-même. Ça n’a pas planté, grâce à la manière dont le langage python gère la portée des variables.
- Ton programme principal est dans un certain contexte, avec des variables.
- Tu exécutes la fonction « dessiner_diams », qui se crée un petit sous-contexte pour elle toute seule, avec ses variables.
- Le python autorise l’accès aux variables d’un contexte englobant, mais uniquement en lecture.
Tu verras peut-être, dans les différents tutoriels du grand internet, les notions de « variables globales » et « variables locales ». C’est à peu près la même chose, mais je n’aime pas trop ces termes, car ça donne l’impression qu’il n’y a que deux contextes, alors qu’il peut y en avoir bien plus.
Je vais pas trop t’embrouiller avec des choses que t’as pas encore vues. Un module possède lui aussi un contexte. D’autre part, tu peux déclarer une fonction dans une fonction, ce qui crée un sous-sous-contexte, et une fonction dans une fonction dans une fonction. Et en plus ça s’appelle pas des contextes mais des « espaces de nommage ». Oublions tout ce batacouac.
Y’a des fois, c’est justifié d’accéder à une variable du contexte englobant, mais là non, c’est pourri.
Déjà, parce que ça oblige à écrire trois lignes de code pour dessiner un diamant où on veut : deux lignes pour pos_x, pos_y, et la dernière pour la fonction. Et ensuite ça fait bizarre, car le comportement de la fonction dépend de choses extérieures à elle. C’est inhabituel, alambiqué, complexe et source de bugs.
Alors on va ajouter deux paramètres à la fonction. Devine comment on va les appeler ? pos_x et pos_y. Hu hu hu.
Il faut ajouter ces paramètres dans la définition de la fonction (la ligne de code avec le mot-clé « def »), ainsi qu’à chaque exécution de la fonction.
Tu n’as plus besoin des lignes de code définissant les variables pos_x et pos_y. Tu peux mettre les coordonnées directement dans les paramètres d’appel à la fonction. Tiens voilà un exemple issu de la même doc que tout à l’heure . Ne t’attardes pas sur le corps de la fonction, osef. Regarde juste comment elle est déclarée, comment elle est appelée, et tu fais le même genre de chose avec ta fonction à toi.
Tu peux faire un petit test pour bien te rendre compte que les paramètres pos_x et pos_y existent dans l’espace de la fonction, mais plus en dehors. Ajoute « print(pos_x) » à la fin de ta fonction. Ça va fonctionner. Ajoute la même ligne tout à la fin de ton programme, ça va merdoyer.
C’est ce qu’on veut, lecteurtrice. Chaque variable et chaque paramètre doit être présent uniquement là où on en a besoin, et ne pas être accessible ailleurs. Sinon ça embrouille, on se demande ce que ça fout là, et on passe pour une baltringue ou un baltringuet (Wesh ! Écriture inclusive !).
Pour finir ce chapitre sur quelque chose d’over-classe, tu mets une boucle de 20 itérations dans laquelle tu exécutes ta fonction. Pour ses deux paramètres, indique directement le compteur de la boucle.
Ça va faire un truc comme ça :
Lien vers le code si t’as vomi ton cerveau.
On taille les diamants
Maintenant que tu as compris le truc avec les paramètres de fonctions, profitons-en pour en rajouter un troisième, permettant de choisir la taille du diamant.
C’est à peu près comme au chapitre précédent :
- Ajoute un paramètre dans la définition de la fonction, après pos_x et pos_y. On l’appellera « taille ».
- Utilise ce paramètre dans le corps de la fonction. Ça va se passer dans la ligne de code « turtle.circle(100, 90) »
- Ajoute le paramètre lors de l’exécution de la fonction. Dans un premier temps, tu peux indiquer une valeur fixe. Le plus simple est de remettre 100.
Avec ça, tu auras la même image que précédemment, mais ton programme sera plus souple, comme lui :
Modifie la boucle affichant les 20 diamants, en faisant varier leur taille, de 0 pixels (inclus) à 100 pixels (exclus), en avançant par pas de 5 pixels.
Et plop :
Lien vers la réponse si t’es pas de taille.
Recentrons-nous
Hé, j’ai une idée géniale. On pourrait afficher des diamants de taille différente, mais tous en coordonnées (0, 0). Ça ferait un truc trop joli, comme une espèce de porte des étoiles magiques en forme de vagin de l’espace.
Sans plus attendre, re-re-modifie la boucle exécutant la fonction, et indique 0 dans les deux premiers paramètres.
Et paf, c’est moche.
Qu’est-ce à dire que ceci ?
La fonction positionne la tortue aux coordonnées (pos_x, pos_y), puis commence tout de suite à dessiner.
Donc ces coordonnées ne correspondent pas au centre du diamant, mais à la pointe de gauche.
Avant de dessiner, il faut se décaler vers la gauche, d’une distance égale à la taille du diamant.
Y’a deux manières de le faire :
Soit tu te positionnes dès le départ où il faut, en changeant le premier paramètre de l’instruction turtle.setpos. Au lieu de « pos_x », tu mets « pos_x – taille ».
Soit tu laisses le setpos comme il est, mais juste après, tu recules de la taille du diamant. La fonction pour reculer, c’est « turtle.backward », elle fonctionne comme le forward.
Je te conseille fortement la deuxième option. Tu en auras besoin au moment de faire tes devoirs. Eh ouais, lecteurtrice, t’auras encore des devoirs. La vie est dure.
Après avoir appliqué le décalage, ça devrait dessiner ça :

Diamonds are a girl’s best friend
I have a good filling about this
On va momentanément partir sur autre chose.
Teste-moi ça, dans un autre onglet Trinket :
import turtle turtle.fillcolor("red") turtle.begin_fill() turtle.forward(60) turtle.left(120) turtle.forward(60) turtle.left(120) turtle.forward(60) turtle.end_fill()
Ça va dessiner un magnifique triangle rempli de rouge.
Explications :
- La fonction fillcolor est assez simple : elle définit une couleur de remplissage. Tu peux remplacer « red » par « green », « blue » ou d’autres couleurs en anglais.
- La fonction begin_fill indique à la tortue qu’on va commencer à tracer un dessin qui sera à remplir.
- Ensuite, des forward et des left, que tu connais déjà.
- Finalement, la fonction end_fill indique à la tortue qu’on a fini le dessin et que le remplissage doit être effectué.
Ce n’est pas forcément évident à comprendre. Ces fonctions de fill impliquent beaucoup de traitements réalisés en interne par le python.
Lorsque tu es entre un begin_fill et un end_fill, à chaque fois que tu traces un bout de truc, que ce soit avec un forward, un circle ou autre chose, la tortue enregistre tous les pixels par où elle est passée. Au moment du end_fill, la tortue en déduit l’espace interne de pixel délimité par ton tracé, et elle les colorie. Comme l’outil « pot de peinture » dans les logiciels de dessin, t’as vu ?
Pas besoin de te prendre la tête avec ces traitements compliqués, le python le fait tout seul (plus exactement, c’est la librairie de code turtle qui le fait, osef). Mais du coup, c’est pas évident de comprendre ce que ça fait.
On pourrait presque considérer que tout ce que tu fais entre le begin_fill et le end_fill constitue un sous-bloc de code. D’ailleurs, si ça ne tenait qu’à moi, j’aurais fait un context manager, et ça se serait explicitement écrit comme des sous-blocs de code. Un « context manager », c’est un truc spécial du python que tu peux mentionner quand tu veux montrer à tes lecteurtrices à quel point tu es un over-expert du python.
Et là, lecteurtrice, je me plaît à imaginer que tu t’intéresses à ce que je te raconte jusqu’au plus profond de tes neurones, et que donc tu te poses plein de questions :
- Si je dessine n’importe quoi et que je ne reviens pas à mon point de départ, est-ce que ça va colorier toute l’image comme dans Paint ?
- Si je croise des traits, ça va se colorier comment ?
- Si je fais plusieurs begin_fill et/ou plusieurs end_fill à la suite, ça donne quoi ?
Réponse : t’as qu’à tester. Tiens, je t’ai fait quelques exemples.
Bon, ceci étant expliqué, je veux un diamant de sang ! Yaaahahahhaaarrrr !!
Modifie la fonction de façon à ce qu’elle dessine un diamant coloré en rouge. Il suffit d’ajouter les instructions de fill, aux bons endroits.
Ensuite, les diamants vont se dessiner en se recouvrant l’un après l’autre. À la fin, tu auras ça :
Lien vers la réponse, si tu commences à pleurer du sang.
Ce sera tout pour aujourd’hui
Dans mon article précédent, j’ai dit qu’on ferait ça :
On n’y est pas encore, mais on s’en rapproche. Je m’arrête là pour l’instant. J’ai d’autres trucs à faire que d’écrire des cours de python. Désolé. Promis, le mois prochain, on y arrive.
En attendant, pour pas que tu t’ennuies, BADAM-BING ! LES DEVOIRS !!!
Dessine-moi ça :
Petit indice : depuis le début, on dessine des diamants tout droit, parce que l’orientation initiale de la tortue est droite. Et si tu tournais un peu ta tortue avant de dessiner un diamant ? Pas trop, un ou deux degrés…