ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/rxvt-unicode/src/command.C
(Generate patch)

Comparing rxvt-unicode/src/command.C (file contents):
Revision 1.44 by pcg, Fri Feb 13 12:17:07 2004 UTC vs.
Revision 1.59 by pcg, Wed Feb 25 15:39:48 2004 UTC

25 * - extensive modifications 25 * - extensive modifications
26 * Copyright (c) 1998 Alfredo K. Kojima <kojima@windowmaker.org> 26 * Copyright (c) 1998 Alfredo K. Kojima <kojima@windowmaker.org>
27 * Copyright (c) 2001 Marius Gedminas 27 * Copyright (c) 2001 Marius Gedminas
28 * - Ctrl/Mod4+Tab works like Meta+Tab (options) 28 * - Ctrl/Mod4+Tab works like Meta+Tab (options)
29 * Copyright (c) 2003 Rob McMullen <robm@flipturn.org> 29 * Copyright (c) 2003 Rob McMullen <robm@flipturn.org>
30 * Copyright (c) 2003-2004 Marc Lehmann <pcg@goof.com>
30 * 31 *
31 * This program is free software; you can redistribute it and/or modify 32 * This program is free software; you can redistribute it and/or modify
32 * it under the terms of the GNU General Public License as published by 33 * it under the terms of the GNU General Public License as published by
33 * the Free Software Foundation; either version 2 of the License, or 34 * the Free Software Foundation; either version 2 of the License, or
34 * (at your option) any later version. 35 * (at your option) any later version.
55 56
56/*{{{ Convert the keypress event into a string */ 57/*{{{ Convert the keypress event into a string */
57void 58void
58rxvt_term::lookup_key (XKeyEvent &ev) 59rxvt_term::lookup_key (XKeyEvent &ev)
59{ 60{
60 int ctrl, meta, shft, len; 61 int ctrl, meta, shft, len;
61 unsigned int newlen; 62 unsigned int newlen;
62 KeySym keysym; 63 KeySym keysym;
63#ifdef DEBUG_CMD 64#ifdef DEBUG_CMD
64 static int debug_key = 1; /* accessible by a debugger only */ 65 static int debug_key = 1; /* accessible by a debugger only */
65#endif 66#endif
66 int valid_keysym; 67 int valid_keysym;
67 unsigned char kbuf[KBUFSZ]; 68 unsigned char kbuf[KBUFSZ];
68 69
69 /* 70 /*
70 * use Num_Lock to toggle Keypad on/off. If Num_Lock is off, allow an 71 * use Num_Lock to toggle Keypad on/off. If Num_Lock is off, allow an
71 * escape sequence to toggle the Keypad. 72 * escape sequence to toggle the Keypad.
88 if (Input_Context) 89 if (Input_Context)
89 { 90 {
90 Status status_return; 91 Status status_return;
91 92
92#ifdef X_HAVE_UTF8_STRING 93#ifdef X_HAVE_UTF8_STRING
93 if (enc_utf8 && 0) 94 if (enc_utf8 && 0) // currently disabled, doesn't seem to work, nor is useful
94 len = Xutf8LookupString (Input_Context, &ev, (char *)kbuf, 95 len = Xutf8LookupString (Input_Context, &ev, (char *)kbuf,
95 KBUFSZ, &keysym, &status_return); 96 KBUFSZ, &keysym, &status_return);
96 else 97 else
97#endif 98#endif
98
99 { 99 {
100 wchar_t wkbuf[KBUFSZ + 1]; 100 wchar_t wkbuf[KBUFSZ + 1];
101 101
102 // the XOpenIM manpage lies about hardcoding the locale 102 // the XOpenIM manpage lies about hardcoding the locale
103 // at the point of XOpenIM, so temporarily switch locales 103 // at the point of XOpenIM, so temporarily switch locales
108 KBUFSZ, &keysym, &status_return); 108 KBUFSZ, &keysym, &status_return);
109 if (rs[Rs_imLocale]) 109 if (rs[Rs_imLocale])
110 SET_LOCALE (locale); 110 SET_LOCALE (locale);
111 111
112 if (status_return == XLookupChars 112 if (status_return == XLookupChars
113 || status_return == XLookupBoth) 113 || status_return == XLookupBoth)
114 { 114 {
115 /* make sure the user can type ctrl-@, i.e. NUL */
116 if (len == 1 && *wkbuf == 0)
117 {
118 kbuf[0] = 0;
119 len = 1;
120 }
121 else
122 {
115 wkbuf[len] = 0; 123 wkbuf[len] = 0;
116 len = wcstombs ((char *)kbuf, wkbuf, KBUFSZ); 124 len = wcstombs ((char *)kbuf, wkbuf, KBUFSZ);
117 if (len < 0) 125 if (len < 0)
118 len = 0; 126 len = 0;
127 }
119 } 128 }
120 else 129 else
121 len = 0; 130 len = 0;
122 } 131 }
123 132
124 valid_keysym = status_return == XLookupKeySym 133 valid_keysym = status_return == XLookupKeySym
125 || status_return == XLookupBoth; 134 || status_return == XLookupBoth;
126 } 135 }
127 else 136 else
128#endif 137#endif
129
130 { 138 {
131 len = XLookupString (&ev, (char *)kbuf, KBUFSZ, &keysym, &compose); 139 len = XLookupString (&ev, (char *)kbuf, KBUFSZ, &keysym, &compose);
132 valid_keysym = !len; 140 valid_keysym = keysym != NoSymbol;
133 } 141 }
134 142
135 if (valid_keysym) 143 if (valid_keysym)
136 { 144 {
137 /* for some backwards compatibility */ 145 /* for some backwards compatibility */
142 if (meta) 150 if (meta)
143# endif 151# endif
144 { 152 {
145 if (keysym == ks_bigfont) 153 if (keysym == ks_bigfont)
146 { 154 {
147 change_font (0, FONT_UP); 155 change_font (FONT_UP);
148 return; 156 return;
149 } 157 }
150 else if (keysym == ks_smallfont) 158 else if (keysym == ks_smallfont)
151 { 159 {
152 change_font (0, FONT_DN); 160 change_font (FONT_DN);
153 return; 161 return;
154 } 162 }
155 } 163 }
156#endif 164#endif
157 165
162 { 170 {
163#else 171#else
164 if (IS_SCROLL_MOD) 172 if (IS_SCROLL_MOD)
165 { 173 {
166#endif 174#endif
167 int lnsppg; 175 int lnsppg;
168 176
169#ifdef PAGING_CONTEXT_LINES 177#ifdef PAGING_CONTEXT_LINES
170 lnsppg = TermWin.nrow - PAGING_CONTEXT_LINES; 178 lnsppg = TermWin.nrow - PAGING_CONTEXT_LINES;
171#else 179#else
172 lnsppg = TermWin.nrow * 4 / 5; 180 lnsppg = TermWin.nrow * 4 / 5;
210 scr_move_to (1, 0); 218 scr_move_to (1, 0);
211 return; 219 return;
212 } 220 }
213 } 221 }
214#endif 222#endif
215
216 } 223 }
217 224
218 if (shft) 225 if (shft)
219 { 226 {
220 /* Shift + F1 - F10 generates F11 - F20 */ 227 /* Shift + F1 - F10 generates F11 - F20 */
231 case XK_Insert: /* Shift+Insert = paste mouse selection */ 238 case XK_Insert: /* Shift+Insert = paste mouse selection */
232 selection_request (ev.time, 0, 0); 239 selection_request (ev.time, 0, 0);
233 return; 240 return;
234 /* rxvt extras */ 241 /* rxvt extras */
235 case XK_KP_Add: /* Shift+KP_Add = bigger font */ 242 case XK_KP_Add: /* Shift+KP_Add = bigger font */
236 change_font (0, FONT_UP); 243 change_font (FONT_UP);
237 return; 244 return;
238 case XK_KP_Subtract: /* Shift+KP_Subtract = smaller font */ 245 case XK_KP_Subtract: /* Shift+KP_Subtract = smaller font */
239 change_font (0, FONT_DN); 246 change_font (FONT_DN);
240 return; 247 return;
241 } 248 }
242 } 249 }
243 } 250 }
244#ifdef PRINTPIPE 251#ifdef PRINTPIPE
245 if (keysym == XK_Print) 252 if (keysym == XK_Print)
246 { 253 {
247 scr_printscreen (ctrl | shft); 254 scr_printscreen (ctrl | shft);
248 return;
249 }
250#endif
251#ifdef GREEK_SUPPORT
252 if (keysym == ks_greekmodeswith)
253 {
254 greek_mode = !greek_mode;
255 if (greek_mode)
256 {
257 xterm_seq (XTerm_title,
258 (greek_getmode () == GREEK_ELOT928
259 ? "[Greek: iso]" : "[Greek: ibm]"), CHAR_ST);
260 greek_reset ();
261 }
262 else
263 xterm_seq (XTerm_title, APL_NAME "-" VERSION, CHAR_ST);
264 return; 255 return;
265 } 256 }
266#endif 257#endif
267 258
268 if (keysym >= 0xFF00 && keysym <= 0xFFFF) 259 if (keysym >= 0xFF00 && keysym <= 0xFFFF)
286 tt_write (kbuf0, l); 277 tt_write (kbuf0, l);
287 return; 278 return;
288 } 279 }
289 else 280 else
290#endif 281#endif
291
292 { 282 {
293 newlen = 1; 283 newlen = 1;
294 switch (keysym) 284 switch (keysym)
295 { 285 {
296#ifndef NO_BACKSPACE_KEY 286#ifndef NO_BACKSPACE_KEY
349#endif 339#endif
350 newlen = 0; 340 newlen = 0;
351 } 341 }
352 break; 342 break;
353 343
354
355#ifdef XK_KP_Left 344#ifdef XK_KP_Left
356 case XK_KP_Up: /* \033Ox or standard */ 345 case XK_KP_Up: /* \033Ox or standard */
357 case XK_KP_Down: /* \033Or or standard */ 346 case XK_KP_Down: /* \033Or or standard */
358 case XK_KP_Right: /* \033Ov or standard */ 347 case XK_KP_Right: /* \033Ov or standard */
359 case XK_KP_Left: /* \033Ot or standard */ 348 case XK_KP_Left: /* \033Ot or standard */
360 if ((PrivateModes & PrivMode_aplKP) ? !shft : shft) 349 if ((PrivateModes & PrivMode_aplKP) ? !shft : shft)
361 { 350 {
362 STRCPY (kbuf, "\033OZ"); 351 STRCPY (kbuf, "\033OZ");
363 kbuf[2] = ("txvr"[keysym - XK_KP_Left]); 352 kbuf[2] = "txvr"[keysym - XK_KP_Left];
364 break; 353 break;
365 } 354 }
366 else 355 else
367 /* translate to std. cursor key */ 356 /* translate to std. cursor key */
368 keysym = XK_Left + (keysym - XK_KP_Left); 357 keysym = XK_Left + (keysym - XK_KP_Left);
371 case XK_Up: /* "\033[A" */ 360 case XK_Up: /* "\033[A" */
372 case XK_Down: /* "\033[B" */ 361 case XK_Down: /* "\033[B" */
373 case XK_Right: /* "\033[C" */ 362 case XK_Right: /* "\033[C" */
374 case XK_Left: /* "\033[D" */ 363 case XK_Left: /* "\033[D" */
375 STRCPY (kbuf, "\033[Z"); 364 STRCPY (kbuf, "\033[Z");
376 kbuf[2] = ("DACB"[keysym - XK_Left]); 365 kbuf[2] = "DACB"[keysym - XK_Left];
377 /* do Shift first */ 366 /* do Shift first */
378 if (shft) 367 if (shft)
379 kbuf[2] = ("dacb"[keysym - XK_Left]); 368 kbuf[2] = "dacb"[keysym - XK_Left];
380 else if (ctrl) 369 else if (ctrl)
381 { 370 {
382 kbuf[1] = 'O'; 371 kbuf[1] = 'O';
383 kbuf[2] = ("dacb"[keysym - XK_Left]); 372 kbuf[2] = "dacb"[keysym - XK_Left];
384 } 373 }
385 else if (PrivateModes & PrivMode_aplCUR) 374 else if (PrivateModes & PrivMode_aplCUR)
386 kbuf[1] = 'O'; 375 kbuf[1] = 'O';
387#ifdef MULTICHAR_SET 376#ifdef MULTICHAR_SET
388 //TODO: ?? 377 //TODO: ??
482 STRCPY (kbuf, "\033OP"); 471 STRCPY (kbuf, "\033OP");
483 kbuf[2] += (keysym - XK_KP_F1); 472 kbuf[2] += (keysym - XK_KP_F1);
484 break; 473 break;
485 474
486 case XK_KP_Multiply: /* "\033Oj" : "*" */ 475 case XK_KP_Multiply: /* "\033Oj" : "*" */
487 case XK_KP_Add: /* "\033Ok" : "+" */ 476 case XK_KP_Add: /* "\033Ok" : "+" */
488 case XK_KP_Separator: /* "\033Ol" : "," */ 477 case XK_KP_Separator: /* "\033Ol" : "," */
489 case XK_KP_Subtract: /* "\033Om" : "-" */ 478 case XK_KP_Subtract: /* "\033Om" : "-" */
490 case XK_KP_Decimal: /* "\033On" : "." */ 479 case XK_KP_Decimal: /* "\033On" : "." */
491 case XK_KP_Divide: /* "\033Oo" : "/" */ 480 case XK_KP_Divide: /* "\033Oo" : "/" */
492 case XK_KP_0: /* "\033Op" : "0" */ 481 case XK_KP_0: /* "\033Op" : "0" */
642 for (ch = kbuf; ch < kbuf + len; ch++) 631 for (ch = kbuf; ch < kbuf + len; ch++)
643 *ch |= 0x80; 632 *ch |= 0x80;
644 meta = 0; 633 meta = 0;
645 } 634 }
646#endif 635#endif
647#ifdef GREEK_SUPPORT
648 if (greek_mode)
649 len = greek_xlat (kbuf, len);
650#endif
651 /* nil */ ; 636 /* nil */ ;
652 } 637 }
653 } 638 }
654 639
655 if (len <= 0) 640 if (len <= 0)
677 kbuf[len - 1] = (shft ? (ctrl ? '@' : '$') : (ctrl ? '^' : '~')); 662 kbuf[len - 1] = (shft ? (ctrl ? '@' : '$') : (ctrl ? '^' : '~'));
678 663
679 /* escape prefix */ 664 /* escape prefix */
680 if (meta 665 if (meta
681#ifdef META8_OPTION 666#ifdef META8_OPTION
682 && (meta_char == C0_ESC) 667 && meta_char == C0_ESC
683#endif 668#endif
684 ) 669 )
685 { 670 {
686 const unsigned char ch = C0_ESC; 671 const unsigned char ch = C0_ESC;
687
688 tt_write (&ch, 1); 672 tt_write (&ch, 1);
689 } 673 }
674
690#ifdef DEBUG_CMD 675#if defined(DEBUG_CMD)
691 if (debug_key)
692 { /* Display keyboard buffer contents */ 676 /* Display keyboard buffer contents */
693 char *p; 677 unsigned char *p;
694 int i; 678 int i;
695 679
696 fprintf (stderr, "key 0x%04X [%d]: `", (unsigned int)keysym, len); 680 fprintf (stderr, "key 0x%04X [%d]: `", (unsigned int)keysym, len);
697 for (i = 0, p = kbuf; i < len; i++, p++) 681 for (i = 0, p = kbuf; i < len; i++, p++)
698 fprintf (stderr, (*p >= ' ' && *p < '\177' ? "%c" : "\\%03o"), *p); 682 fprintf (stderr, (*p >= ' ' && *p < '\177' ? "%c" : "\\%03o"), *p);
699 fprintf (stderr, "'\n"); 683 fprintf (stderr, "'\n");
700 }
701#endif /* DEBUG_CMD */ 684#endif /* DEBUG_CMD */
702 tt_write (kbuf, (unsigned int)len); 685 tt_write (kbuf, (unsigned int)len);
703} 686}
704/*}}} */ 687/*}}} */
705 688
711{ 694{
712 unsigned int n, s; 695 unsigned int n, s;
713 696
714 n = cmdbuf_ptr - cmdbuf_base; 697 n = cmdbuf_ptr - cmdbuf_base;
715 s = cmdbuf_base + BUFSIZ - 1 - cmdbuf_endp; 698 s = cmdbuf_base + BUFSIZ - 1 - cmdbuf_endp;
699
716 if (n > 0 && s < count) 700 if (n > 0 && s < count)
717 { 701 {
718 MEMMOVE (cmdbuf_base, cmdbuf_ptr, 702 MEMMOVE (cmdbuf_base, cmdbuf_ptr,
719 (unsigned int) (cmdbuf_endp - cmdbuf_ptr)); 703 (unsigned int) (cmdbuf_endp - cmdbuf_ptr));
720 cmdbuf_ptr = cmdbuf_base; 704 cmdbuf_ptr = cmdbuf_base;
721 cmdbuf_endp -= n; 705 cmdbuf_endp -= n;
722 s += n; 706 s += n;
723 } 707 }
708
724 if (count > s) 709 if (count > s)
725 { 710 {
726 rxvt_print_error ("data loss: cmd_write too large"); 711 rxvt_print_error ("data loss: cmd_write too large");
727 count = s; 712 count = s;
728 } 713 }
714
729 for (; count--;) 715 for (; count--;)
730 *cmdbuf_endp++ = *str++; 716 *cmdbuf_endp++ = *str++;
717
718 cmd_parse ();
719
731 return 0; 720 return 0;
732} 721}
733#endif /* MENUBAR_MAX */ 722#endif /* MENUBAR_MAX */
734 723
735void 724void
807 cmdbuf_endp += n; 796 cmdbuf_endp += n;
808 return true; 797 return true;
809 } 798 }
810 else if (n < 0 && errno != EAGAIN) 799 else if (n < 0 && errno != EAGAIN)
811 destroy (); 800 destroy ();
812 801
813 return false; 802 return false;
814} 803}
815 804
816void 805void
817rxvt_term::pty_cb (io_watcher &w, short revents) 806rxvt_term::pty_cb (io_watcher &w, short revents)
834 seen_input = 1; 823 seen_input = 1;
835 /* once we know the shell is running, send the screen size. Again! */ 824 /* once we know the shell is running, send the screen size. Again! */
836 tt_winch (); 825 tt_winch ();
837 } 826 }
838 827
828 if (cmd_parse ())
829 break;
830 }
831 }
832}
833
834bool
835rxvt_term::cmd_parse ()
836{
837 bool flag = false;
839 uint32_t ch = NOCHAR; 838 uint32_t ch = NOCHAR;
839
840 for (;;)
841 {
842 if (ch == NOCHAR)
843 ch = next_char ();
844
845 if (ch == NOCHAR) // TODO: improve
846 break;
847
848 if (ch >= ' ' || ch == '\t' || ch == '\n' || ch == '\r')
849 {
850 /* Read a text string from the input buffer */
851 uint32_t buf[BUFSIZ];
852 bool refreshnow = false;
853 int nlines = 0;
854 uint32_t *str = buf;
855
856 *str++ = ch;
840 857
841 for (;;) 858 for (;;)
842 { 859 {
843 if (ch == NOCHAR)
844 ch = next_char (); 860 ch = next_char ();
845 861
846 if (ch == NOCHAR) // TODO: improve 862 if (ch == NOCHAR || (ch < ' ' && ch != '\t' && ch != '\n' && ch != '\r'))
847 break; 863 break;
848 864 else
849 if (ch >= ' ' || ch == '\t' || ch == '\n' || ch == '\r')
850 { 865 {
851 /* Read a text string from the input buffer */
852 uint32_t buf[BUFSIZ];
853 bool refreshnow = false;
854 int nlines = 0;
855 uint32_t *str = buf;
856
857 *str++ = ch; 866 *str++ = ch;
858 867
859 for (;;) 868 if (ch == '\n')
860 { 869 {
861 ch = next_char ();
862
863 if (ch == NOCHAR || (ch < ' ' && ch != '\t' && ch != '\n' && ch != '\r'))
864 break;
865 else 870 nlines++;
871 refresh_count++;
872
873 if (! (Options & Opt_jumpScroll)
874 || (refresh_count >= (refresh_limit * (TermWin.nrow - 1))))
866 { 875 {
867 *str++ = ch;
868
869 if (ch == '\n')
870 {
871 nlines++;
872 refresh_count++;
873
874 if (! (Options & Opt_jumpScroll)
875 || (refresh_count >= (refresh_limit * (TermWin.nrow - 1))))
876 {
877 refreshnow = true; 876 refreshnow = true;
878 flag = false; 877 flag = false;
879 ch = NOCHAR; 878 ch = NOCHAR;
880 break; 879 break;
881 } 880 }
882 881
883 // scr_add_lines only works for nlines < TermWin.nrow - 1. 882 // scr_add_lines only works for nlines < TermWin.nrow - 1.
884 if (nlines >= TermWin.nrow - 1) 883 if (nlines >= TermWin.nrow - 1)
885 { 884 {
886 scr_add_lines (buf, nlines, str - buf); 885 scr_add_lines (buf, nlines, str - buf);
887 nlines = 0; 886 nlines = 0;
888 str = buf; 887 str = buf;
889 }
890 }
891
892 if (str >= buf + BUFSIZ)
893 {
894 ch = NOCHAR;
895 break;
896 }
897 } 888 }
898 } 889 }
899 890
900 scr_add_lines (buf, nlines, str - buf); 891 if (str >= buf + BUFSIZ)
901
902 /*
903 * If there have been a lot of new lines, then update the screen
904 * What the heck I'll cheat and only refresh less than every page-full.
905 * the number of pages between refreshes is refresh_limit, which
906 * is incremented here because we must be doing flat-out scrolling.
907 *
908 * refreshing should be correct for small scrolls, because of the
909 * time-out
910 */
911 if (refreshnow)
912 { 892 {
913 if ((Options & Opt_jumpScroll) && refresh_limit < REFRESH_PERIOD) 893 ch = NOCHAR;
914 refresh_limit++; 894 break;
915
916 scr_refresh (refresh_type);
917 } 895 }
918
919 }
920 else
921 {
922 switch (ch)
923 {
924 default:
925 process_nonprinting (ch);
926 break;
927 case C0_ESC: /* escape char */
928 process_escape_seq ();
929 break;
930 /*case 0x9b: */ /* CSI */
931 /* process_csi_seq (); */
932 }
933
934 ch = NOCHAR;
935 } 896 }
936 } 897 }
898
899 scr_add_lines (buf, nlines, str - buf);
900
901 /*
902 * If there have been a lot of new lines, then update the screen
903 * What the heck I'll cheat and only refresh less than every page-full.
904 * the number of pages between refreshes is refresh_limit, which
905 * is incremented here because we must be doing flat-out scrolling.
906 *
907 * refreshing should be correct for small scrolls, because of the
908 * time-out
909 */
910 if (refreshnow)
911 {
912 if ((Options & Opt_jumpScroll) && refresh_limit < REFRESH_PERIOD)
913 refresh_limit++;
914
915 scr_refresh (refresh_type);
916 }
917
918 }
919 else
937 } 920 {
921 switch (ch)
922 {
923 default:
924 process_nonprinting (ch);
925 break;
926 case C0_ESC: /* escape char */
927 process_escape_seq ();
928 break;
929 /*case 0x9b: */ /* CSI */
930 /* process_csi_seq (); */
931 }
932
933 ch = NOCHAR;
934 }
938 } 935 }
936
937 return flag;
939} 938}
940 939
941// read the next character, currently handles UTF-8 940// read the next character, currently handles UTF-8
942// will probably handle all sorts of other stuff in the future 941// will probably handle all sorts of other stuff in the future
943uint32_t 942uint32_t
947 { 946 {
948 if (*cmdbuf_ptr < 0x80) // assume < 0x80 to be ascii ALWAYS (all shift-states etc.) uh-oh 947 if (*cmdbuf_ptr < 0x80) // assume < 0x80 to be ascii ALWAYS (all shift-states etc.) uh-oh
949 return *cmdbuf_ptr++; 948 return *cmdbuf_ptr++;
950 949
951 wchar_t wc; 950 wchar_t wc;
952 size_t len = mbrtowc (&wc, (char *)cmdbuf_ptr, cmdbuf_endp - cmdbuf_ptr, &mbstate.mbs); 951 size_t len = mbrtowc (&wc, (char *)cmdbuf_ptr, cmdbuf_endp - cmdbuf_ptr, mbstate);
953 952
954 if (len == (size_t)-2) 953 if (len == (size_t)-2)
955 return NOCHAR; 954 return NOCHAR;
956 955
957 if (len == (size_t)-1) 956 if (len == (size_t)-1)
1021 pointer_blank (); 1020 pointer_blank ();
1022} 1021}
1023#endif 1022#endif
1024 1023
1025void 1024void
1026rxvt_term::mouse_report (const XButtonEvent &ev) 1025rxvt_term::mouse_report (XButtonEvent &ev)
1027{ 1026{
1028 int button_number, key_state = 0; 1027 int button_number, key_state = 0;
1029 int x, y; 1028 int x, y;
1030 1029
1031 x = ev.x; 1030 x = ev.x;
1032 y = ev.y; 1031 y = ev.y;
1033 pixel_position (&x, &y); 1032 pixel_position (&x, &y);
1034 1033
1428 } 1427 }
1429#ifdef MENUBAR 1428#ifdef MENUBAR
1430 if (menubar_visible () && isMenuBarWindow (ev.xany.window)) 1429 if (menubar_visible () && isMenuBarWindow (ev.xany.window))
1431 menubar_expose (); 1430 menubar_expose ();
1432#endif 1431#endif
1433#ifdef RXVT_GRAPHICS
1434 Gr_expose (ev.xany.window);
1435#endif
1436
1437 } 1432 }
1438 break; 1433 break;
1439 1434
1440 case MotionNotify: 1435 case MotionNotify:
1441#ifdef POINTER_BLANK 1436#ifdef POINTER_BLANK
1443 pointer_unblank (); 1438 pointer_unblank ();
1444#endif 1439#endif
1445#if MENUBAR 1440#if MENUBAR
1446 if (isMenuBarWindow (ev.xany.window)) 1441 if (isMenuBarWindow (ev.xany.window))
1447 { 1442 {
1448 menubar_control (& (ev.xbutton)); 1443 menubar_control (ev.xbutton);
1449 break; 1444 break;
1450 } 1445 }
1451#endif 1446#endif
1452 if ((PrivateModes & PrivMode_mouse_report) && ! (bypass_keystate)) 1447 if ((PrivateModes & PrivMode_mouse_report) && ! (bypass_keystate))
1453 break; 1448 break;
1582#endif 1577#endif
1583 } 1578 }
1584} 1579}
1585 1580
1586void 1581void
1587rxvt_term::button_press (const XButtonEvent &ev) 1582rxvt_term::button_press (XButtonEvent &ev)
1588{ 1583{
1589 int reportmode = 0, clickintime; 1584 int reportmode = 0, clickintime;
1590 1585
1591 bypass_keystate = ev.state & (ModMetaMask | ShiftMask); 1586 bypass_keystate = ev.state & (ModMetaMask | ShiftMask);
1592 if (!bypass_keystate) 1587 if (!bypass_keystate)
1594 /* 1589 /*
1595 * VT window processing of button press 1590 * VT window processing of button press
1596 */ 1591 */
1597 if (ev.window == TermWin.vt) 1592 if (ev.window == TermWin.vt)
1598 { 1593 {
1599#if RXVT_GRAPHICS
1600 if (ev.subwindow != None)
1601 rxvt_Gr_ButtonPress (ev.x, ev.y);
1602 else
1603#endif
1604
1605 {
1606 clickintime = ev.time - MEvent.time < MULTICLICK_TIME; 1594 clickintime = ev.time - MEvent.time < MULTICLICK_TIME;
1607 if (reportmode) 1595 if (reportmode)
1596 {
1597 /* mouse report from vt window */
1598 /* save the xbutton state (for ButtonRelease) */
1599 MEvent.state = ev.state;
1600#ifdef MOUSE_REPORT_DOUBLECLICK
1601 if (ev.button == MEvent.button && clickintime)
1608 { 1602 {
1609 /* mouse report from vt window */ 1603 /* same button, within alloted time */
1610 /* save the xbutton state (for ButtonRelease) */ 1604 MEvent.clicks++;
1611 MEvent.state = ev.state; 1605 if (MEvent.clicks > 1)
1612#ifdef MOUSE_REPORT_DOUBLECLICK
1613 if (ev.button == MEvent.button && clickintime)
1614 { 1606 {
1615 /* same button, within alloted time */
1616 MEvent.clicks++;
1617 if (MEvent.clicks > 1)
1618 {
1619 /* only report double clicks */ 1607 /* only report double clicks */
1620 MEvent.clicks = 2; 1608 MEvent.clicks = 2;
1621 mouse_report (ev); 1609 mouse_report (ev);
1622 1610
1623 /* don't report the release */ 1611 /* don't report the release */
1624 MEvent.clicks = 0; 1612 MEvent.clicks = 0;
1625 MEvent.button = AnyButton; 1613 MEvent.button = AnyButton;
1626 }
1627 } 1614 }
1628 else
1629 {
1630 /* different button, or time expired */
1631 MEvent.clicks = 1;
1632 MEvent.button = ev.button;
1633 mouse_report (ev);
1634 }
1635#else
1636 MEvent.button = ev.button;
1637 mouse_report (ev);
1638#endif /* MOUSE_REPORT_DOUBLECLICK */
1639
1640 } 1615 }
1641 else 1616 else
1642 { 1617 {
1618 /* different button, or time expired */
1619 MEvent.clicks = 1;
1620 MEvent.button = ev.button;
1621 mouse_report (ev);
1622 }
1623#else
1624 MEvent.button = ev.button;
1625 mouse_report (ev);
1626#endif /* MOUSE_REPORT_DOUBLECLICK */
1627
1628 }
1629 else
1630 {
1643 if (ev.button != MEvent.button) 1631 if (ev.button != MEvent.button)
1644 MEvent.clicks = 0; 1632 MEvent.clicks = 0;
1645 switch (ev.button) 1633 switch (ev.button)
1646 { 1634 {
1647 case Button1: 1635 case Button1:
1648 /* allow shift+left click to extend selection */ 1636 /* allow shift+left click to extend selection */
1649 if (ev.state & ShiftMask && ! (PrivateModes & PrivMode_mouse_report)) 1637 if (ev.state & ShiftMask && ! (PrivateModes & PrivMode_mouse_report))
1650 { 1638 {
1651 if (MEvent.button == Button1 && clickintime)
1652 selection_rotate (ev.x, ev.y);
1653 else
1654 selection_extend (ev.x, ev.y, 1);
1655 }
1656 else
1657 {
1658 if (MEvent.button == Button1 && clickintime)
1659 MEvent.clicks++;
1660 else
1661 MEvent.clicks = 1;
1662
1663 selection_click (MEvent.clicks, ev.x, ev.y);
1664 }
1665
1666 MEvent.button = Button1;
1667 break;
1668
1669 case Button3:
1670 if (MEvent.button == Button3 && clickintime) 1639 if (MEvent.button == Button1 && clickintime)
1671 selection_rotate (ev.x, ev.y); 1640 selection_rotate (ev.x, ev.y);
1672 else 1641 else
1673 selection_extend (ev.x, ev.y, 1); 1642 selection_extend (ev.x, ev.y, 1);
1643 }
1644 else
1645 {
1646 if (MEvent.button == Button1 && clickintime)
1647 MEvent.clicks++;
1648 else
1649 MEvent.clicks = 1;
1650
1651 selection_click (MEvent.clicks, ev.x, ev.y);
1652 }
1653
1654 MEvent.button = Button1;
1655 break;
1656
1657 case Button3:
1658 if (MEvent.button == Button3 && clickintime)
1659 selection_rotate (ev.x, ev.y);
1660 else
1661 selection_extend (ev.x, ev.y, 1);
1674 MEvent.button = Button3; 1662 MEvent.button = Button3;
1675 break; 1663 break;
1676 }
1677 } 1664 }
1665 }
1678 MEvent.time = ev.time; 1666 MEvent.time = ev.time;
1679 return; 1667 return;
1680 }
1681 } 1668 }
1682 1669
1683 /* 1670 /*
1684 * Scrollbar window processing of button press 1671 * Scrollbar window processing of button press
1685 */ 1672 */
1828 menubar_control (ev); 1815 menubar_control (ev);
1829#endif 1816#endif
1830} 1817}
1831 1818
1832void 1819void
1833rxvt_term::button_release (const XButtonEvent &ev) 1820rxvt_term::button_release (XButtonEvent &ev)
1834{ 1821{
1835 int reportmode = 0; 1822 int reportmode = 0;
1836 1823
1837 csrO = 0; /* reset csr Offset */ 1824 csrO = 0; /* reset csr Offset */
1838 if (!bypass_keystate) 1825 if (!bypass_keystate)
1850#ifdef SELECTION_SCROLLING 1837#ifdef SELECTION_SCROLLING
1851 pending_scroll_selection=0; 1838 pending_scroll_selection=0;
1852#endif 1839#endif
1853 if (ev.window == TermWin.vt) 1840 if (ev.window == TermWin.vt)
1854 { 1841 {
1855#ifdef RXVT_GRAPHICS
1856 if (ev.subwindow != None)
1857 rxvt_Gr_ButtonRelease (ev.x, ev.y);
1858 else
1859#endif
1860
1861 {
1862 if (reportmode) 1842 if (reportmode)
1843 {
1844 /* mouse report from vt window */
1845 /* don't report release of wheel "buttons" */
1846 if (ev.button >= 4)
1847 return;
1848#ifdef MOUSE_REPORT_DOUBLECLICK
1849 /* only report the release of 'slow' single clicks */
1850 if (MEvent.button != AnyButton
1851 && (ev.button != MEvent.button
1852 || (ev.time - MEvent.time
1853 > MULTICLICK_TIME / 2)))
1863 { 1854 {
1864 /* mouse report from vt window */
1865 /* don't report release of wheel "buttons" */
1866 if (ev.button >= 4)
1867 return;
1868#ifdef MOUSE_REPORT_DOUBLECLICK
1869 /* only report the release of 'slow' single clicks */
1870 if (MEvent.button != AnyButton
1871 && (ev.button != MEvent.button
1872 || (ev.time - MEvent.time
1873 > MULTICLICK_TIME / 2)))
1874 {
1875 MEvent.clicks = 0; 1855 MEvent.clicks = 0;
1876 MEvent.button = AnyButton;
1877 mouse_report (ev);
1878 }
1879#else /* MOUSE_REPORT_DOUBLECLICK */
1880 MEvent.button = AnyButton; 1856 MEvent.button = AnyButton;
1881 mouse_report (ev); 1857 mouse_report (ev);
1858 }
1859#else /* MOUSE_REPORT_DOUBLECLICK */
1860 MEvent.button = AnyButton;
1861 mouse_report (ev);
1882#endif /* MOUSE_REPORT_DOUBLECLICK */ 1862#endif /* MOUSE_REPORT_DOUBLECLICK */
1883 return; 1863 return;
1884 } 1864 }
1885 /* 1865 /*
1886 * dumb hack to compensate for the failure of click-and-drag 1866 * dumb hack to compensate for the failure of click-and-drag
1887 * when overriding mouse reporting 1867 * when overriding mouse reporting
1888 */ 1868 */
1889 if (PrivateModes & PrivMode_mouse_report 1869 if (PrivateModes & PrivMode_mouse_report
1890 && bypass_keystate 1870 && bypass_keystate
1891 && ev.button == Button1 && MEvent.clicks <= 1) 1871 && ev.button == Button1 && MEvent.clicks <= 1)
1892 selection_extend (ev.x, ev.y, 0); 1872 selection_extend (ev.x, ev.y, 0);
1893 1873
1894 switch (ev.button) 1874 switch (ev.button)
1875 {
1876 case Button1:
1877 case Button3:
1878 selection_make (ev.time);
1879 break;
1880 case Button2:
1881 selection_request (ev.time, ev.x, ev.y);
1882 break;
1883#ifdef MOUSE_WHEEL
1884 case Button4:
1885 case Button5:
1895 { 1886 {
1896 case Button1: 1887 int i;
1897 case Button3: 1888 page_dirn v;
1898 selection_make (ev.time); 1889
1890 v = (ev.button == Button4) ? UP : DN;
1891 if (ev.state & ShiftMask)
1899 break; 1892 i = 1;
1900 case Button2: 1893 else if ((Options & Opt_mouseWheelScrollPage))
1901 selection_request (ev.time, ev.x, ev.y); 1894 i = TermWin.nrow - 1;
1895 else
1902 break; 1896 i = 5;
1903#ifdef MOUSE_WHEEL 1897# ifdef MOUSE_SLIP_WHEELING
1904 case Button4: 1898 if (ev.state & ControlMask)
1905 case Button5:
1906 { 1899 {
1907 int i;
1908 page_dirn v;
1909
1910 v = (ev.button == Button4) ? UP : DN;
1911 if (ev.state & ShiftMask)
1912 i = 1;
1913 else if ((Options & Opt_mouseWheelScrollPage))
1914 i = TermWin.nrow - 1;
1915 else
1916 i = 5;
1917# ifdef MOUSE_SLIP_WHEELING
1918 if (ev.state & ControlMask)
1919 {
1920 mouse_slip_wheel_speed += (v ? -1 : 1); 1900 mouse_slip_wheel_speed += (v ? -1 : 1);
1921 mouse_slip_wheel_delay = SCROLLBAR_CONTINUOUS_DELAY; 1901 mouse_slip_wheel_delay = SCROLLBAR_CONTINUOUS_DELAY;
1922 } 1902 }
1923# endif 1903# endif
1924# ifdef JUMP_MOUSE_WHEEL 1904# ifdef JUMP_MOUSE_WHEEL
1905 scr_page (v, i);
1906 scr_refresh (SMOOTH_REFRESH);
1907 scrollbar_show (1);
1908# else
1909 while (i--)
1910 {
1925 scr_page (v, i); 1911 scr_page (v, 1);
1926 scr_refresh (SMOOTH_REFRESH); 1912 scr_refresh (SMOOTH_REFRESH);
1927 scrollbar_show (1); 1913 scrollbar_show (1);
1928# else
1929 while (i--)
1930 {
1931 scr_page (v, 1);
1932 scr_refresh (SMOOTH_REFRESH);
1933 scrollbar_show (1);
1934 } 1914 }
1935# endif 1915# endif
1936 1916
1937 }
1938 break;
1939#endif
1940
1941 } 1917 }
1918 break;
1919#endif
1920
1942 } 1921 }
1943 } 1922 }
1944#ifdef MENUBAR 1923#ifdef MENUBAR
1945 else if (isMenuBarWindow (ev.window)) 1924 else if (isMenuBarWindow (ev.window))
1946 menubar_control (ev); 1925 menubar_control (ev);
3015 * 19 = change underlined character color 2994 * 19 = change underlined character color
3016 * 46 = change logfile (not implemented) 2995 * 46 = change logfile (not implemented)
3017 * 50 = change font 2996 * 50 = change font
3018 * 2997 *
3019 * rxvt extensions: 2998 * rxvt extensions:
2999 * 9 = change locale (NYI)
3020 * 10 = menu (may change in future) 3000 * 10 = menu (may change in future)
3021 * 20 = bg pixmap 3001 * 20 = bg pixmap
3022 * 39 = change default fg color 3002 * 39 = change default fg color
3023 * 49 = change default bg color 3003 * 49 = change default bg color
3024 * 55 = dump scrollback buffer and all of screen 3004 * 55 = dump scrollback buffer and all of screen
3115 set_window_color (Color_bg, str); 3095 set_window_color (Color_bg, str);
3116 break; 3096 break;
3117 case XTerm_logfile: 3097 case XTerm_logfile:
3118 break; 3098 break;
3119 case XTerm_font: 3099 case XTerm_font:
3120 change_font (0, str); 3100 change_font (str);
3101 break;
3102 case XTerm_locale:
3103 if (str[0] == '?' && !str[1])
3104 tt_printf ("%-.250s\n", locale);
3105 else
3106 {
3107 set_locale (str);
3108 im_cb ();
3109
3110 // TODO: call selection_make with the right values set
3111 // to re-fresh the selection.
3112 if (display->selection_owner == this)
3113 display->set_selection_owner (0);
3114 }
3121 break; 3115 break;
3122#if 0 3116#if 0
3123 case XTerm_dumpscreen: /* no error notices */ 3117 case XTerm_dumpscreen: /* no error notices */
3124 { 3118 {
3125 int fd; 3119 int fd;
3476void 3470void
3477rxvt_term::process_graphics () 3471rxvt_term::process_graphics ()
3478{ 3472{
3479 unsigned char ch, cmd = cmd_getc (); 3473 unsigned char ch, cmd = cmd_getc ();
3480 3474
3481#ifndef RXVT_GRAPHICS
3482 if (cmd == 'Q') 3475 if (cmd == 'Q')
3483 { /* query graphics */ 3476 { /* query graphics */
3484 tt_printf ("\033G0\n"); /* no graphics */ 3477 tt_printf ("\033G0\n"); /* no graphics */
3485 return; 3478 return;
3486 } 3479 }
3487 /* swallow other graphics sequences until terminating ':' */ 3480 /* swallow other graphics sequences until terminating ':' */
3488 do 3481 do
3489 ch = cmd_getc (); 3482 ch = cmd_getc ();
3490 while (ch != ':'); 3483 while (ch != ':');
3491#else
3492 unsigned int nargs;
3493 int args[NGRX_PTS];
3494 unsigned char *text = NULL;
3495
3496 if (cmd == 'Q')
3497 { /* query graphics */
3498 tt_printf ("\033G1\n"); /* yes, graphics (color) */
3499 return;
3500 }
3501 for (nargs = 0; nargs < (sizeof (args) / sizeof (args[0])) - 1;)
3502 {
3503 int neg;
3504
3505 ch = cmd_getc ();
3506 neg = (ch == '-');
3507 if (neg || ch == '+')
3508 ch = cmd_getc ();
3509
3510 for (args[nargs] = 0; isdigit (ch); ch = cmd_getc ())
3511 args[nargs] = args[nargs] * 10 + (ch - '0');
3512 if (neg)
3513 args[nargs] = -args[nargs];
3514
3515 nargs++;
3516 args[nargs] = 0;
3517 if (ch != ';')
3518 break;
3519 }
3520
3521 if ((cmd == 'T') && (nargs >= 5))
3522 {
3523 int i, len = args[4];
3524
3525 text = (unsigned char *)rxvt_malloc ((len + 1) * sizeof (char));
3526
3527 if (text != NULL)
3528 {
3529 for (i = 0; i < len; i++)
3530 text[i] = cmd_getc ();
3531 text[len] = '\0';
3532 }
3533 }
3534 Gr_do_graphics (cmd, nargs, args, text);
3535#endif
3536} 3484}
3537/*}}} */ 3485/*}}} */
3538 3486
3539/* ------------------------------------------------------------------------- */ 3487/* ------------------------------------------------------------------------- */
3540 3488

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines