Exemple 4 : Une image au format choisi àl’endroit choisi

Dans ce tutoriel nous allons créer une fonction qui découpe une portion d’image àune taille choisie. Ceci permettra de combiner un appel de fonction avec un retour de fonction, une nouvelle notion.

Précédent | 9/15 | Suivant

Une fonction avec un "retour de fonction"

Un article concernant les fonctions détaillait les raisons pour lesquelles on les emploie, comment les écrire et les appeler.
Une fonction est un ensemble d’instructions rassemblées sous un même nom, que l’on peut appeler en lui envoyant des arguments, c’est àdire des informations spécifiques que la fonction peut utiliser. Mais une fonction peut aussi, une fois son travail terminé, renvoyer quelque chose : un chiffre, une chaine de caractère ou même une image.
La métaphore utilisée àplusieurs reprises est celle du majordome àqui on demande un café. La fonction contient la série d’instructions permettant de faire le café, et le café est évidemment rapporté àla fin de la procédure. Le café est dans ce cas le retour de fonction.
C’est làque le "void" qui précède les fonctions prend son sens.
Si nous créons une fonction pour ranger une chambre :

void ranger_chambre(){
     move("livres","étagère");
     move("linge sale","bac à linge");
     aspirateur();
 }

La fonction, une fois appelée, permet de ranger une chambre, mais ne renvoie rien. Une fois le travail fait, ben il est fait. L’appel se fait comme ceci :

ranger_chambre();

Mais dans le cas du majordome, on veut àla fin de la séquence recevoir le café. Le code sera plutôt :

café prepare_un_cafe(int nb_sucres){
    chauffer_eau();
    mettre_café_dans_filtre();
    verser_eau_bouillante();
    verser_cafe_dans_tasse();
    // ajouter le bon nombre de sucres
    ajouter_sucre(nb_sucres);
    return café;
}

Le nom de la fonction commence dans ce cas nom pas par void mais par café, qui annonce que la fonction renvoie, quand elle est exécutée, un élément de type café.
Et en effet, la dernière ligne de la fonction "return café" renvoie vers l’endroit où la fonction a été appelée le café.

La fonction s’appelle comme ceci :

café moncafé=prepare_un_cafe(0);

La variable moncafé, de type café, sera "remplie" d’un café sans sucre après l’appel de la fonction...

Du concret avec une fonction "get_sample()"

Voilàenfin cette fonction. Elle requiert 3 arguments :
 le nom de l’image (juste son nom, la fonction charge l’image)
 la largeur de l’image finale en pixels
 la hauteur de l’image finale en pixels

// créer une image qui exploite le maximum de la surface du cadre demandé
PImage get_sample(String source, int largeur, int hauteur) {
  PImage im=loadImage(source);
  // creer une image au format définitif
  PGraphics pg=createGraphics(largeur, hauteur);

  // Calculer le ratio largeur/hauteur du cadre et de l'image
  float ratio_cadre=(largeur*1.0)/(hauteur*1.0);
  float ratio_image=(im.width*1.0)/(im.height*1.0);

  // crée une image temporaire en remplissant le cadre demandé
  pg.beginDraw();
  pg.background(255);
  if (ratio_cadre < ratio_image) {
    println("cadre plus étroit que l'image");
    float nl=hauteur*ratio_image;
    float px=random(-nl+largeur, 0);
    pg.image(im, px, 0, nl, hauteur);
  } else {
    println("cadre plus large que l'image");
    float nh=width/ratio_image;
    float py=random(-nh+hauteur, 0);
    pg.image(im, 0, py, largeur, nh);
  }
  pg.endDraw();
  return pg; // renvoyer l'image produite
}

Cette fonction utilise la fonction PGraphics, qui permet de créer une image dans la mémoire de l’ordinateur. Un outil puissant pour créer des images àpartir de rien et dessiner dedans, mais qu’on utilise ici de manière minimale.
On crée une image vide au format demandé, et on y place l’image envoyée par l’utilisateur en exploitant le maximum de celle-ci. Elle a déjàfait l’objet d’un tutoriel ici sous une forme légèrement différente.
Il y a deux cas de figure : si on adapte l’image àla plus petite des deux dimensions de l’image, l’image va dépasser en largeur ou en hauteur :

Le script compare donc les deux tailles, celle de l’image et du recadrage demandé, pour savoir comment disposer les deux. Il est une des multiples façons de résoudre ce problème.

Une fois la nouvelle image crée avec PGraphics remplie avec l’image de l’utilisateur au bon format, elle est renvoyée par la fonction, qui doit récupérer cette image comme ceci :

PImage monimage=get_sample("nyan-cat-1280x720.jpg", 400,580);
image(monimage,10,10);

Associé ànotre script de base de couverture, ça peut donner ça :

Mais cette fonction peut servir de base àd’autres scripts, et ça c’est l’objet du tutoriel qui suit !