Obligement - L'Amiga au maximum

Dimanche 25 août 2019 - 17:49  

Translate

En De Nl Nl
Es Pt It Nl


Rubriques

 · Actualité (récente)
 · Actualité (archive)
 · Comparatifs
 · Dossiers
 · Entrevues
 · Matériel (tests)
 · Matériel (bidouilles)
 · Points de vue
 · En pratique
 · Programmation
 · Reportages
 · Quizz
 · Tests de jeux
 · Tests de logiciels
 · Tests de compilations
 · Trucs et astuces
 · Articles divers

 · Articles in english
 · Articles en d'autres langues


Twitter

Suivez-nous sur Twitter




Liste des jeux Amiga

0, A, B, C, D, E, F,
G, H, I, J, K, L, M,
N, O, P, Q, R, S, T,
U, V, W, X, Y, Z


Trucs et astuces

0, A, B, C, D, E, F,
G, H, I, J, K, L, M,
N, O, P, Q, R, S, T,
U, V, W, X, Y, Z


Glossaire

0, A, B, C, D, E, F,
G, H, I, J, K, L, M,
N, O, P, Q, R, S, T,
U, V, W, X, Y, Z


Galeries

 · Menu des galeries

 · BD d'Amiga Spécial
 · Caricatures Dudai
 · Caricatures Jet d'ail
 · Diagrammes de Jay Miner
 · Images insolites
 · Fin de jeux (de A à E)
 · Fin de Jeux (de F à O)
 · Fin de jeux (de P à Z)
 · Galerie de Mike Dafunk
 · Logos d'Obligement
 · Systèmes d'exploitation
 · Trombinoscope Alchimie 7
 · Vidéos


Téléchargement

 · Documents
 · Jeux
 · Logiciels
 · Magazines
 · Divers


Liens

 · Sites de téléchargements
 · Associations
 · Pages Personnelles
 · Matériel
 · Réparateurs
 · Revendeurs
 · Presse et médias
 · Programmation
 · Logiciels
 · Jeux
 · Scène démo
 · Divers


Partenaires

Annuaire Amiga

Amedia Computer

Relec

Hit Parade


A Propos

A propos d'Obligement

A Propos


Contact

David Brunet

Courriel

 


Programmation : ARexx - Les bibliothèques Rexxarp et Rexxmathlib
(Article écrit par François Gueugnon et extrait d'Amiga News Tech - mars 1992)


Après avoir vu le traitement des erreurs et défauts d'un programme ARexx, nous pouvons nous lancer dans l'utilisation de deux bibliothèques, la rexxarp.library et la rexxmathlib.library.

Bien que ce ne soit pas la vocation d'ARexx, il a été muni par Willy Langeveld, de ces deux bibliothèques qui permettent d'une part de profiter des avantages d'Intuition (écrans, fenêtres, menus et gadgets de toutes sortes) et d'autre part, de calculer l'inverse de la tangente hyperbolique sans trop se casser la tête. La bibliothèque graphique - ou du moins visuelle - est moins riche qu'Intuition, mais elle permet de réaliser des écrans passablement conviviaux, c'est-à-dire ergonomiques, même si la variété, par exemple des gadgets, est assez limitée. Quant à la bibliothèque mathématique, elle est, elle, plutôt riche.

Trois bibliothèques spécifiques doivent être présentes dans le répertoire Libs: pour que l'on puisse espérer modeler la visualisation à son gré : rexxsupport.library, rexxmathlib.library et rexxarplib.library. Il est recommandé de tester leur présence dès le début du programme :

IF ~SHOW('1',"rexxarplib.library") THEN DO
   test=ADDLIB('rexxarp.library',0,-30,0)
   IF TEST ~=1 THEN DO
       SAY 'rexxarplib est introuvable'
       CALL DELAY 100
       EXIT
   END
END

0, -30 et 0 correspondent respectivement à la priorité, l'offset (ou décalage) et à la version ; on les laisse traditionnellement à cette valeur, surtout l'offset !

Cet exemple doit être étendu à chacune des bibliothèques précitées. Dans le cas présent, le test regarde si la bibliothèque a été effectivement ajoutée au traitement résident, sinon il annonce le défaut pendant "DELAY 100" avant de quitter le programme. Dès que tout est en ordre on peut se lancer.

Écrans publics

Ces écrans sont réputés publics parce qu'on peut les adresser et agir sur eux par leur nom, qui est connu. Ce pourra être l'écran que l'on va définir ou un autre dont on connaît le nom (l'adresse, en fait !). Cette définition d'écran n'est pas utile si l'on veut se servir de l'écran courant uniquement. On rappelle ici qu'un écran ne définit que le mode graphique : nombre de bitplanes (correspondant au nombre maximal de couleurs) et résolution en lignes et colonnes. Un écran doit suivre des règles précises, en particulier pour ce qui est de la superposition des écrans de résolution différentes. Dans le cas présent, la seule liberté qui nous est laissée est la hauteur à laquelle commence l'écran, à partir du haut.

Pour ouvrir un écran, on utilise la séquence suivante :

resultat=OpenScreen(haut, profond, mode, titre, nom)
  • haut : hauteur d'ouverture à partir du sommet de l'écran matériel.
  • profond : nombre de bitplanes. C'est la puissance de 2 donnant le nombre de couleurs, en accord avec le mode. Si profond = 3, le nombre de couleurs possibles est 2 puissance 3 = 8.
  • mode : outre le mode normal (mode=0), on peut choisir HIRES, LACE, HAM, SCREENBEHIND et TRUNCATE. HIRES donne 640 (points horizontaux et 16 couleurs maximum, LACE est l'entrelaçage donc en PAL, donne 512 lignes) et HAM donne accès au mode 4096 couleurs. Quant à TRUNCATE, il permet de limiter la hauteur de l'écran créé à sa partie visible si l'on a utilisé haut non égal à 0. Sinon, l'écran aurait une hauteur normale déplacée de haut à partir du sommet et consommant de la mémoire pour rien.
  • titre : nom donné à l'écran dans la ligne de titre, et qui est purement arbitraire ou décoratif.
  • nom : c'est le nom public, c'est-à-dire l'adresse, qui permettra de s'adresser à cet écran.
Tous les arguments doivent être pris en compte. Donc, s'il y en a qui sont laissés a la valeur par défaut, il faut marquer leur position par les virgules de la séquence d'appel. Certains peuvent coexister avec d'autres (LACE en particulier), ou peuvent être incompatibles (par exemple 6 bitplanes et HIRES). Si incompatibilité il y a, l'appel ne réussit pas. Lorsque l'appel a réussi, resultat doit être égal à 1, sinon il vaut 0.

Enfin, un écran doit être fermé après emploi :

resultat=CloseScreen(nam)

En cas de défaut, il se peut que le programme se termine sans passer par la fermeture des écrans publics qu'il aura ouverts. Or, il n'est plus possible de réouvrir cet écran après rectification du ou des défauts ; il faut d'abord le fermer. Une solution est de se rappeler le nom de l'écran et à partir de la console taper :

rx 'closescreen(nom)'

OpenScreen et CloseScreen s'appliquent indifféremment à tous les écrans publics ouverts par vous ou par une autre application. La seule connaissance nécessaire est celle du nom de l'écran considéré.

Paramètres d'un écran

Il peut être intéressant ou utile de connaître les caractéristiques d'un écran public que l'on veut utiliser et que l'on n'a pas défini soi-même. Quatre fonctions spéciales effectuent ce travail :
  • lignes = ScreenRows(nom) donne le nombre de lignes de l'écran nom.
  • colonnes = ScreenCols(nom) donne le nombre de colonnes.
  • lace = ScreenLace(nom) donne 1 si l'écran est en mode entrelacé, et 0 sinon.
  • couleur = ScreenColors(nom, numero) donne pour le numéro de couleur choisi, une chaîne RVB valant de 0 à 15 par couleur Rouge, Verte et Bleue.
Pour les trois premières fonctions, le nom est optionnel et s'il n'est pas donné c'est l'écran Workbench qui est pris par défaut. Le nom est nécessaire pour la dernière. Si aucune valeur n'est disponible, par exemple par mauvaise appellation de l'écran, ou parce qu'il n'existe pas, alors -1 est retourné.

Position relative d'un écran

Lorsqu'un écran est créé, on peut le placer à volonté devant tous les autres au moyen de ScreenToFront(nom), ou derrière avec ScreenToBack(nom). Ces deux fonctions retournent 1 en cas de succès et 0 dans l'autre cas.

Barre d'écran

La fonction ShowTitle(nom, ouinon) permet de faire apparaître le titre de l'écran ou de le cacher à volonté. Si ouinon vaut 1, la barre de titre montre le titre de l'écran nom, sinon elle le cache.

C'est sur cette instruction, dont l'importance n'échappera pas aux plus attentifs de nos lecteurs, que nous fermerons le chapitre écran !

Fenêtres

C'est la partie visible de la création d'un environnement. Pour pouvoir interagir avec la fenêtre, il faut créer des moyens d'accès nommés "Ports" selon l'usage en vigueur dans le système de l'Amiga. Il y a deux types d'accès à une fenêtre : l'écriture ou la lecture de quelque chose se passant dans cette fenêtre. Il va donc falloir créer deux canaux de communication, l'un allant vers la fenêtre, l'autre venant de la fenêtre. Il n'est pas nécessaire que ces deux canaux (Ports) existent simultanément : on ne crée que ceux dont on a besoin. Enfin, on ne peut créer de telles relations qu'avec un écran connu, ou le Workbench par défaut.

Création des ports

Il y a plusieurs façons de créer les ports.

Address AREXX "'CALL CreateHost(ECRIT,LIT,nom)'"

Ce qui, traduit en quelque chose de supposé plus intelligible, veut dire : ordre à AREXX (port permanent du système) de créer un port ECRIT permettant d'écrire et un port LIT, permettant de recevoir des informations de la fenêtre qui va être créée dans l'écran : nom. De la même façon, on pourrait écrire :

RunWsh 'CALL CreateHost(ECRIT,LIT,nom)'

Il est alors utile de patienter quelque peu, le temps de la création. Voici différentes façons de faire.

DO FOR 50 WHILE ~Show('Ports','ECRIT')
    CALL DELAY 10
END

Ceci teste régulièrement la présence du port en construction ; le "FOR 50" étant là pour limiter la durée si, par hasard, il n'y avait pas d'ouverture possible. Une autre possibilité est d'utiliser la fonction :

retour = WaitForPort ECRIT

Ou encore :

WaitForPort ~immediate ECRIT

Qui donne dans retour et au bout de 10 secondes maximum, 0 si le port existe ou 5 dans le cas contraire.

Il faut faire attention à respecter les majuscules et minuscules dans l'orthographe du nom du port. En règle générale, simplifier au plus le nom du port est une heureuse initiative ! Notons enfin qu'il faut ouvrir le port :

CALL OpenPort(ECRIT)

La fenêtre proprement dit

Une fenêtre est caractérisée par plusieurs éléments :
  • Le nom de son port d'écriture, ici ECRIT.
  • Ses dimensions et sa position, qui sont données sous la forme position à gauche du début de la fenêtre, position à partir du haut de l'écran, largeur et hauteur.
  • Son nom.
  • Les gadgets standards des fenêtres : tirage, fermeture, dimensions...
  • Les messages IDCMP qu'elle est peut émettre le cas échéant - en supposant qu'elle ait été construite en ce sens.
Pour simplifier l'écriture d'une instruction passablement longue, on utilise traditionnellement deux chaînes : IDCMP et FLAGS (ou le nom que l'on veut !).

FLAGS='WINDOCLOSE+WINDOWDRAG+WINDOWDEPTH+WINDOWSIZING'

On peut encore y ajouter BORDERLESS, NOCAREREFRESH, ACTIVATE ou BACKFILL, chacun de ces termes étant présent ou absent selon le besoin.

IDCMP représente les messages qui seront émis par la fenêtre. Ils sont nombreux et concernent les gadgets, les menus, la position de la souris, le lecteur de disquette (pour savoir si l'on a changé la disquette), etc. On aurait par exemple :

IDCMP='CLOSEWINDOW+GADGETDOWN+DISKINSERTED+MOUSEMOVE'

...et bien d'autres (NDLR : on ne va tout de même pas vous refaire un cours complet sur les fenêtres, non ?).

L'ouverture de la fenêtre s'effectue selon le cérémonial suivant :

FLAGS='...
IDCMP='...
CALL OpenWindow(ECRIT,haut,larg,hauteur,IDCMP,FLAGS,'titre')
  • haut est la distance à partir du haut de l'écran.
  • largeur est... la largeur de la fenêtre.
  • hauteur représente... sa hauteur.
  • titre est une chaîne de caractères, spécifiant le titre voulu.
Comme d'habitude en ARexx, les termes entre guillemets ou apostrophes sont pris littéralement. Les autres sont des variables et hauteur, par exemple, peut être le résultat d'une opération tout à fait quelconque.

De la même façon que pour les écrans, une fenêtre peut être placée devant ou derrière toutes les autres, dans son écran.

CALL WindowToFront(nomduport)
CALL WindowToBack(nomduport)

...où "nomduport" est le nom du port d'écriture dans la fenêtre.

On peut également la rendre active par :

CALL ActivateWindow(nomduport)

Enfin, il faut pouvoir la fermer : Close Window(nomduport), Exit(nomduport), Quit(nomduport) et Stop(nomduport) sont synonymes.

Ces commandes, dont la multiplicité n'a pas de raison ouvertement avouée, ferment la fenêtre considérée, désallouent les ressources et provoquent la sortie, à l'exception de CloseWindow qui peut supporter une option CloseWindow(nomcluport, 'CONTINUE') permettant à l'hôte de rester actif tout en fermant la fenêtre.

Comme dans le cas de l'écran, en cas de sortie intempestive du programme, sur défaut par exemple, la ou les fenêtres en cours ne sont pas automatiquement fermées. On peut les fermer à partir de la console par "rx 'Closewindow(nomport)". On devra fermer d'abord toutes les fenêtres d'un écran avant de lancer la fermeture de l'écran lui-même. On voit l'intérêt de se rappeler le nom des fenêtres ou celui des écrans pendant la mise au point et de ne leur donner que des noms simples. Sinon c'est le redémarrage assuré.

Ce que raconte une fenêtre

Nous verrons par la suite comment extraire un message issu d'une fenêtre. Pour le moment, on admet avoir reçu un message. Que contient-il ? Si rien n'a été précisé (autre que les IDCMP), le message contient par exemple : CLOSEWINDOW si CLOSEWINDOW a été sollicité, DISKREMOVED si la disquette a été retirée et l'IDCMP correspondant initialisé... A part la chaîne contenue dans le gadget et qui est retournée par les IDCMP GADGETUP et GADGETDOWN, on ne reçoit que le nom ou la classe de l'IDCMP. En particulier avec MOUSEMOVE, on ne sait qu'une seule chose : la souris a été déplacée. Cela peut suffire mais c'est plutôt la quantité dont elle a été déplacée qui est intéressante.

Pour les menus c'est la même chose. Il faut donc préciser ce que l'on veut recevoir. C'est l'objet de la commande ModifyHost. Le message envoyé peut être organisé en arguments consécutifs, contenant chacun ce que l'on souhaite. Par défaut, on obtenait sans avoir rien précisé l'Arg(0), qui contenait les noms des IDCMP. Nous allons pouvoir préciser ce que l'on veut et dans quel argument (de 0 à 15), on veut le trouver. On invoque le modificateur de la façon suivante :

CALL ModifyHost(nomport,IDCMP,'xxxxxxxxxxx')

IDCMP est le message que l'on veut traiter. Imaginons pour l'exemple que ce soit MOUSEMOVE. La chaîne de x s'écrit :

%3 %x %x

...ce qui se traduit : dans l'argument 3, mettre la position x puis la position y de la souris. Donc, "CALL ModifyHost(nomport, MOUSEMOVE, %3%x, %y)" permettra ultérieurement (après extraction de l'argument 3) de trouver la position de la souris dans une chaîne du genre : 145 23. La précision de l'argument ne fait qu'effectuer un pré-tri pour le cas où beaucoup de messages sont possibles.

On trouve de nombreuses possibilités. Par exemple, "%m" donne le numéro du menu sollicité ; "%s" permet d'obtenir le numéro de sous-menu ; "%h" permet d'obtenir la hauteur de la fenêtre alors que "%t" donne le nombre de secondes écoulées depuis le 1 janvier 1980, à l'instant où l'évènement est survenu.

Il y a 16 types d'IDCMP concernant les fenêtres, la souris et ses boutons, les gadgets, les menus et sous-menus, les touches du clavier, les préférences et les disquettes.

Il y a 18 modifications possibles, et 16 arguments. La souplesse s'obtient en augmentant la complexité. Alors que la réception de messages met en jeu un mécanisme compliqué, mais tout à fait conforme a celui que l'on met en oeuvre avec Intuition, l'écriture dans la fenêtre est beaucoup plus simple et très facilement manipulable. C'est peut-être une consolation.

Avant de passer à des exemples plus concrets, notons encore les commandes "SetNotify(nomport,IDCMP,nouveauport)" qui permet de réaffecter le message émis à un nouveau port et "ReadHost(nomport,portreçois,texte)" qui permet de déclencher l'envoi de texte au port reçois après les modifications éventuellement effectuées par "ModifyHost".


[Retour en haut] / [Retour aux articles] [Article précédent] / [Article suivant]