aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/ChangeLog18
-rw-r--r--src/w32console.c89
-rw-r--r--src/w32inevt.c59
-rw-r--r--src/xdisp.c2
4 files changed, 163 insertions, 5 deletions
diff --git a/src/ChangeLog b/src/ChangeLog
index 2981e754c8a..c71ea45dded 100644
--- a/src/ChangeLog
+++ b/src/ChangeLog
@@ -1,3 +1,21 @@
12012-05-26 Eli Zaretskii <eliz@gnu.org>
2
3 Extend mouse support on W32 text-mode console.
4 * xdisp.c (draw_row_with_mouse_face): Call
5 tty_draw_row_with_mouse_face for WINDOWSNT as well.
6
7 * w32console.c: Include window.h.
8 (w32con_write_glyphs_with_face, tty_draw_row_with_mouse_face): New
9 functions.
10 (initialize_w32_display): Initialize mouse-highlight data.
11
12 * w32inevt.c: Include termchar.h and window.h.
13 (do_mouse_event): Support mouse-autoselect-window. When the mouse
14 moves, call note_mouse_highlight. If help_echo changed, call
15 gen_help_event to produce help-echo message in the echo area.
16 Call clear_mouse_face if mouse_face_hidden is set in the mouse
17 highlight info.
18
12012-05-26 Paul Eggert <eggert@cs.ucla.edu> 192012-05-26 Paul Eggert <eggert@cs.ucla.edu>
2 20
3 * lread.c (read1): Simplify slightly to avoid an overflow warning 21 * lread.c (read1): Simplify slightly to avoid an overflow warning
diff --git a/src/w32console.c b/src/w32console.c
index e8b0f621b4f..22f329e239d 100644
--- a/src/w32console.c
+++ b/src/w32console.c
@@ -33,6 +33,7 @@ along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */
33#include "coding.h" 33#include "coding.h"
34#include "disptab.h" 34#include "disptab.h"
35#include "frame.h" 35#include "frame.h"
36#include "window.h"
36#include "termhooks.h" 37#include "termhooks.h"
37#include "termchar.h" 38#include "termchar.h"
38#include "dispextern.h" 39#include "dispextern.h"
@@ -339,6 +340,84 @@ w32con_write_glyphs (struct frame *f, register struct glyph *string,
339 } 340 }
340} 341}
341 342
343/* Used for mouse highlight. */
344static void
345w32con_write_glyphs_with_face (struct frame *f, register int x, register int y,
346 register struct glyph *string, register int len,
347 register int face_id)
348{
349 unsigned char *conversion_buffer;
350 struct coding_system *coding;
351
352 if (len <= 0)
353 return;
354
355 /* If terminal_coding does any conversion, use it, otherwise use
356 safe_terminal_coding. We can't use CODING_REQUIRE_ENCODING here
357 because it always return 1 if the member src_multibyte is 1. */
358 coding = (FRAME_TERMINAL_CODING (f)->common_flags & CODING_REQUIRE_ENCODING_MASK
359 ? FRAME_TERMINAL_CODING (f) : &safe_terminal_coding);
360 /* We are going to write the entire block of glyphs in one go, as
361 they all have the same face. So this _is_ the last block. */
362 coding->mode |= CODING_MODE_LAST_BLOCK;
363
364 conversion_buffer = encode_terminal_code (string, len, coding);
365 if (coding->produced > 0)
366 {
367 DWORD filled, written;
368 /* Compute the character attributes corresponding to the face. */
369 DWORD char_attr = w32_face_attributes (f, face_id);
370 COORD start_coords;
371
372 start_coords.X = x;
373 start_coords.Y = y;
374 /* Set the attribute for these characters. */
375 if (!FillConsoleOutputAttribute (cur_screen, char_attr,
376 coding->produced, start_coords,
377 &filled))
378 DebPrint (("Failed writing console attributes: %d\n", GetLastError ()));
379 else
380 {
381 /* Write the characters. */
382 if (!WriteConsoleOutputCharacter (cur_screen, conversion_buffer,
383 filled, start_coords, &written))
384 DebPrint (("Failed writing console characters: %d\n",
385 GetLastError ()));
386 }
387 }
388}
389
390/* Implementation of draw_row_with_mouse_face for W32 console. */
391void
392tty_draw_row_with_mouse_face (struct window *w, struct glyph_row *row,
393 int start_hpos, int end_hpos,
394 enum draw_glyphs_face draw)
395{
396 int nglyphs = end_hpos - start_hpos;
397 struct frame *f = XFRAME (WINDOW_FRAME (w));
398 struct tty_display_info *tty = FRAME_TTY (f);
399 int face_id = tty->mouse_highlight.mouse_face_face_id;
400 int pos_x, pos_y;
401
402 if (end_hpos >= row->used[TEXT_AREA])
403 nglyphs = row->used[TEXT_AREA] - start_hpos;
404
405 pos_y = row->y + WINDOW_TOP_EDGE_Y (w);
406 pos_x = row->used[LEFT_MARGIN_AREA] + start_hpos + WINDOW_LEFT_EDGE_X (w);
407
408 if (draw == DRAW_MOUSE_FACE)
409 w32con_write_glyphs_with_face (f, pos_x, pos_y,
410 row->glyphs[TEXT_AREA] + start_hpos,
411 nglyphs, face_id);
412 else if (draw == DRAW_NORMAL_TEXT)
413 {
414 COORD save_coords = cursor_coords;
415
416 w32con_move_cursor (f, pos_y, pos_x);
417 write_glyphs (f, row->glyphs[TEXT_AREA] + start_hpos, nglyphs);
418 w32con_move_cursor (f, save_coords.Y, save_coords.X);
419 }
420}
342 421
343static void 422static void
344w32con_delete_glyphs (struct frame *f, int n) 423w32con_delete_glyphs (struct frame *f, int n)
@@ -570,6 +649,7 @@ void
570initialize_w32_display (struct terminal *term) 649initialize_w32_display (struct terminal *term)
571{ 650{
572 CONSOLE_SCREEN_BUFFER_INFO info; 651 CONSOLE_SCREEN_BUFFER_INFO info;
652 Mouse_HLInfo *hlinfo;
573 653
574 term->rif = 0; /* No window based redisplay on the console. */ 654 term->rif = 0; /* No window based redisplay on the console. */
575 term->cursor_to_hook = w32con_move_cursor; 655 term->cursor_to_hook = w32con_move_cursor;
@@ -600,6 +680,15 @@ initialize_w32_display (struct terminal *term)
600 term->judge_scroll_bars_hook = 0; 680 term->judge_scroll_bars_hook = 0;
601 term->frame_up_to_date_hook = 0; 681 term->frame_up_to_date_hook = 0;
602 682
683 /* Initialize the mouse-highlight data. */
684 hlinfo = &term->display_info.tty->mouse_highlight;
685 hlinfo->mouse_face_beg_row = hlinfo->mouse_face_beg_col = -1;
686 hlinfo->mouse_face_end_row = hlinfo->mouse_face_end_col = -1;
687 hlinfo->mouse_face_face_id = DEFAULT_FACE_ID;
688 hlinfo->mouse_face_mouse_frame = NULL;
689 hlinfo->mouse_face_window = Qnil;
690 hlinfo->mouse_face_hidden = 0;
691
603 /* Initialize interrupt_handle. */ 692 /* Initialize interrupt_handle. */
604 init_crit (); 693 init_crit ();
605 694
diff --git a/src/w32inevt.c b/src/w32inevt.c
index e7a8bf629d6..a85fdbbe435 100644
--- a/src/w32inevt.c
+++ b/src/w32inevt.c
@@ -35,8 +35,10 @@ along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */
35#include "keyboard.h" 35#include "keyboard.h"
36#include "frame.h" 36#include "frame.h"
37#include "dispextern.h" 37#include "dispextern.h"
38#include "window.h"
38#include "blockinput.h" 39#include "blockinput.h"
39#include "termhooks.h" 40#include "termhooks.h"
41#include "termchar.h"
40#include "w32heap.h" 42#include "w32heap.h"
41#include "w32term.h" 43#include "w32term.h"
42 44
@@ -566,7 +568,7 @@ w32_console_mouse_position (FRAME_PTR *f,
566static void 568static void
567mouse_moved_to (int x, int y) 569mouse_moved_to (int x, int y)
568{ 570{
569 /* If we're in the same place, ignore it */ 571 /* If we're in the same place, ignore it. */
570 if (x != movement_pos.X || y != movement_pos.Y) 572 if (x != movement_pos.X || y != movement_pos.Y)
571 { 573 {
572 SELECTED_FRAME ()->mouse_moved = 1; 574 SELECTED_FRAME ()->mouse_moved = 1;
@@ -599,14 +601,63 @@ do_mouse_event (MOUSE_EVENT_RECORD *event,
599 struct input_event *emacs_ev) 601 struct input_event *emacs_ev)
600{ 602{
601 static DWORD button_state = 0; 603 static DWORD button_state = 0;
604 static Lisp_Object last_mouse_window;
602 DWORD but_change, mask; 605 DWORD but_change, mask;
603 int i; 606 int i;
604 607
605 if (event->dwEventFlags == MOUSE_MOVED) 608 if (event->dwEventFlags == MOUSE_MOVED)
606 { 609 {
607 /* For movement events we just note that the mouse has moved 610 FRAME_PTR f = SELECTED_FRAME ();
608 so that emacs will generate drag events. */ 611 Mouse_HLInfo *hlinfo = MOUSE_HL_INFO (f);
609 mouse_moved_to (event->dwMousePosition.X, event->dwMousePosition.Y); 612 int mx = event->dwMousePosition.X, my = event->dwMousePosition.Y;
613
614 mouse_moved_to (mx, my);
615
616 if (f->mouse_moved)
617 {
618 if (hlinfo->mouse_face_hidden)
619 {
620 hlinfo->mouse_face_hidden = 0;
621 clear_mouse_face (hlinfo);
622 }
623
624 /* Generate SELECT_WINDOW_EVENTs when needed. */
625 if (!NILP (Vmouse_autoselect_window))
626 {
627 Lisp_Object mouse_window = window_from_coordinates (f, mx, my,
628 0, 0);
629 /* A window will be selected only when it is not
630 selected now, and the last mouse movement event was
631 not in it. A minibuffer window will be selected iff
632 it is active. */
633 if (WINDOWP (mouse_window)
634 && !EQ (mouse_window, last_mouse_window)
635 && !EQ (mouse_window, selected_window))
636 {
637 struct input_event event;
638
639 EVENT_INIT (event);
640 event.kind = SELECT_WINDOW_EVENT;
641 event.frame_or_window = mouse_window;
642 event.arg = Qnil;
643 event.timestamp = movement_time;
644 kbd_buffer_store_event (&event);
645 }
646 last_mouse_window = mouse_window;
647 }
648 else
649 last_mouse_window = Qnil;
650
651 previous_help_echo_string = help_echo_string;
652 help_echo_string = help_echo_object = help_echo_window = Qnil;
653 help_echo_pos = -1;
654 note_mouse_highlight (f, mx, my);
655 /* If the contents of the global variable help_echo has
656 changed (inside note_mouse_highlight), generate a HELP_EVENT. */
657 if (!NILP (help_echo_string) || !NILP (previous_help_echo_string))
658 gen_help_event (help_echo_string, selected_frame, help_echo_window,
659 help_echo_object, help_echo_pos);
660 }
610 return 0; 661 return 0;
611 } 662 }
612 663
diff --git a/src/xdisp.c b/src/xdisp.c
index 0a25eab1cbc..794355af153 100644
--- a/src/xdisp.c
+++ b/src/xdisp.c
@@ -25832,7 +25832,7 @@ draw_row_with_mouse_face (struct window *w, int start_x, struct glyph_row *row,
25832 return; 25832 return;
25833 } 25833 }
25834#endif 25834#endif
25835#if defined (HAVE_GPM) || defined (MSDOS) 25835#if defined (HAVE_GPM) || defined (MSDOS) || defined (WINDOWSNT)
25836 tty_draw_row_with_mouse_face (w, row, start_hpos, end_hpos, draw); 25836 tty_draw_row_with_mouse_face (w, row, start_hpos, end_hpos, draw);
25837#endif 25837#endif
25838} 25838}