emacs-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Emacs Mac port


From: Eli Zaretskii
Subject: Re: Emacs Mac port
Date: Mon, 15 Apr 2013 08:44:04 +0300

> Date: Mon, 15 Apr 2013 11:17:20 +0900
> From: YAMAMOTO Mitsuharu <address@hidden>
> Cc: address@hidden
> 
> Simply recording the value of `cursor-in-echo-area' seems to work and
> need only a small change.  Recording the calculated cursor shape would
> be more efficient, but would require nontrivial changes.
> 
> === modified file 'src/dispextern.h'
> *** src/dispextern.h  2013-03-28 14:04:49 +0000
> --- src/dispextern.h  2013-04-15 01:48:51 +0000
> ***************
> *** 665,670 ****
> --- 665,674 ----
>        line.  */
>     unsigned header_line_p : 1;
>   
> +   /* Value of cursor_in_echo_area as of last window update.  Set in
> +      set_window_cursor_after_update.  */
> +   unsigned cursor_in_echo_area_p : 1;
> + 
>   #ifdef GLYPH_DEBUG
>     /* A string identifying the method used to display the matrix.  */
>     char method[512];
> 
> === modified file 'src/dispnew.c'
> *** src/dispnew.c     2013-04-02 01:54:56 +0000
> --- src/dispnew.c     2013-04-15 01:48:51 +0000
> ***************
> *** 3860,3865 ****
> --- 3860,3866 ----
>     /* Not intended for frame matrix updates.  */
>     eassert (FRAME_WINDOW_P (f));
>   
> +   w->current_matrix->cursor_in_echo_area_p = cursor_in_echo_area;
>     if (cursor_in_echo_area
>         && !NILP (echo_area_buffer[0])
>         /* If we are showing a message instead of the mini-buffer,
> 
> === modified file 'src/xdisp.c'
> *** src/xdisp.c       2013-04-02 01:54:56 +0000
> --- src/xdisp.c       2013-04-15 01:48:51 +0000
> ***************
> *** 25481,25487 ****
>     *active_cursor = 1;
>   
>     /* Echo area */
> !   if (cursor_in_echo_area
>         && FRAME_HAS_MINIBUF_P (f)
>         && EQ (FRAME_MINIBUF_WINDOW (f), echo_area_window))
>       {
> --- 25481,25487 ----
>     *active_cursor = 1;
>   
>     /* Echo area */
> !   if (w->current_matrix && w->current_matrix->cursor_in_echo_area_p
>         && FRAME_HAS_MINIBUF_P (f)
>         && EQ (FRAME_MINIBUF_WINDOW (f), echo_area_window))
>       {
> 
> 
> The actual scenario on the latest version of the Mac port: (you can
> skip it)
> 
> First of all, on OS X 10.7 and later, the bottom corners of an
> ordinary window are rounded if every drawing happens in response to an
> "expose" (in X11 terminology) event.  This does not apply to Emacs,
> and the previous versions of the Mac port (and also the current NS
> port) show square frame bottom corner(s) if internal-border-width is
> 0.
> 
> The newest version of the Mac port implements rounded bottom corners
> by invalidating the bottom area (containing echo area partly) when
> drawing operations outside "expose" events might have drawn into one
> of the bottom corners.  This invalidation triggers an "expose" event
> at the next event.
> 
> 1. A Lisp program (e.g. isearch) shows a message with temporarily
>    setting `cursor-in-echo-area' by let-binding.
> 
> 2. Emacs performs redisplay.  At this moment, the cursor is drawn in
>    the echo area because `cursor-in-echo-area' is set.
> 
> 3. At the end of update, the invalidation explained above happens.
>    The height of the invalidated area is 4 (~ the radius of the
>    rounded corner) and it partially overlaps with the echo area.
> 
> 4. At the next event loop, expose_frame is called, and the echo area
>    is redrawn with setting the clipping area to the invalidated area.
>    But at this moment, `cursor-in-echo-area' is already cleared.  So
>    the cursor is not drawn and the lower half of the cursor is cleared
>    and upper half remains displayed because of clipping.
> 
> 5. The Lisp program shows the same message again, but
>    `cursor-in-echo-area' is nil this time.
> 
> 6. Redisplay happens again.  The display engine considers the cursor
>    has already been cleared (at the last expose) and do not clear or
>    draw the cursor.  As a result, the upper half of the cursor remains
>    displayed and lower half looks cleared.

Thanks.

I wish that platform-specific display tricks would not abuse
platform-independent display mechanisms in this way.  I mean, making
the window edges round by triggering expose events as result of
previous redisplay.  Can't this be done in the Mac display back-end
instead?

While adding a flag to the glyph matrix looks like a no-brainer at
first sight, doing so for a benefit of a single platform is something
that at the very least should be heavily commented (including the
above sequence).  Otherwise, a few years from now, when this issue is
no longer relevant, how can we even start thinking whether this flag
is still needed or not?

Also, there are several details that need to be figured out:

 . what about the same flag of the desired_matrix -- should it be
   cleared explicitly, and if so, where?

 . should this flag of the current_matrix be cleared after the cursor
   is displayed?  If not, how can we be sure that during the next
   redisplay cycle, optimizations that bypass most of glyph matrix
   construction will not use a stale value?

 . what if redisplay was preempted? in that case,
   set_window_cursor_after_update is not called, and the flag keeps
   its previous value even if cursor_in_echo_area has changed.

etc., etc.

IOW, I'm unhappy with this change, and would like much better a
solution that doesn't affect every platform out there (including
text-mode display, btw).



reply via email to

[Prev in Thread] Current Thread [Next in Thread]