comparison src/msdos.c @ 28092:ce3bf4da00a9

(vga_installed): New function, code moved from dos_set_window_size. (Qbar, Qcursor_type, outside_cursor): New variables. (syms_of_msdos): Intern and staticpro them. (dos_ttraw) [__DJGPP__ >= 2, !HAVE_X_WINDOWS]: Save the cursor shape used outside Emacs when called for the first time. (dos_ttcooked) [__DJGPP__ >= 2, !HAVE_X_WINDOWS]: Restore the cursor shape used outside Emacs. (msdos_set_cursor_shape, IT_set_cursor_type): New functions. (IT_frame_up_to_date): Call IT_set_cursor_type, in case the cursor type has changed. (IT_set_frame_parameters): Call IT_set_cursor_type if the frame parameters specify the cursor. Make qreverse a global variable (renamed to Qreverse).
author Eli Zaretskii <eliz@gnu.org>
date Sun, 12 Mar 2000 12:32:17 +0000
parents 5b87cdbef5a8
children 4bba3027ae58
comparison
equal deleted inserted replaced
28091:d28d789a8521 28092:ce3bf4da00a9
340 340
341 static clock_t startup_time; 341 static clock_t startup_time;
342 342
343 static int term_setup_done; 343 static int term_setup_done;
344 344
345 static unsigned short outside_cursor;
346
345 /* Similar to the_only_frame. */ 347 /* Similar to the_only_frame. */
346 struct x_output the_only_x_display; 348 struct x_output the_only_x_display;
347 349
348 /* Support for DOS/V (allows Japanese characters to be displayed on 350 /* Support for DOS/V (allows Japanese characters to be displayed on
349 standard, non-Japanese, ATs). Only supported for DJGPP v2 and later. */ 351 standard, non-Japanese, ATs). Only supported for DJGPP v2 and later. */
353 /* Segment and offset of the virtual screen. If 0, DOS/V is NOT loaded. */ 355 /* Segment and offset of the virtual screen. If 0, DOS/V is NOT loaded. */
354 static unsigned short screen_virtual_segment = 0; 356 static unsigned short screen_virtual_segment = 0;
355 static unsigned short screen_virtual_offset = 0; 357 static unsigned short screen_virtual_offset = 0;
356 /* A flag to control how to display unibyte 8-bit characters. */ 358 /* A flag to control how to display unibyte 8-bit characters. */
357 extern int unibyte_display_via_language_environment; 359 extern int unibyte_display_via_language_environment;
360
361 Lisp_Object Qbar;
358 362
359 #if __DJGPP__ > 1 363 #if __DJGPP__ > 1
360 /* Update the screen from a part of relocated DOS/V screen buffer which 364 /* Update the screen from a part of relocated DOS/V screen buffer which
361 begins at OFFSET and includes COUNT characters. */ 365 begins at OFFSET and includes COUNT characters. */
362 static void 366 static void
483 regs.x.ax = 0x1003; 487 regs.x.ax = 0x1003;
484 int86 (0x10, &regs, &regs); 488 int86 (0x10, &regs, &regs);
485 } 489 }
486 } 490 }
487 491
492 /* Return non-zero if the system has a VGA adapter. */
493 static int
494 vga_installed (void)
495 {
496 union REGS regs;
497
498 regs.x.ax = 0x1a00;
499 int86 (0x10, &regs, &regs);
500 if (regs.h.al == 0x1a && regs.h.bl > 5 && regs.h.bl < 13)
501 return 1;
502 return 0;
503 }
504
488 /* Set the screen dimensions so that it can show no less than 505 /* Set the screen dimensions so that it can show no less than
489 ROWS x COLS frame. */ 506 ROWS x COLS frame. */
490 507
491 void 508 void
492 dos_set_window_size (rows, cols) 509 dos_set_window_size (rows, cols)
500 int current_rows = ScreenRows (), current_cols = ScreenCols (); 517 int current_rows = ScreenRows (), current_cols = ScreenCols ();
501 518
502 if (*rows == current_rows && *cols == current_cols) 519 if (*rows == current_rows && *cols == current_cols)
503 return; 520 return;
504 521
505 /* Do we have a VGA? */
506 regs.x.ax = 0x1a00;
507 int86 (0x10, &regs, &regs);
508 if (regs.h.al == 0x1a && regs.h.bl > 5 && regs.h.bl < 13)
509 have_vga = 1;
510
511 mouse_off (); 522 mouse_off ();
523 have_vga = vga_installed ();
512 524
513 /* If the user specified a special video mode for these dimensions, 525 /* If the user specified a special video mode for these dimensions,
514 use that mode. */ 526 use that mode. */
515 sprintf (video_name, "screen-dimensions-%dx%d", *rows, *cols); 527 sprintf (video_name, "screen-dimensions-%dx%d", *rows, *cols);
516 video_mode = XSYMBOL (Fintern_soft (build_string (video_name), 528 video_mode = XSYMBOL (Fintern_soft (build_string (video_name),
652 mouse_get_xy (&x, &y); 664 mouse_get_xy (&x, &y);
653 if (y != new_pos_Y || x < new_pos_X) 665 if (y != new_pos_Y || x < new_pos_X)
654 return; 666 return;
655 667
656 mouse_off (); 668 mouse_off ();
669 }
670
671 #define DEFAULT_CURSOR_START (-1)
672 #define DEFAULT_CURSOR_WIDTH (-1)
673 #define BOX_CURSOR_WIDTH (-32)
674
675 /* Set cursor to begin at scan line START_LINE in the character cell
676 and extend for WIDTH scan lines. Scan lines are counted from top
677 of the character cell, starting from zero. */
678 static void
679 msdos_set_cursor_shape (struct frame *f, int start_line, int width)
680 {
681 #if __DJGPP__ > 1
682 unsigned desired_cursor;
683 __dpmi_regs regs;
684 int max_line, top_line, bot_line;
685
686 /* Avoid the costly BIOS call if F isn't the currently selected
687 frame. Allow for NULL as unconditionally meaning the selected
688 frame. */
689 if (f && f != SELECTED_FRAME())
690 return;
691
692 /* The character cell size in scan lines is stored at 40:85 in the
693 BIOS data area. */
694 max_line = _farpeekw (_dos_ds, 0x485) - 1;
695 switch (max_line)
696 {
697 default: /* this relies on CGA cursor emulation being ON! */
698 case 7:
699 bot_line = 7;
700 break;
701 case 9:
702 bot_line = 9;
703 break;
704 case 13:
705 bot_line = 12;
706 break;
707 case 15:
708 bot_line = 14;
709 break;
710 }
711
712 if (width < 0)
713 {
714 if (width == BOX_CURSOR_WIDTH)
715 {
716 top_line = 0;
717 bot_line = max_line;
718 }
719 else if (start_line != DEFAULT_CURSOR_START)
720 {
721 top_line = start_line;
722 bot_line = top_line - width - 1;
723 }
724 else if (width != DEFAULT_CURSOR_WIDTH)
725 {
726 top_line = 0;
727 bot_line = -1 - width;
728 }
729 else
730 top_line = bot_line + 1;
731 }
732 else if (width == 0)
733 {
734 /* [31, 0] seems to DTRT for all screen sizes. */
735 top_line = 31;
736 bot_line = 0;
737 }
738 else /* WIDTH is positive */
739 {
740 if (start_line != DEFAULT_CURSOR_START)
741 bot_line = start_line;
742 top_line = bot_line - (width - 1);
743 }
744
745 /* If the current cursor shape is already what they want, we are
746 history here. */
747 desired_cursor = ((top_line & 0x1f) << 8) | (bot_line & 0x1f);
748 if (desired_cursor == _farpeekw (_dos_ds, 0x460))
749 return;
750
751 regs.h.ah = 1;
752 regs.x.cx = desired_cursor;
753 __dpmi_int (0x10, &regs);
754 #endif /* __DJGPP__ > 1 */
755 }
756
757 static void
758 IT_set_cursor_type (struct frame *f, Lisp_Object cursor_type)
759 {
760 if (EQ (cursor_type, Qbar))
761 {
762 /* Just BAR means the normal EGA/VGA cursor. */
763 msdos_set_cursor_shape (f, DEFAULT_CURSOR_START, DEFAULT_CURSOR_WIDTH);
764 }
765 else if (CONSP (cursor_type) && EQ (XCAR (cursor_type), Qbar))
766 {
767 Lisp_Object bar_parms = XCDR (cursor_type);
768 int width;
769
770 if (INTEGERP (bar_parms))
771 {
772 /* Feature: negative WIDTH means cursor at the top
773 of the character cell, zero means invisible cursor. */
774 width = XINT (bar_parms);
775 msdos_set_cursor_shape (f, width >= 0 ? DEFAULT_CURSOR_START : 0,
776 width);
777 }
778 else if (CONSP (bar_parms)
779 && INTEGERP (XCAR (bar_parms))
780 && INTEGERP (XCDR (bar_parms)))
781 {
782 int start_line = XINT (XCDR (bar_parms));
783
784 width = XINT (XCAR (bar_parms));
785 msdos_set_cursor_shape (f, start_line, width);
786 }
787 }
788 else
789 /* Treat anything unknown as "box cursor". This includes nil, so
790 that a frame which doesn't specify a cursor type gets a box,
791 which is the default in Emacs. */
792 msdos_set_cursor_shape (f, 0, BOX_CURSOR_WIDTH);
657 } 793 }
658 794
659 static void 795 static void
660 IT_ring_bell (void) 796 IT_ring_bell (void)
661 { 797 {
1754 { 1890 {
1755 highlight = 0; 1891 highlight = 0;
1756 FRAME_X_DISPLAY_INFO (f)->mouse_face_defer = 0; 1892 FRAME_X_DISPLAY_INFO (f)->mouse_face_defer = 0;
1757 } 1893 }
1758 1894
1895 Lisp_Object Qcursor_type;
1896
1759 static void 1897 static void
1760 IT_frame_up_to_date (struct frame *f) 1898 IT_frame_up_to_date (struct frame *f)
1761 { 1899 {
1762 struct display_info *dpyinfo = FRAME_X_DISPLAY_INFO (f); 1900 struct display_info *dpyinfo = FRAME_X_DISPLAY_INFO (f);
1763 1901
1771 dpyinfo->mouse_face_mouse_y); 1909 dpyinfo->mouse_face_mouse_y);
1772 dpyinfo->mouse_face_deferred_gc = 0; 1910 dpyinfo->mouse_face_deferred_gc = 0;
1773 UNBLOCK_INPUT; 1911 UNBLOCK_INPUT;
1774 } 1912 }
1775 1913
1914 /* Set the cursor type to whatever they wanted. */
1915 IT_set_cursor_type (f, Fcdr (Fassq (Qcursor_type, f->param_alist)));
1916
1776 IT_cmgoto (f); /* position cursor when update is done */ 1917 IT_cmgoto (f); /* position cursor when update is done */
1777 } 1918 }
1778 1919
1779 /* Copy LEN glyphs displayed on a single line whose vertical position 1920 /* Copy LEN glyphs displayed on a single line whose vertical position
1780 is YPOS, beginning at horizontal position XFROM to horizontal 1921 is YPOS, beginning at horizontal position XFROM to horizontal
1845 1986
1846 /* This was copied from xfns.c */ 1987 /* This was copied from xfns.c */
1847 1988
1848 Lisp_Object Qbackground_color; 1989 Lisp_Object Qbackground_color;
1849 Lisp_Object Qforeground_color; 1990 Lisp_Object Qforeground_color;
1991 Lisp_Object Qreverse;
1850 extern Lisp_Object Qtitle; 1992 extern Lisp_Object Qtitle;
1851 1993
1852 /* IT_set_terminal_modes is called when emacs is started, 1994 /* IT_set_terminal_modes is called when emacs is started,
1853 resumed, and whenever the screen is redrawn! */ 1995 resumed, and whenever the screen is redrawn! */
1854 1996
2038 int i, j; 2180 int i, j;
2039 Lisp_Object *parms 2181 Lisp_Object *parms
2040 = (Lisp_Object *) alloca (length * sizeof (Lisp_Object)); 2182 = (Lisp_Object *) alloca (length * sizeof (Lisp_Object));
2041 Lisp_Object *values 2183 Lisp_Object *values
2042 = (Lisp_Object *) alloca (length * sizeof (Lisp_Object)); 2184 = (Lisp_Object *) alloca (length * sizeof (Lisp_Object));
2043 Lisp_Object qreverse = intern ("reverse");
2044 /* Do we have to reverse the foreground and background colors? */ 2185 /* Do we have to reverse the foreground and background colors? */
2045 int reverse = EQ (Fcdr (Fassq (qreverse, f->param_alist)), Qt); 2186 int reverse = EQ (Fcdr (Fassq (Qreverse, f->param_alist)), Qt);
2046 int was_reverse = reverse; 2187 int was_reverse = reverse;
2047 int redraw = 0, fg_set = 0, bg_set = 0; 2188 int redraw = 0, fg_set = 0, bg_set = 0;
2048 unsigned long orig_fg; 2189 unsigned long orig_fg;
2049 unsigned long orig_bg; 2190 unsigned long orig_bg;
2050 2191
2077 for (i = 0; i < j; i++) 2218 for (i = 0; i < j; i++)
2078 { 2219 {
2079 Lisp_Object prop = parms[i]; 2220 Lisp_Object prop = parms[i];
2080 Lisp_Object val = values[i]; 2221 Lisp_Object val = values[i];
2081 2222
2082 if (EQ (prop, qreverse)) 2223 if (EQ (prop, Qreverse))
2083 reverse = EQ (val, Qt); 2224 reverse = EQ (val, Qt);
2084 } 2225 }
2085 2226
2086 if (termscript && reverse && !was_reverse) 2227 if (termscript && reverse && !was_reverse)
2087 fprintf (termscript, "<INVERSE-VIDEO>\n"); 2228 fprintf (termscript, "<INVERSE-VIDEO>\n");
2135 else if (EQ (prop, Qtitle)) 2276 else if (EQ (prop, Qtitle))
2136 { 2277 {
2137 x_set_title (f, val); 2278 x_set_title (f, val);
2138 if (termscript) 2279 if (termscript)
2139 fprintf (termscript, "<TITLE: %s>\n", XSTRING (val)->data); 2280 fprintf (termscript, "<TITLE: %s>\n", XSTRING (val)->data);
2281 }
2282 else if (EQ (prop, Qcursor_type))
2283 {
2284 IT_set_cursor_type (f, val);
2285 if (termscript)
2286 fprintf (termscript, "<CTYPE: %s>\n",
2287 EQ (val, Qbar) || CONSP (val) && EQ (XCAR (val), Qbar)
2288 ? "bar" : "box");
2140 } 2289 }
2141 store_frame_param (f, prop, val); 2290 store_frame_param (f, prop, val);
2142 } 2291 }
2143 2292
2144 /* If they specified "reverse", but not the colors, we need to swap 2293 /* If they specified "reverse", but not the colors, we need to swap
4265 mouse_button_translate[1] = 1; 4414 mouse_button_translate[1] = 1;
4266 } 4415 }
4267 mouse_position_hook = &mouse_get_pos; 4416 mouse_position_hook = &mouse_get_pos;
4268 mouse_init (); 4417 mouse_init ();
4269 } 4418 }
4419
4420 #ifndef HAVE_X_WINDOWS
4421 #if __DJGPP__ >= 2
4422 /* Save the cursor shape used outside Emacs. */
4423 outside_cursor = _farpeekw (_dos_ds, 0x460);
4424 #endif
4425 #endif
4270 } 4426 }
4271 4427
4272 first_time = 0; 4428 first_time = 0;
4273 4429
4274 #if __DJGPP__ >= 2 4430 #if __DJGPP__ >= 2
4309 4465
4310 setcbrk (break_stat); 4466 setcbrk (break_stat);
4311 mouse_off (); 4467 mouse_off ();
4312 4468
4313 #if __DJGPP__ >= 2 4469 #if __DJGPP__ >= 2
4470
4471 #ifndef HAVE_X_WINDOWS
4472 /* Restore the cursor shape we found on startup. */
4473 if (outside_cursor)
4474 {
4475 inregs.h.ah = 1;
4476 inregs.x.cx = outside_cursor;
4477 int86 (0x10, &inregs, &outregs);
4478 }
4479 #endif
4314 4480
4315 return (setmode (fileno (stdin), stdin_stat) != -1); 4481 return (setmode (fileno (stdin), stdin_stat) != -1);
4316 4482
4317 #else /* not __DJGPP__ >= 2 */ 4483 #else /* not __DJGPP__ >= 2 */
4318 4484
4902 /* The following three are from xfns.c: */ 5068 /* The following three are from xfns.c: */
4903 Qbackground_color = intern ("background-color"); 5069 Qbackground_color = intern ("background-color");
4904 staticpro (&Qbackground_color); 5070 staticpro (&Qbackground_color);
4905 Qforeground_color = intern ("foreground-color"); 5071 Qforeground_color = intern ("foreground-color");
4906 staticpro (&Qforeground_color); 5072 staticpro (&Qforeground_color);
5073 Qbar = intern ("bar");
5074 staticpro (&Qbar);
5075 Qcursor_type = intern ("cursor-type");
5076 staticpro (&Qcursor_type);
5077 Qreverse = intern ("reverse");
5078 staticpro (&Qreverse);
4907 5079
4908 DEFVAR_LISP ("dos-unsupported-char-glyph", &Vdos_unsupported_char_glyph, 5080 DEFVAR_LISP ("dos-unsupported-char-glyph", &Vdos_unsupported_char_glyph,
4909 "*Glyph to display instead of chars not supported by current codepage.\n\ 5081 "*Glyph to display instead of chars not supported by current codepage.\n\
4910 5082
4911 This variable is used only by MSDOS terminals."); 5083 This variable is used only by MSDOS terminals.");