]> code.delx.au - gnu-emacs/blobdiff - src/w32term.c
2002-08-10 Andrew Choi <akochoi@shaw.ca>
[gnu-emacs] / src / w32term.c
index 8a2e40616a37f927d4ca8f98ad26bf8949644b44..c9628277a470470b1c5a4c29fa05d5d05e96bcac 100644 (file)
@@ -86,7 +86,7 @@ enum fringe_bitmap_type
 #define zv_width 8
 #define zv_height 72
 #define zv_period 3
-static unsigned char zv_bits[] = {
+static unsigned short zv_bits[] = {
   0x00, 0x3c, 0x00, 0x00, 0x3c, 0x00, 0x00, 0x3c, 0x00,
   0x00, 0x3c, 0x00, 0x00, 0x3c, 0x00, 0x00, 0x3c, 0x00,
   0x00, 0x3c, 0x00, 0x00, 0x3c, 0x00, 0x00, 0x3c, 0x00,
@@ -172,7 +172,7 @@ static int any_help_event_p;
 
 /* Non-zero means autoselect window with the mouse cursor.  */
 
-int x_autoselect_window_p;
+int mouse_autoselect_window;
 
 /* Non-zero means draw block and hollow cursor as wide as the glyph
    under it.  For example, if a block cursor is over a tab, it will be
@@ -397,7 +397,8 @@ static void x_new_focus_frame P_ ((struct w32_display_info *,
 static void w32_frame_rehighlight P_ ((struct frame *));
 static void x_frame_rehighlight P_ ((struct w32_display_info *));
 static void x_draw_hollow_cursor P_ ((struct window *, struct glyph_row *));
-static void x_draw_bar_cursor P_ ((struct window *, struct glyph_row *, int));
+static void x_draw_bar_cursor P_ ((struct window *, struct glyph_row *, int,
+                                  enum text_cursor_kinds));
 static void expose_frame P_ ((struct frame *, int, int, int, int));
 static int expose_window_tree P_ ((struct window *, RECT *));
 static int expose_window P_ ((struct window *, RECT *));
@@ -3728,14 +3729,14 @@ w32_draw_relief_rect (f, left_x, top_y, right_x, bottom_y, width,
   for (i = 0; i < width; ++i)
     w32_fill_area (f, hdc, gc.foreground,
                   left_x + i * left_p, top_y + i,
-                  (right_x + 1 - i * right_p) - (left_x + i * left_p) + 1, 1);
+                  right_x - left_x - i * (left_p + right_p ) + 1, 1);
 
   /* Left.  */
   if (left_p)
     for (i = 0; i < width; ++i)
       w32_fill_area (f, hdc, gc.foreground,
                     left_x + i, top_y + i, 1,
-                    (bottom_y - i) - (top_y + i) + 2);
+                    bottom_y - top_y - 2 * i + 1);
 
   if (raised_p)
     gc.foreground = f->output_data.w32->black_relief.gc->foreground;
@@ -3746,14 +3747,14 @@ w32_draw_relief_rect (f, left_x, top_y, right_x, bottom_y, width,
   for (i = 0; i < width; ++i)
     w32_fill_area (f, hdc, gc.foreground, 
                   left_x + i * left_p, bottom_y - i,
-                  (right_x - i * right_p) - (left_x + i * left_p) + 2, 1);
+                  right_x - left_x - i * (left_p + right_p) + 1, 1);
 
   /* Right.  */
   if (right_p)
     for (i = 0; i < width; ++i)
       w32_fill_area (f, hdc, gc.foreground,
                     right_x - i, top_y + i + 1, 1,
-                    (bottom_y - i) - (top_y + i));
+                    bottom_y - top_y - 2 * i - 1);
 
   w32_set_clip_rectangle (hdc, NULL);
   
@@ -3946,8 +3947,12 @@ x_draw_image_foreground (s)
             the image.  I believe it's looking better if we do
             nothing here for mouse-face.  */
          if (s->hl == DRAW_CURSOR)
-            w32_draw_rectangle (s->hdc, s->gc, x, y, s->img->width - 1,
-                                s->img->height - 1);
+           {
+             int r = s->img->relief;
+             if (r < 0) r = -r;
+             w32_draw_rectangle (s->hdc, s->gc, x - r, y - r ,
+                                 s->img->width + r*2 - 1, s->img->height + r*2 - 1);
+           }
           w32_set_clip_rectangle (s->hdc, NULL);
        }
     }
@@ -4087,8 +4092,12 @@ w32_draw_image_foreground_1 (s, pixmap)
             the image.  I believe it's looking better if we do
             nothing here for mouse-face.  */
          if (s->hl == DRAW_CURSOR)
-            w32_draw_rectangle (hdc, s->gc, x, y, s->img->width - 1,
-                                s->img->height - 1);
+           {
+             int r = s->img->relief;
+             if (r < 0) r = -r;
+             w32_draw_rectangle (s->hdc, s->gc, x - r, y - r ,
+                                 s->img->width + r*2 - 1, s->img->height + r*2 - 1);
+           }
        }
     }
   else
@@ -6179,9 +6188,9 @@ construct_mouse_click (result, msg, f)
   parse_button (msg->msg.message, HIWORD (msg->msg.wParam),
                &button, &up);
 
-  /* Make the event type no_event; we'll change that when we decide
+  /* Make the event type NO_EVENT; we'll change that when we decide
      otherwise.  */
-  result->kind = mouse_click;
+  result->kind = MOUSE_CLICK_EVENT;
   result->code = button;
   result->timestamp = msg->msg.time;
   result->modifiers = (msg->dwModifiers
@@ -6203,7 +6212,7 @@ construct_mouse_wheel (result, msg, f)
      struct frame *f;
 {
   POINT p;
-  result->kind = mouse_wheel;
+  result->kind = MOUSE_WHEEL_EVENT;
   result->code = (short) HIWORD (msg->msg.wParam);
   result->timestamp = msg->msg.time;
   result->modifiers = msg->dwModifiers;
@@ -6231,7 +6240,7 @@ construct_drag_n_drop (result, msg, f)
   char *name;
   int i, len;
 
-  result->kind = drag_n_drop;
+  result->kind = DRAG_N_DROP_EVENT;
   result->code = 0;
   result->timestamp = msg->msg.time;
   result->modifiers = msg->dwModifiers;
@@ -6258,7 +6267,7 @@ construct_drag_n_drop (result, msg, f)
        continue;
       name = alloca (len + 1);
       DragQueryFile (hdrop, i, name, len + 1);
-      files = Fcons (build_string (name), files);
+      files = Fcons (DECODE_FILE (build_string (name)), files);
     }
 
   DragFinish (hdrop);
@@ -6295,7 +6304,8 @@ note_mouse_movement (frame, msg)
   memcpy (&last_mouse_motion_event, msg, sizeof (last_mouse_motion_event));
   XSETFRAME (last_mouse_motion_frame, frame);
 
-  if (x_autoselect_window_p)
+#if 0 /* Calling Lisp asynchronously is not safe.  */
+  if (mouse_autoselect_window)
     {
       int area;
       Lisp_Object window;
@@ -6304,7 +6314,7 @@ note_mouse_movement (frame, msg)
       window = window_from_coordinates (frame, mouse_x, mouse_y, &area, 0);
 
       /* Window will be selected only when it is not selected now and
-        last mouse movement event was not in it.  Minubuffer window
+        last mouse movement event was not in it.  Minibuffer window
         will be selected iff it is active.  */
       if (!EQ (window, last_window)
          && !EQ (window, selected_window)
@@ -6314,6 +6324,7 @@ note_mouse_movement (frame, msg)
 
       last_window=window;
     }
+#endif
 
   if (msg->hwnd != FRAME_W32_WINDOW (frame))
     {
@@ -6497,9 +6508,9 @@ note_mode_line_highlight (w, x, mode_line_p)
 
       if (glyph < end
          && STRINGP (glyph->object)
-         && XSTRING (glyph->object)->intervals
+         && STRING_INTERVALS (glyph->object)
          && glyph->charpos >= 0
-         && glyph->charpos < XSTRING (glyph->object)->size)
+         && glyph->charpos < SCHARS (glyph->object))
        {
          /* If we're on a string with `help-echo' text property,
             arrange for the help to be displayed.  This is done by
@@ -6818,7 +6829,7 @@ note_mouse_highlight (f, x, y)
              if (NILP (b))
                b = make_number (0);
              if (NILP (e))
-               e = make_number (XSTRING (object)->size - 1);
+               e = make_number (SCHARS (object) - 1);
              fast_find_string_pos (w, XINT (b), object,
                                    &dpyinfo->mouse_face_beg_col,
                                    &dpyinfo->mouse_face_beg_row,
@@ -6916,7 +6927,7 @@ note_mouse_highlight (f, x, y)
            /* Try text properties.  */
            if (STRINGP (object)
                && charpos >= 0
-               && charpos < XSTRING (object)->size)
+               && charpos < SCHARS (object))
              {
                help = Fget_text_property (make_number (charpos),
                                           Qhelp_echo, object);
@@ -7064,7 +7075,7 @@ w32_handle_tool_bar_click (f, button_event)
   if (NILP (enabled_p))
     return;
   
-  if (button_event->kind == mouse_click)
+  if (button_event->modifiers & down_modifier)
     {
       /* Show item in pressed state.  */
       show_mouse_face (dpyinfo, DRAW_IMAGE_SUNKEN);
@@ -7091,7 +7102,8 @@ w32_handle_tool_bar_click (f, button_event)
       event.kind = TOOL_BAR_EVENT;
       event.frame_or_window = frame;
       event.arg = key;
-      event.modifiers = button_event->modifiers;
+      /* The keyboard buffer doesn't like the up modifier being set.  */
+      event.modifiers = button_event->modifiers & ~up_modifier;
       kbd_buffer_store_event (&event);
       last_tool_bar_item = -1;
     }
@@ -8307,7 +8319,7 @@ w32_judge_scroll_bars (f)
 }
 
 /* Handle a mouse click on the scroll bar BAR.  If *EMACS_EVENT's kind
-   is set to something other than no_event, it is enqueued.
+   is set to something other than NO_EVENT, it is enqueued.
 
    This may be called from a signal handler, so we have to ignore GC
    mark bits.  */
@@ -8321,7 +8333,7 @@ w32_scroll_bar_handle_click (bar, msg, emacs_event)
   if (! GC_WINDOWP (bar->window))
     abort ();
 
-  emacs_event->kind = w32_scroll_bar_click;
+  emacs_event->kind = W32_SCROLL_BAR_CLICK_EVENT;
   emacs_event->code = 0;
   /* not really meaningful to distinguish up/down */
   emacs_event->modifiers = msg->dwModifiers;
@@ -8421,7 +8433,7 @@ w32_scroll_bar_handle_click (bar, msg, emacs_event)
          }
        /* fall through */
       default:
-       emacs_event->kind = no_event;
+       emacs_event->kind = NO_EVENT;
        return FALSE;
       }
 
@@ -8607,7 +8619,7 @@ w32_read_socket (sd, bufp, numchars, expected)
                  /* We may get paint messages even though the client
                     area is clipped - these are not expose events. */
                  DebPrint (("clipped frame %p (%s) got WM_PAINT - ignored\n", f,
-                            XSTRING (f->name)->data));
+                            SDATA (f->name)));
                }
              else if (f->async_visible != 1)
                {
@@ -8616,13 +8628,13 @@ w32_read_socket (sd, bufp, numchars, expected)
                  f->async_iconified = 0;
                  SET_FRAME_GARBAGED (f);
                  DebPrint (("frame %p (%s) reexposed by WM_PAINT\n", f,
-                            XSTRING (f->name)->data));
+                            SDATA (f->name)));
 
                  /* WM_PAINT serves as MapNotify as well, so report
                     visibility changes properly.  */
                  if (f->iconified)
                    {
-                     bufp->kind = deiconify_event;
+                     bufp->kind = DEICONIFY_EVENT;
                      XSETFRAME (bufp->frame_or_window, f);
                      bufp->arg = Qnil;
                      bufp++;
@@ -8660,7 +8672,7 @@ w32_read_socket (sd, bufp, numchars, expected)
              if (numchars == 0)
                abort ();
          
-             bufp->kind = language_change_event;
+             bufp->kind = LANGUAGE_CHANGE_EVENT;
              XSETFRAME (bufp->frame_or_window, f);
              bufp->arg = Qnil;
              bufp->code = msg.msg.wParam;
@@ -8686,7 +8698,7 @@ w32_read_socket (sd, bufp, numchars, expected)
              if (temp_index == sizeof temp_buffer / sizeof (short))
                temp_index = 0;
              temp_buffer[temp_index++] = msg.msg.wParam;
-             bufp->kind = non_ascii_keystroke;
+             bufp->kind = NON_ASCII_KEYSTROKE_EVENT;
              bufp->code = msg.msg.wParam;
              bufp->modifiers = msg.dwModifiers;
              XSETFRAME (bufp->frame_or_window, f);
@@ -8713,7 +8725,7 @@ w32_read_socket (sd, bufp, numchars, expected)
              if (temp_index == sizeof temp_buffer / sizeof (short))
                temp_index = 0;
              temp_buffer[temp_index++] = msg.msg.wParam;
-             bufp->kind = ascii_keystroke;
+             bufp->kind = ASCII_KEYSTROKE_EVENT;
              bufp->code = msg.msg.wParam;
              bufp->modifiers = msg.dwModifiers;
              XSETFRAME (bufp->frame_or_window, f);
@@ -8787,7 +8799,7 @@ w32_read_socket (sd, bufp, numchars, expected)
            int button;
            int up;
 
-            emacs_event.kind = no_event;
+            emacs_event.kind = NO_EVENT;
            
            if (dpyinfo->grabbed && last_mouse_frame
                && FRAME_LIVE_P (last_mouse_frame))
@@ -8810,10 +8822,8 @@ w32_read_socket (sd, bufp, numchars, expected)
                    y = XFASTINT (emacs_event.y);
 
                     /* Set x and y.  */
-                    window = window_from_coordinates (f,
-                                                      emacs_event.x,
-                                                      emacs_event.y,
-                                                      &p, 1);
+                    window = window_from_coordinates (f, x, y, &p, 1);
+
                     if (EQ (window, f->tool_bar_window))
                       {
                         w32_handle_tool_bar_click (f, &emacs_event);
@@ -8981,7 +8991,7 @@ w32_read_socket (sd, bufp, numchars, expected)
                  f->async_visible = 0;
                  f->async_iconified = 1;
                  
-                 bufp->kind = iconify_event;
+                 bufp->kind = ICONIFY_EVENT;
                  XSETFRAME (bufp->frame_or_window, f);
                  bufp->arg = Qnil;
                  bufp++;
@@ -9011,7 +9021,7 @@ w32_read_socket (sd, bufp, numchars, expected)
                       f->output_data.w32->left_pos = x;
                       f->output_data.w32->top_pos = y;
 
-                     bufp->kind = deiconify_event;
+                     bufp->kind = DEICONIFY_EVENT;
                      XSETFRAME (bufp->frame_or_window, f);
                      bufp->arg = Qnil;
                      bufp++;
@@ -9159,7 +9169,7 @@ w32_read_socket (sd, bufp, numchars, expected)
              if (numchars == 0)
                abort ();
              
-             bufp->kind = delete_window_event;
+             bufp->kind = DELETE_WINDOW_EVENT;
              XSETFRAME (bufp->frame_or_window, f);
              bufp->arg = Qnil;
              bufp++;
@@ -9176,7 +9186,7 @@ w32_read_socket (sd, bufp, numchars, expected)
              if (numchars == 0)
                abort ();
          
-             bufp->kind = menu_bar_activate_event;
+             bufp->kind = MENU_BAR_ACTIVATE_EVENT;
              XSETFRAME (bufp->frame_or_window, f);
              bufp->arg = Qnil;
              bufp++;
@@ -9298,7 +9308,7 @@ w32_read_socket (sd, bufp, numchars, expected)
                  if (!FRAME_OBSCURED_P (f))
                    {
                      DebPrint (("frame %p (%s) obscured\n", f,
-                                XSTRING (f->name)->data));
+                                SDATA (f->name)));
                    }
                }
              else
@@ -9310,7 +9320,7 @@ w32_read_socket (sd, bufp, numchars, expected)
                    {
                      SET_FRAME_GARBAGED (f);
                      DebPrint (("obscured frame %p (%s) found to be visible\n", f,
-                                XSTRING (f->name)->data));
+                                SDATA (f->name)));
 
                      /* Force a redisplay sooner or later.  */
                      record_asynch_buffer_change ();
@@ -9446,10 +9456,11 @@ x_draw_hollow_cursor (w, row)
    --gerd.  */
 
 static void
-x_draw_bar_cursor (w, row, width)
+x_draw_bar_cursor (w, row, width, kind)
      struct window *w;
      struct glyph_row *row;
      int width;
+     enum text_cursor_kinds kind;
 {
   struct frame *f = XFRAME (w->frame);
   struct glyph *cursor_glyph;
@@ -9479,6 +9490,7 @@ x_draw_bar_cursor (w, row, width)
 
       if (width < 0)
         width = f->output_data.w32->cursor_width;
+      width = min (cursor_glyph->pixel_width, width);
 
       /* If the glyph's background equals the color we normally draw
         the bar cursor in, the bar cursor in its normal color is
@@ -9491,10 +9503,20 @@ x_draw_bar_cursor (w, row, width)
       x = WINDOW_TEXT_TO_FRAME_PIXEL_X (w, w->phys_cursor.x);
       hdc = get_frame_dc (f);
       w32_clip_to_row (w, row, hdc, 0);
-      w32_fill_area (f, hdc, cursor_color, x,
-                     WINDOW_TO_FRAME_PIXEL_Y (w, w->phys_cursor.y),
-                     min (cursor_glyph->pixel_width, width),
-                     row->height);
+
+      if (kind == BAR_CURSOR)
+       {
+         w32_fill_area (f, hdc, cursor_color, x,
+                        WINDOW_TO_FRAME_PIXEL_Y (w, w->phys_cursor.y),
+                        width, row->height);
+       }
+      else
+       {
+         w32_fill_area (f, hdc, cursor_color, x,
+                        WINDOW_TO_FRAME_PIXEL_Y (w, w->phys_cursor.y +
+                                                 row->height - width),
+                        cursor_glyph->pixel_width, width);
+       }
       release_frame_dc (f, hdc);
     }
 }
@@ -9863,7 +9885,11 @@ x_display_and_set_cursor (w, on, hpos, vpos, x, y)
          break;
 
        case BAR_CURSOR:
-         x_draw_bar_cursor (w, glyph_row, new_cursor_width);
+         x_draw_bar_cursor (w, glyph_row, new_cursor_width, BAR_CURSOR);
+         break;
+
+       case HBAR_CURSOR:
+         x_draw_bar_cursor (w, glyph_row, new_cursor_width, HBAR_CURSOR);
          break;
 
        case NO_CURSOR:
@@ -9965,7 +9991,7 @@ x_bitmap_icon (f, icon)
   if (NILP (icon))
     hicon = LoadIcon (hinst, EMACS_CLASS);
   else if (STRINGP (icon))
-    hicon = LoadImage (NULL, (LPCTSTR) XSTRING (icon)->data, IMAGE_ICON, 0, 0,
+    hicon = LoadImage (NULL, (LPCTSTR) SDATA (icon), IMAGE_ICON, 0, 0,
                       LR_DEFAULTSIZE | LR_LOADFROMFILE);
   else if (SYMBOLP (icon))
     {
@@ -10095,7 +10121,7 @@ x_new_fontset (f, fontsetname)
        to do.  */
     return fontset_name (fontset);
 
-  result = x_new_font (f, (XSTRING (fontset_ascii (fontset))->data));
+  result = x_new_font (f, (SDATA (fontset_ascii (fontset))));
 
   if (!STRINGP (result))
     /* Can't load ASCII font.  */
@@ -11021,11 +11047,11 @@ w32_initialize_display_info (display_name)
   dpyinfo->name_list_element = XCAR (w32_display_name_list);
   
   dpyinfo->w32_id_name
-    = (char *) xmalloc (XSTRING (Vinvocation_name)->size
-                       + XSTRING (Vsystem_name)->size
+    = (char *) xmalloc (SCHARS (Vinvocation_name)
+                       + SCHARS (Vsystem_name)
                        + 2);
   sprintf (dpyinfo->w32_id_name, "%s@%s",
-          XSTRING (Vinvocation_name)->data, XSTRING (Vsystem_name)->data);
+          SDATA (Vinvocation_name), SDATA (Vsystem_name));
 
   /* Default Console mode values - overridden when running in GUI mode
      with values obtained from system metrics.  */
@@ -11387,9 +11413,9 @@ affect on NT machines.  */);
   staticpro (&previous_help_echo);
   help_echo_pos = -1;
 
-  DEFVAR_BOOL ("x-autoselect-window", &x_autoselect_window_p,
+  DEFVAR_BOOL ("mouse-autoselect-window", &mouse_autoselect_window,
     doc: /* *Non-nil means autoselect window with mouse pointer.  */);
-  x_autoselect_window_p = 0;
+  mouse_autoselect_window = 0;
 
   DEFVAR_BOOL ("w32-use-visible-system-caret",
               &w32_use_visible_system_caret,
@@ -11416,7 +11442,6 @@ For example, if a block cursor is over a tab, it will be drawn as
 wide as that tab on the display.  */);
   x_stretch_cursor_p = 0;
 
-#if 0 /* TODO: Setting underline position from font properties.  */
   DEFVAR_BOOL ("x-use-underline-position-properties",
               &x_use_underline_position_properties,
               doc: /* *Non-nil means make use of UNDERLINE_POSITION font properties.
@@ -11424,7 +11449,6 @@ nil means ignore them.  If you encounter fonts with bogus
 UNDERLINE_POSITION font properties, for example 7x13 on XFree prior
 to 4.1, set this to nil.  */);
   x_use_underline_position_properties = 1;
-#endif
 
   DEFVAR_LISP ("x-toolkit-scroll-bars", &Vx_toolkit_scroll_bars,
               doc: /* If not nil, Emacs uses toolkit scroll bars.  */);