changeset 103704:6a4e411bd83b

* xterm.h (struct x_display_info): Add invisible_cursor. (struct x_output): Add current_cursor. * xterm.c (XTtoggle_invisible_pointer): New function. (x_define_frame_cursor): Don't define cursor if invisible or the same as before. Set current_cursor. (x_create_terminal): Set toggle_invisible_pointer_hook. * xfns.c (make_invisible_cursor): New function. (x_set_mouse_color): Call make_invisible_cursor. Set current_cursor. (x_window): Set current_cursor. * termhooks.h (struct terminal): Add toggle_invisible_pointer_hook. * keyboard.c (command_loop_1): Call frame_make_pointer_invisible after inserting a character. (read_avail_input): Call frame_make_pointer_visible. * frame.c (Vmake_pointer_invisible): New variable. (frame_make_pointer_invisible, frame_make_pointer_visible): New functions. (syms_of_frame): DEFVAR make-pointer-invisible, initialize to Qt. * frame.h: Declare frame_make_pointer_invisible and frame_make_pointer_visible. (struct frame): Add pointer_invisible. * cus-start.el (all): Added make-pointer-invisible.
author Jan Djärv <jan.h.d@swipnet.se>
date Fri, 03 Jul 2009 11:07:02 +0000
parents e133c93925f6
children bc2b1f7e7bc0
files etc/NEWS lisp/ChangeLog lisp/cus-start.el src/ChangeLog src/frame.c src/frame.h src/keyboard.c src/termhooks.h src/xfns.c src/xterm.c src/xterm.h
diffstat 11 files changed, 154 insertions(+), 7 deletions(-) [+]
line wrap: on
line diff
--- a/etc/NEWS	Fri Jul 03 01:43:33 2009 +0000
+++ b/etc/NEWS	Fri Jul 03 11:07:02 2009 +0000
@@ -38,6 +38,9 @@
 +++
 ** New frame parameter sticky makes Emacs frames sticky in virtual desktops.
 
+** The pointer now becomes invisible when typing.
+Customize make-pointer-invisible to turn it off.
+
 
 * Changes in Specialized Modes and Packages in Emacs 23.2
 
--- a/lisp/ChangeLog	Fri Jul 03 01:43:33 2009 +0000
+++ b/lisp/ChangeLog	Fri Jul 03 11:07:02 2009 +0000
@@ -1,3 +1,7 @@
+2009-07-03  Jan Djärv  <jan.h.d@swipnet.se>
+
+	* cus-start.el (all): Added make-pointer-invisible.
+
 2009-07-03  Jay Belanger  <jay.p.belanger@gmail.com>
 
 	* calc-math.el (math-use-emacs-fn): Make sure that the number is
--- a/lisp/cus-start.el	Fri Jul 03 01:43:33 2009 +0000
+++ b/lisp/cus-start.el	Fri Jul 03 11:07:02 2009 +0000
@@ -179,6 +179,7 @@
 					    (const :tag "always shown" t)
 					    (other :tag "hidden by keypress" 1))
 			      "22.1")
+	     (make-pointer-invisible mouse boolean "23.2")
 	     ;; fringe.c
 	     (overflow-newline-into-fringe fringe boolean)
 	     ;; indent.c
--- a/src/ChangeLog	Fri Jul 03 01:43:33 2009 +0000
+++ b/src/ChangeLog	Fri Jul 03 11:07:02 2009 +0000
@@ -1,3 +1,33 @@
+2009-07-03  Jan Djärv  <jan.h.d@swipnet.se>
+
+	* xterm.h (struct x_display_info): Add invisible_cursor.
+	(struct x_output): Add current_cursor.
+
+	* xterm.c (XTtoggle_invisible_pointer): New function.
+	(x_define_frame_cursor): Don't define cursor if invisible or the
+	same as before.  Set current_cursor.
+	(x_create_terminal): Set toggle_invisible_pointer_hook.
+
+	* xfns.c (make_invisible_cursor): New function.
+	(x_set_mouse_color): Call make_invisible_cursor.
+	Set current_cursor.
+	(x_window): Set current_cursor.
+
+	* termhooks.h (struct terminal): Add toggle_invisible_pointer_hook.
+
+	* keyboard.c (command_loop_1): Call frame_make_pointer_invisible after
+	inserting a character.
+	(read_avail_input): Call frame_make_pointer_visible.
+
+	* frame.c (Vmake_pointer_invisible): New variable.
+	(frame_make_pointer_invisible, frame_make_pointer_visible): New
+	functions.
+	(syms_of_frame): DEFVAR make-pointer-invisible, initialize to Qt.
+
+	* frame.h: Declare frame_make_pointer_invisible and
+	frame_make_pointer_visible.
+	(struct frame): Add pointer_invisible.
+
 2009-07-02  Jan Djärv  <jan.h.d@swipnet.se>
 
 	* gtkutil.c (xg_frame_set_char_size): Do set width/height if the
--- a/src/frame.c	Fri Jul 03 01:43:33 2009 +0000
+++ b/src/frame.c	Fri Jul 03 11:07:02 2009 +0000
@@ -52,6 +52,9 @@
 #endif
 
 
+/* If we shall make pointer invisible when typing or not.  */
+Lisp_Object Vmake_pointer_invisible;
+
 #ifdef HAVE_WINDOW_SYSTEM
 
 /* The name we're using in resource queries.  Most often "emacs".  */
@@ -4350,6 +4353,37 @@
 
 #endif /* HAVE_WINDOW_SYSTEM */
 
+void
+frame_make_pointer_invisible ()
+{
+  if (! NILP (Vmake_pointer_invisible))
+    {
+      struct frame *f = SELECTED_FRAME ();
+      if (f && !f->pointer_invisible
+          && FRAME_TERMINAL (f)->toggle_invisible_pointer_hook)
+        {
+          f->mouse_moved = 0;
+          FRAME_TERMINAL (f)->toggle_invisible_pointer_hook (f, 1);
+          f->pointer_invisible = 1;
+        }
+    }
+}
+
+void
+frame_make_pointer_visible ()
+{
+  /* We don't check Vmake_pointer_invisible here in case the
+     pointer was invisible when Vmake_pointer_invisible was set to nil.  */
+
+  struct frame *f = SELECTED_FRAME ();
+  if (f && f->pointer_invisible && f->mouse_moved
+      && FRAME_TERMINAL (f)->toggle_invisible_pointer_hook)
+    {
+      FRAME_TERMINAL (f)->toggle_invisible_pointer_hook (f, 0);
+      f->pointer_invisible = 0;
+    }
+}
+
 
 
 /***********************************************************************
@@ -4552,6 +4586,11 @@
 when the mouse is over clickable text.  */);
   Vmouse_highlight = Qt;
 
+  DEFVAR_LISP ("make-pointer-invisible", &Vmake_pointer_invisible,
+               doc: /* If non-nil, make pointer invisible while typing.
+The pointer becomes visible again when the mouse is moved.  */);
+  Vmake_pointer_invisible = Qt;
+
   DEFVAR_LISP ("delete-frame-functions", &Vdelete_frame_functions,
 	       doc: /* Functions to be run before deleting a frame.
 The functions are run with one arg, the frame to be deleted.
--- a/src/frame.h	Fri Jul 03 01:43:33 2009 +0000
+++ b/src/frame.h	Fri Jul 03 11:07:02 2009 +0000
@@ -440,6 +440,9 @@
      since the last time we checked.  */
   unsigned char mouse_moved :1;
 
+  /* Nonzero means that the pointer is invisible. */
+  unsigned char pointer_invisible :1;
+
   /* If can_have_scroll_bars is non-zero, this is non-zero if we should
      actually display them on this frame.  */
   enum vertical_scroll_bar_type vertical_scroll_bar_type;
@@ -830,6 +833,8 @@
 							Lisp_Object));
 #endif /* HAVE_WINDOW_SYSTEM */
 extern int other_visible_frames P_ ((struct frame *));
+extern void frame_make_pointer_invisible P_ ((void));
+extern void frame_make_pointer_visible P_ ((void));
 
 extern Lisp_Object Vframe_list;
 extern Lisp_Object Vdefault_frame_alist;
@@ -1110,7 +1115,7 @@
 extern void x_set_alpha P_ ((struct frame *, Lisp_Object, Lisp_Object));
 
 extern void validate_x_resource_name P_ ((void));
-
+                                           
 extern Lisp_Object display_x_get_resource (Display_Info *,
 					   Lisp_Object attribute,
 					   Lisp_Object class,
--- a/src/keyboard.c	Fri Jul 03 01:43:33 2009 +0000
+++ b/src/keyboard.c	Fri Jul 03 11:07:02 2009 +0000
@@ -1867,6 +1867,8 @@
 		  if (value == 2)
 		    nonundocount = 0;
 
+                  frame_make_pointer_invisible ();
+
 		  if (! NILP (Vpost_command_hook))
 		    /* Put this before calling adjust_point_for_property
 		       so it will only get called once in any case.  */
@@ -7134,6 +7136,8 @@
   if (err && !nread)
     nread = -1;
 
+  frame_make_pointer_visible ();
+
   return nread;
 }
 
--- a/src/termhooks.h	Fri Jul 03 01:43:33 2009 +0000
+++ b/src/termhooks.h	Fri Jul 03 11:07:02 2009 +0000
@@ -427,6 +427,7 @@
   void (*delete_glyphs_hook) P_ ((struct frame *, int));
 
   void (*ring_bell_hook) P_ ((struct frame *f));
+  void (*toggle_invisible_pointer_hook) P_ ((struct frame *f, int invisible));
 
   void (*reset_terminal_modes_hook) P_ ((struct terminal *));
   void (*set_terminal_modes_hook) P_ ((struct terminal *));
--- a/src/xfns.c	Fri Jul 03 01:43:33 2009 +0000
+++ b/src/xfns.c	Fri Jul 03 11:07:02 2009 +0000
@@ -941,6 +941,35 @@
     }
 }
 
+static Cursor
+make_invisible_cursor (f)
+     struct frame *f;
+{
+  Display *dpy = FRAME_X_DISPLAY (f);
+  static char const no_data[] = { 0 };
+  Pixmap pix;
+  XColor col;
+  Cursor c;
+
+  x_catch_errors (dpy);
+  pix = XCreateBitmapFromData (dpy, FRAME_X_DISPLAY_INFO (f)->root_window,
+                               no_data, 1, 1);
+  if (! x_had_errors_p (dpy) && pix != None)
+    {
+      col.pixel = 0;
+      col.red = col.green = col.blue = 0;
+      col.flags = DoRed | DoGreen | DoBlue;
+      c = XCreatePixmapCursor (dpy, pix, pix, &col, &col, 0, 0);
+      if (x_had_errors_p (dpy) || c == None)
+        c = 0;
+      XFreePixmap (dpy, pix);
+    }
+
+  x_uncatch_errors ();
+
+  return c;
+}
+
 void
 x_set_mouse_color (f, arg, oldval)
      struct frame *f;
@@ -1046,8 +1075,12 @@
   }
 
   if (FRAME_X_WINDOW (f) != 0)
-    XDefineCursor (dpy, FRAME_X_WINDOW (f), cursor);
-
+    XDefineCursor (dpy, FRAME_X_WINDOW (f),
+                   f->output_data.x->current_cursor = cursor);
+
+  if (FRAME_X_DISPLAY_INFO (f)->invisible_cursor == 0)
+    FRAME_X_DISPLAY_INFO (f)->invisible_cursor = make_invisible_cursor (f);
+  
   if (cursor != x->text_cursor
       && x->text_cursor != 0)
     XFreeCursor (dpy, x->text_cursor);
@@ -2671,7 +2704,7 @@
   }
 
   XDefineCursor (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f),
-		 f->output_data.x->text_cursor);
+		 f->output.x->current_cursor = f->output_data.x->text_cursor);
 
   UNBLOCK_INPUT;
 
@@ -2816,7 +2849,7 @@
   }
 
   XDefineCursor (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f),
-		 f->output_data.x->text_cursor);
+		 f->output.x->current_cursor = f->output_data.x->text_cursor);
 
   UNBLOCK_INPUT;
 
--- a/src/xterm.c	Fri Jul 03 01:43:33 2009 +0000
+++ b/src/xterm.c	Fri Jul 03 11:07:02 2009 +0000
@@ -3128,6 +3128,25 @@
 #endif /* defined (HAVE_TIMEVAL) && defined (HAVE_SELECT) */
 
 
+static void
+XTtoggle_invisible_pointer (f, invisible)
+     FRAME_PTR f;
+     int invisible;
+{
+  BLOCK_INPUT;
+  if (invisible) 
+    {
+      if (FRAME_X_DISPLAY_INFO (f)->invisible_cursor != 0)
+        XDefineCursor (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f),
+                       FRAME_X_DISPLAY_INFO (f)->invisible_cursor);
+    }
+  else
+    XDefineCursor (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f),
+                   f->output_data.x->current_cursor);
+  UNBLOCK_INPUT;
+}
+
+
 /* Make audible bell.  */
 
 void
@@ -4568,7 +4587,7 @@
   /* Set the cursor to an arrow.  I didn't find a resource to do that.
      And I'm wondering why it hasn't an arrow cursor by default.  */
   XDefineCursor (XtDisplay (widget), XtWindow (widget),
-		 f->output_data.x->nontext_cursor);
+                 f->output_data.x->nontext_cursor);
 
 #else /* !USE_MOTIF i.e. use Xaw */
 
@@ -7344,7 +7363,10 @@
      struct frame *f;
      Cursor cursor;
 {
-  XDefineCursor (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f), cursor);
+  if (!f->pointer_invisible
+      && f->output_data.x->current_cursor != cursor)
+    XDefineCursor (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f), cursor);
+  f->output_data.x->current_cursor = cursor;
 }
 
 
@@ -10657,6 +10679,7 @@
   terminal->ins_del_lines_hook = x_ins_del_lines;
   terminal->delete_glyphs_hook = x_delete_glyphs;
   terminal->ring_bell_hook = XTring_bell;
+  terminal->toggle_invisible_pointer_hook = XTtoggle_invisible_pointer;
   terminal->reset_terminal_modes_hook = XTreset_terminal_modes;
   terminal->set_terminal_modes_hook = XTset_terminal_modes;
   terminal->update_begin_hook = x_update_begin;
--- a/src/xterm.h	Fri Jul 03 01:43:33 2009 +0000
+++ b/src/xterm.h	Fri Jul 03 11:07:02 2009 +0000
@@ -166,6 +166,9 @@
   /* The cursor to use for vertical scroll bars.  */
   Cursor vertical_scroll_bar_cursor;
 
+  /* The invisible cursor used for pointer blanking.  */
+  Cursor invisible_cursor;
+
 #ifdef USE_GTK
   /* The GDK cursor for scroll bars and popup menus.  */
   GdkCursor *xg_cursor;
@@ -522,6 +525,7 @@
   Cursor hand_cursor;
   Cursor hourglass_cursor;
   Cursor horizontal_drag_cursor;
+  Cursor current_cursor;
 
   /* Window whose cursor is hourglass_cursor.  This window is temporarily
      mapped to display an hourglass cursor.  */