1 /* $Id: joyc.c,v 1.7 2005-04-04 09:18:08 btb Exp $ */
3 THE COMPUTER CODE CONTAINED HEREIN IS THE SOLE PROPERTY OF PARALLAX
4 SOFTWARE CORPORATION ("PARALLAX"). PARALLAX, IN DISTRIBUTING THE CODE TO
5 END-USERS, AND SUBJECT TO ALL OF THE TERMS AND CONDITIONS HEREIN, GRANTS A
6 ROYALTY-FREE, PERPETUAL LICENSE TO SUCH END-USERS FOR USE BY SUCH END-USERS
7 IN USING, DISPLAYING, AND CREATING DERIVATIVE WORKS THEREOF, SO LONG AS
8 SUCH USE, DISPLAY OR CREATION IS FOR NON-COMMERCIAL, ROYALTY OR REVENUE
9 FREE PURPOSES. IN NO EVENT SHALL THE END-USER USE THE COMPUTER CODE
10 CONTAINED HEREIN FOR REVENUE-BEARING PURPOSES. THE END-USER UNDERSTANDS
11 AND AGREES TO THE TERMS HEREIN AND ACCEPTS THE SAME BY USE OF THIS FILE.
12 COPYRIGHT 1993-1998 PARALLAX SOFTWARE CORPORATION. ALL RIGHTS RESERVED.
17 * Routines for joystick reading.
39 extern int joy_bogus_reading;
40 int JOY_PORT = 513; //201h;
43 int joy_read_stick_asm2( int read_masks, int * event_buffer, int timeout );
44 int joy_read_stick_friendly2( int read_masks, int * event_buffer, int timeout );
45 int joy_read_stick_polled2( int read_masks, int * event_buffer, int timeout );
46 int joy_read_stick_bios2( int read_masks, int * event_buffer, int timeout );
47 int joy_read_buttons_bios2();
48 void joy_read_buttons_bios_end2();
53 // edi = pointer to buffer
54 // returns number of events
56 char joy_installed = 0;
59 typedef struct Button_info {
68 typedef struct Joy_info {
74 Button_info buttons[JOY_MAX_BUTTONS];
82 ubyte joy_read_buttons()
84 return ((~(inp(JOY_PORT) >> 4))&0xf);
87 void joy_get_cal_vals(int *axis_min, int *axis_center, int *axis_max)
91 for (i = 0; i < JOY_NUM_AXES; i++)
93 axis_min[i] = joystick.axis_min[i];
94 axis_center[i] = joystick.axis_center[i];
95 axis_max[i] = joystick.axis_max[i];
99 void joy_set_cal_vals(int *axis_min, int *axis_center, int *axis_max)
103 for (i = 0; i < JOY_NUM_AXES; i++)
105 joystick.axis_min[i] = axis_min[i];
106 joystick.axis_center[i] = axis_center[i];
107 joystick.axis_max[i] = axis_max[i];
112 ubyte joy_get_present_mask() {
113 return joystick.present_mask;
116 void joy_set_timer_rate(int max_value ) {
118 joystick.max_timer = max_value;
122 int joy_get_timer_rate() {
123 return joystick.max_timer;
130 if (!joy_installed) return;
133 for (i = 0; i < JOY_MAX_BUTTONS; i++)
135 joystick.buttons[i].ignore = 0;
136 joystick.buttons[i].state = 0;
137 joystick.buttons[i].timedown = 0;
138 joystick.buttons[i].downcount = 0;
139 joystick.buttons[i].upcount = 0;
146 void joy_handler(int ticks_this_time) {
149 Button_info * button;
151 // joystick.max_timer = ticks_this_time;
153 if ( joystick.slow_read & JOY_BIOS_READINGS ) {
154 joystick.read_count++;
155 if ( joystick.read_count > 7 ) {
156 joystick.read_count = 0;
157 value = joy_read_buttons_bios2();
158 joystick.last_value = value;
160 value = joystick.last_value;
163 value = joy_read_buttons(); //JOY_READ_BUTTONS;
166 for (i = 0; i < JOY_MAX_BUTTONS; i++)
168 button = &joystick.buttons[i];
169 if (!button->ignore) {
171 state = (value >> i) & 1;
172 else if (i==(value+4))
177 if ( button->last_state == state ) {
178 if (state) button->timedown += ticks_this_time;
181 button->downcount += state;
184 button->upcount += button->state;
187 button->last_state = state;
193 void joy_handler_end() { // Dummy function to help calculate size of joystick handler function
197 ubyte joy_read_raw_buttons() {
198 if ( joystick.slow_read & JOY_BIOS_READINGS )
199 return joy_read_buttons_bios2();
201 return joy_read_buttons(); //JOY_READ_BUTTONS;
204 void joy_set_slow_reading(int flag)
206 joystick.slow_read |= flag;
210 ubyte joystick_read_raw_axis( ubyte mask, int * axis )
212 ubyte read_masks, org_masks;
213 int t, t1, t2, buffer[4*2+2];
214 int e, i, num_channels, c;
216 axis[0] = 0; axis[1] = 0;
217 axis[2] = 0; axis[3] = 0;
219 if (!joy_installed) return 0;
224 mask &= joystick.present_mask; // Don't read non-present channels
226 return 0; // Don't read if no stick connected.
229 if ( joystick.slow_read & JOY_SLOW_READINGS ) {
230 for (c=0; c<4; c++ ) {
231 if ( mask & (1 << c)) {
232 // Time out at (1/100th of a second)
234 if ( joystick.slow_read & JOY_POLLED_READINGS )
235 num_channels = joy_read_stick_polled2( (1 << c), buffer, 65536 );
236 else if ( joystick.slow_read & JOY_BIOS_READINGS )
237 num_channels = joy_read_stick_bios2( (1 << c), buffer, 65536 );
238 else if ( joystick.slow_read & JOY_FRIENDLY_READINGS )
239 num_channels = joy_read_stick_friendly2( (1 << c), buffer, (1193180/100) );
241 num_channels = joy_read_stick_asm2( (1 << c), buffer, (1193180/100) );
243 if ( num_channels > 0 ) {
247 if ( joystick.slow_read & (JOY_POLLED_READINGS|JOY_BIOS_READINGS) ) {
253 t = t1 + joystick.max_timer - t2;
254 //mprintf( 0, "%d, %d, %d, %d\n", t1, t2, joystick.max_timer, t );
258 if ( e & 1 ) { axis[0] = t; read_masks |= 1; }
259 if ( e & 2 ) { axis[1] = t; read_masks |= 2; }
260 if ( e & 4 ) { axis[2] = t; read_masks |= 4; }
261 if ( e & 8 ) { axis[3] = t; read_masks |= 8; }
266 // Time out at (1/100th of a second)
267 if ( joystick.slow_read & JOY_POLLED_READINGS )
268 num_channels = joy_read_stick_polled2( mask, buffer, 65536 );
269 else if ( joystick.slow_read & JOY_BIOS_READINGS )
270 num_channels = joy_read_stick_bios2( mask, buffer, 65536 );
271 else if ( joystick.slow_read & JOY_FRIENDLY_READINGS )
272 num_channels = joy_read_stick_friendly2( mask, buffer, (1193180/100) );
274 num_channels = joy_read_stick_asm2( mask, buffer, (1193180/100) );
275 //mprintf(( 0, "(%d)\n", num_channels ));
277 for (i=0; i<num_channels; i++ ) {
281 if ( joystick.slow_read & (JOY_POLLED_READINGS|JOY_BIOS_READINGS) ) {
287 t = t1 + joystick.max_timer - t2;
288 //mprintf(( 0, "%d, %d, %d, %d\n", t1, t2, joystick.max_timer, t ));
293 if ( e & 1 ) { axis[0] = t; read_masks |= 1; }
294 if ( e & 2 ) { axis[1] = t; read_masks |= 2; }
295 if ( e & 4 ) { axis[2] = t; read_masks |= 4; }
296 if ( e & 8 ) { axis[3] = t; read_masks |= 8; }
313 // if(FindArg("-joy209"))
314 // use_alt_joyport=1;
315 if(FindArg("-joy209"))
316 JOY_PORT = 521; //209h;
321 for (i = 0; i < JOY_MAX_BUTTONS; i++)
322 joystick.buttons[i].last_state = 0;
325 if ( !joy_installed ) {
328 //joystick.max_timer = 65536;
329 joystick.slow_read = 0;
330 joystick.read_count = 0;
331 joystick.last_value = 0;
333 //--------------- lock everything for the virtal memory ----------------------------------
334 if (!dpmi_lock_region ((void near *)joy_read_buttons_bios2, (char *)joy_read_buttons_bios_end2 - (char near *)joy_read_buttons_bios2)) {
335 printf( "Error locking joystick handler (read bios)!\n" );
341 if (!dpmi_lock_region ((void near *)joy_handler, (char *)joy_handler_end - (char near *)joy_handler)) {
342 printf( "Error locking joystick handler!\n" );
346 if (!dpmi_lock_region (&joystick, sizeof(Joy_info))) {
347 printf( "Error locking joystick handler's data!\n" );
351 timer_set_joyhandler(joy_handler);
354 // Do initial cheapy calibration...
355 joystick.present_mask = JOY_ALL_AXIS; // Assume they're all present
357 joystick.present_mask = joystick_read_raw_axis( JOY_ALL_AXIS, temp_axis );
358 } while( joy_bogus_reading );
360 if ( joystick.present_mask & 3 )
370 if (!joy_installed) return;
376 joystick.present_mask = JOY_ALL_AXIS; // Assume they're all present
378 joystick.present_mask = joystick_read_raw_axis( JOY_ALL_AXIS, joystick.axis_min );
379 } while( joy_bogus_reading );
380 if ( joystick.present_mask & 3 )
388 joystick.present_mask = JOY_ALL_AXIS; // Assume they're all present
390 joystick.present_mask = joystick_read_raw_axis( JOY_ALL_AXIS, joystick.axis_max );
391 } while( joy_bogus_reading );
393 if ( joystick.present_mask & 3 )
401 joystick.present_mask = JOY_ALL_AXIS; // Assume they're all present
403 joystick.present_mask = joystick_read_raw_axis( JOY_ALL_AXIS, joystick.axis_center );
404 } while( joy_bogus_reading );
406 if ( joystick.present_mask & 3 )
412 void joy_set_cen_fake(int channel)
416 int minx, maxx, cenx;
420 for (i=0; i<4; i++ ) {
421 if ( (joystick.present_mask & (1<<i)) && (i!=channel) ) {
423 minx += joystick.axis_min[i];
424 maxx += joystick.axis_max[i];
425 cenx += joystick.axis_center[i];
432 joystick.axis_min[channel] = minx;
433 joystick.axis_max[channel] = maxx;
434 joystick.axis_center[channel] = cenx;
437 int joy_get_scaled_reading( int raw, int axn )
441 // Make sure it's calibrated properly.
442 //added/changed on 8/14/98 to allow smaller calibrating sticks to work (by Eivind Brendryen)--was <5
443 if ( joystick.axis_center[axn] - joystick.axis_min[axn] < 2 )
445 if ( joystick.axis_max[axn] - joystick.axis_center[axn] < 2 )
447 //end change - Victor Rachels (by Eivind Brendryen)
449 raw -= joystick.axis_center[axn];
452 d = joystick.axis_center[axn]-joystick.axis_min[axn];
454 d = joystick.axis_max[axn]-joystick.axis_center[axn];
468 //added on 4/13/99 by Victor Rachels to add deadzone control
469 dz = (joy_deadzone) * 6;
470 if ((x > (-1*dz)) && (x < dz))
472 //end this section addition -VR
477 int last_reading[4] = { 0, 0, 0, 0 };
479 void joy_get_pos( int *x, int *y )
484 if ((!joy_installed)||(!joy_present)) { *x=*y=0; return; }
486 flags=joystick_read_raw_axis( JOY_1_X_AXIS+JOY_1_Y_AXIS, axis );
488 if ( joy_bogus_reading ) {
489 axis[0] = last_reading[0];
490 axis[1] = last_reading[1];
491 flags = JOY_1_X_AXIS+JOY_1_Y_AXIS;
493 last_reading[0] = axis[0];
494 last_reading[1] = axis[1];
497 if ( flags & JOY_1_X_AXIS )
498 *x = joy_get_scaled_reading( axis[0], 0 );
502 if ( flags & JOY_1_Y_AXIS )
503 *y = joy_get_scaled_reading( axis[1], 1 );
508 ubyte joy_read_stick( ubyte masks, int *axis )
513 if ((!joy_installed)||(!joy_present)) {
514 axis[0] = 0; axis[1] = 0;
515 axis[2] = 0; axis[3] = 0;
519 flags=joystick_read_raw_axis( masks, raw_axis );
521 if ( joy_bogus_reading ) {
522 axis[0] = last_reading[0];
523 axis[1] = last_reading[1];
524 axis[2] = last_reading[2];
525 axis[3] = last_reading[3];
528 last_reading[0] = axis[0];
529 last_reading[1] = axis[1];
530 last_reading[2] = axis[2];
531 last_reading[3] = axis[3];
534 if ( flags & JOY_1_X_AXIS )
535 axis[0] = joy_get_scaled_reading( raw_axis[0], 0 );
539 if ( flags & JOY_1_Y_AXIS )
540 axis[1] = joy_get_scaled_reading( raw_axis[1], 1 );
544 if ( flags & JOY_2_X_AXIS )
545 axis[2] = joy_get_scaled_reading( raw_axis[2], 2 );
549 if ( flags & JOY_2_Y_AXIS )
550 axis[3] = joy_get_scaled_reading( raw_axis[3], 3 );
560 if ((!joy_installed)||(!joy_present)) return 0;
562 return joy_read_raw_buttons();
565 void joy_get_btn_down_cnt( int *btn0, int *btn1 )
567 if ((!joy_installed)||(!joy_present)) { *btn0=*btn1=0; return; }
570 *btn0 = joystick.buttons[0].downcount;
571 joystick.buttons[0].downcount = 0;
572 *btn1 = joystick.buttons[1].downcount;
573 joystick.buttons[1].downcount = 0;
577 int joy_get_button_state( int btn )
581 if ((!joy_installed)||(!joy_present)) return 0;
583 if (btn >= JOY_MAX_BUTTONS)
587 count = joystick.buttons[btn].state;
593 int joy_get_button_up_cnt( int btn )
597 if ((!joy_installed)||(!joy_present)) return 0;
599 if (btn >= JOY_MAX_BUTTONS)
603 count = joystick.buttons[btn].upcount;
604 joystick.buttons[btn].upcount = 0;
610 int joy_get_button_down_cnt( int btn )
614 if ((!joy_installed)||(!joy_present)) return 0;
615 if (btn >= JOY_MAX_BUTTONS)
619 count = joystick.buttons[btn].downcount;
620 joystick.buttons[btn].downcount = 0;
627 fix joy_get_button_down_time( int btn )
631 if ((!joy_installed)||(!joy_present)) return 0;
632 if (btn >= JOY_MAX_BUTTONS)
636 count = joystick.buttons[btn].timedown;
637 joystick.buttons[btn].timedown = 0;
640 return fixmuldiv(count, 65536, 1193180 );
643 void joy_get_btn_up_cnt( int *btn0, int *btn1 )
645 if ((!joy_installed)||(!joy_present)) { *btn0=*btn1=0; return; }
648 *btn0 = joystick.buttons[0].upcount;
649 joystick.buttons[0].upcount = 0;
650 *btn1 = joystick.buttons[1].upcount;
651 joystick.buttons[1].upcount = 0;
655 void joy_set_btn_values( int btn, int state, fix timedown, int downcount, int upcount )
658 joystick.buttons[btn].ignore = 1;
659 joystick.buttons[btn].state = state;
660 joystick.buttons[btn].timedown = fixmuldiv( timedown, 1193180, 65536 );
661 joystick.buttons[btn].downcount = downcount;
662 joystick.buttons[btn].upcount = upcount;
668 if ( joystick.slow_read & JOY_BIOS_READINGS )
669 joystick.last_value = joy_read_buttons_bios2();