Felton.PA@XEROX.ARPA (12/03/85)
>How do I read the joystick ports on the 520ST?
Good Question! I have asked it twice on the net already. If anyone
knows please post the answer so that we will all know.
Thanks,
John
sansom@trwrba.UUCP (Richard E. Sansom) (12/05/85)
> >>How do I read the joystick ports on the 520ST? > > >Good Question! I have asked it twice on the net already. If anyone >knows please post the answer so that we will all know. > (You may be sorry you asked!) There is quite a bit you have to know to read thejoystick/mouse ports. If you don't want to read all of this, look for part 2 of this document - I'll include a sample source listing to show you how to do it. Both the joystick port and the mouse port are controlled by the "Intelligent Keyboard" (ikbd) which (quoting Atari's documentation) "communicates with the main processor over a high speed bi-directional serial interface...", and, "...can function in a variety of modes to facilitate different applications of the keyboard, joysticks, or mouse." Keyboard -------- The keyboard always returns key make/break (press/release) codes. The break (release) codes are obtained by ORing 0x80 with the make (press) codes. The key codes are defined as follows: Code Key Code Key Code Key -------- -------- -------- 00 undefined(?) 10 Q 20 D 01 ESC 11 W 21 F 02 1 12 E 22 G 03 2 13 R 23 H 04 3 14 T 24 J 05 4 15 Y 25 K 06 5 16 U 26 L 07 6 17 I 27 ; 08 7 18 O 28 ' 09 8 19 P 29 ` 0A 9 1A [ 2A LSHIFT 0B 0 1B ] 2B \ 0C - 1C RET 2C Z 0D == 1D CTRL 2D X 0E BS 1E A 2E C 0F TAB 1F S 2F V Code Key Code Key Code Key -------- -------- -------- 30 B 40 F6 50 DOWN ARROW 31 N 41 F7 51 {not used} 32 M 42 F8 52 INS 33 , 43 F9 53 DEL 34 . 44 F10 54 {not used} 35 / 45 {not used} 55 {not used} 36 RSHIFT 46 {not used} 56 {not used} 37 {not used} 47 HOME 57 {not used} 38 ALT 48 UP ARROW 58 {not used} 39 SPACE 49 {not used} 59 {not used} 3A CAPS LOCK 4A KEYPAD - 5A {not used} 3B F1 4B LEFT ARROW 5B {not used} 3C F2 4C {not used} 5C {not used} 3D F3 4D RIGHT ARROW 5D {not used} 3E F4 4E KEYPAD + 5E {not used} 3F F5 4F {not used} 5F {not used} Code Key Code Key -------- -------- 60 ISO KEY 70 KEYPAD 0 61 UNDO 71 KEYPAD . 62 HELP 72 KEYPAD ENTER 63 KEYPAD ( 64 KEYPAD ) 65 KEYPAD / 66 KEYPAD * 67 KEYPAD 7 68 KEYPAD 8 69 KEYPAD 9 6A KEYPAD 4 6B KEYPAD 5 6C KEYPAD 6 6D KEYPAD 1 6E KEYPAD 2 6F KEYPAD 3 Mouse ----- There are 3 different ways ikbd can report mouse motion: relative, absolute, and by converting mouse motion into cursor control key equivalents. The mouse buttons can either be treated as part of the mouse or as additional keyboard keys. Relative Position Reporting: When a mouse event (mouse button pressed or released, or motion in either axis) occurs, ikbd returns a three byte record containing: %111110xx ; mouse position record flag || |------- ; right button state -------- ; left button state %xxxxxxxx ; delta X (twos complement integer) %xxxxxxxx ; delta Y (twos complement integer) NOTE - ikbd may return more than threshold delta X or Y since no relative mouse motion events will be generated during certain operations. Also, if the accumulated motion exceeds +127..-128, then the motion is broken into multiple packets. Absolute Position Reporting: Commands exist for reseting the mouse position, setting X & Y scaling, and interrogating the current mouse position (see below). Mouse Cursor Key Mode: ikbd can translate mouse motion into the equivalent cursor keystrokes - the number of "clicks" per keystroke being independently programable in each axis. Mouse motion produces the cursor key make (press) code immediately followed by the break (release) code for the appropriate cursor key. The mouse buttons produce scan codes above those normally assigned for the largest envisioned keyboard (i.e. LEFT=0x74, RIGHT=0x75). Joystick -------- As in mouse reporting, ikbd can report changes in the joystick state in several different ways: joystick event reporting, joystick interrogation, joystick monitoring, fire button monitoring, and joystick key code equivalents. Joystick Event Reporting: ikbd will generate a record when the joystick undergoes a change of state (i.e. when pressing forward, pulling back, or pressing the trigger). The event record consists of two bytes: %1111111x ; joystick event marker | ------- ; joystick number (0 or 1) %x000yyyy | |||| | ---------- ; stick position -------------- ; trigger Joystick Interrogation: The current state of the joystick ports may be interrogated at any time by sending the "Interrogate Joystick" command (see below) to ikbd. The response is a three byte report: 0xFD ; joystick report header %x000yyyy ; joystick 0 %x000yyyy ; joystick 1 ; where x is the trigger ; and yyyy is the position Joystick Monitoring: It is possible to devote nearly all of the keyboard communications time to reporting the state of the joystick ports, at a user specified rate (see below). Fire Button Monitoring: A mode exists which permits monitoring a single input bit at the maximum rate permitted by the serial communications channel. ikbd monitors joystick 1 and packs the data, 8 bits per byte for transmission. Joystick Key Code Mode: ikbd may be commanded to translate the use of either joystick into the equivalent cursor control keys. Joystick events produce the make (press) code, immediately followed by the break (release) code for the appropriate cursor motion. The trigger produces key scan codes above those used used by the largest keyboard envisioned. Power-up Mode ------------- ikbd performs a number of self-test diagnostics on power-up. If no erros are detected, the code 0xF0 is returned. (Actually, depending on the version, you may get 0xF1, 0xF2, etc.) ikbd defaults to mouse position reporting with threshold unit of 1 in either axis, and the Y=0 origin at the top of the screen, and joystick event reporting mode for joystick 1, with both buttons being logically assigned to the mouse. After any joystick commands, ikbd assumes joysticks are connected to both joystick ports. Any mouse command (except "Mouse Disable") then again causes port 0 to be scanned as if it were a mouse, and both buttons are logically connected to it. ikbd Commands ------------- Commands may be sent to ikbdws using the Ikbdws() function (ikbd Write String): VOID Ikbdws(cnt,ptr) WORD cnt; /* number of bytes to send minus 1 */ LONG ptr; /* pointer to the string of bytes */ Reset - return ikbd to power-up state 0x80 0x81 Set Mouse Button Action - select mouse button mode 0x07 %00000mss ; mouse button action ||| ; (m is presumed to be 1 when in ||| ; Mouse Keycode mode) --------- ; 0wx mouse button press or release ; || causes mouse position report ; || (wx only relevant if in ; || absolute mouse pos. mode) ; |-- 1 -> mouse key press causes ; | absolute pos. report ; --- 1 -> mouse key release causes ; absolute pos. report ; 100 = mouse buttons act like keys Set Relative Mouse Position Reporting (default) 0x08 Set Absolute Mouse Positioning 0x09 Xmsb ; X maximum (scaled mouse clicks) Xlsb Ymsb ; Y maximum (scaled mouse clicks) Ylsb Select Mouse Keycode Mode 0x0A deltax ; distance in X clicks to return deltay ; distance in Y clicks to return Set Mouse Threshold 0x0B X ; x threshold in clicks Y ; y threshold in clicks Set Mouse Scale 0x0C X ; horz. mouse ticks per internal X Y ; vert. mouse ticks per internal Y Interrogate Mouse Position 0x0D returns: 0xF7 ; abs. mouse pos. header %0000xxxx ; buttons |||| |||------- ; right button down ||| ; since last interrogation ||-------- ; right button up since last... |--------- ; left button down since last... ---------- ; left button up dince last... Xmsb ; X coordinate Xlsb Ymsb ; Y coordinate Ylsb That's about all I have time for now. I'll finish up the list of commands, and give an example (in C source) of how to put all of this together in a couple of days. Richard E. Sansom {decvax,ucbvax,ihnp4}!trwrb!trwrba!sansom
tlz@druxu.UUCP (ZrustTL) (12/07/85)
How do I read the joystick ports on the 520ST via Basic? I didn't see STICK() or STRIG() or MOUSE() :-) anywhere in my manual. Where do I peek()? Thanks! Terry Zrust ATTISL Denver (303) 538-4547 -- druxu!tlz _ Terry L. Zrust (_) /~\ AT&T Information Systems /~\ / \/\ 11900 North Pecos Street / \ /\ / | \ \ Denver, Colorado 80234 /\ / \ \/ /|\ \ \ Mail Stop 30L49 / \ / \ / //|\\ \ \ (303) 538-4547 ___ \_/ ___ \ ///|\\\ _\ Cornet 374-4547 _________________ _______ | _________
Felton.PA@XEROX.ARPA (12/09/85)
Richard, Thanks for sharing your knowlege of the Atari ST joystick/mouse ports with us. Not konwing how to access the joysticks has been driving me crazy for a couple of months now. I am anxiously awaiting the next exciting installment (especially the example C source code). John
info-atari@ucbvax.UUCP (12/12/85)
No such info appeared on my net! PLEASE! HOW DO YOU ACCESS THE JOYSTICK PORT? Thanks in advance!
sansom@trwrba.UUCP (Richard E. Sansom) (12/16/85)
Here are the rest of the ikbd commands, and a C program which will read joystick 0 (sorry it took me so long to get back to this!). Load Mouse Position 0x0E 0x00 ; filler (?) XMSB ; X coordinate (scaled coordinate system) XLSB ; YMSB ; Y coordinate YLSB Set Y=0 at Bottom 0x0F Set Y=0 at Top 0x10 Resume - Resume sending data to host (after a pause) 0x11 Disable Mouse - Disable mouse event reporting (any mouse command resumes) 0x12 Pause - Stop sending data to the host 0x13 Set Joystick Event Reporting (default) 0x14 Set Joystick Interrogate Mode 0x15 Interrogate Joystick 0x16 Set Joystick Monitoring 0x17 ; rate ; time between samples in hundredths of a second Returns: (in packets of two as long as in mode) %000000xy || |--- ; JOYSTICK1 Fire button ---- ; JOYSTICK0 Fire button %nnnnmmmm |||||||| ||||------ ; JOYSTICK1 state ---------- ; JOYSTICK0 state Set Fire Button Monitoring 0x18 Returns: (as long as in mode) %bbbbbbbb ; state of JOYSTICK1 packed 8 bits ; per byte Set Joystick Keycode Mode 0x19 RX ; horizontal velocity breakpoint (tenths of seconds) RY ; vertical velocity breakpoint (tenths of seconds) TX ; horizontal cursor key generation delay (tenths) TY ; vertical cursor key generation delay (tenths) VX ; horizontal cursor key generation repeat (tenths) VY ; vertical cursor key generation repeat (tenths) Disable Joysticks 0x1A Time-of-Day Clock Set 0x1B YY ; year (two least significant digits) MM ; month DD ; day hh ; hour mm ; minute ss ; second NOTE: all time-of-day data should be sent as packed BCD. Interrogate Time-of-Day Clock 0x1C Returns: 0xFC ; time-of-day event header YY ; year MM ; month DD ; day hh ; hour mm ; minute ss ; second NOTE: time-of-day data returned as packed BCD. Memory Load - load ikbd controller memory 0x20 ADDRMSB ; address of controller memory (high) ADDRLSB ; address of controller memory (low) NUM ; number of bytes (0-128) {data} Memory Read - read ikbd controller memory 0x21 ADDRMSB ; address of controller memory (high) ADDRLSB ; address of controller memory (low) Returns: 0xF6 ; status header 0x20 ; memory access {data} ; 6 data bytes starting at ADDR Controller Execute - execute ikbd controller subroutine 0x22 ADDRMSB ; address of subroutine in controller ADDRLSB ; memory to be called Status Inquiries ---------------- All status commands are formed by ORing 0x80 with the relevant SET command. Valid Status Inquiry commands are: 0x87 mouse button action 0x88 mouse mode 0x89 0x8A 0x8B mouse threshold 0x8C mouse scale 0x8F mouse vertical coordinates 0x90 (returns 0x0F if Y=0 at bottom, 0x10 if Y=0 at top) 0x92 mouse enable/disable (0x00=enabled, 0x12=disabled) 0x94 joystick mode 0x95 0x99 0x9A joystick enable/disable (0x00=enabled, 0x1A=disabled) NOTE: Status Inquiry commands are NOT VALID if the ikbd is in Joystick Monitoring Mode or Fire Button Monitoring Mode. Phew! Now that you've got all that stuff memorized, you can forget most of it. As far as I can tell, the ST is set-up to not monitor the joysticks at all! If you use the Kbdvbase() call, you will get a pointer to a structure containing all of the ikbd handlers. Now, in the version of TOS I have, the joystick handler vector (joyvec) points to a RTS (return from subroutine) instruction. So, since I did not want to write my own handler, I used the simplest of the joystick monitoring modes, Joystick Keycode Mode, in the following program. If I eventually do write a handler, I will post it to the net also. In the meantime, enjoy! ------------------------------------------------------------------------------- /* * Atari 520ST Joystick/Keyboard Monitoring Demo * * Richard E. Sansom December 1985 * * This is a no-frills program which will monitor joystick 0, and will * report joystick events as keystrokes. No claims are made as to its * efficiency (or elegance). * */ #include <stdio.h> #include <osbinds.h> /* * defines */ #define JOY_UP 0x48 #define JOY_LEFT 0x4B #define JOY_RIGHT 0x4D #define JOY_DOWN 0x50 #define JOY_FIRE 0x74 #define TRUE 1 #define FALSE 0 /* * globals */ static char set_joy_key_mode [] = { 0x19 /* Set Joystick Keycode Mode */ 0x00,0x00, /* RX, RY */ 0x00,0x00, /* TX, TY */ 0x01,0x01 /* VX, VY */ }; static char reset_ikbd [] = { 0x80,0x01 /* Reset */ }; /* * main program */ main() { int lo_chr,hi_chr,more; long chr; /* * clear screen, prompt for joystick */ Cconout(0x1B); Cconout(0x45); printf("Plug joystick into port 0, hit any key when ready..."); while (!Cconis()) ; Cconin(); printf("\n"); /* * write command string to ikbd */ Ikbdws(6,set_joy_key_mode); /* * loop until 'Q' is hit */ more = TRUE; while (more) { while (Bconstat(2)) { chr = Bconin(2); lo_chr = chr & 0x00FF; /* ascii code */ hi_chr = chr >> 0x10; /* scan code */ switch (hi_chr) { case JOY_UP: { printf("Joystick UP "); break; /* Ok, so I'm no purist */ } case JOY_LEFT: { printf("Joystick LEFT "); break; } case JOY_RIGHT: { printf("Joystick RIGHT "); break; } case JOY_DOWN: { printf("Joystick DOWN "); break; } case JOY_FIRE: { printf("Joystick FIRE "); break; } default: printf("Keystroke "); } printf("(scan=0x%x, ascii=0x%x\n)",hi_chr,lo_chr); more = !(lo_chr == 'Q'); } } /* * reset ikbd, exit */ Ikbdws(1,reset_ikbd); _exit(0); } ------------------------------------------------------------------------------- For those of you using the Hippo-C compiler - I've heard that not all of the ST bios and xbios calls are defined (at least in the documentation), so you may want to try the following defines, and see what happens. #define Cconis() conis() #define Cconin() conin() #define Bconstat(dev) bios(1,dev) #define Bconin(dev) bios(2,dev) #define Ikbdws(cnt,ptr) xbios(25,cnt,ptr) I don't know if you have a bios() call available, so you may have to build your own: .text .global _bios _bios: move.l (sp)+,.save ; save return address trap #13 ; call bios move.l .save,-(sp) ; restore return address rts ; return .bss .save .ds.l ; storage area You may have to build your own xbios() call also: .text .global _xbios _xbios: move.l (sp)+,.save ; save return address trap #14 ; call xbios move.l .save,-(sp) ; restore return address rts ; return .bss .save .ds.l ; storage area I don't know whether the Hippo-C compiler pushes all of its args on the stack as longs (the DRI compiler does NOT), so you may have to take that into consideration also. Richard E. Sansom {decvax,ucbvax,ihnp4}!trwrb!trwrba!sansom