]> icculus.org git repositories - btb/d2x.git/blob - main/old/joydefsw.c
portability
[btb/d2x.git] / main / old / joydefsw.c
1 /*
2 THE COMPUTER CODE CONTAINED HEREIN IS THE SOLE PROPERTY OF PARALLAX
3 SOFTWARE CORPORATION ("PARALLAX").  PARALLAX, IN DISTRIBUTING THE CODE TO
4 END-USERS, AND SUBJECT TO ALL OF THE TERMS AND CONDITIONS HEREIN, GRANTS A
5 ROYALTY-FREE, PERPETUAL LICENSE TO SUCH END-USERS FOR USE BY SUCH END-USERS
6 IN USING, DISPLAYING,  AND CREATING DERIVATIVE WORKS THEREOF, SO LONG AS
7 SUCH USE, DISPLAY OR CREATION IS FOR NON-COMMERCIAL, ROYALTY OR REVENUE
8 FREE PURPOSES.  IN NO EVENT SHALL THE END-USER USE THE COMPUTER CODE
9 CONTAINED HEREIN FOR REVENUE-BEARING PURPOSES.  THE END-USER UNDERSTANDS
10 AND AGREES TO THE TERMS HEREIN AND ACCEPTS THE SAME BY USE OF THIS FILE.  
11 COPYRIGHT 1993-1999 PARALLAX SOFTWARE CORPORATION.  ALL RIGHTS RESERVED.
12 */
13
14
15 #pragma off (unreferenced)
16 static char rcsid[] = "$Id: joydefsw.c,v 1.1.1.1 2001-01-19 03:30:14 bradleyb Exp $";
17 #pragma on (unreferenced)
18
19 #include "desw.h"
20 #include <mmsystem.h>
21
22 #include <stdlib.h>
23 #include <stdio.h>
24 #include <string.h>
25 #include <dos.h>
26
27 #include "mono.h"
28 #include "key.h"
29 #include "joy.h"
30 #include "timer.h"
31 #include "error.h"
32
33 #include "inferno.h"
34 #include "game.h"
35 #include "object.h"
36 #include "player.h"
37
38 #include "controls.h"
39 #include "joydefs.h"
40 #include "victor.h"
41 #include "render.h"
42 #include "palette.h"
43 #include "newmenu.h"
44 #include "args.h"
45 #include "gamefont.h"
46 #include "text.h"
47 #include "kconfig.h"
48 #include "digi.h"
49 #include "playsave.h"
50 #include "screens.h"
51 #include "config.h"
52
53 //      Extra control stuff
54
55 // #include "cyberimp.h"
56
57
58 //##int joydefs_calibrate_flag = 0;
59 int joydefs_max_joysticks = 0;
60 int joydefs_num_joysticks = 0;
61 int Joystick_calibrating = 0;
62
63
64 extern int WriteConfigFile();   
65 extern void kconfig_set_fcs_button(int btn, int button);
66
67
68 WinJoystickDesc WinJoyDesc;
69
70 //      Windows 95:
71 //              Calibration and Menus because of automatic joystick detection
72 //              and 6 axis' (XYZ-RUV)
73
74 extern ubyte default_kconfig_settings[][MAX_CONTROLS];
75
76
77 void win95_autodetect_joystick()
78 {
79         JOYCAPS jc;
80
81 //      Set default windows joystick settings.
82 //      AUTODETECT !!!
83         joyGetDevCaps(JOYSTICKID1, &jc, sizeof(jc));
84
85 //      Do buttons first
86         default_kconfig_settings[CONTROL_WINJOYSTICK][1] = 0xff;
87         default_kconfig_settings[CONTROL_WINJOYSTICK][4] = 0xff;
88         default_kconfig_settings[CONTROL_WINJOYSTICK][26] = 0xff;
89
90         default_kconfig_settings[CONTROL_WINJOYSTICK][0] = 0x0;
91         if (jc.wMaxButtons > 1) 
92                 default_kconfig_settings[CONTROL_WINJOYSTICK][1] = 0x1;
93         if (jc.wMaxButtons > 2) 
94                 default_kconfig_settings[CONTROL_WINJOYSTICK][4] = 0x2;
95         if (jc.wMaxButtons > 3) 
96                 default_kconfig_settings[CONTROL_WINJOYSTICK][26] = 0x3;
97
98 //      Do Hat!
99         default_kconfig_settings[CONTROL_WINJOYSTICK][6] = 0xff;
100         default_kconfig_settings[CONTROL_WINJOYSTICK][7] = 0xff;
101         default_kconfig_settings[CONTROL_WINJOYSTICK][8] = 0xff;
102         default_kconfig_settings[CONTROL_WINJOYSTICK][9] = 0xff;
103
104         if (jc.wCaps & JOYCAPS_HASPOV) {
105                 default_kconfig_settings[CONTROL_WINJOYSTICK][6] = 0x10;
106                 default_kconfig_settings[CONTROL_WINJOYSTICK][7] = 0x12;
107                 default_kconfig_settings[CONTROL_WINJOYSTICK][8] = 0x13;
108                 default_kconfig_settings[CONTROL_WINJOYSTICK][9] = 0x11;
109         } 
110
111 //      Do Z-Axis (Throttle)
112
113 //      Do rudder? (R-AXIS) 
114                 
115 }
116
117
118 int win95_controls_init()
119 {
120         //int i = 0;
121         int spjoy = 0;
122
123         if (FindArg("-SpecialDevice")) spjoy = 1;
124
125         joydefs_max_joysticks = joy_init(0,spjoy);
126         if (!joy95_init_stick(1, spjoy)) return 0;
127
128 //@@    for (i = 2; i <= joydefs_max_joysticks; i++)
129 //@@            if (!joy95_init_stick(i,0)) {
130 //@@                    joydefs_max_joysticks = i-1;
131 //@@                    break;
132 //@@            }
133
134         joy_handler_win(0,0,0,0);
135         win95_autodetect_joystick();
136
137         return 1;
138 }
139
140
141 void joy_delay()
142 {
143         stop_time();
144         WinDelay(250);                  
145         joy_flush();
146         start_time();
147 }
148
149 void dump_axis_vals(int *t_vals)
150 {
151         mprintf_at((0, 2, 32, "X:%6d\n", t_vals[0]));
152         mprintf_at((0, 3, 32, "Y:%6d\n", t_vals[1]));
153         mprintf_at((0, 4, 32, "Z:%6d\n", t_vals[2]));
154         mprintf_at((0, 5, 32, "R:%6d\n", t_vals[4]));
155         mprintf_at((0, 6, 32, "U:%6d\n", t_vals[5]));
156         mprintf_at((0, 7, 32, "V:%6d\n", t_vals[6]));
157 }
158
159
160 //      MAIN CALIBRATION ROUTINES
161 //      ----------------------------------------------------------------------------
162
163 void joydefs_calibrate(void)
164 {
165         DWORD dwval;
166         BOOL flag;
167         STARTUPINFO si;
168         PROCESS_INFORMATION pi;
169         char name[80];
170         char oldname[80];
171         int j;
172         int old_mode= -1;
173         
174         Joystick_calibrating = 1;
175
176         if (GRMODEINFO(modex)) {
177                 old_mode = Screen_mode;
178                 set_screen_mode(SCREEN_MENU);
179         }
180         palette_save();
181         apply_modified_palette();
182         reset_palette_add();
183
184         gr_palette_load(gr_palette);
185
186 //      Call calibration Applet
187         joy95_get_name(JOYSTICKID1, oldname, 79);
188
189         logentry("Closing joystick for control panel init.\n");
190         joy_close();                                                    // Close down joystick polling
191
192         memset(&si, 0, sizeof(si));
193         si.cb = sizeof(si);
194         si.dwFlags = STARTF_USESHOWWINDOW;
195         si.wShowWindow = SW_SHOW;
196
197         flag = CreateProcess(
198                         NULL,
199                         "rundll32.exe shell32.dll,Control_RunDLL joy.cpl",
200                         NULL, NULL,
201                         FALSE, NORMAL_PRIORITY_CLASS, NULL, NULL,
202                         &si, &pi);                      
203         if (!flag) {
204                 nm_messagebox( NULL, 1, TXT_OK, "UNABLE TO INITIATE\nJOYSTICK CONTROL PANEL");
205         }
206         else {
207                 dwval = WaitForInputIdle(pi.hProcess, INFINITE);
208                 mprintf((1, "JOY.CPL initiated?\n"));
209                 WinDelayIdle();                                                 // Clear out messages.
210
211                 while (WaitForSingleObject(pi.hProcess, 0) != WAIT_OBJECT_0)
212                 {
213                         if (multi_menu_poll()==-1)      {
214                                 TerminateProcess(pi.hProcess,0);
215                                 Sleep(100); 
216                                 CloseHandle(pi.hThread);
217                                 CloseHandle(pi.hProcess);
218                                 break;
219                         }
220                 }
221
222                 mprintf((1, "JOY.CPL process finished?\n"));
223                 ShowWindow(_hAppWnd, SW_MAXIMIZE);
224                 WinDelayIdle();
225                 SetForegroundWindow(_hAppWnd);
226                 WinDelayIdle();
227                 _RedrawScreen = FALSE;
228         }
229
230         if (win95_controls_init())                                      // Reinitializing joystick polling.
231                 logentry("Reinitialized joystick with new settings.\n");
232         else 
233                 logentry("Failed to reinitialize joystick.\n");
234
235 //      Set kconfig settings to updated vals.
236         joy95_get_name(JOYSTICKID1, name, 79);
237
238         if (Config_control_type == CONTROL_WINJOYSTICK) {
239                 if (strcmp(name, oldname)) {
240                         for (j=0; j<MAX_CONTROLS; j++ )
241                                 kconfig_settings[CONTROL_WINJOYSTICK][j] = default_kconfig_settings[CONTROL_WINJOYSTICK][j];
242                         kc_set_controls();
243                 }
244         }
245
246 //@@    joydefs_calibrate2();
247         
248         reset_cockpit();
249
250         palette_restore();
251
252         if (old_mode != -1)     {
253                 set_screen_mode(old_mode);
254         }
255         
256         Joystick_calibrating = 0;
257 }
258
259
260 //@@//  We should make our own windowed calibrator
261 //@@void joydefs_calibrate2()
262 //@@{
263 //@@    ubyte masks;
264 //@@    char calmsg[6][32];
265 //@@
266 //@@    int org_axis_min[7];
267 //@@    int org_axis_center[7];
268 //@@    int org_axis_max[7];
269 //@@
270 //@@    int axis_min[7] = { 0, 0, 0, 0, 0, 0, 0 };
271 //@@    int axis_cen[7] = { 0, 0, 0, 0, 0, 0, 0 };
272 //@@    int axis_max[7] = { 0, 0, 0, 0, 0, 0, 0 };
273 //@@
274 //@@    int t_vals[7];
275 //@@
276 //@@    char title[50];
277 //@@    char text[50];
278 //@@    int res;
279 //@@    int nsticks = 0;
280 //@@
281 //@@//  Get Current Calibration stuff
282 //@@    joydefs_calibrate_flag = 0;
283 //@@
284 //@@    joy_get_cal_vals(org_axis_min, org_axis_center, org_axis_max);
285 //@@
286 //@@    joy_set_cen();
287 //@@
288 //@@    masks = joystick_read_raw_axis( JOY_ALL_AXIS+JOY_EXT_AXIS, t_vals );
289 //@@
290 //@@    if (!joy_present)       {
291 //@@            nm_messagebox( NULL, 1, TXT_OK, TXT_NO_JOYSTICK );
292 //@@            return;
293 //@@    }
294 //@@    
295 //@@    masks = joy_get_present_mask();
296 //@@
297 //@@    nsticks = 1;
298 //@@
299 //@@    res = joy_calibrate_xy(&axis_min[0], &axis_cen[0],      &axis_max[0],
300 //@@                                                                    &axis_min[1], &axis_cen[1], &axis_max[1]);
301 //@@    
302 //@@    if (!res) {
303 //@@            joy_set_cal_vals(org_axis_min, org_axis_center, org_axis_max);
304 //@@            return;
305 //@@    }
306 //@@
307 //@@    strcpy(calmsg[0], "MOVE JOYSTICK UNTIL BAR REACHES");
308 //@@    strcpy(calmsg[1], "TOP AND PRESS BUTTON");
309 //@@    strcpy(calmsg[2], "MOVE JOYSTICK UNTIL BAR REACHES");
310 //@@    strcpy(calmsg[3], "BOTTOM AND PRESS BUTTON");
311 //@@    strcpy(calmsg[4], "RELEASE JOYSTICK");
312 //@@    strcpy(calmsg[5], "AND PRESS BUTTON");
313 //@@
314 //@@    mprintf((0, "Masks: %x\n", masks));
315 //@@
316 //@@    if (masks&JOY_1_Z_AXIS) {
317 //@@            res = joy_calibrate_bar(2, "CALIBRATE Z-AXIS", calmsg,
318 //@@                                                    &axis_min[2], &axis_cen[2], &axis_max[2]);
319 //@@            if (!res) {
320 //@@                    joy_set_cal_vals(org_axis_min, org_axis_center, org_axis_max);
321 //@@                    return;
322 //@@            }
323 //@@    }
324 //@@
325 //@@    if (masks&JOY_1_R_AXIS) {
326 //@@            res = joy_calibrate_bar(4, "CALIBRATE RUDDER", calmsg,
327 //@@                                                    &axis_min[4], &axis_cen[4], &axis_max[4]);
328 //@@            if (!res) {
329 //@@                    joy_set_cal_vals(org_axis_min, org_axis_center, org_axis_max);
330 //@@                    return;
331 //@@            }
332 //@@    }
333 //@@
334 //@@    if (masks&JOY_1_U_AXIS) {
335 //@@            res = joy_calibrate_bar(5, "CALIBRATE U-AXIS", calmsg,
336 //@@                                                    &axis_min[5], &axis_cen[5], &axis_max[5]);
337 //@@            if (!res) {
338 //@@                    joy_set_cal_vals(org_axis_min, org_axis_center, org_axis_max);
339 //@@                    return;
340 //@@            }
341 //@@    }
342 //@@
343 //@@    if (masks&JOY_1_V_AXIS) {
344 //@@            res = joy_calibrate_bar(6, "CALIBRATE V-AXIS", calmsg,
345 //@@                                                    &axis_min[6], &axis_cen[6], &axis_max[6]);
346 //@@            if (!res) {
347 //@@                    joy_set_cal_vals(org_axis_min, org_axis_center, org_axis_max);
348 //@@                    return;
349 //@@            }
350 //@@    }
351 //@@
352 //@@
353 //@@    joy_set_cal_vals(axis_min, axis_cen, axis_max);
354 //@@
355 //@@    WriteConfigFile();      
356 //@@}
357
358
359 //      Joydefs button detection
360 //              This function will do Windows Joystick Button stuff
361 //              may emulate Thrustmaster FCS, Flightstick Pro, etc.
362                 
363 int joydefsw_do_button()
364 {
365         int axis[7];    
366         int code=255;
367         int i;
368
369         joystick_read_raw_axis(JOY_ALL_AXIS, axis);     
370
371         switch (Config_control_type) 
372         {
373                 case CONTROL_WINJOYSTICK:
374                         code = joydefsw_do_winjoybutton(axis);
375                         break;
376         }
377
378 //      Get standard buttons
379         for (i=0; i<16; i++ )   {
380                 if ( joy_get_button_state(i) )
381                         code = i;
382         }
383
384         return code;                      
385 }
386
387
388 int joydefsw_do_winjoybutton(int *axis)
389 {
390 //      Do POV detection first.  We should use the same
391 // procedure as the DOS version so that we can emulate the
392 // Thrustmaster selections (to keep Player files the same between
393 //      versions.  (19,15,11,7,0)
394         int button;
395
396         if (axis[3] == JOY_POVBACKWARD) 
397                 button = 17;
398         else if (axis[3] == JOY_POVFORWARD)
399                 button = 19;
400         else if (axis[3] == JOY_POVLEFT)
401                 button = 16;
402         else if (axis[3] == JOY_POVRIGHT)
403                 button = 18;
404         else if (axis[3] == JOY_POVCENTERED) 
405                 button = 0;
406
407         kconfig_set_fcs_button(19,button);
408         kconfig_set_fcs_button(18,button);
409         kconfig_set_fcs_button(17,button);
410         kconfig_set_fcs_button(16, button);
411
412         if (button == 0) button = 255;
413
414         return button;
415
416
417
418
419 //      Joystick Menu 
420 //              We want to keep the config files the same for the Windows/DOS
421 //              versions.  But we also autodetect joystick stuff.
422 //              Find some way to keep this easier than the DOS version without screwing 
423 //              up configuration files.
424
425 void joydef_menuset_1(int nitems, newmenu_item * items, int *last_key, int citem )
426 {
427         //int i;
428         int oc_type = Config_control_type;
429
430         nitems = nitems;
431         last_key = last_key;
432         citem = citem;          
433
434         if (items[0].value) Config_control_type = CONTROL_NONE;
435         else if (items[1].value) Config_control_type = CONTROL_MOUSE;
436         else if (items[2].value) Config_control_type = CONTROL_WINJOYSTICK;
437
438 //@@    if ( (oc_type != Config_control_type) && (Config_control_type == CONTROL_THRUSTMASTER_FCS ) )   {
439 //@@                    nm_messagebox( TXT_IMPORTANT_NOTE, 1, TXT_OK, TXT_FCS );
440 //@@            }
441
442         if (oc_type != Config_control_type) {
443                 //##switch (Config_control_type) {
444                 //##    case    CONTROL_WINJOYSTICK:
445                 //##            joydefs_calibrate_flag = 1;
446                 //##}
447                 kc_set_controls();
448         }
449
450 }
451
452 extern ubyte kc_use_external_control;
453 extern ubyte kc_enable_external_control;
454 extern ubyte *kc_external_name;
455
456 void joydefs_config()
457 {
458         int i, old_masks, masks,nitems;
459         newmenu_item m[13];
460         int i1=11;
461         char xtext[92];
462         char joytext[128];
463         int no_joystick_option = 0;
464
465         //##joydefs_calibrate_flag = 0;
466
467         joy95_get_name(JOYSTICKID1, xtext, 127);
468         if (!strcmpi(xtext, "NO JOYSTICK DETECTED") && (Config_control_type == CONTROL_WINJOYSTICK))    {
469                 Config_control_type = CONTROL_NONE;
470                 no_joystick_option = 1;
471         }
472         else no_joystick_option = 0;
473         nm_wrap_text(joytext, xtext, 20);
474         
475         do {
476                 nitems=10;
477                 m[0].type = NM_TYPE_RADIO; m[0].text = CONTROL_TEXT(0); m[0].value = 0; m[0].group = 0;
478                 m[1].type = NM_TYPE_RADIO; m[1].text = CONTROL_TEXT(5); m[1].value = 0; m[1].group = 0;
479         
480                 if (no_joystick_option) {
481                         m[2].type = NM_TYPE_TEXT; m[2].text = joytext; m[2].value = 0; m[2].group = 0;
482                 } else {
483                         m[2].type = NM_TYPE_RADIO; m[2].text = joytext; m[2].value = 0; m[2].group = 0;
484                 }
485
486                 m[3].type = NM_TYPE_TEXT;  m[3].text="";
487                 m[4].type = NM_TYPE_MENU; m[4].text=TXT_CUST_ABOVE;
488                 m[5].type = NM_TYPE_TEXT;  m[5].text="";
489                 m[6].type = NM_TYPE_SLIDER; m[6].text=TXT_JOYS_SENSITIVITY; m[6].value=Config_joystick_sensitivity; m[6].min_value =0; m[6].max_value = 8;
490                 m[7].type = NM_TYPE_TEXT;   m[7].text="";
491                 m[8].type = NM_TYPE_TEXT;   m[8].text="";
492                 m[9].type = NM_TYPE_MENU; m[9].text=TXT_CUST_KEYBOARD;
493
494                 if (Config_control_type == CONTROL_WINJOYSTICK) m[2].value = 1;
495                 else if (Config_control_type == CONTROL_MOUSE) m[1].value = 1;
496                 else if (Config_control_type == CONTROL_NONE) m[0].value = 1;
497                 else m[0].value = 1;   
498
499                 i1 = newmenu_do1( NULL, TXT_CONTROLS, nitems, m, joydef_menuset_1, i1 );
500                 Config_joystick_sensitivity = m[6].value;
501
502                 switch(i1)      {
503                 case 4: {
504                                 old_masks = 0;
505                                 for (i=0; i<4; i++ )            {
506                                         if (kconfig_is_axes_used(i))
507                                                 old_masks |= (1<<i);
508                                 }
509                                 if ( Config_control_type==0 )
510                                         Config_control_type=0;
511                                 else if ( Config_control_type < CONTROL_MOUSE ) 
512                                         kconfig(1, CONTROL_TEXT(Config_control_type) ); 
513                                 else if ( Config_control_type == CONTROL_WINJOYSTICK) 
514                                         kconfig(3, CONTROL_TEXT(Config_control_type) );
515                                 else 
516                                         kconfig(2, CONTROL_TEXT(Config_control_type) ); 
517
518                                 masks = 0;
519                                 for (i=0; i<4; i++ )            {
520                                         if (kconfig_is_axes_used(i))
521                                                 masks |= (1<<i);
522                                 }
523
524                                 //##switch (Config_control_type) {
525                                 //##case        CONTROL_WINJOYSTICK:
526                                 //##    {
527                                 //##            for (i=0; i<4; i++ )    {
528                                 //##                    if ( (masks&(1<<i)) && (!(old_masks&(1<<i))))
529                                 //##                            joydefs_calibrate_flag = 1;
530                                 //##            }
531                                 //##    }
532                                 //##    break;
533                                 //##}
534                         }
535                         break;
536                 case 9: 
537                         kconfig(0, TXT_KEYBOARD); 
538                         break;
539                 } 
540
541         } while(i1 > -1);
542
543 //      No calibration under new system where control panel does this.
544 //      switch (Config_control_type) {
545 //              case    CONTROL_WINJOYSTICK:
546 //                      if ( joydefs_calibrate_flag )
547 //                              joydefs_calibrate();
548 //                      break;
549 //      }
550 }
551
552
553 //      Extended joystick menu
554 //      ----------------------------------------------------------------------------
555 void joydefsw_win_joyselect(char *title)
556 {
557         FILE *fp;
558         char filename[64];
559         char *token;
560         ubyte axis;
561
562         if (newmenu_filelist("Windows 95 Controls", "*.joy", filename)) {
563                 fp = fopen(filename, "rb");
564                 if (!fp) {
565                         nm_messagebox(TXT_ERROR, 1, TXT_OK, "Unable to find control file");
566                         strcpy(title, "Windows 95 Custom");
567                         return;
568                 }
569         
570         // Get Axis support.
571                 if (!fread(&axis, sizeof(ubyte), 1, fp)) {
572                         nm_messagebox(TXT_ERROR, 1, TXT_OK, "Illegal or corrupt control file");
573                         strcpy(title, "Windows 95 Custom");
574                         fclose(fp);
575                         return;
576                 }
577
578
579                 if (fread(kconfig_settings[CONTROL_WINJOYSTICK], 
580                                         sizeof(kconfig_settings[CONTROL_WINJOYSTICK]), 
581                                 1, fp) != 1) {
582                         nm_messagebox(TXT_ERROR, 1, TXT_OK, "Illegal or corrupt control file");
583                         strcpy(title, "Windows 95 Custom");
584                         fclose(fp);
585                         return;
586                 }                       
587                 fclose(fp);                                     
588
589                 token = strtok(filename, ".");
590                 strcpy(title, token);
591         }
592         else strcpy(title, "Windows 95 Custom");
593 }
594