]> icculus.org git repositories - taylor/freespace2.git/blob - src/io/mouse.cpp
Warning cleanups
[taylor/freespace2.git] / src / io / mouse.cpp
1 /*
2  * Copyright (C) Volition, Inc. 1999.  All rights reserved.
3  *
4  * All source code herein is the property of Volition, Inc. You may not sell 
5  * or otherwise commercially exploit the source or things you created based on
6  * the source.
7  */
8
9 /*
10  * $Logfile: /Freespace2/code/Io/Mouse.cpp $
11  * $Revision$
12  * $Date$
13  * $Author$
14  *
15  * Routines to read the mouse.
16  *
17  * $Log$
18  * Revision 1.6  2002/07/13 06:46:48  theoddone33
19  * Warning cleanups
20  *
21  * Revision 1.5  2002/06/09 04:41:22  relnev
22  * added copyright header
23  *
24  * Revision 1.4  2002/06/02 04:26:34  relnev
25  * warning cleanup
26  *
27  * Revision 1.3  2002/05/29 06:25:13  theoddone33
28  * Keyboard input, mouse tracking now work
29  *
30  * Revision 1.2  2002/05/07 03:16:46  theoddone33
31  * The Great Newline Fix
32  *
33  * Revision 1.1.1.1  2002/05/03 03:28:09  root
34  * Initial import.
35  *
36  * 
37  * 4     7/15/99 9:20a Andsager
38  * FS2_DEMO initial checkin
39  * 
40  * 3     6/02/99 6:18p Dave
41  * Fixed TNT lockup problems! Wheeeee!
42  * 
43  * 2     10/07/98 10:53a Dave
44  * Initial checkin.
45  * 
46  * 1     10/07/98 10:49a Dave
47  * 
48  * 29    6/10/98 2:52p Hoffoss
49  * Made mouse code use DI by default, but fall back on normal code if that
50  * fails.
51  * 
52  * 28    5/24/98 1:35p Hoffoss
53  * Fixed bug where  mouse cursor is always recentering with a
54  * mouse_flush() call in debug version.
55  * 
56  * 27    5/22/98 4:50p Hoffoss
57  * Trying to fix mouse acceleration problem..
58  * 
59  * 26    5/21/98 12:26p Lawrance
60  * Fixed mouse jerk at mission start while in debug build only.
61  * 
62  * 25    5/15/98 2:41p Hoffoss
63  * Made mouse default to off (for flying ship) and fixed some new pilot
64  * init bugs.
65  * 
66  * 24    5/08/98 4:13p Hoffoss
67  * Fixed problem with mouse pointer centering causing lost keypresses.
68  * 
69  * 23    5/07/98 6:58p Hoffoss
70  * Made changes to mouse code to fix a number of problems.
71  * 
72  * 22    5/05/98 8:38p Hoffoss
73  * Added sensitivity adjustment to options menu and made it save to pilot
74  * file.
75  * 
76  * 21    5/05/98 1:03p Hoffoss
77  * Fixed initialization bug.
78  * 
79  * 20    5/01/98 5:45p Hoffoss
80  * Made further improvements to the mouse code.
81  * 
82  * 19    5/01/98 3:35p Hoffoss
83  * Made changes to release version of mouse code.
84  * 
85  * 18    5/01/98 1:14p Hoffoss
86  * Changed mouse usage so directInput is only used for release version.
87  * 
88  * 17    4/30/98 5:40p Hoffoss
89  * Added mouse as a supported control to fly the ship.
90  * 
91  * 16    4/29/98 12:13a Lawrance
92  * Add function to check down count of mouse button without reseting the
93  * internal count.  Added hook to reset demo trailer timer when a button
94  * is pressed.
95  * 
96  * 15    4/02/98 5:26p John
97  * 
98  * 14    1/19/98 6:15p John
99  * Fixed all my Optimized Build compiler warnings
100  * 
101  * 13    12/04/97 3:47p John
102  * Made joystick move mouse cursor
103  * 
104  * 12    11/20/97 5:36p Dave
105  * Hooked in a bunch of main hall changes (including sound). Made it
106  * possible to reposition (rewind/ffwd) 
107  * sound buffer pointers. Fixed animation direction change framerate
108  * problem.
109  * 
110  * 11    5/12/97 11:41a John
111  * Added range checking to mouse position
112  * 
113  * 10    4/22/97 5:55p Lawrance
114  * let mouse.cpp decide if mouse has moved
115  * 
116  * 9     4/22/97 12:29p John
117  * Changed mouse code so that you have to call mouse_init for the mouse
118  * stuff to work.
119  * 
120  * 8     4/22/97 10:56a John
121  * fixed some resource leaks.
122  * 
123  * 7     3/26/97 10:52a Lawrance
124  * mouse always on in menus, disappears in gameplay after 1 second
125  * 
126  * 6     3/11/97 1:37p Lawrance
127  * added mouse_up_count(), changed mouse_mark() to mouse_mark_button() &
128  * mouse_mark_move()
129  * 
130  * 5     12/09/96 1:29p Lawrance
131  * adding 3 button support
132  * 
133  * 4     12/03/96 4:19p John
134  * Added some code so that holding down the mouse buttons between menus
135  * doesn't select the next menu.
136  *
137  * $NoKeywords: $
138  */
139
140 #ifndef PLAT_UNIX
141 #include <windows.h>
142 #include <windowsx.h>
143 #endif
144
145 #include "mouse.h"
146 #include "2d.h"
147 #include "osapi.h"
148
149 #define MOUSE_MODE_DI   0
150 #define MOUSE_MODE_WIN  1
151
152 #ifdef NDEBUG
153 LOCAL int Mouse_mode = MOUSE_MODE_DI;
154 #else
155 LOCAL int Mouse_mode = MOUSE_MODE_WIN;
156 #endif
157
158 LOCAL int mouse_inited = 0;
159 #ifndef PLAT_UNIX
160 LOCAL int Di_mouse_inited = 0;
161 #endif
162 LOCAL int Mouse_x;
163 LOCAL int Mouse_y;
164
165 CRITICAL_SECTION mouse_lock;
166
167 // #define USE_DIRECTINPUT
168
169 int mouse_flags;
170 int mouse_left_pressed = 0;
171 int mouse_right_pressed = 0;
172 int mouse_middle_pressed = 0;
173 int mouse_left_up = 0;
174 int mouse_right_up = 0;
175 int mouse_middle_up = 0;
176 int Mouse_dx = 0;
177 int Mouse_dy = 0;
178 int Mouse_dz = 0;
179
180 int Mouse_sensitivity = 4;
181 int Use_mouse_to_fly = 0;
182 int Mouse_hidden = 0;
183 int Keep_mouse_centered = 0;;
184
185 int di_init();
186 void di_cleanup();
187 void mouse_force_pos(int x, int y);
188 void mouse_eval_deltas_di();
189
190 int mouse_is_visible()
191 {
192         return !Mouse_hidden;
193 }
194
195 void mouse_close()
196 {
197         if (!mouse_inited)
198                 return;
199
200 #ifdef USE_DIRECTINPUT
201         di_cleanup();
202 #endif
203         mouse_inited = 0;
204 #ifdef PLAT_UNIX
205         STUB_FUNCTION;
206 #else
207         DeleteCriticalSection( &mouse_lock );
208 #endif
209 }
210
211 void mouse_init()
212 {
213         // Initialize queue
214         if ( mouse_inited ) return;
215         mouse_inited = 1;
216
217 #ifdef PLAT_UNIX
218         STUB_FUNCTION;
219 #else
220         InitializeCriticalSection( &mouse_lock );
221 #endif
222
223         ENTER_CRITICAL_SECTION(&mouse_lock);
224
225         mouse_flags = 0;
226         Mouse_x = gr_screen.max_w / 2;
227         Mouse_y = gr_screen.max_h / 2;
228
229 #ifdef USE_DIRECTINPUT
230         if (!di_init())
231                 Mouse_mode = MOUSE_MODE_WIN;
232 #else
233         Mouse_mode = MOUSE_MODE_WIN;
234 #endif
235
236         LEAVE_CRITICAL_SECTION(&mouse_lock);    
237
238         atexit( mouse_close );
239 }
240
241
242 // ----------------------------------------------------------------------------
243 // mouse_mark_button() is called asynchronously by the OS when a mouse button
244 // goes up or down.  The mouse button that is affected is passed via the 
245 // flags parameter.  
246 //
247 // parameters:   flags ==> mouse button pressed/released
248 //               set   ==> 1 - button is pressed
249 //                         0 - button is released
250
251 void mouse_mark_button( uint flags, int set)
252 {
253         if ( !mouse_inited ) return;
254
255         ENTER_CRITICAL_SECTION(&mouse_lock);
256
257         if ( !(mouse_flags & MOUSE_LEFT_BUTTON) )       {
258
259                 if ( (flags & MOUSE_LEFT_BUTTON) && (set == 1) ) {
260                         mouse_left_pressed++;
261
262 ////////////////////////////
263 /// SOMETHING TERRIBLE IS ABOUT TO HAPPEN.  I FEEL THIS IS NECESSARY FOR THE DEMO, SINCE
264 /// I DON'T WANT TO CALL CRITICAL SECTION CODE EACH FRAME TO CHECK THE LEFT MOUSE BUTTON.
265 /// PLEASE SEE ALAN FOR MORE INFORMATION.
266 ////////////////////////////
267 #ifdef FS2_DEMO
268                                         {
269                                         extern void demo_reset_trailer_timer();
270                                         demo_reset_trailer_timer();
271                                         }
272 #endif
273 ////////////////////////////
274 /// IT'S OVER.  SEE, IT WASN'T SO BAD RIGHT?  IT'S IS VERY UGLY LOOKING, I KNOW.
275 ////////////////////////////
276
277                 }
278         }
279         else {
280                 if ( (flags & MOUSE_LEFT_BUTTON) && (set == 0) ){
281                         mouse_left_up++;
282                 }
283         }
284
285         if ( !(mouse_flags & MOUSE_RIGHT_BUTTON) )      {
286
287                 if ( (flags & MOUSE_RIGHT_BUTTON) && (set == 1) ){
288                         mouse_right_pressed++;
289                 }
290         }
291         else {
292                 if ( (flags & MOUSE_RIGHT_BUTTON) && (set == 0) ){
293                         mouse_right_up++;
294                 }
295         }
296
297         if ( !(mouse_flags & MOUSE_MIDDLE_BUTTON) )     {
298
299                 if ( (flags & MOUSE_MIDDLE_BUTTON) && (set == 1) ){
300                         mouse_middle_pressed++;
301                 }
302         }
303         else {
304                 if ( (flags & MOUSE_MIDDLE_BUTTON) && (set == 0) ){
305                         mouse_middle_up++;
306                 }
307         }
308
309         if ( set ){
310                 mouse_flags |= flags;
311         } else {
312                 mouse_flags &= ~flags;
313         }
314
315         LEAVE_CRITICAL_SECTION(&mouse_lock);    
316 }
317
318 void mouse_flush()
319 {
320         if (!mouse_inited)
321                 return;
322
323         mouse_eval_deltas();
324         Mouse_dx = Mouse_dy = Mouse_dz = 0;
325         ENTER_CRITICAL_SECTION(&mouse_lock);
326         mouse_left_pressed = 0;
327         mouse_right_pressed = 0;
328         mouse_middle_pressed = 0;
329         mouse_flags = 0;
330         LEAVE_CRITICAL_SECTION(&mouse_lock);    
331 }
332
333 int mouse_down_count(int n, int reset_count)
334 {
335         int tmp = 0;
336         if ( !mouse_inited ) return 0;
337
338         if ( (n < LOWEST_MOUSE_BUTTON) || (n > HIGHEST_MOUSE_BUTTON)) return 0;
339
340         ENTER_CRITICAL_SECTION(&mouse_lock);
341
342         switch (n) {
343                 case MOUSE_LEFT_BUTTON:
344                         tmp = mouse_left_pressed;
345                         if ( reset_count ) {
346                                 mouse_left_pressed = 0;
347                         }
348                         break;
349
350                 case MOUSE_RIGHT_BUTTON:
351                         tmp = mouse_right_pressed;
352                         if ( reset_count ) {
353                                 mouse_right_pressed = 0;
354                         }
355                         break;
356
357                 case MOUSE_MIDDLE_BUTTON:
358                         tmp = mouse_middle_pressed;
359                         if ( reset_count ) {
360                                 mouse_middle_pressed = 0;
361                         }
362                         break;
363         } // end switch
364
365         LEAVE_CRITICAL_SECTION(&mouse_lock);    
366
367         return tmp;
368 }
369
370 // mouse_up_count() returns the number of times button n has gone from down to up
371 // since the last call
372 //
373 // parameters:  n - button of mouse (see #define's in mouse.h)
374 //
375 int mouse_up_count(int n)
376 {
377         int tmp = 0;
378         if ( !mouse_inited ) return 0;
379
380         if ( (n < LOWEST_MOUSE_BUTTON) || (n > HIGHEST_MOUSE_BUTTON)) return 0;
381
382         ENTER_CRITICAL_SECTION(&mouse_lock);
383
384         switch (n) {
385                 case MOUSE_LEFT_BUTTON:
386                         tmp = mouse_left_up;
387                         mouse_left_up = 0;
388                         break;
389
390                 case MOUSE_RIGHT_BUTTON:
391                         tmp = mouse_right_up;
392                         mouse_right_up = 0;
393                         break;
394
395                 case MOUSE_MIDDLE_BUTTON:
396                         tmp = mouse_middle_up;
397                         mouse_middle_up = 0;
398                         break;
399
400                 default:
401                         Assert(0);      // can't happen
402                         break;
403         } // end switch
404
405         LEAVE_CRITICAL_SECTION(&mouse_lock);    
406
407         return tmp;
408 }
409
410 // returns 1 if mouse button btn is down, 0 otherwise
411
412 int mouse_down(int btn)
413 {
414         int tmp;
415         if ( !mouse_inited ) return 0;
416
417         if ( (btn < LOWEST_MOUSE_BUTTON) || (btn > HIGHEST_MOUSE_BUTTON)) return 0;
418
419
420         ENTER_CRITICAL_SECTION(&mouse_lock);
421
422
423         if ( mouse_flags & btn )
424                 tmp = 1;
425         else
426                 tmp = 0;
427
428         LEAVE_CRITICAL_SECTION(&mouse_lock);    
429
430         return tmp;
431 }
432
433 // returns the fraction of time btn has been down since last call 
434 // (currently returns 1 if buttons is down, 0 otherwise)
435 //
436 float mouse_down_time(int btn)
437 {
438         float tmp;
439         if ( !mouse_inited ) return 0.0f;
440
441         if ( (btn < LOWEST_MOUSE_BUTTON) || (btn > HIGHEST_MOUSE_BUTTON)) return 0.0f;
442
443         ENTER_CRITICAL_SECTION(&mouse_lock);
444
445         if ( mouse_flags & btn )
446                 tmp = 1.0f;
447         else
448                 tmp = 0.0f;
449
450         LEAVE_CRITICAL_SECTION(&mouse_lock);
451
452         return tmp;
453 }
454
455 void mouse_get_delta(int *dx, int *dy, int *dz)
456 {
457         if (dx)
458                 *dx = Mouse_dx;
459         if (dy)
460                 *dy = Mouse_dy;
461         if (dz)
462                 *dz = Mouse_dz;
463 }
464
465 // Forces the actual windows cursor to be at (x,y).  This may be independent of our tracked (x,y) mouse pos.
466 void mouse_force_pos(int x, int y)
467 {
468         if (os_foreground()) {  // only mess with windows's mouse if we are in control of it
469 #ifdef PLAT_UNIX
470                 SDL_WarpMouse(x, y);
471 #else
472                 POINT pnt;
473
474                 pnt.x = x;
475                 pnt.y = y;
476                 ClientToScreen((HWND) os_get_window(), &pnt);
477                 SetCursorPos(pnt.x, pnt.y);
478 #endif
479         }
480 }
481
482 #include "gamesequence.h"
483
484 // change in mouse position since last call
485 void mouse_eval_deltas()
486 {
487         static int old_x = 0;
488         static int old_y = 0;
489         int tmp_x, tmp_y, cx, cy;
490
491         Mouse_dx = Mouse_dy = Mouse_dz = 0;
492         if (!mouse_inited)
493                 return;
494
495         if (Mouse_mode == MOUSE_MODE_DI) {
496                 mouse_eval_deltas_di();
497                 return;
498         }
499
500         cx = gr_screen.max_w / 2;
501         cy = gr_screen.max_h / 2;
502
503         ENTER_CRITICAL_SECTION(&mouse_lock);
504
505 #ifdef PLAT_UNIX
506         SDL_GetMouseState (&tmp_x, &tmp_y);
507 #else
508         POINT pnt;
509         GetCursorPos(&pnt);
510         ScreenToClient((HWND)os_get_window(), &pnt);
511         tmp_x = pnt.x;
512         tmp_y = pnt.y;
513 #endif
514
515         Mouse_dx = tmp_x - old_x;
516         Mouse_dy = tmp_y - old_y;
517         Mouse_dz = 0;
518
519         if (Keep_mouse_centered && Mouse_hidden) {
520                 if (Mouse_dx || Mouse_dy)
521                         mouse_force_pos(cx, cy);
522
523                 old_x = cx;
524                 old_y = cy;
525
526         } else {
527                 old_x = tmp_x;
528                 old_y = tmp_y;
529         }
530
531         LEAVE_CRITICAL_SECTION(&mouse_lock);
532 }
533
534 #ifndef PLAT_UNIX
535 #include "vdinput.h"
536
537 static LPDIRECTINPUT                    Di_mouse_obj = NULL;
538 static LPDIRECTINPUTDEVICE      Di_mouse = NULL;
539 #endif
540
541 void mouse_eval_deltas_di()
542 {
543 #ifdef PLAT_UNIX
544         STUB_FUNCTION;
545 #else
546         int repeat = 1;
547         HRESULT hr = 0;
548         DIMOUSESTATE mouse_state;
549
550         Mouse_dx = Mouse_dy = Mouse_dz = 0;
551         if (!Di_mouse_inited)
552                 return;
553
554         repeat = 1;
555         memset(&mouse_state, 0, sizeof(mouse_state));
556         while (repeat) {
557                 repeat = 0;
558
559                 hr = Di_mouse->GetDeviceState(sizeof(mouse_state), &mouse_state);
560                 if ((hr == DIERR_INPUTLOST) || (hr == DIERR_NOTACQUIRED)) {
561                         // DirectInput is telling us that the input stream has
562                         // been interrupted.  We aren't tracking any state
563                         // between polls, so we don't have any special reset
564                         // that needs to be done.  We just re-acquire and
565                         // try again.
566                         Sleep(500);             // Pause a half second...
567                         hr = Di_mouse->Acquire();
568                         if (SUCCEEDED(hr))
569                                 repeat = 1;
570                 }
571         }
572
573         if (SUCCEEDED(hr)) {
574                 Mouse_dx = (int) mouse_state.lX;
575                 Mouse_dy = (int) mouse_state.lY;
576                 Mouse_dz = (int) mouse_state.lZ;
577
578         } else {
579                 Mouse_dx = Mouse_dy = Mouse_dz = 0;
580         }
581
582         Mouse_x += Mouse_dx;
583         Mouse_y += Mouse_dy;
584
585         if (Mouse_x < 0)
586                 Mouse_x = 0;
587
588         if (Mouse_y < 0)
589                 Mouse_y = 0;
590
591         if (Mouse_x >= gr_screen.max_w)
592                 Mouse_x = gr_screen.max_w - 1;
593
594         if (Mouse_y >= gr_screen.max_h)
595                 Mouse_y = gr_screen.max_h - 1;
596
597         // keep the mouse inside our window so we don't switch applications or anything (debug bug people reported?)
598         // JH: Dang!  This makes the mouse readings in DirectInput act screwy!
599 //      mouse_force_pos(gr_screen.max_w / 2, gr_screen.max_h / 2);
600 #endif
601 }
602
603 int mouse_get_pos(int *xpos, int *ypos)
604 {
605         int flags;
606
607         if (Mouse_mode == MOUSE_MODE_DI) {
608                 if (xpos)
609                         *xpos = Mouse_x;
610
611                 if (ypos)
612                         *ypos = Mouse_y;
613
614                 return mouse_flags;
615         }
616
617         if (!mouse_inited) {
618                 *xpos = *ypos = 0;
619                 return 0;
620         }
621
622 #ifdef PLAT_UNIX
623         flags = SDL_GetMouseState (&Mouse_x, &Mouse_y);
624         // DDOI - FIXME?
625 #else
626         POINT pnt;
627         GetCursorPos(&pnt);
628         ScreenToClient((HWND)os_get_window(), &pnt);
629
630 //      EnterCriticalSection(&mouse_lock);
631
632         flags = mouse_flags;
633         Mouse_x = pnt.x;
634         Mouse_y = pnt.y;
635 #endif
636
637 //      LeaveCriticalSection(&mouse_lock);
638
639         if (Mouse_x < 0){
640                 Mouse_x = 0;
641         }
642
643         if (Mouse_y < 0){
644                 Mouse_y = 0;
645         }
646
647         if (Mouse_x >= gr_screen.max_w){
648                 Mouse_x = gr_screen.max_w - 1;
649         }
650
651         if (Mouse_y >= gr_screen.max_h){
652                 Mouse_y = gr_screen.max_h - 1;
653         }
654         
655         if (xpos){
656                 *xpos = Mouse_x;
657         }
658
659         if (ypos){
660                 *ypos = Mouse_y;
661         }
662
663         return flags;
664 }
665
666 void mouse_get_real_pos(int *mx, int *my)
667 {
668         if (Mouse_mode == MOUSE_MODE_DI) {
669                 *mx = Mouse_x;
670                 *my = Mouse_y;
671                 return;
672         }
673
674 #ifdef PLAT_UNIX
675         SDL_GetMouseState (mx, my);
676 #else
677         POINT pnt;
678         GetCursorPos(&pnt);
679         ScreenToClient((HWND)os_get_window(), &pnt);
680         
681         *mx = pnt.x;
682         *my = pnt.y;
683 #endif
684 }
685
686 void mouse_set_pos(int xpos, int ypos)
687 {
688         if (Mouse_mode == MOUSE_MODE_DI) {
689                 Mouse_x = xpos;
690                 Mouse_y = ypos;
691                 return;
692         }
693
694         if ((xpos != Mouse_x) || (ypos != Mouse_y)){
695                 mouse_force_pos(xpos, ypos);
696         }
697 }
698
699 int di_init()
700 {
701 #ifdef PLAT_UNIX
702         STUB_FUNCTION;
703         return 0;
704 #else
705         HRESULT hr;
706
707         if (Mouse_mode == MOUSE_MODE_WIN){
708                 return 0;
709         }
710
711         Di_mouse_inited = 0;
712         hr = DirectInputCreate(GetModuleHandle(NULL), DIRECTINPUT_VERSION, &Di_mouse_obj, NULL);
713         if (FAILED(hr)) {
714                 hr = DirectInputCreate(GetModuleHandle(NULL), 0x300, &Di_mouse_obj, NULL);
715                 if (FAILED(hr)) {
716                         mprintf(( "DirectInputCreate() failed!\n" ));
717                         return FALSE;
718                 }
719         }
720
721         hr = Di_mouse_obj->CreateDevice(GUID_SysMouse, &Di_mouse, NULL);
722         if (FAILED(hr)) {
723                 mprintf(( "CreateDevice() failed!\n" ));
724                 return FALSE;
725         }
726
727         hr = Di_mouse->SetDataFormat(&c_dfDIMouse);
728         if (FAILED(hr)) {
729                 mprintf(( "SetDataFormat() failed!\n" ));
730                 return FALSE;
731         }
732
733         hr = Di_mouse->SetCooperativeLevel((HWND)os_get_window(), DISCL_NONEXCLUSIVE | DISCL_FOREGROUND);
734         if (FAILED(hr)) {
735                 mprintf(( "SetCooperativeLevel() failed!\n" ));
736                 return FALSE;
737         }
738 /*
739         DIPROPDWORD hdr;
740
741         // Turn on buffering
742         hdr.diph.dwSize = sizeof(DIPROPDWORD); 
743         hdr.diph.dwHeaderSize = sizeof(DIPROPHEADER);
744         hdr.diph.dwObj = 0;             
745         hdr.diph.dwHow = DIPH_DEVICE;   // Apply to entire device
746         hdr.dwData = 16;        //MAX_BUFFERED_KEYBOARD_EVENTS;
747
748         hr = Di_mouse->SetProperty( DIPROP_BUFFERSIZE, &hdr.diph );
749         if (FAILED(hr)) {
750                 mprintf(( "SetProperty DIPROP_BUFFERSIZE failed\n" ));
751                 return FALSE;
752         }
753
754         Di_event = CreateEvent( NULL, FALSE, FALSE, NULL );
755         Assert(Di_event != NULL);
756
757         hr = Di_mouse->SetEventNotification(Di_event);
758         if (FAILED(hr)) {
759                 mprintf(( "SetEventNotification failed\n" ));
760                 return FALSE;
761         }
762 */
763         Di_mouse->Acquire();
764
765         Di_mouse_inited = 1;
766         return TRUE;
767 #endif
768 }
769
770 void di_cleanup()
771 {
772 #ifdef PLAT_UNIX
773         STUB_FUNCTION;
774 #else
775         // Destroy any lingering IDirectInputDevice object.
776         if (Di_mouse) {
777                 // Unacquire the device one last time just in case we got really confused
778                 // and tried to exit while the device is still acquired.
779                 Di_mouse->Unacquire();
780
781                 Di_mouse->Release();
782                 Di_mouse = NULL;
783         }
784
785         // Destroy any lingering IDirectInput object.
786         if (Di_mouse_obj) {
787                 Di_mouse_obj->Release();
788                 Di_mouse_obj = NULL;
789         }
790
791         Di_mouse_inited = 0;
792 #endif
793 }
794