Tachibana
Langue : français

Groupe 11 — Souris Officiel

11,1 Move display cursor · 11,2 Set mouse display cursor on/off · 11,3 Get mouse state · 11,4 Test mouse present · 11,5 Select mouse Cursor

La souris se branche en USB. Le firmware garde sa position en pixels d'écran, l'état de ses boutons (bit 0 gauche, bit 1 droit, bit 2 milieu) et un compteur de molette. Son curseur est dessiné par le RP2040 par-dessus l'écran, caché au démarrage : c'est au programme de le montrer (11,2).

Tant qu'aucune souris n'est branchée, 11,3 rend 0 partout, même après un 11,1 : un programme doit d'abord tester sa présence (11,4).

Au banc, l'émulateur simule une souris branchée en (100, 80), puis, pour 11,3, un clic gauche ; sur la carte, il faut en brancher une et cliquer soi-même.

11,1 Move display cursor Officiel

Place le curseur de la souris en un point de l'écran.

Entrées
OctetsTypeRôle
P0-P1uint16X en pixels
P2-P3uint16Y en pixels

Sorties : aucune.

La position est celle que rend 11,3 ; les mouvements suivants de la souris partent de là. Sans souris branchée, 11,3 rend quand même 0, 0 (vérifié au banc). En NeoBASIC, mouse to x, y fait cet appel.

Mots-clés NeoBASIC qui font cet appel : mouse

Texte de la documentation du firmware (anglais)

Positions the display cursor at Parameters:0,1,Parameters:2,3

C (llvm-mos)
/* Placer le curseur de la souris, puis relire sa position (groupe 11, fonction 1). */
#include <stdio.h>
#include <neo6502.h>
#include <neo/api.h>

/* Appel brut de la boîte aux lettres : fonction puis groupe (écrit en dernier, il lance l'appel). */
static void api(uint8_t groupe, uint8_t fonction) {
    ControlPort.function = fonction;
    ControlPort.command = groupe;
    while (ControlPort.command)        /* attendre la fin */
        ;
}
static void libre(void) {              /* attendre que la boîte aux lettres soit libre */
    while (ControlPort.command)
        ;
}

int main(void) {
    uint16_t x, y;
    libre();
    ControlPort.params[0] = 200;                /* P0-P1 : X */
    ControlPort.params[1] = 0;
    ControlPort.params[2] = 150;                /* P2-P3 : Y */
    ControlPort.params[3] = 0;
    api(11, 1);                                 /* Move display cursor */
    libre();
    api(11, 3);                                 /* 11,3 : relire l'état de la souris */
    x = ControlPort.params[0] | ControlPort.params[1] << 8;
    y = ControlPort.params[2] | ControlPort.params[3] << 8;
    printf("Position : %u, %u\n", x, y);
    return 0;
}
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Position : 200, 150
Mad Pascal
// Placer le curseur de la souris, puis relire sa position (groupe 11, fonction 1).
program souris1;
uses crt, neo6502;
var x, y: word;
begin
  NeoSetCursorXY(200, 150);                     // Move display cursor
  NeoReadMouse;                                 // 11,3 : relire l'état de la souris
  NeoWaitMessage;
  x := neoMouseX;                               // copiés avant writeln, qui réutilise la boîte aux lettres
  y := neoMouseY;
  writeln('Position : ', x, ', ', y);
end.
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Position : 200, 150
NeoBASIC
10 ' Placer le curseur de la souris, puis relire sa position (groupe 11, fonction 1)
20 mouse to 200, 150 : ' Move display cursor
30 b = mouse(x, y) : ' 11,3 : relire l'etat de la souris
40 print "Position : ";x;", ";y
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Position : 200, 150
Assembleur 65C02 (64tass)
; Placer le curseur de la souris, puis relire sa position (groupe 11, fonction 1).
        .cpu "65c02"
        * = $0800
ControlPort    = $FF00             ; +0 groupe, +1 fonction, +2 erreur, +4.. paramètres
WaitMessage    = $FFF4             ; attend que la boîte aux lettres soit libre
WriteCharacter = $FFF1             ; affiche le caractère de A

start: lda #<place
        ldx #>place
        jsr envoi
        jsr lire                   ; 11,3 : relire l'état de la souris
        lda #<t0
        ldx #>t0
        jsr ecrire
        lda etat
        ldx etat+1
        jsr decimal16
        lda #<t1
        ldx #>t1
        jsr ecrire
        lda etat+2
        ldx etat+3
        jsr decimal16
        lda #13
        jsr WriteCharacter
        rts

; 11,3 : état de la souris copié dans etat (x, y sur 16 bits, boutons, molette), à l'abri avant d'afficher.
lire:   jsr WaitMessage
        lda #11
        ldx #3                     ; 11,3 : Get mouse state
        jsr appel
        ldx #5
_c:     lda ControlPort+4,x
        sta etat,x
        dex
        bpl _c
        rts
etat:   .fill 6

; Affiche en décimal le nombre de 16 bits A (poids faible) X (poids fort).
decimal16:
        sta n16
        stx n16+1
        ldy #0                     ; nombre de chiffres empilés
_div10: ldx #16                    ; n16 / 10 : quotient dans n16, reste dans A
        lda #0
_bit:   asl n16
        rol n16+1
        rol a
        cmp #10
        bcc _pas
        sbc #10
        inc n16
_pas:   dex
        bne _bit
        pha
        iny
        lda n16
        ora n16+1
        bne _div10
_sort:  pla
        ora #'0'
        jsr WriteCharacter
        dey
        bne _sort
        rts
n16:    .word 0

place:  .byte 11, 1, 4             ; 11,1 : Move display cursor
        .word 200, 150             ; X, Y
t0:     .text "Position : ", 0
t1:     .text ", ", 0

; Appel décrit par un bloc dont l'adresse est dans A (poids faible) et X (poids fort) :
; groupe, fonction, nombre de paramètres, puis les paramètres (P0, P1...).
envoi:  sta blk
        stx blk+1
        jsr WaitMessage
        ldy #2
        lda (blk),y                ; nombre de paramètres
        clc
        adc #3
        sta fin
        ldy #3
_copie: cpy fin
        beq _lance
        lda (blk),y
        sta ControlPort+1,y        ; octet 3 du bloc -> P0 ($FF04)...
        iny
        bra _copie
_lance: ldy #1
        lda (blk),y
        tax
        lda (blk)
        jmp appel

; Affiche la chaîne terminée par 0 dont l'adresse est dans A (poids faible) et X (poids fort).
ecrire: sta ptr
        stx ptr+1
        ldy #0
_e:     lda (ptr),y
        beq _f
        jsr WriteCharacter
        iny
        bne _e
_f:     rts

; Affiche A (0-255) en décimal, sans zéros de tête.
decimal:
        phx
        phy
        ldx #0
        ldy #100
        jsr _chiffre
        ldy #10
        jsr _chiffre
        ora #'0'
        jsr WriteCharacter
        ply
        plx
        rts
_chiffre:
        sty diviseur
        ldy #0
_div:   cmp diviseur
        bcc _fini
        sbc diviseur
        iny
        bne _div
_fini:  pha
        tya
        bne _ecrit
        cpx #0
        beq _saute
_ecrit: ora #'0'
        jsr WriteCharacter
        ldx #1
_saute: pla
        rts

; Appel : A = groupe, X = fonction (les paramètres sont déjà en place).
appel:  stx ControlPort+1
        sta ControlPort            ; écrit en dernier : lance l'appel
        jmp WaitMessage

ptr      = $80
blk      = $82
diviseur: .byte 0
fin:     .byte 0
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Position : 200, 150

11,2 Set mouse display cursor on/off Modifié par Trinity

Montre ou cache le curseur de la souris.

Entrées
OctetsTypeRôle
P0uint80 cache, autre valeur montre

Sorties : aucune.

Le curseur est caché au démarrage (Trinity : c'est au programme de décider). L'effet ne se voit qu'à l'écran : l'API ne relit pas le curseur, l'exemple vérifie seulement que les deux appels passent. En NeoBASIC, mouse show et mouse hide font cet appel.

Mots-clés NeoBASIC qui font cet appel : mouse

Texte de la documentation du firmware (anglais)

Shows or hides the mouse cursor depending on the Parameter:0 (hidden at reset : the program decides, bmarty 2026-09-21).

C (llvm-mos)
/* Montrer puis cacher le curseur de la souris (groupe 11, fonction 2). */
#include <stdio.h>
#include <neo6502.h>
#include <neo/api.h>

/* Appel brut de la boîte aux lettres : fonction puis groupe (écrit en dernier, il lance l'appel). */
static void api(uint8_t groupe, uint8_t fonction) {
    ControlPort.function = fonction;
    ControlPort.command = groupe;
    while (ControlPort.command)        /* attendre la fin */
        ;
}
static void libre(void) {              /* attendre que la boîte aux lettres soit libre */
    while (ControlPort.command)
        ;
}

static uint8_t montrer(uint8_t oui) {           /* Set mouse display cursor on/off */
    libre();
    ControlPort.params[0] = oui;                /* P0 : 0 cache, autre valeur montre */
    api(11, 2);
    return ControlPort.error;
}

int main(void) {
    uint8_t a = montrer(1);
    uint8_t b = montrer(0);                     /* caché au départ : on le rend tel qu'on l'a trouvé */
    printf("Montre : erreur %u, cache : erreur %u\n", a, b);
    return 0;
}
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Montre : erreur 0, cache : erreur 0
Mad Pascal
// Montrer puis cacher le curseur de la souris (groupe 11, fonction 2).
program souris2;
uses crt, neo6502;
var a, b: byte;

function montrer(oui: byte): byte;              // Set mouse display cursor on/off
begin
  NeoShowCursor(oui);                           // 0 cache, autre valeur montre
  NeoWaitMessage;
  result := NeoMessage.error;
end;

begin
  a := montrer(1);
  b := montrer(0);                              // caché au départ : on le rend tel qu'on l'a trouvé
  writeln('Montre : erreur ', a, ', cache : erreur ', b);
end.
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Montre : erreur 0, cache : erreur 0
NeoBASIC
10 ' Montrer puis cacher le curseur de la souris (groupe 11, fonction 2)
20 mouse show : a = peek($ff02) : ' Set mouse display cursor on/off, puis l'indicateur d'erreur
30 mouse hide : b = peek($ff02) : ' cache au depart : on le rend tel qu'on l'a trouve
40 print "Montre : erreur ";a;", cache : erreur ";b
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Montre : erreur 0, cache : erreur 0
Assembleur 65C02 (64tass)
; Montrer puis cacher le curseur de la souris (groupe 11, fonction 2).
        .cpu "65c02"
        * = $0800
ControlPort    = $FF00             ; +0 groupe, +1 fonction, +2 erreur, +4.. paramètres
WaitMessage    = $FFF4             ; attend que la boîte aux lettres soit libre
WriteCharacter = $FFF1             ; affiche le caractère de A

start: lda #<montre
        ldx #>montre
        jsr envoi
        lda ControlPort+2
        sta a
        lda #<cache
        ldx #>cache
        jsr envoi
        lda ControlPort+2
        sta b
        lda #<t0
        ldx #>t0
        jsr ecrire
        lda a
        jsr decimal
        lda #<t1
        ldx #>t1
        jsr ecrire
        lda b
        jsr decimal
        lda #13
        jsr WriteCharacter
        rts

montre: .byte 11, 2, 1, 1          ; 11,2 : P0 non nul, le curseur est montré
cache:  .byte 11, 2, 1, 0          ; P0 = 0 : caché (état de départ, on le rend tel qu'on l'a trouvé)
t0:     .text "Montre : erreur ", 0
t1:     .text ", cache : erreur ", 0
a:      .byte 0
b:      .byte 0

; Appel décrit par un bloc dont l'adresse est dans A (poids faible) et X (poids fort) :
; groupe, fonction, nombre de paramètres, puis les paramètres (P0, P1...).
envoi:  sta blk
        stx blk+1
        jsr WaitMessage
        ldy #2
        lda (blk),y                ; nombre de paramètres
        clc
        adc #3
        sta fin
        ldy #3
_copie: cpy fin
        beq _lance
        lda (blk),y
        sta ControlPort+1,y        ; octet 3 du bloc -> P0 ($FF04)...
        iny
        bra _copie
_lance: ldy #1
        lda (blk),y
        tax
        lda (blk)
        jmp appel

; Affiche la chaîne terminée par 0 dont l'adresse est dans A (poids faible) et X (poids fort).
ecrire: sta ptr
        stx ptr+1
        ldy #0
_e:     lda (ptr),y
        beq _f
        jsr WriteCharacter
        iny
        bne _e
_f:     rts

; Affiche A (0-255) en décimal, sans zéros de tête.
decimal:
        phx
        phy
        ldx #0
        ldy #100
        jsr _chiffre
        ldy #10
        jsr _chiffre
        ora #'0'
        jsr WriteCharacter
        ply
        plx
        rts
_chiffre:
        sty diviseur
        ldy #0
_div:   cmp diviseur
        bcc _fini
        sbc diviseur
        iny
        bne _div
_fini:  pha
        tya
        bne _ecrit
        cpx #0
        beq _saute
_ecrit: ora #'0'
        jsr WriteCharacter
        ldx #1
_saute: pla
        rts

; Appel : A = groupe, X = fonction (les paramètres sont déjà en place).
appel:  stx ControlPort+1
        sta ControlPort            ; écrit en dernier : lance l'appel
        jmp WaitMessage

ptr      = $80
blk      = $82
diviseur: .byte 0
fin:     .byte 0
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Montre : erreur 0, cache : erreur 0

11,3 Get mouse state Officiel

Donne la position de la souris, l'état de ses boutons et son compteur de molette.

Entrées : aucune.

Sorties
OctetsTypeRôle
P0-P1uint16X en pixels
P2-P3uint16Y en pixels
P4uint8boutons appuyés : bit 0 gauche, bit 1 droit, bit 2 milieu
P5uint8compteur de molette (augmente ou diminue à chaque cran, modulo 256)

Tout vaut 0 tant qu'aucune souris n'est branchée. La molette est un compteur, pas un état : on compare deux lectures. L'exemple attend un clic. En NeoBASIC, b = mouse(x, y [, m]) fait cet appel : il rend les boutons et range la position (et la molette) dans les variables.

Mots-clés NeoBASIC qui font cet appel : mouse()

Texte de la documentation du firmware (anglais)

Returns the mouse position (screen pixel, unsigned) in x Parameters:0,1 and y Parameters:2,3, buttonstate in Parameter:4 (button 1 is 0x1, button 2 0x2 etc., set when pressed), scrollwheelstate in Parameter:5 as uint8 which changes according to scrolls.

C (llvm-mos)
/* Attendre un clic et lire l'état de la souris (groupe 11, fonction 3). */
#include <stdio.h>
#include <neo6502.h>
#include <neo/api.h>

/* Appel brut de la boîte aux lettres : fonction puis groupe (écrit en dernier, il lance l'appel). */
static void api(uint8_t groupe, uint8_t fonction) {
    ControlPort.function = fonction;
    ControlPort.command = groupe;
    while (ControlPort.command)        /* attendre la fin */
        ;
}
static void libre(void) {              /* attendre que la boîte aux lettres soit libre */
    while (ControlPort.command)
        ;
}

int main(void) {
    uint16_t x, y;
    uint8_t b, m;
    printf("Cliquez\n");
    do {
        libre();
        api(11, 3);                             /* Get mouse state */
        b = ControlPort.params[4];              /* boutons : bit 0 gauche, bit 1 droit... */
    } while (b == 0);
    x = ControlPort.params[0] | ControlPort.params[1] << 8;
    y = ControlPort.params[2] | ControlPort.params[3] << 8;
    m = ControlPort.params[5];                  /* molette */
    printf("Clic en %u, %u : boutons %u, molette %u\n", x, y, b, m);
    return 0;
}
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Cliquez
Clic en 100, 80 : boutons 1, molette 0
Mad Pascal
// Attendre un clic et lire l'état de la souris (groupe 11, fonction 3).
program souris3;
uses crt, neo6502;
var x, y: word;
    b, m: byte;
begin
  writeln('Cliquez');
  repeat
    NeoReadMouse;                               // Get mouse state
    NeoWaitMessage;
    b := neoMouseButtons;                       // bit 0 gauche, bit 1 droit...
  until b <> 0;
  x := neoMouseX;
  y := neoMouseY;
  m := neoMouseWheel;                           // molette
  writeln('Clic en ', x, ', ', y, ' : boutons ', b, ', molette ', m);
end.
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Cliquez
Clic en 100, 80 : boutons 1, molette 0
NeoBASIC
10 ' Attendre un clic et lire l'etat de la souris (groupe 11, fonction 3)
20 print "Cliquez"
30 repeat : b = mouse(x, y, m) : until b <> 0 : ' Get mouse state : boutons, puis x, y et molette
40 print "Clic en ";x;", ";y;" : boutons ";b;", molette ";m
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Cliquez
Clic en 100, 80 : boutons 1, molette 0
Assembleur 65C02 (64tass)
; Attendre un clic et lire l'état de la souris (groupe 11, fonction 3).
        .cpu "65c02"
        * = $0800
ControlPort    = $FF00             ; +0 groupe, +1 fonction, +2 erreur, +4.. paramètres
WaitMessage    = $FFF4             ; attend que la boîte aux lettres soit libre
WriteCharacter = $FFF1             ; affiche le caractère de A

start:   lda #<t0
        ldx #>t0
        jsr ecrire
_att:   jsr lire                   ; Get mouse state
        lda etat+4                 ; boutons : bit 0 gauche, bit 1 droit...
        beq _att
        lda #<t1
        ldx #>t1
        jsr ecrire
        lda etat
        ldx etat+1
        jsr decimal16
        lda #<t2
        ldx #>t2
        jsr ecrire
        lda etat+2
        ldx etat+3
        jsr decimal16
        lda #<t3
        ldx #>t3
        jsr ecrire
        lda etat+4
        jsr decimal
        lda #<t4
        ldx #>t4
        jsr ecrire
        lda etat+5
        jsr decimal
        lda #13
        jsr WriteCharacter
        rts

; 11,3 : état de la souris copié dans etat (x, y sur 16 bits, boutons, molette), à l'abri avant d'afficher.
lire:   jsr WaitMessage
        lda #11
        ldx #3                     ; 11,3 : Get mouse state
        jsr appel
        ldx #5
_c:     lda ControlPort+4,x
        sta etat,x
        dex
        bpl _c
        rts
etat:   .fill 6

; Affiche en décimal le nombre de 16 bits A (poids faible) X (poids fort).
decimal16:
        sta n16
        stx n16+1
        ldy #0                     ; nombre de chiffres empilés
_div10: ldx #16                    ; n16 / 10 : quotient dans n16, reste dans A
        lda #0
_bit:   asl n16
        rol n16+1
        rol a
        cmp #10
        bcc _pas
        sbc #10
        inc n16
_pas:   dex
        bne _bit
        pha
        iny
        lda n16
        ora n16+1
        bne _div10
_sort:  pla
        ora #'0'
        jsr WriteCharacter
        dey
        bne _sort
        rts
n16:    .word 0

t0:     .text "Cliquez", 13, 0
t1:     .text "Clic en ", 0
t2:     .text ", ", 0
t3:     .text " : boutons ", 0
t4:     .text ", molette ", 0

; Appel décrit par un bloc dont l'adresse est dans A (poids faible) et X (poids fort) :
; groupe, fonction, nombre de paramètres, puis les paramètres (P0, P1...).
envoi:  sta blk
        stx blk+1
        jsr WaitMessage
        ldy #2
        lda (blk),y                ; nombre de paramètres
        clc
        adc #3
        sta fin
        ldy #3
_copie: cpy fin
        beq _lance
        lda (blk),y
        sta ControlPort+1,y        ; octet 3 du bloc -> P0 ($FF04)...
        iny
        bra _copie
_lance: ldy #1
        lda (blk),y
        tax
        lda (blk)
        jmp appel

; Affiche la chaîne terminée par 0 dont l'adresse est dans A (poids faible) et X (poids fort).
ecrire: sta ptr
        stx ptr+1
        ldy #0
_e:     lda (ptr),y
        beq _f
        jsr WriteCharacter
        iny
        bne _e
_f:     rts

; Affiche A (0-255) en décimal, sans zéros de tête.
decimal:
        phx
        phy
        ldx #0
        ldy #100
        jsr _chiffre
        ldy #10
        jsr _chiffre
        ora #'0'
        jsr WriteCharacter
        ply
        plx
        rts
_chiffre:
        sty diviseur
        ldy #0
_div:   cmp diviseur
        bcc _fini
        sbc diviseur
        iny
        bne _div
_fini:  pha
        tya
        bne _ecrit
        cpx #0
        beq _saute
_ecrit: ora #'0'
        jsr WriteCharacter
        ldx #1
_saute: pla
        rts

; Appel : A = groupe, X = fonction (les paramètres sont déjà en place).
appel:  stx ControlPort+1
        sta ControlPort            ; écrit en dernier : lance l'appel
        jmp WaitMessage

ptr      = $80
blk      = $82
diviseur: .byte 0
fin:     .byte 0
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Cliquez
Clic en 100, 80 : boutons 1, molette 0

11,4 Test mouse present Officiel

Dit si une souris est branchée.

Entrées : aucune.

Sorties
OctetsTypeRôle
P0uint81 si une souris est branchée, 0 sinon

À appeler avant 11,3, qui rend 0 sans souris. Sans souris simulée, l'exemple affiche « absente » (vérifié au banc). En NeoBASIC, havemouse() fait cet appel.

Mots-clés NeoBASIC qui font cet appel : havemouse()

Texte de la documentation du firmware (anglais)

Returns non zero if a mouse is plugged in in Parameter:0

C (llvm-mos)
/* Savoir si une souris est branchée (groupe 11, fonction 4). */
#include <stdio.h>
#include <neo6502.h>
#include <neo/api.h>

/* Appel brut de la boîte aux lettres : fonction puis groupe (écrit en dernier, il lance l'appel). */
static void api(uint8_t groupe, uint8_t fonction) {
    ControlPort.function = fonction;
    ControlPort.command = groupe;
    while (ControlPort.command)        /* attendre la fin */
        ;
}
static void libre(void) {              /* attendre que la boîte aux lettres soit libre */
    while (ControlPort.command)
        ;
}

int main(void) {
    libre();
    api(11, 4);                                 /* Test mouse present */
    printf("Souris : %s\n", ControlPort.params[0] ? "presente" : "absente");
    return 0;
}
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Souris : presente
Mad Pascal
// Savoir si une souris est branchée (groupe 11, fonction 4).
program souris4;
uses crt, neo6502;
begin
  if NeoIsMousePresent then                     // Test mouse present
    writeln('Souris : presente')
  else
    writeln('Souris : absente');
end.
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Souris : presente
NeoBASIC
10 ' Savoir si une souris est branchee (groupe 11, fonction 4)
20 s$ = "absente" : if havemouse() then s$ = "presente" : ' Test mouse present
30 print "Souris : ";s$
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Souris : presente
Assembleur 65C02 (64tass)
; Savoir si une souris est branchée (groupe 11, fonction 4).
        .cpu "65c02"
        * = $0800
ControlPort    = $FF00             ; +0 groupe, +1 fonction, +2 erreur, +4.. paramètres
WaitMessage    = $FFF4             ; attend que la boîte aux lettres soit libre
WriteCharacter = $FFF1             ; affiche le caractère de A

start: lda #<test
        ldx #>test
        jsr envoi
        lda ControlPort+4          ; non nul : souris branchée
        bne _oui
        lda #<ta
        ldx #>ta
        jsr ecrire
        rts
_oui:   lda #<tp
        ldx #>tp
        jsr ecrire
        rts

test:   .byte 11, 4, 0             ; 11,4 : Test mouse present
ta:     .text "Souris : absente", 13, 0
tp:     .text "Souris : presente", 13, 0

; Appel décrit par un bloc dont l'adresse est dans A (poids faible) et X (poids fort) :
; groupe, fonction, nombre de paramètres, puis les paramètres (P0, P1...).
envoi:  sta blk
        stx blk+1
        jsr WaitMessage
        ldy #2
        lda (blk),y                ; nombre de paramètres
        clc
        adc #3
        sta fin
        ldy #3
_copie: cpy fin
        beq _lance
        lda (blk),y
        sta ControlPort+1,y        ; octet 3 du bloc -> P0 ($FF04)...
        iny
        bra _copie
_lance: ldy #1
        lda (blk),y
        tax
        lda (blk)
        jmp appel

; Affiche la chaîne terminée par 0 dont l'adresse est dans A (poids faible) et X (poids fort).
ecrire: sta ptr
        stx ptr+1
        ldy #0
_e:     lda (ptr),y
        beq _f
        jsr WriteCharacter
        iny
        bne _e
_f:     rts

; Affiche A (0-255) en décimal, sans zéros de tête.
decimal:
        phx
        phy
        ldx #0
        ldy #100
        jsr _chiffre
        ldy #10
        jsr _chiffre
        ora #'0'
        jsr WriteCharacter
        ply
        plx
        rts
_chiffre:
        sty diviseur
        ldy #0
_div:   cmp diviseur
        bcc _fini
        sbc diviseur
        iny
        bne _div
_fini:  pha
        tya
        bne _ecrit
        cpx #0
        beq _saute
_ecrit: ora #'0'
        jsr WriteCharacter
        ldx #1
_saute: pla
        rts

; Appel : A = groupe, X = fonction (les paramètres sont déjà en place).
appel:  stx ControlPort+1
        sta ControlPort            ; écrit en dernier : lance l'appel
        jmp WaitMessage

ptr      = $80
blk      = $82
diviseur: .byte 0
fin:     .byte 0
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Souris : presente

11,5 Select mouse Cursor Officiel

Choisit l'image du curseur de la souris parmi 39 (0 à 38).

Entrées
OctetsTypeRôle
P0uint8numéro de l'image, 0 à 38
Sorties
OctetsTypeRôle
erreuruint81 si le numéro dépasse 38

Un numéro invalide ne laisse pas le curseur tel quel : il remet l'image 0, en plus de l'erreur. En NeoBASIC, mouse cursor n fait cet appel et lève une erreur de plage si n est invalide ; l'exemple NeoBASIC écrit la boîte aux lettres pour montrer l'erreur.

Mots-clés NeoBASIC qui font cet appel : mouse

Texte de la documentation du firmware (anglais)

Select a mouse cursor in Parameter:0 ; returns error status if the cursor is not available.

C (llvm-mos)
/* Choisir l'image du curseur de la souris (groupe 11, fonction 5). */
#include <stdio.h>
#include <neo6502.h>
#include <neo/api.h>

/* Appel brut de la boîte aux lettres : fonction puis groupe (écrit en dernier, il lance l'appel). */
static void api(uint8_t groupe, uint8_t fonction) {
    ControlPort.function = fonction;
    ControlPort.command = groupe;
    while (ControlPort.command)        /* attendre la fin */
        ;
}
static void libre(void) {              /* attendre que la boîte aux lettres soit libre */
    while (ControlPort.command)
        ;
}

static uint8_t curseur(uint8_t n) {             /* Select mouse Cursor : rend l'indicateur d'erreur */
    libre();
    ControlPort.params[0] = n;
    api(11, 5);
    return ControlPort.error;
}

int main(void) {
    uint8_t a = curseur(5);
    uint8_t b = curseur(39);                    /* 39 curseurs : 0 à 38 */
    printf("Curseur 5 : erreur %u, curseur 39 : erreur %u\n", a, b);
    return 0;
}
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Curseur 5 : erreur 0, curseur 39 : erreur 1
Mad Pascal
// Choisir l'image du curseur de la souris (groupe 11, fonction 5).
program souris5;
uses crt, neo6502;
var a, b: byte;

function curseur(n: byte): byte;                // Select mouse Cursor : rend l'indicateur d'erreur
begin
  NeoSelectCursor(n);
  NeoWaitMessage;
  result := NeoMessage.error;
end;

begin
  a := curseur(5);
  b := curseur(39);                             // 39 curseurs : 0 à 38
  writeln('Curseur 5 : erreur ', a, ', curseur 39 : erreur ', b);
end.
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Curseur 5 : erreur 0, curseur 39 : erreur 1
NeoBASIC
10 ' Choisir l'image du curseur de la souris (groupe 11, fonction 5)
20 c = 5 : gosub 1000 : a = e
30 c = 39 : gosub 1000 : b = e : ' 39 curseurs : 0 a 38
40 print "Curseur 5 : erreur ";a;", curseur 39 : erreur ";b
50 end
1000 ' Select mouse Cursor : curseur c, erreur dans e (mouse cursor c leve une erreur de plage)
1010 while peek($ff00) : wend : poke $ff04, c : poke $ff01, 5 : poke $ff00, 11
1020 while peek($ff00) : wend : e = peek($ff02)
1030 return
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Curseur 5 : erreur 0, curseur 39 : erreur 1
Assembleur 65C02 (64tass)
; Choisir l'image du curseur de la souris (groupe 11, fonction 5).
        .cpu "65c02"
        * = $0800
ControlPort    = $FF00             ; +0 groupe, +1 fonction, +2 erreur, +4.. paramètres
WaitMessage    = $FFF4             ; attend que la boîte aux lettres soit libre
WriteCharacter = $FFF1             ; affiche le caractère de A

start: lda #<c5
        ldx #>c5
        jsr envoi
        lda ControlPort+2
        sta a
        lda #<c39
        ldx #>c39
        jsr envoi
        lda ControlPort+2
        sta b
        lda #<t0
        ldx #>t0
        jsr ecrire
        lda a
        jsr decimal
        lda #<t1
        ldx #>t1
        jsr ecrire
        lda b
        jsr decimal
        lda #13
        jsr WriteCharacter
        rts

c5:     .byte 11, 5, 1, 5          ; 11,5 : Select mouse Cursor, curseur 5
c39:    .byte 11, 5, 1, 39         ; 39 curseurs : 0 à 38
t0:     .text "Curseur 5 : erreur ", 0
t1:     .text ", curseur 39 : erreur ", 0
a:      .byte 0
b:      .byte 0

; Appel décrit par un bloc dont l'adresse est dans A (poids faible) et X (poids fort) :
; groupe, fonction, nombre de paramètres, puis les paramètres (P0, P1...).
envoi:  sta blk
        stx blk+1
        jsr WaitMessage
        ldy #2
        lda (blk),y                ; nombre de paramètres
        clc
        adc #3
        sta fin
        ldy #3
_copie: cpy fin
        beq _lance
        lda (blk),y
        sta ControlPort+1,y        ; octet 3 du bloc -> P0 ($FF04)...
        iny
        bra _copie
_lance: ldy #1
        lda (blk),y
        tax
        lda (blk)
        jmp appel

; Affiche la chaîne terminée par 0 dont l'adresse est dans A (poids faible) et X (poids fort).
ecrire: sta ptr
        stx ptr+1
        ldy #0
_e:     lda (ptr),y
        beq _f
        jsr WriteCharacter
        iny
        bne _e
_f:     rts

; Affiche A (0-255) en décimal, sans zéros de tête.
decimal:
        phx
        phy
        ldx #0
        ldy #100
        jsr _chiffre
        ldy #10
        jsr _chiffre
        ora #'0'
        jsr WriteCharacter
        ply
        plx
        rts
_chiffre:
        sty diviseur
        ldy #0
_div:   cmp diviseur
        bcc _fini
        sbc diviseur
        iny
        bne _div
_fini:  pha
        tya
        bne _ecrit
        cpx #0
        beq _saute
_ecrit: ora #'0'
        jsr WriteCharacter
        ldx #1
_saute: pla
        rts

; Appel : A = groupe, X = fonction (les paramètres sont déjà en place).
appel:  stx ControlPort+1
        sta ControlPort            ; écrit en dernier : lance l'appel
        jmp WaitMessage

ptr      = $80
blk      = $82
diviseur: .byte 0
fin:     .byte 0
Sortie observée dans l'émulateur Phosphoneo, firmware Trinity 0.16.69 :
Curseur 5 : erreur 0, curseur 39 : erreur 1

← L'API du Neo6502