-
Notifications
You must be signed in to change notification settings - Fork 3
Découvrir Linotte 3 en dix minutes
- Ce document présente rapidement quelques fonctionnalités du langage Linotte.
- Ce n'est pas un tutoriel pour apprendre à programmer.
- Avoir installé l'Atelier Linotte : http://langagelinotte.free.fr/wordpress
Linotte est un langage de programmation très simple à prendre en main. Ces principales caractéristiques sont :
- programmation fonctionnelle
- programmation orientée objet
- programmation graphique et événementielle
- programmation web dynamique
Malgré sa simplicité apparente, le langage peut produire des programmes complexes.
affiche "Bonjour !"
En 1 ligne, nous avons écrit un premier programme qui peut être directement exécuté dans l'atelier Linotte.
La notion de variables en Linotte s'exprime à travers la notion d'acteurs. Un acteur est caractérisé par un nom, un rôle (un type) et une valeur.
prénom prend "Nicolas"
affiche "Bonjour, " + prénom
Cet exemple créé l'acteur prénom typé texte et contiendra la valeur "Nicolas".
Si vous l'essayez dans l'Atelier, vous obtiendrez à l'affichage :
Bonjour, Nicolas
Le langage propose seulement 5 types qui sont : texte, nombre, drapeau, casier, espèce
Nous verrons à travers les exemples comment les utiliser.
Le verbe Demander interroge l'utilisateur :
prénom est un texte
affiche "Quel est ton prénom ?"
demande prénom
affiche "Bonjour, " + prénom
Le verbe Questionner peut être également utilisé :
prénom est un texte
questionne prénom sur "Quel est ton prénom ?"
affiche "Bonjour, " + prénom
Les fonctions disponibles sont :
- Carré d'un nombre :
carré x
- Cosinus :
cos x
- Sinus :
sin x
- Fonction exponentielle :
exp x
- Logarithme décimal:
log x
- Logarithme naturel:
logn x
- Valeur absolue :
abs x
- Racine carrée :
racine x
- Arrondi :
arrondi x
- Cube d'un nombre :
cube x
- Puissance :
x puiss n
- Modulo :
x mod n
- Et logique :
x et n
- Ou logique :
x ou n
- Xou logique :
x xou n
- Tangente :
tan x
- Arc cosinus :
acos x
- Arc sin :
asin x
- Arc tangente :
atan x
- Hasard :
hasard x
Exemple simple :
affiche carré 4
affiche 2 puiss 4
affiche vrai ou faux
affiche (2 puiss 23 + 5 * 6 - 1) / 3
Exemple plus complexe :
durée est un nombre
e est un nombre
demande e
tant que e != 1
durée prend durée + 1
si (e mod 2) = 0, e prend e / 2
sinon e prend e * 3 + 1
ferme
affiche durée
Le langage propose les conditions suivantes :
si 1 = 1 affiche "vrai"
si 1 != 1 affiche "faux"
si 2 > 1 affiche "vrai"
si 1 < 2 affiche "vrai"
si 1 >= 1 affiche "vrai"
si 2 <= 2 affiche "vrai"
-
si ?.collision(?) affiche "vrai"
(à utiliser avec des objets graphiques) si vrai affiche "vrai"
si "a" contient "banane" affiche "vrai"
Les conditions peuvent s'utiliser simplement sur une ligne :
si (2 * 2) = (2 + 2) affiche "j'ai raison !"
si (3 * 3) > (3 + 3) affiche "j'ai encore raison !"
On peut utiliser les blocs :
si (1 * 1) != (1 * 1)
affiche "j'ai dit :"
attends 500 millisecondes
affiche "tu as tort !"
ferme
La clause Sinon peut également être utilisée :
si (1 * 1) != (1 * 1)
affiche "j'ai dit :"
attends 500 millisecondes
affiche "tu as tort !"
ferme
sinon
affiche "j'ai dit :"
attends 500 millisecondes
affiche "j'ai toujours raison !"
ferme
Il est parfois utile de découper un programme en plusieurs fonctions :
// Exemple inspiré du manuel utilisateur du CPC 6128 (page 32)
efface tableau
affiche dame("")
affiche "Noire dans le gris du soir,"
affiche dame("")
affiche "Grise dans le noir.
"
affiche nuage(",")
affiche "Il fait noir comme dans un four,"
affiche nuage(".")
affiche "Tiens le petit jour.
"
affiche dame(",")
affiche "Rose dans les rayons bleus,"
affiche dame(" :")
affiche "Debout, paresseux.
Paul Verlaine."
dame : suffix
retourne "Dame souris trotte" + suffix
nuage : suffix
retourne "Un nuage passe" + suffix
- Les blocs
Les blocs sont des structures internes à une fonction. On peut les utiliser dans des conditions ou les boucles. Un bloc termine avec le verbe fermer.
capitale est un texte
tant que capitale != "Paris"
affiche "Quelle est la capitale de la France ?"
demande capitale
ferme
affiche "Bravo, tu es trop fort !"
Implémenter des algorithmes récursifs en Linotte est possible. Le meilleur exemple... la suite de Fibonacci :
n est un nombre
affiche "Entrez un nombre :"
demande n
affiche fibo(n)
fibo : n
si n < 2 retourne n
sinon retourne fibo(n-1) + fibo(n-2)
Les boucles, briques essentielles lors de l'élaboration d'algorithme sont présentes sous différentes formes dans le langage Linotte.
La forme la plus usuelle est "pour n de a à b ... " :
notes est un casier de nombres
prénoms est un casier de textes valant "Pierre", "Jacques", "Hugo"
b est un nombre
pour b de 0 à 2
ajoute question( prénoms{b} ) dans notes
ferme
pour b de 0 à 2
affiche "La note de " + prénoms{b} + " est " + notes{b}
ferme
question : prénom
valeur est un nombre
affiche "Quelle est la note de " + prénom + " ?"
demande valeur
retourne valeur
La forme "tant que condition ... " est également disponible :
notes est un casier de nombres
prénoms est un casier de textes valant "Pierre", "Jacques", "Hugo"
b est un nombre
tant que b < 3
ajoute question( prénoms{b} ) dans notes
b prend b + 1
ferme
tant que b > 0
b prend b - 1
affiche "La note de " + prénoms{b} + " est " + notes{b}
ferme
question : prénom
valeur est un nombre
affiche "Quelle est la note de " + prénom + " ?"
demande valeur
retourne valeur
Quelques raccourcis très utiles sont proposés.
- Raccourci pour le verbe Afficher :
"Bonjour" !
- Raccourci pour le verbe Demander :
prénom est un texte
prénom ?
"Bonjour, " + prénom !
- Raccourci pour le verbe Prendre :
prénom prend "Jules"
prénom = "Jules"
- Forcer l'Atelier à demander des valeurs :
Si la première commande d'un programme est une fonction avec des paramètres, automatiquement, l'Atelier va demander à l'utilisateur les valeurs des paramètres.
Si la dernière commande est le verbe retourner
, l'Atelier affiche la valeur sur le tableau.
fibo : n
si n < 2 retourne n
sinon retourne fibo(n-1) + fibo(n-2)
L'exécution de ce programme va produire cet affichage :
Quelle est la valeur de l'acteur 'n' ? 20
6765
- Interpolation de chaîne :
prénom prend "Amandine"
affiche "Bonjour, {prénom} !"
- Regrouper plusieurs actions identiques en une ligne :
Au lieu d'écrire :
prénom est un texte
nom est un texte
demande prénom
demande nom
affiche "Je vous présente : "
affiche prénom
affiche nom
L'utilisation de l'esperluette compacte le livre ainsi :
prénom & nom est un texte
demande prénom & nom
affiche "Je vous présente : " & prénom & nom
- Regrouper plusieurs actions différentes en une ligne :
prénom & nom est un texte
demande prénom ; affiche prénom
demande nom ; affiche nom
- Syntaxe simplifiée pour écrire des casiers :
Forme normale :
animaux est un casier de textes valant "Koala", "Panda", "Kangourou"
pour chaque animaux affiche joker
Et la forme simplifiée :
pour chaque {"Koala", "Panda", "Kangourou"} affiche joker
Le joker est un acteur particulier car celui-ci est alimenté par Linotte dés que l'on utilise la forme simple des boucles : "pour chaque X ". Dans cet exemple, à chaque itération, il prend une valeur successive du casier "animaux".
- Inférence de types : L'interprète Linotte détermine automatique le rôle d'un acteur s'il n'est pas précisé.
prénom prend "Amandine" // nous avons supprimé "est un texte"
âge prend 1
affiche "Bonjour, {prénom} a {âge*12} mois !"
- Le verbe fermer :
Le verbe fermer ferme
peut être remplacé par le symbole §
si heure < 12
affiche "Nous sommes le matin"
§
sinon
affiche "Nous sommes l'après-midi"
§
Nous sommes tous un peu des têtes de linotte... Une erreur est vite arrivée dans l'élaboration d'un algorithme. Pour s'en protéger, et surtout, pour mieux comprendre l'origine du problème, on entoure son algorithme du bloc Essayer. Celui-ci permet au développeur de procéder à son l'analyse et à sa correction :
/* Algorithme farfelu */
valeur prend 10
essaie
tant que valeur > 0
valeur temporaire prend valeur - 1
si (valeur / valeur temporaire) > 0
affiche "Je peux continuer"
valeur prend valeur - 1
ferme
sinon valeur prend valeur - 2
ferme
ferme
sinon affiche "Pfff, une erreur dans ton algorithme lorsque valeur=" + valeur
Et si l'erreur est vraiment insaisissable, utilisons les grands moyens : le débogage.
/* Algorithme farfelu */
débogue
valeur prend 10
tant que valeur > 0
valeur temporaire prend valeur - 1
si (valeur / valeur temporaire) > 0
affiche "Je peux continuer"
valeur prend valeur - 1
ferme
sinon valeur prend valeur - 2
ferme
On avance dans l'algorithme en cliquant sur le bouton "Pas à pas" de l'Atelier.
Linotte est une tête bien faite ! Ce n'est pas une tâche mais plusieurs qu'elle est capable de traiter en même temps ! Pas besoin de longues explications car c'est très simple à mettre en place. Au lieu d'utiliser le verbe Parcourir, on utilise le verbe Appeler :
appelle alarme
appelle pièces
attends 10 secondes
affiche "Don Salluste : Gouzi, gouzi, gouzi !"
observe pièces
affiche "Don Salluste : Il en manque une !!"
alarme :
attends 8 secondes
affiche "Blaze : C'est l'hoooor, il est l'hoooor, Monsignoooor !"
attends 8 secondes
affiche "Blaze : Il est l'hoooor de se réveiller, il est huit hoooor !"
reviens
pièces :
pour chaque 10
attends 1 seconde
affiche "[clic clic !]"
attends 1 seconde
affiche "[clac ding !]"
ferme
reviens
Le verbe Observer attend que la tâche "pièces" soit terminée. Ce programme va produire ce texte :
[clic clic !]
[clac ding !]
[clic clic !]
[clac ding !]
[clic clic !]
[clac ding !]
[clic clic !]
Blaze : C'est l'hoooor, il est l'hoooor, Monsignoooor !
[clac ding !]
[clic clic !]
Don Salluste : Gouzi, gouzi, gouzi !
[clac ding !]
[clic clic !]
[clac ding !]
[clic clic !]
[clac ding !]
[clic clic !]
Blaze : Il est l'hoooor de se réveiller, il est huit hoooor !
[clac ding !]
[clic clic !]
[clac ding !]
[clic clic !]
[clac ding !]
Don Salluste : Il en manque une !!
Verbe parcourir
todo
todo
code :
chaine prend "bonjour la TERRE et les terriens !"
affiche chaine.inverser()
affiche chaine.minuscule()
affiche chaine.majuscule()
affiche chaine.minuscule().remplacer("terr", "lun").majuscule()
affiche chaine.taille()
affiche chaine.position(0,"terr")
affiche chaine.position(0,"lun")
affiche chaine.position(13,"terr")
affiche chaine.extraire(0,7)
affiche chaine.capitaliser()
affiche chaine.mélanger()
! sneirret sel te ERRET al ruojnob
bonjour la terre et les terriens !
BONJOUR LA TERRE ET LES TERRIENS !
BONJOUR LA LUNE ET LES LUNIENS !
34
11
-1
24
bonjour
Bonjour La Terre Et Les Terriens !
tnralsR Eueo rEnR!ejso beltei rT
L'exemple suivant introduit un nouveau type de variable : les espèces. Celles-ci peuvent contenir une ou plusieurs caractéristiques (ou attributs) :
espèces
patte est un nombre
famille & repas & nom est un texte
espèce animal contient patte, famille, repas, nom
principal :
chat est un animal, patte prend 4, nom prend "chat", famille prend "félin", repas prend "souris"
chien est un animal, patte prend 4, nom prend "chien", famille prend "canidé", repas prend "os"
affiche détail(chat)
affiche détail(chien)
détail : bébête
retourne "Le " + nom de bébête + " de la famille des " + famille de bébête + "s" + " mange des " + repas de bébête
L'exécution de cet exemple affiche sur le tableau de l'Atelier les lignes suivantes :
Le chat de la famille des félins mange des souris
Le chien de la famille des canidés mange des os
Le langage Linotte propose des espèces qui ont des capacités graphiques : elles peuvent s'afficher sur la toile. Voici le graffiti dont le rôle est d'afficher du texte ; Linotte propose également le cercle, le rectangle, l'image, le praxinoscope. La liste complète est disponible dans le tutoriel du langage.
Chaque espèce contient ces attributs spécifiques tels que : la taille, la couleur, la transparence, etc. Ces attributs sont définis par le langage et sont modifiables par le programmeur.
Regardons cet exemple simple affichant un nuage de points :
champs est une toile, couleur prend "jaune mimosa"
pour chaque couleurs, semer(joker)
semer : nom
fleur est un point
couleur@fleur prend nom
taille@fleur prend 10
déplace fleur vers hasard(600) et hasard(600)
retourne fleur
Exécutez ce programme dans l'atelier et admirez le résultat !
Remarque sucrée : avez-vous remarqué dans le programme ci-dessus que l'on peut écrire couleur de fleur
ainsi couleur@fleur
?
Toutes les couleurs connues du langage s'affichent aléatoirement. Ce tableau est beau mais presque inutile ! Ce que l'on souhaite : c'est afficher le nom de la couleur dés que l'on passe la souris sur un des points colorés.
Pour cela, nous allons créer l'espèce fleur qui héritera du point et qui contiendra un nouvel attribut : nom. Il portera le nom de la couleur.
espèces
nom est un texte
espèce fleur hérite de point et contient nom
principal :
champs est une toile, couleur prend "jaune mimosa"
fleurs est un casier de fleur
message_fleur est un graffiti, x prend 114, y prend 539, couleur prend "noir", texte prend "Déplace la souris sur les fleurs !", position prend 1, taille prend 10
pointeur est un point, couleur prend "blanc"
//projette champs & message_fleur & pointeur
pour chaque couleurs ajoute semer(joker) dans fleurs
tant que vrai
déplace pointeur vers sourisx et sourisy
pour chaque fleurs
si pointeur.collision(joker)
texte@message_fleur prend nom@joker
ferme
ferme
temporise // Bloc le programme et attend que la souris de l'utilisateur bouge
ferme
semer : nom
fleur est une fleur
couleur@fleur & nom@fleur prend nom
taille@fleur prend 20
déplace fleur vers hasard(600) et hasard(600)
retourne fleur
Vous êtes enfin prêt pour admirer, puis réviser vos couleurs !
L'interaction avec les éléments graphiques est facilitée par l'association d'un traitement à une action effectuée par l'utilisateur.
Dans l'exemple suivant, une action sera exécutée à la fin d'un glisser-déposer sur un des deux objets centre ou boule :
centre est un cercle, x prend 311, y prend 285, couleur prend "rouge", plein prend "oui", rayon prend 50
boule est un rectangle, largeur prend 40, hauteur prend 20, couleur prend "noir", plein prend "oui"
salle est une toile, couleur prend "blanc"
fais réagir boule & centre à "glisser-déposer" pour changement
tant que vrai temporise // boucle infinie
changement : // ce n'est pas une fonction mais une méthode (aucune valeur doit être retounée)
si boule.collision(centre)
couleur@centre prend "jaune"
ferme
sinon couleur@centre prend "rouge"
reviens
D'autres types d'évènements peuvent être utilisés : souris entrante, souris sortante, clic souris, double clic souris et clic droit souris.
Tels des Legos, les espèces sont des objets modifiables : on peut les enrichir pour y ajouter des nouveaux attributs et même, des fonctions.
Dans l'exemple suivant, on associe la fonctionne présentation à l'espèce Marjordome.
espèces
espèce marjordome hérite de entité // entité est une espèce vide
principal :
messager est un marjordome
nom prend "Jules"
attache nom à messager
attache présentation à messager
affiche messager.présentation()
présentation : // Implicitement, le paramètre moi est créé.
retourne "Je suis votre serviteur {nom@moi}."
Et sur le tableau, s'affiche :
Je suis votre serviteur Jules.
Linotte supporte nativement le clonage (duplication d'un objet à l'identique). Celui-ci est effectué en préfixant la variable du symbole dièse :
espèces
énergie prend 1000
espèce stormtrooper hérite de entité et contient énergie
principal :
prototype est un stormtrooper, énergie prend 1000
armée est un casier de stormtrooper
soldat est un nombre
attache attaquer à prototype
// On clone le prototype 100 fois pour constituer notre armée :
de 0 à 99, ajoute #prototype dans armée
affiche "àààà l'attaaaqueeee !"
pour soldat de 0 à 99 affiche "Le stormtrooper va effectuer une attaque de " + (armée{soldat}.attaquer()) + " points !"
attaquer :
retourne hasard(1000) + énergie@moi
Sur le tableau, s'affiche 100 fois :
Le stormtrooper va effectuer une attaque de 1125 points !
Remarque : pour cloner un objet, au lieu d'utiliser le symbole #, vous pouvez utiliser la fonction clone() : ajoute clone(prototype) dans armée
Et pour le plaisir, voici un exemple de création d'IHM en quelques lignes :
form est un formulaire, titre prend "Première question", largeur prend 400, hauteur prend 260
bouton1 est un bouton, texte prend "Blanc", x prend 30, y prend 60
bouton2 est un bouton, texte prend "Noir", x prend 100, y prend 60
étiquette1 est un étiquette, texte prend "Quelle est la couleur du cheval blanc d'Henri 4 ?", x prend 30, y prend 30
étiquette2 est un étiquette, texte prend "", x prend 30, y prend 100
ajoute bouton1 & bouton2 dans form // On ajoute les éléments de l'IHM à notre fenêtre "form"
ajoute étiquette1 & étiquette2 dans form
fais réagir bouton2 à "clic souris" pour réponse fausse
fais réagir bouton1 à "souris entrante" pour bouger bouton
fais réagir bouton1 à "clic souris" pour bouger bouton
tant que vrai temporise
réponse fausse : bouton // Objet qui reçoit l'action. Ici, le bouton "Noir"
texte de étiquette2 prend "Tu es bien trop mauvais pour continuer le test !"
reviens
bouger bouton : bouton // Objet qui reçoit l'action. Ici, le bouton "Blanc"
x de bouton prend hasard(320) + 30
y de bouton prend hasard(220) + 30
reviens
Testez cet exemple dans l'Atelier et répondez bien ! 😜