Mercurial > hg > xemacs-beta
annotate src/scrollbar-msw.c @ 5366:f00192e1cd49
Examining the result of #'length: `eql', not `=', it's better style & cheaper
2011-03-08 Aidan Kehoe <kehoea@parhasard.net>
* buff-menu.el (list-buffers-noselect):
* byte-optimize.el (byte-optimize-identity):
* byte-optimize.el (byte-optimize-if):
* byte-optimize.el (byte-optimize-nth):
* byte-optimize.el (byte-optimize-nthcdr):
* bytecomp.el (byte-compile-warn-wrong-args):
* bytecomp.el (byte-compile-two-args-19->20):
* bytecomp.el (byte-compile-list):
* bytecomp.el (byte-compile-beginning-of-line):
* bytecomp.el (byte-compile-set):
* bytecomp.el (byte-compile-set-default):
* bytecomp.el (byte-compile-values):
* bytecomp.el (byte-compile-values-list):
* bytecomp.el (byte-compile-integerp):
* bytecomp.el (byte-compile-multiple-value-list-internal):
* bytecomp.el (byte-compile-throw):
* cl-macs.el (cl-do-arglist):
* cl-macs.el (cl-parse-loop-clause):
* cl-macs.el (multiple-value-bind):
* cl-macs.el (multiple-value-setq):
* cl-macs.el (get-setf-method):
* cmdloop.el (command-error):
* cmdloop.el (y-or-n-p-minibuf):
* cmdloop.el (yes-or-no-p-minibuf):
* coding.el (unencodable-char-position):
* cus-edit.el (custom-face-prompt):
* cus-edit.el (custom-buffer-create-internal):
* cus-edit.el (widget-face-action):
* cus-edit.el (custom-group-value-create):
* descr-text.el (describe-char-unicode-data):
* dialog-gtk.el (popup-builtin-question-dialog):
* dragdrop.el (experimental-dragdrop-drop-log-function):
* dragdrop.el (experimental-dragdrop-drop-mime-default):
* easymenu.el (easy-menu-add):
* easymenu.el (easy-menu-remove):
* faces.el (read-face-name):
* faces.el (set-face-stipple):
* files.el (file-name-non-special):
* font.el (font-combine-fonts):
* font.el (font-set-face-font):
* font.el (font-parse-rgb-components):
* font.el (font-rgb-color-p):
* font.el (font-color-rgb-components):
* gnuserv.el (gnuserv-edit-files):
* help.el (key-or-menu-binding):
* help.el (function-documentation-1):
* help.el (function-documentation):
* info.el (info):
* isearch-mode.el (isearch-exit):
* isearch-mode.el (isearch-edit-string):
* isearch-mode.el (isearch-*-char):
* isearch-mode.el (isearch-complete1):
* ldap.el (ldap-encode-country-string):
* ldap.el (ldap-decode-string):
* minibuf.el (read-file-name-internal-1):
* minibuf.el (read-non-nil-coding-system):
* minibuf.el (get-user-response):
* mouse.el (drag-window-divider):
* mule/ccl.el:
* mule/ccl.el (ccl-compile-if):
* mule/ccl.el (ccl-compile-break):
* mule/ccl.el (ccl-compile-repeat):
* mule/ccl.el (ccl-compile-write-repeat):
* mule/ccl.el (ccl-compile-call):
* mule/ccl.el (ccl-compile-end):
* mule/ccl.el (ccl-compile-read-multibyte-character):
* mule/ccl.el (ccl-compile-write-multibyte-character):
* mule/ccl.el (ccl-compile-translate-character):
* mule/ccl.el (ccl-compile-mule-to-unicode):
* mule/ccl.el (ccl-compile-unicode-to-mule):
* mule/ccl.el (ccl-compile-lookup-integer):
* mule/ccl.el (ccl-compile-lookup-character):
* mule/ccl.el (ccl-compile-map-multiple):
* mule/ccl.el (ccl-compile-map-single):
* mule/devan-util.el (devanagari-compose-to-one-glyph):
* mule/devan-util.el (devanagari-composition-component):
* mule/mule-cmds.el (finish-set-language-environment):
* mule/viet-util.el:
* mule/viet-util.el (viet-encode-viscii-char):
* multicast.el (open-multicast-group):
* newcomment.el (comment-quote-nested):
* newcomment.el (comment-region):
* newcomment.el (comment-dwim):
* regexp-opt.el (regexp-opt-group):
* replace.el (map-query-replace-regexp):
* specifier.el (derive-device-type-from-tag-set):
* subr.el (skip-chars-quote):
* test-harness.el (test-harness-from-buffer):
* test-harness.el (batch-test-emacs):
* wid-edit.el (widget-choice-action):
* wid-edit.el (widget-symbol-prompt-internal):
* wid-edit.el (widget-color-action):
* window-xemacs.el (push-window-configuration):
* window-xemacs.el (pop-window-configuration):
* window.el (quit-window):
* x-compose.el (electric-diacritic):
It's better style, and cheaper (often one assembler instruction
vs. a C funcall in the byte code), to use `eql' instead of `='
when it's clear what numerical type a given result will be. Change
much of our code to do this, with the help of a byte-compiler
change (not comitted) that looked for calls to #'length (which
always returns an integer) in its args.
author | Aidan Kehoe <kehoea@parhasard.net> |
---|---|
date | Tue, 08 Mar 2011 23:41:52 +0000 |
parents | 71ee43b8a74d |
children | 308d34e9f07d |
rev | line source |
---|---|
428 | 1 /* scrollbar implementation -- mswindows interface. |
2 Copyright (C) 1994, 1995 Board of Trustees, University of Illinois. | |
3 Copyright (C) 1994 Amdahl Corporation. | |
4 Copyright (C) 1995 Sun Microsystems, Inc. | |
5 Copyright (C) 1995 Darrell Kindred <dkindred+@cmu.edu>. | |
5169
6c6d78781d59
cleanup of code related to xfree(), better KKCC backtrace capabilities, document XD_INLINE_LISP_OBJECT_BLOCK_PTR, fix some memory leaks, other code cleanup
Ben Wing <ben@xemacs.org>
parents:
5157
diff
changeset
|
6 Copyright (C) 2001, 2002, 2010 Ben Wing. |
428 | 7 |
8 This file is part of XEmacs. | |
9 | |
10 XEmacs is free software; you can redistribute it and/or modify it | |
11 under the terms of the GNU General Public License as published by the | |
12 Free Software Foundation; either version 2, or (at your option) any | |
13 later version. | |
14 | |
15 XEmacs is distributed in the hope that it will be useful, but WITHOUT | |
16 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | |
17 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | |
18 for more details. | |
19 | |
20 You should have received a copy of the GNU General Public License | |
21 along with XEmacs; see the file COPYING. If not, write to | |
22 the Free Software Foundation, Inc., 59 Temple Place - Suite 330, | |
23 Boston, MA 02111-1307, USA. */ | |
24 | |
25 /* Synched up with: Not in FSF. */ | |
26 | |
771 | 27 /* This file essentially Mule-ized (except perhaps some Unicode splitting). |
28 5-2000. */ | |
29 | |
428 | 30 #include <config.h> |
31 #include "lisp.h" | |
32 | |
800 | 33 #include "device.h" |
617 | 34 #include "elhash.h" |
428 | 35 #include "events.h" |
872 | 36 #include "frame-impl.h" |
617 | 37 #include "opaque.h" |
428 | 38 #include "scrollbar.h" |
39 #include "specifier.h" | |
872 | 40 #include "window-impl.h" |
428 | 41 |
872 | 42 #include "console-msw-impl.h" |
800 | 43 #include "scrollbar-msw.h" |
44 | |
428 | 45 /* We use a similar sort of vertical scrollbar drag hack for mswindows |
46 * scrollbars as is used for Motif or Lucid scrollbars under X. | |
47 * We do character-based instead of line-based scrolling, which can mean that | |
48 * without the hack it is impossible to drag to the end of a buffer. */ | |
49 #define VERTICAL_SCROLLBAR_DRAG_HACK | |
50 | |
51 static int vertical_drag_in_progress = 0; | |
673 | 52 extern Lisp_Object mswindows_find_frame (HWND hwnd); |
428 | 53 |
617 | 54 /* As long as the HWND is around, the scrollbar instance must be GC-protected. |
55 We have gotten crashes, apparently from trying to access a dead, freed | |
56 frame inside of a window mirror pointed to by the scrollbar structure. */ | |
57 static Lisp_Object Vmswindows_scrollbar_instance_table; | |
58 | |
428 | 59 static void |
60 mswindows_create_scrollbar_instance (struct frame *f, int vertical, | |
61 struct scrollbar_instance *sb) | |
62 { | |
63 int orientation; | |
617 | 64 Lisp_Object ptr; |
442 | 65 |
428 | 66 sb->scrollbar_data = xnew_and_zero (struct mswindows_scrollbar_data); |
442 | 67 |
428 | 68 if (vertical) |
69 orientation = SBS_VERT; | |
70 else | |
71 orientation = SBS_HORZ; | |
442 | 72 |
428 | 73 SCROLLBAR_MSW_HANDLE (sb) = |
771 | 74 qxeCreateWindowEx (0, XETEXT ("SCROLLBAR"), 0, orientation|WS_CHILD, |
75 CW_USEDEFAULT, CW_USEDEFAULT, | |
76 CW_USEDEFAULT, CW_USEDEFAULT, | |
77 FRAME_MSWINDOWS_HANDLE (f), | |
78 NULL, NULL, NULL); | |
546 | 79 SCROLLBAR_MSW_INFO (sb).cbSize = sizeof (SCROLLINFO); |
428 | 80 SCROLLBAR_MSW_INFO (sb).fMask = SIF_ALL; |
617 | 81 GetScrollInfo (SCROLLBAR_MSW_HANDLE (sb), SB_CTL, |
82 &SCROLLBAR_MSW_INFO (sb)); | |
83 ptr = make_opaque_ptr (SCROLLBAR_MSW_HANDLE (sb)); | |
84 Fputhash (ptr, wrap_scrollbar_instance (sb), | |
85 Vmswindows_scrollbar_instance_table); | |
771 | 86 qxeSetWindowLong (SCROLLBAR_MSW_HANDLE (sb), GWL_USERDATA, |
5013 | 87 (LONG) STORE_LISP_IN_VOID (ptr)); |
428 | 88 } |
89 | |
90 static void | |
91 mswindows_free_scrollbar_instance (struct scrollbar_instance *sb) | |
92 { | |
3482 | 93 if (sb->scrollbar_data) |
94 { | |
95 void *opaque = | |
96 (void *) qxeGetWindowLong (SCROLLBAR_MSW_HANDLE (sb), GWL_USERDATA); | |
97 Lisp_Object ptr; | |
617 | 98 |
5013 | 99 ptr = GET_LISP_FROM_VOID (opaque); |
3482 | 100 assert (OPAQUE_PTRP (ptr)); |
101 ptr = Fremhash (ptr, Vmswindows_scrollbar_instance_table); | |
102 assert (!NILP (ptr)); | |
103 DestroyWindow (SCROLLBAR_MSW_HANDLE (sb)); | |
4976
16112448d484
Rename xfree(FOO, TYPE) -> xfree(FOO)
Ben Wing <ben@xemacs.org>
parents:
3482
diff
changeset
|
104 xfree (sb->scrollbar_data); |
5169
6c6d78781d59
cleanup of code related to xfree(), better KKCC backtrace capabilities, document XD_INLINE_LISP_OBJECT_BLOCK_PTR, fix some memory leaks, other code cleanup
Ben Wing <ben@xemacs.org>
parents:
5157
diff
changeset
|
105 sb->scrollbar_data = 0; |
3482 | 106 } |
428 | 107 } |
108 | |
109 static void | |
611 | 110 unshow_that_mofo (void *handle) |
111 { | |
112 ShowScrollBar ((HWND) handle, SB_CTL, 0); | |
113 } | |
114 | |
115 static void | |
428 | 116 mswindows_release_scrollbar_instance (struct scrollbar_instance *sb) |
117 { | |
611 | 118 if (gc_in_progress) |
119 /* #### way bogus! need to remove the offending call. | |
120 see mark_redisplay(). */ | |
121 register_post_gc_action (unshow_that_mofo, | |
122 (void *) SCROLLBAR_MSW_HANDLE (sb)); | |
123 else | |
124 ShowScrollBar (SCROLLBAR_MSW_HANDLE (sb), SB_CTL, 0); | |
428 | 125 SCROLLBAR_MSW_SIZE (sb) = 0; |
126 } | |
127 | |
128 #define UPDATE_POS_FIELD(field) \ | |
129 if (new_##field >= 0 && SCROLLBAR_MSW_DATA (sb)->field != new_##field) { \ | |
130 SCROLLBAR_MSW_DATA (sb)->field = new_##field; \ | |
131 pos_changed = 1; \ | |
132 } | |
133 | |
134 static void | |
2286 | 135 mswindows_update_scrollbar_instance_values (struct window *UNUSED (w), |
428 | 136 struct scrollbar_instance *sb, |
2286 | 137 int UNUSED (new_line_increment), |
138 int UNUSED (new_page_increment), | |
428 | 139 int new_minimum, int new_maximum, |
140 int new_slider_size, | |
141 int new_slider_position, | |
142 int new_scrollbar_width, | |
143 int new_scrollbar_height, | |
144 int new_scrollbar_x, | |
145 int new_scrollbar_y) | |
146 { | |
147 int pos_changed = 0; | |
771 | 148 int vert = qxeGetWindowLong (SCROLLBAR_MSW_HANDLE (sb), GWL_STYLE) & SBS_VERT; |
428 | 149 |
150 #if 0 | |
151 stderr_out ("[%d, %d], page = %d, pos = %d, inhibit = %d\n", new_minimum, new_maximum, | |
152 new_slider_size, new_slider_position,inhibit_slider_size_change); | |
153 #endif | |
154 | |
155 /* These might be optimized, but since at least one will change at each | |
156 call, it's probably not worth it. */ | |
157 SCROLLBAR_MSW_INFO (sb).nMin = new_minimum; | |
158 SCROLLBAR_MSW_INFO (sb).nMax = new_maximum; | |
159 SCROLLBAR_MSW_INFO (sb).nPage = new_slider_size + 1; /* +1 for DISABLENOSCROLL */ | |
160 SCROLLBAR_MSW_INFO (sb).nPos = new_slider_position; | |
161 #ifndef VERTICAL_SCROLLBAR_DRAG_HACK | |
162 SCROLLBAR_MSW_INFO (sb).fMask = ((vert && vertical_drag_in_progress) | |
163 ? SIF_RANGE | SIF_POS | |
164 : SIF_ALL | SIF_DISABLENOSCROLL); | |
165 #else | |
166 SCROLLBAR_MSW_INFO (sb).fMask = SIF_ALL | SIF_DISABLENOSCROLL; | |
167 | |
168 /* Ignore XEmacs' requests to update the thumb position and size; they don't | |
169 * bear any relation to reality because we're reporting made-up positions */ | |
170 if (!(vert && vertical_drag_in_progress)) | |
171 #endif | |
172 SetScrollInfo (SCROLLBAR_MSW_HANDLE (sb), SB_CTL, &SCROLLBAR_MSW_INFO (sb), | |
173 TRUE); | |
174 | |
175 UPDATE_POS_FIELD (scrollbar_x); | |
176 UPDATE_POS_FIELD (scrollbar_y); | |
177 UPDATE_POS_FIELD (scrollbar_width); | |
178 UPDATE_POS_FIELD (scrollbar_height); | |
179 | |
442 | 180 if (pos_changed) |
428 | 181 { |
617 | 182 MoveWindow (SCROLLBAR_MSW_HANDLE (sb), |
183 new_scrollbar_x, new_scrollbar_y, | |
184 new_scrollbar_width, new_scrollbar_height, | |
185 TRUE); | |
428 | 186 } |
187 } | |
188 | |
189 static void | |
2286 | 190 mswindows_update_scrollbar_instance_status (struct window *UNUSED (w), |
191 int UNUSED (active), int size, | |
428 | 192 struct scrollbar_instance *sb) |
193 { | |
194 if (SCROLLBAR_MSW_SIZE (sb) != size) | |
195 { | |
196 SCROLLBAR_MSW_SIZE (sb) = size; | |
197 ShowScrollBar (SCROLLBAR_MSW_HANDLE (sb), SB_CTL, | |
198 SCROLLBAR_MSW_SIZE (sb)); | |
199 SCROLLBAR_MSW_INFO(sb).fMask |= SIF_DISABLENOSCROLL; | |
200 SetScrollInfo(SCROLLBAR_MSW_HANDLE (sb), SB_CTL, &SCROLLBAR_MSW_INFO (sb), TRUE); | |
201 } | |
202 } | |
203 | |
204 void | |
2286 | 205 mswindows_handle_scrollbar_event (HWND hwnd, int code, int UNUSED (pos)) |
428 | 206 { |
207 struct frame *f; | |
208 Lisp_Object win, frame; | |
617 | 209 struct scrollbar_instance *sb = 0; |
210 void *v; | |
428 | 211 SCROLLINFO scrollinfo; |
771 | 212 int vert = qxeGetWindowLong (hwnd, GWL_STYLE) & SBS_VERT; |
428 | 213 int value; |
214 | |
771 | 215 v = (void *) qxeGetWindowLong (hwnd, GWL_USERDATA); |
617 | 216 if (!v) |
546 | 217 { |
617 | 218 /* apparently this can happen, as it was definitely necessary |
219 to put the check in for sb below (VERTICAL_SCROLLBAR_DRAG_HACK) */ | |
546 | 220 frame = mswindows_find_frame (hwnd); |
221 f = XFRAME (frame); | |
222 win = FRAME_SELECTED_WINDOW (f); | |
223 } | |
224 else | |
225 { | |
617 | 226 Lisp_Object ptr; |
5013 | 227 ptr = GET_LISP_FROM_VOID (v); |
617 | 228 assert (OPAQUE_PTRP (ptr)); |
229 ptr = Fgethash (ptr, Vmswindows_scrollbar_instance_table, Qnil); | |
230 sb = XSCROLLBAR_INSTANCE (ptr); | |
664 | 231 /* #### we're still hitting an abort here with 0 as the second |
232 parameter, although only occasionally. It seems that sometimes we | |
233 receive events for scrollbars that don't exist anymore. I assume | |
234 it must happen like this: The user does something that causes a | |
235 scrollbar to disappear (e.g. Alt-TAB, causing recomputation of | |
236 everything in the new frame) and then immediately uses the mouse | |
237 wheel, generating scrollbar events. Both events get posted before | |
238 we have a chance to process them, and in processing the first, the | |
239 scrollbar mentioned in the second disappears. */ | |
240 win = real_window (sb->mirror, 1); | |
241 if (NILP (win)) | |
242 return; | |
617 | 243 frame = WINDOW_FRAME (XWINDOW (win)); |
546 | 244 f = XFRAME (frame); |
245 } | |
428 | 246 |
673 | 247 /* SB_LINEDOWN == SB_CHARLEFT etc. This is the way they will |
248 always be - any Windows is binary compatible backward with | |
249 old programs */ | |
428 | 250 |
251 switch (code) | |
252 { | |
253 case SB_LINEDOWN: | |
254 mswindows_enqueue_misc_user_event | |
255 (frame, vert ? Qscrollbar_line_down : Qscrollbar_char_right, win); | |
256 break; | |
442 | 257 |
428 | 258 case SB_LINEUP: |
259 mswindows_enqueue_misc_user_event | |
260 (frame, vert ? Qscrollbar_line_up : Qscrollbar_char_left, win); | |
261 break; | |
442 | 262 |
428 | 263 case SB_PAGEDOWN: |
264 mswindows_enqueue_misc_user_event | |
265 (win, vert ? Qscrollbar_page_down : Qscrollbar_page_right, | |
266 vert ? Fcons (win, Qnil) : win); | |
267 break; | |
268 | |
269 case SB_PAGEUP: | |
270 mswindows_enqueue_misc_user_event | |
271 (frame, | |
272 vert ? Qscrollbar_page_up : Qscrollbar_page_left, | |
273 vert ? Fcons (win, Qnil) : win); | |
274 break; | |
442 | 275 |
428 | 276 case SB_BOTTOM: |
277 mswindows_enqueue_misc_user_event | |
278 (frame, vert ? Qscrollbar_to_bottom : Qscrollbar_to_right, win); | |
279 break; | |
280 | |
281 case SB_TOP: | |
282 mswindows_enqueue_misc_user_event | |
283 (frame, vert ? Qscrollbar_to_top : Qscrollbar_to_left, win); | |
284 break; | |
285 | |
286 case SB_THUMBTRACK: | |
287 case SB_THUMBPOSITION: | |
288 scrollinfo.cbSize = sizeof(SCROLLINFO); | |
289 scrollinfo.fMask = SIF_ALL; | |
290 GetScrollInfo (hwnd, SB_CTL, &scrollinfo); | |
291 vertical_drag_in_progress = vert; | |
292 #ifdef VERTICAL_SCROLLBAR_DRAG_HACK | |
293 if (vert && (scrollinfo.nTrackPos > scrollinfo.nPos)) | |
294 /* new buffer position = | |
295 * buffer position at start of drag + | |
296 * ((text remaining in buffer at start of drag) * | |
297 * (amount that the thumb has been moved) / | |
298 * (space that remained past end of the thumb at start of drag)) */ | |
299 value = (int) | |
300 (scrollinfo.nPos | |
301 + (((double) | |
302 (scrollinfo.nMax - scrollinfo.nPos) | |
303 * (scrollinfo.nTrackPos - scrollinfo.nPos)) | |
304 / (scrollinfo.nMax - scrollinfo.nPage - scrollinfo.nPos))) | |
305 - 2; /* ensure that the last line doesn't disappear off screen */ | |
306 else | |
307 #endif | |
308 value = scrollinfo.nTrackPos; | |
309 mswindows_enqueue_misc_user_event | |
310 (frame, | |
311 vert ? Qscrollbar_vertical_drag : Qscrollbar_horizontal_drag, | |
312 Fcons (win, make_int (value))); | |
313 break; | |
314 | |
315 case SB_ENDSCROLL: | |
316 #ifdef VERTICAL_SCROLLBAR_DRAG_HACK | |
546 | 317 if (vertical_drag_in_progress && sb) |
428 | 318 /* User has just dropped the thumb - finally update it */ |
319 SetScrollInfo (SCROLLBAR_MSW_HANDLE (sb), SB_CTL, | |
320 &SCROLLBAR_MSW_INFO (sb), TRUE); | |
321 #endif | |
322 vertical_drag_in_progress = 0; | |
323 break; | |
324 } | |
325 } | |
326 | |
327 static int | |
771 | 328 can_scroll (struct scrollbar_instance *scrollbar) |
428 | 329 { |
330 return scrollbar != NULL | |
331 && IsWindowVisible (SCROLLBAR_MSW_HANDLE (scrollbar)) | |
332 && IsWindowEnabled (SCROLLBAR_MSW_HANDLE (scrollbar)); | |
333 } | |
334 | |
335 int | |
464 | 336 mswindows_handle_mousewheel_event (Lisp_Object frame, int keys, int delta, |
337 POINTS where) | |
428 | 338 { |
442 | 339 int hasVertBar, hasHorzBar; /* Indicates presence of scroll bars */ |
428 | 340 unsigned wheelScrollLines = 0; /* Number of lines per wheel notch */ |
826 | 341 Lisp_Object win = Qnil, corpore, sano; |
464 | 342 struct window_mirror *mirror; |
707 | 343 int mene, _mene, tekel, upharsin; |
344 Charbpos mens, sana; | |
345 Charcount in; | |
346 struct window *needle_in_haystack = 0; | |
464 | 347 POINT donde_esta; |
428 | 348 |
464 | 349 donde_esta.x = where.x; |
350 donde_esta.y = where.y; | |
351 | |
352 /* Find the window to scroll */ | |
353 | |
707 | 354 /* The mouse event could actually occur outside of the emacs |
355 frame. */ | |
356 if (ScreenToClient (FRAME_MSWINDOWS_HANDLE (XFRAME (frame)), | |
357 &donde_esta) != 0) | |
358 { | |
819 | 359 /* stderr_out ("donde_esta: %d %d\n", donde_esta.x, donde_esta.y); */ |
360 pixel_to_glyph_translation (XFRAME (frame), donde_esta.x, donde_esta.y, | |
361 &mene, &_mene, &tekel, &upharsin, | |
362 &needle_in_haystack, | |
363 &mens, &sana, &in, &corpore, &sano); | |
364 | |
365 if (needle_in_haystack) | |
366 { | |
367 win = wrap_window (needle_in_haystack); | |
368 /* stderr_out ("found needle\n"); | |
369 debug_print (win); */ | |
370 } | |
707 | 371 } |
819 | 372 |
373 if (!needle_in_haystack) | |
707 | 374 { |
375 win = FRAME_SELECTED_WINDOW (XFRAME (frame)); | |
376 needle_in_haystack = XWINDOW (win); | |
377 } | |
464 | 378 |
707 | 379 mirror = find_window_mirror (needle_in_haystack); |
428 | 380 |
381 /* Check that there is something to scroll */ | |
382 hasVertBar = can_scroll (mirror->scrollbar_vertical_instance); | |
383 hasHorzBar = can_scroll (mirror->scrollbar_horizontal_instance); | |
384 if (!hasVertBar && !hasHorzBar) | |
385 return FALSE; | |
386 | |
387 /* No support for panning and zooming, so ignore */ | |
388 if (keys & (MK_SHIFT | MK_CONTROL)) | |
389 return FALSE; | |
390 | |
391 /* Get the number of lines per wheel delta */ | |
771 | 392 qxeSystemParametersInfo (SPI_GETWHEELSCROLLLINES, 0, &wheelScrollLines, 0); |
428 | 393 |
394 /* Calculate the amount to scroll */ | |
395 if (wheelScrollLines == WHEEL_PAGESCROLL) | |
396 { | |
397 /* Scroll by a page */ | |
398 Lisp_Object function; | |
399 if (hasVertBar) | |
400 function = delta > 0 ? Qscrollbar_page_up : Qscrollbar_page_down; | |
401 else | |
402 function = delta > 0 ? Qscrollbar_page_left : Qscrollbar_page_right; | |
403 mswindows_enqueue_misc_user_event (frame, function, Fcons (win, Qnil)); | |
404 } | |
405 else /* Scroll by a number of lines */ | |
406 { | |
407 /* Calc the number of lines to scroll */ | |
408 int toScroll = MulDiv (delta, wheelScrollLines, WHEEL_DELTA); | |
409 | |
410 /* Do the scroll */ | |
411 Lisp_Object function; | |
412 if (hasVertBar) | |
413 function = delta > 0 ? Qscrollbar_line_up : Qscrollbar_line_down; | |
414 else | |
415 function = delta > 0 ? Qscrollbar_char_left : Qscrollbar_char_right; | |
416 if (toScroll < 0) | |
417 toScroll = -toScroll; | |
418 while (toScroll--) | |
419 mswindows_enqueue_misc_user_event (frame, function, win); | |
420 } | |
421 | |
422 return TRUE; | |
423 } | |
424 | |
425 #ifdef MEMORY_USAGE_STATS | |
426 | |
5170
5ddbab03b0e6
various fixes to memory-usage stats
Ben Wing <ben@xemacs.org>
parents:
5169
diff
changeset
|
427 static Bytecount |
2286 | 428 mswindows_compute_scrollbar_instance_usage (struct device *UNUSED (d), |
429 struct scrollbar_instance *inst, | |
5157
1fae11d56ad2
redo memory-usage mechanism, add way of dynamically initializing Lisp objects
Ben Wing <ben@xemacs.org>
parents:
5013
diff
changeset
|
430 struct usage_stats *ustats) |
428 | 431 { |
5170
5ddbab03b0e6
various fixes to memory-usage stats
Ben Wing <ben@xemacs.org>
parents:
5169
diff
changeset
|
432 struct mswindows_scrollbar_data *data = |
5ddbab03b0e6
various fixes to memory-usage stats
Ben Wing <ben@xemacs.org>
parents:
5169
diff
changeset
|
433 (struct mswindows_scrollbar_data *) inst->scrollbar_data; |
428 | 434 |
5170
5ddbab03b0e6
various fixes to memory-usage stats
Ben Wing <ben@xemacs.org>
parents:
5169
diff
changeset
|
435 return malloced_storage_size (data, sizeof (*data), ustats); |
428 | 436 } |
437 | |
438 #endif /* MEMORY_USAGE_STATS */ | |
439 | |
440 /************************************************************************/ | |
441 /* Device-specific ghost specifiers initialization */ | |
442 /************************************************************************/ | |
443 | |
617 | 444 DEFUN ("mswindows-init-scrollbar-metrics", Fmswindows_init_scrollbar_metrics, |
445 1, 1, 0, /* | |
428 | 446 */ |
447 (locale)) | |
448 { | |
449 if (DEVICEP (locale)) | |
450 { | |
451 add_spec_to_ghost_specifier (Vscrollbar_width, | |
452 make_int (GetSystemMetrics (SM_CXVSCROLL)), | |
453 locale, Qmswindows, Qnil); | |
454 add_spec_to_ghost_specifier (Vscrollbar_height, | |
455 make_int (GetSystemMetrics (SM_CYHSCROLL)), | |
456 locale, Qmswindows, Qnil); | |
457 } | |
458 return Qnil; | |
459 } | |
460 | |
461 | |
462 /************************************************************************/ | |
463 /* initialization */ | |
464 /************************************************************************/ | |
465 | |
466 void | |
467 console_type_create_scrollbar_mswindows (void) | |
468 { | |
469 CONSOLE_HAS_METHOD (mswindows, create_scrollbar_instance); | |
470 CONSOLE_HAS_METHOD (mswindows, free_scrollbar_instance); | |
471 CONSOLE_HAS_METHOD (mswindows, release_scrollbar_instance); | |
472 CONSOLE_HAS_METHOD (mswindows, update_scrollbar_instance_values); | |
473 CONSOLE_HAS_METHOD (mswindows, update_scrollbar_instance_status); | |
474 /* CONSOLE_HAS_METHOD (mswindows, scrollbar_width_changed_in_frame); */ | |
475 #ifdef MEMORY_USAGE_STATS | |
476 CONSOLE_HAS_METHOD (mswindows, compute_scrollbar_instance_usage); | |
477 #endif | |
478 } | |
479 | |
480 void | |
617 | 481 syms_of_scrollbar_mswindows (void) |
428 | 482 { |
483 DEFSUBR (Fmswindows_init_scrollbar_metrics); | |
484 } | |
485 | |
486 void | |
617 | 487 vars_of_scrollbar_mswindows (void) |
428 | 488 { |
489 Fprovide (intern ("mswindows-scrollbars")); | |
490 | |
617 | 491 staticpro (&Vmswindows_scrollbar_instance_table); |
492 Vmswindows_scrollbar_instance_table = | |
5191
71ee43b8a74d
Add #'equalp as a hash test by default; add #'define-hash-table-test, GNU API
Aidan Kehoe <kehoea@parhasard.net>
parents:
5170
diff
changeset
|
493 make_lisp_hash_table (100, HASH_TABLE_NON_WEAK, Qeq); |
617 | 494 } |