1 /*======================================================================*\
2 |*		Editor mined						*|
3 |*		MSDOS mouse functions					*|
4 |*		currently included from io.c				*|
5 \*======================================================================*/
6 
7 #define dpmi_call
8 
9 #ifdef __TURBOC__
10 #undef dpmi_call
11 #endif
12 
13 #ifdef dpmi_call
14 #include <dpmi.h>
15 #endif
16 
17 #ifndef __TURBOC__
18 #include <pc.h>
19 #endif
20 
21 
22 extern void mouseinit _((void));
23 extern void hidemouse _((void));
24 extern void mousestat _((void));
25 extern int mousegetch _((int msec));
26 extern void DIRECTdosmousegetxy _((void));
27 
28 
29 /*======================================================================*\
30 |*		mouse functions and data				*|
31 \*======================================================================*/
32 
33 #ifdef dpmi_call
34 static __dpmi_regs mregs;
35 #else
36 static union REGS mregs;
37 #endif
38 
39 
40 static
41 void
mousecall()42 mousecall ()
43 {
44 	mregs.x.bx = 0;
45 #ifdef dpmi_call
46 	__dpmi_int (0x33, & mregs);
47 #else
48 	int86 (0x33, & mregs, & mregs);
49 #endif
50 }
51 
52 void
mouseinit()53 mouseinit ()
54 {
55 	mregs.x.ax = 0;
56 	mousecall ();
57 }
58 
59 static
60 void
showmouse()61 showmouse ()
62 {
63 	mregs.x.ax = 1;
64 	mousecall ();
65 }
66 
67 void
hidemouse()68 hidemouse ()
69 {
70 	mregs.x.ax = 2;
71 	mousecall ();
72 }
73 
74 void
mousestat()75 mousestat ()
76 {
77 	mregs.x.ax = 3;
78 	mousecall ();
79 }
80 
81 
82 static
83 void
yield_cpu()84 yield_cpu ()
85 {
86 	mregs.x.ax = 0x1680;
87 #ifdef dpmi_call
88 	__dpmi_int (0x2F, & mregs);
89 #else
90 	/* no effect in this case !?! */
91 	int86 (0x2F, & mregs, & mregs);
92 #endif
93 }
94 
95 
96 static mousebutton_type new_button;
97 static int new_x, new_y;
98 
99 
100 #define dont_debug_mousegetch
101 
102 static
103 long
timediff()104 timediff ()
105 {
106   static long prevmsec = 0;
107   long msec;
108   long msecdiff;
109 
110 #define gettime_2
111 
112 #ifdef gettime_1
113   {	struct timeval now;
114 	gettimeofday (& now, 0);
115 	msec = now.tv_sec * 1000 + now.tv_usec / 1000;
116   }
117 #else
118 #ifdef gettime_2
119   {	struct time now;
120 	gettime (& now);
121 	msec = ((now.ti_hour * 60 + now.ti_min) * 60 + now.ti_sec) * 1000 + now.ti_hund * 10;
122   }
123 #else
124 #ifdef gettime_3
125   {	struct _dostime_t now;
126 	_dos_gettime (& now);
127 	msec = ((now.hour * 60 + now.minute) * 60 + now.second) * 1000 + now.hsecond * 10;
128   }
129 #else
130 #error no gettime method selected
131 #endif
132 #endif
133 #endif
134 
135   msecdiff = msec - prevmsec;
136   if (msecdiff < 0) {	/* @ midnight */
137 	msecdiff += 24 * 60 * 60 * 1000;
138   }
139 #ifdef debug_mousegetch
140   printf (" - timediff %ld ms\n", msecdiff);
141 #endif
142 
143   prevmsec = msec;
144   return msecdiff;
145 }
146 
147 
148 /**
149    mousegetch: check for keyboard or mouse input
150    @param msec
151    	< 0: read; wait for keyboard or mouse event
152    	= 0: check if available; do not wait
153    		(like kbhit function)
154    	> 0: check with timeout; wait for max msec ms
155    		(aka half-delay mode)
156    @return
157    	>= 0: byte read (if msec < 0)
158    	FUNcmd ( < -1): mouse input (if msec < 0);
159    		call DIRECTdosmousegetxy () to retrieve parameters
160    	-1: no input available / timeout (if msec >= 0)
161    	-2: keyboard input available (if msec >= 0)
162    	-3: mouse input available (if msec >= 0)
163  */
164 int
mousegetch(msec)165 mousegetch (msec)
166   int msec;	/* timeout */
167 {
168 	int stat;
169 	long timeout = msec;	/* timeout count-down */
170 	static int mhit = 0;
171 
172 #ifdef debug_mousegetch
173 	printf ("mousegetch (%d)\n", msec);
174 #endif
175 
176 	/* return mouse event that was previously detected available */
177 	if (msec < 0 && mhit) {
178 		mhit = 0;
179 		return FUNcmd;
180 	}
181 	mhit = 0;
182 
183 	showmouse ();
184 	mousestat ();
185 	stat = mregs.x.bx;
186 	new_y = mregs.x.dx;
187 	new_x = mregs.x.cx;
188 
189 	if (msec >= 0) {
190 		(void) timediff ();
191 	}
192 /*	check key input with bioskey (1) or kbhit () */
193 	while (! kbhit () && mregs.x.bx == stat
194 		&& mregs.x.dx == new_y && mregs.x.cx == new_x
195 		&& (msec < 0 || timeout > 0)
196 		)
197 	{
198 #ifdef debug_mousegetch
199 		napms (222);	/* needs -lpdcurses */
200 #endif
201 		/* avoid using 99% CPU */
202 		yield_cpu ();	/* or call __dpmi_yield (); */
203 
204 		/* check timeout */
205 		if (msec >= 0) {
206 			timeout -= timediff ();
207 		}
208 
209 		/* check mouse again */
210 		mousestat ();
211 	}
212 
213 	if (kbhit ()) {
214 		hidemouse ();
215 #ifdef debug_mousegetch
216 		printf ("  return key\n");
217 #endif
218 		if (msec < 0) {
219 #ifdef __TURBOC__
220 			return getch ();
221 #else
222 			return getxkey ();
223 #endif
224 		} else {
225 			return -2;	/* indicate keyboard input available */
226 		}
227 	} else {
228 		/* report timeout */
229 		if (msec >= 0 && timeout <= 0) {
230 			/* no need to check mouse events in this case? */
231 #ifdef debug_mousegetch
232 			printf ("  return timeout\n");
233 #endif
234 			return -1;	/* indicate no input available */
235 		}
236 
237 	/*	bx: button - 1 = left, 2 = right, 4 = middle
238 		cx: column * 8 (first is 0)
239 		dx: line * 8 (first is 0)
240 	*/
241 		if (mregs.x.bx == stat) {
242 			if (in_menu_mouse_mode) {
243 				new_button = movebutton;
244 			} else {
245 #ifdef debug_mousegetch
246 				printf ("  recurse\n");
247 #endif
248 				return mousegetch (timeout);
249 			}
250 		} else if (mregs.x.bx == 1) {
251 			new_button = leftbutton;
252 		} else if (mregs.x.bx == 4) {
253 			new_button = middlebutton;
254 		} else if (mregs.x.bx == 2) {
255 			new_button = rightbutton;
256 		} else {
257 			new_button = releasebutton;
258 		}
259 		hidemouse ();
260 #ifdef debug_mousegetch
261 		printf ("  return mouse\n");
262 #endif
263 		if (msec < 0) {
264 			return FUNcmd;
265 		} else {
266 			mhit = 1;
267 			return -3;	/* indicate mouse input available */
268 		}
269 	}
270 }
271 
272 
273 void
DIRECTdosmousegetxy()274 DIRECTdosmousegetxy ()
275 {
276   /* remember previous mouse click */
277   if (mouse_button == leftbutton || mouse_button == rightbutton || mouse_button == middlebutton) {
278 	mouse_prevbutton = mouse_button;
279 	mouse_prevxpos = mouse_xpos;
280 	mouse_prevypos = mouse_ypos;
281   }
282 
283   mouse_button = new_button;
284 
285   /*
286 	mouse_xpos: column (first is 0)
287 	mouse_ypos: line after menu (first is 0, menu line is -1)
288   */
289   mouse_ypos = (new_y >> 3) - MENU;
290   mouse_xpos = new_x >> 3;
291 }
292 
293 
294 /*======================================================================*\
295 |*				End					*|
296 \*======================================================================*/
297