diff options
| -rw-r--r-- | src/ChangeLog | 23 | ||||
| -rw-r--r-- | src/bidi.c | 22 | ||||
| -rw-r--r-- | src/dispextern.h | 5 | ||||
| -rw-r--r-- | src/xdisp.c | 430 |
4 files changed, 300 insertions, 180 deletions
diff --git a/src/ChangeLog b/src/ChangeLog index fdb98351672..f7807b90941 100644 --- a/src/ChangeLog +++ b/src/ChangeLog | |||
| @@ -1,3 +1,26 @@ | |||
| 1 | 2011-05-21 Eli Zaretskii <eliz@gnu.org> | ||
| 2 | |||
| 3 | * xdisp.c (handle_display_spec): New function, refactored from the | ||
| 4 | last portion of handle_display_prop. | ||
| 5 | (compute_display_string_pos): Accept additional argument | ||
| 6 | FRAME_WINDOW_P. Call handle_display_spec to determine whether the | ||
| 7 | value of a `display' property is a "replacing spec". | ||
| 8 | (handle_single_display_spec): Accept 2 additional arguments BUFPOS | ||
| 9 | and FRAME_WINDOW_P. If IT is NULL, don't set up the iterator from | ||
| 10 | the display property, but just return a value indicating whether | ||
| 11 | the display property will replace the characters it covers. | ||
| 12 | (Fcurrent_bidi_paragraph_direction): Initialize the nchars and | ||
| 13 | frame_window_p members of struct bidi_it. | ||
| 14 | |||
| 15 | * bidi.c (bidi_fetch_char): Accept additional argument | ||
| 16 | FRAME_WINDOW_P and pass it to compute_display_string_pos. All | ||
| 17 | callers changed. | ||
| 18 | (bidi_init_it): Accept additional argument FRAME_WINDOW_P and use | ||
| 19 | it to initialize the frame_window_p member of struct bidi_it. | ||
| 20 | |||
| 21 | * dispextern.h (struct bidi_it): New member frame_window_p. | ||
| 22 | (bidi_init_it, compute_display_string_pos): Update prototypes. | ||
| 23 | |||
| 1 | 2011-05-14 Eli Zaretskii <eliz@gnu.org> | 24 | 2011-05-14 Eli Zaretskii <eliz@gnu.org> |
| 2 | 25 | ||
| 3 | * xdisp.c (compute_display_string_pos): Non-trivial implementation. | 26 | * xdisp.c (compute_display_string_pos): Non-trivial implementation. |
diff --git a/src/bidi.c b/src/bidi.c index 742224607e4..17cb1214c73 100644 --- a/src/bidi.c +++ b/src/bidi.c | |||
| @@ -581,7 +581,7 @@ bidi_line_init (struct bidi_it *bidi_it) | |||
| 581 | string. */ | 581 | string. */ |
| 582 | static INLINE int | 582 | static INLINE int |
| 583 | bidi_fetch_char (EMACS_INT bytepos, EMACS_INT charpos, EMACS_INT *disp_pos, | 583 | bidi_fetch_char (EMACS_INT bytepos, EMACS_INT charpos, EMACS_INT *disp_pos, |
| 584 | EMACS_INT *ch_len, EMACS_INT *nchars) | 584 | int frame_window_p, EMACS_INT *ch_len, EMACS_INT *nchars) |
| 585 | { | 585 | { |
| 586 | int ch; | 586 | int ch; |
| 587 | 587 | ||
| @@ -589,7 +589,7 @@ bidi_fetch_char (EMACS_INT bytepos, EMACS_INT charpos, EMACS_INT *disp_pos, | |||
| 589 | /* If we got past the last known position of display string, compute | 589 | /* If we got past the last known position of display string, compute |
| 590 | the position of the next one. That position could be at BYTEPOS. */ | 590 | the position of the next one. That position could be at BYTEPOS. */ |
| 591 | if (charpos < ZV && charpos > *disp_pos) | 591 | if (charpos < ZV && charpos > *disp_pos) |
| 592 | *disp_pos = compute_display_string_pos (charpos); | 592 | *disp_pos = compute_display_string_pos (charpos, frame_window_p); |
| 593 | 593 | ||
| 594 | /* Fetch the character at BYTEPOS. */ | 594 | /* Fetch the character at BYTEPOS. */ |
| 595 | if (bytepos >= ZV_BYTE) | 595 | if (bytepos >= ZV_BYTE) |
| @@ -625,7 +625,7 @@ bidi_fetch_char (EMACS_INT bytepos, EMACS_INT charpos, EMACS_INT *disp_pos, | |||
| 625 | /* If we just entered a run of characters covered by a display | 625 | /* If we just entered a run of characters covered by a display |
| 626 | string, compute the position of the next display string. */ | 626 | string, compute the position of the next display string. */ |
| 627 | if (charpos + *nchars <= ZV && charpos + *nchars > *disp_pos) | 627 | if (charpos + *nchars <= ZV && charpos + *nchars > *disp_pos) |
| 628 | *disp_pos = compute_display_string_pos (charpos + *nchars); | 628 | *disp_pos = compute_display_string_pos (charpos + *nchars, frame_window_p); |
| 629 | 629 | ||
| 630 | return ch; | 630 | return ch; |
| 631 | } | 631 | } |
| @@ -754,7 +754,8 @@ bidi_paragraph_init (bidi_dir_t dir, struct bidi_it *bidi_it, int no_default_p) | |||
| 754 | do { | 754 | do { |
| 755 | bytepos = pstartbyte; | 755 | bytepos = pstartbyte; |
| 756 | pos = BYTE_TO_CHAR (bytepos); | 756 | pos = BYTE_TO_CHAR (bytepos); |
| 757 | ch = bidi_fetch_char (bytepos, pos, &disp_pos, &ch_len, &nchars); | 757 | ch = bidi_fetch_char (bytepos, pos, &disp_pos, bidi_it->frame_window_p, |
| 758 | &ch_len, &nchars); | ||
| 758 | type = bidi_get_type (ch, NEUTRAL_DIR); | 759 | type = bidi_get_type (ch, NEUTRAL_DIR); |
| 759 | 760 | ||
| 760 | for (pos += nchars, bytepos += ch_len; | 761 | for (pos += nchars, bytepos += ch_len; |
| @@ -778,7 +779,8 @@ bidi_paragraph_init (bidi_dir_t dir, struct bidi_it *bidi_it, int no_default_p) | |||
| 778 | break; | 779 | break; |
| 779 | } | 780 | } |
| 780 | /* Fetch next character and advance to get past it. */ | 781 | /* Fetch next character and advance to get past it. */ |
| 781 | ch = bidi_fetch_char (bytepos, pos, &disp_pos, &ch_len, &nchars); | 782 | ch = bidi_fetch_char (bytepos, pos, &disp_pos, |
| 783 | bidi_it->frame_window_p, &ch_len, &nchars); | ||
| 782 | pos += nchars; | 784 | pos += nchars; |
| 783 | bytepos += ch_len; | 785 | bytepos += ch_len; |
| 784 | } | 786 | } |
| @@ -840,12 +842,14 @@ bidi_set_paragraph_end (struct bidi_it *bidi_it) | |||
| 840 | 842 | ||
| 841 | /* Initialize the bidi iterator from buffer/string position CHARPOS. */ | 843 | /* Initialize the bidi iterator from buffer/string position CHARPOS. */ |
| 842 | void | 844 | void |
| 843 | bidi_init_it (EMACS_INT charpos, EMACS_INT bytepos, struct bidi_it *bidi_it) | 845 | bidi_init_it (EMACS_INT charpos, EMACS_INT bytepos, int frame_window_p, |
| 846 | struct bidi_it *bidi_it) | ||
| 844 | { | 847 | { |
| 845 | if (! bidi_initialized) | 848 | if (! bidi_initialized) |
| 846 | bidi_initialize (); | 849 | bidi_initialize (); |
| 847 | bidi_it->charpos = charpos; | 850 | bidi_it->charpos = charpos; |
| 848 | bidi_it->bytepos = bytepos; | 851 | bidi_it->bytepos = bytepos; |
| 852 | bidi_it->frame_window_p = frame_window_p; | ||
| 849 | bidi_it->nchars = -1; /* to be computed in bidi_resolve_explicit_1 */ | 853 | bidi_it->nchars = -1; /* to be computed in bidi_resolve_explicit_1 */ |
| 850 | bidi_it->first_elt = 1; | 854 | bidi_it->first_elt = 1; |
| 851 | bidi_set_paragraph_end (bidi_it); | 855 | bidi_set_paragraph_end (bidi_it); |
| @@ -996,7 +1000,7 @@ bidi_resolve_explicit_1 (struct bidi_it *bidi_it) | |||
| 996 | display string, treat the entire run of covered characters as | 1000 | display string, treat the entire run of covered characters as |
| 997 | a single character u+FFFC. */ | 1001 | a single character u+FFFC. */ |
| 998 | curchar = bidi_fetch_char (bidi_it->bytepos, bidi_it->charpos, | 1002 | curchar = bidi_fetch_char (bidi_it->bytepos, bidi_it->charpos, |
| 999 | &bidi_it->disp_pos, | 1003 | &bidi_it->disp_pos, bidi_it->frame_window_p, |
| 1000 | &bidi_it->ch_len, &bidi_it->nchars); | 1004 | &bidi_it->ch_len, &bidi_it->nchars); |
| 1001 | } | 1005 | } |
| 1002 | bidi_it->ch = curchar; | 1006 | bidi_it->ch = curchar; |
| @@ -1674,11 +1678,13 @@ bidi_level_of_next_char (struct bidi_it *bidi_it) | |||
| 1674 | EMACS_INT disp_pos = bidi_it->disp_pos; | 1678 | EMACS_INT disp_pos = bidi_it->disp_pos; |
| 1675 | EMACS_INT nc = bidi_it->nchars; | 1679 | EMACS_INT nc = bidi_it->nchars; |
| 1676 | bidi_type_t chtype; | 1680 | bidi_type_t chtype; |
| 1681 | int fwp = bidi_it->frame_window_p; | ||
| 1677 | 1682 | ||
| 1678 | if (bidi_it->nchars <= 0) | 1683 | if (bidi_it->nchars <= 0) |
| 1679 | abort (); | 1684 | abort (); |
| 1680 | do { | 1685 | do { |
| 1681 | ch = bidi_fetch_char (bpos += clen, cpos += nc, &disp_pos, &clen, &nc); | 1686 | ch = bidi_fetch_char (bpos += clen, cpos += nc, &disp_pos, fwp, |
| 1687 | &clen, &nc); | ||
| 1682 | if (ch == '\n' || ch == BIDI_EOB /* || ch == LINESEP_CHAR */) | 1688 | if (ch == '\n' || ch == BIDI_EOB /* || ch == LINESEP_CHAR */) |
| 1683 | chtype = NEUTRAL_B; | 1689 | chtype = NEUTRAL_B; |
| 1684 | else | 1690 | else |
diff --git a/src/dispextern.h b/src/dispextern.h index f5036169f75..6c09f21a78f 100644 --- a/src/dispextern.h +++ b/src/dispextern.h | |||
| @@ -1847,6 +1847,7 @@ struct bidi_it { | |||
| 1847 | int first_elt; /* if non-zero, examine current char first */ | 1847 | int first_elt; /* if non-zero, examine current char first */ |
| 1848 | bidi_dir_t paragraph_dir; /* current paragraph direction */ | 1848 | bidi_dir_t paragraph_dir; /* current paragraph direction */ |
| 1849 | int new_paragraph; /* if non-zero, we expect a new paragraph */ | 1849 | int new_paragraph; /* if non-zero, we expect a new paragraph */ |
| 1850 | int frame_window_p; /* non-zero if displaying on a GUI frame */ | ||
| 1850 | EMACS_INT separator_limit; /* where paragraph separator should end */ | 1851 | EMACS_INT separator_limit; /* where paragraph separator should end */ |
| 1851 | EMACS_INT disp_pos; /* position of display string after ch */ | 1852 | EMACS_INT disp_pos; /* position of display string after ch */ |
| 1852 | }; | 1853 | }; |
| @@ -2945,7 +2946,7 @@ enum tool_bar_item_image | |||
| 2945 | 2946 | ||
| 2946 | /* Defined in bidi.c */ | 2947 | /* Defined in bidi.c */ |
| 2947 | 2948 | ||
| 2948 | extern void bidi_init_it (EMACS_INT, EMACS_INT, struct bidi_it *); | 2949 | extern void bidi_init_it (EMACS_INT, EMACS_INT, int, struct bidi_it *); |
| 2949 | extern void bidi_move_to_visually_next (struct bidi_it *); | 2950 | extern void bidi_move_to_visually_next (struct bidi_it *); |
| 2950 | extern void bidi_paragraph_init (bidi_dir_t, struct bidi_it *, int); | 2951 | extern void bidi_paragraph_init (bidi_dir_t, struct bidi_it *, int); |
| 2951 | extern int bidi_mirror_char (int); | 2952 | extern int bidi_mirror_char (int); |
| @@ -3006,7 +3007,7 @@ extern void reseat_at_previous_visible_line_start (struct it *); | |||
| 3006 | extern Lisp_Object lookup_glyphless_char_display (int, struct it *); | 3007 | extern Lisp_Object lookup_glyphless_char_display (int, struct it *); |
| 3007 | extern int calc_pixel_width_or_height (double *, struct it *, Lisp_Object, | 3008 | extern int calc_pixel_width_or_height (double *, struct it *, Lisp_Object, |
| 3008 | struct font *, int, int *); | 3009 | struct font *, int, int *); |
| 3009 | extern EMACS_INT compute_display_string_pos (EMACS_INT); | 3010 | extern EMACS_INT compute_display_string_pos (EMACS_INT, int); |
| 3010 | extern EMACS_INT compute_display_string_end (EMACS_INT); | 3011 | extern EMACS_INT compute_display_string_end (EMACS_INT); |
| 3011 | 3012 | ||
| 3012 | #ifdef HAVE_WINDOW_SYSTEM | 3013 | #ifdef HAVE_WINDOW_SYSTEM |
diff --git a/src/xdisp.c b/src/xdisp.c index 6ea6f92a3f7..8665acf8fdd 100644 --- a/src/xdisp.c +++ b/src/xdisp.c | |||
| @@ -884,9 +884,11 @@ static void compute_string_pos (struct text_pos *, struct text_pos, | |||
| 884 | Lisp_Object); | 884 | Lisp_Object); |
| 885 | static int face_before_or_after_it_pos (struct it *, int); | 885 | static int face_before_or_after_it_pos (struct it *, int); |
| 886 | static EMACS_INT next_overlay_change (EMACS_INT); | 886 | static EMACS_INT next_overlay_change (EMACS_INT); |
| 887 | static int handle_display_spec (struct it *, Lisp_Object, Lisp_Object, | ||
| 888 | Lisp_Object, struct text_pos *, EMACS_INT, int); | ||
| 887 | static int handle_single_display_spec (struct it *, Lisp_Object, | 889 | static int handle_single_display_spec (struct it *, Lisp_Object, |
| 888 | Lisp_Object, Lisp_Object, | 890 | Lisp_Object, Lisp_Object, |
| 889 | struct text_pos *, int); | 891 | struct text_pos *, EMACS_INT, int, int); |
| 890 | static int underlying_face_id (struct it *); | 892 | static int underlying_face_id (struct it *); |
| 891 | static int in_ellipses_for_invisible_text_p (struct display_pos *, | 893 | static int in_ellipses_for_invisible_text_p (struct display_pos *, |
| 892 | struct window *); | 894 | struct window *); |
| @@ -2564,7 +2566,7 @@ init_iterator (struct it *it, struct window *w, | |||
| 2564 | it->paragraph_embedding = R2L; | 2566 | it->paragraph_embedding = R2L; |
| 2565 | else | 2567 | else |
| 2566 | it->paragraph_embedding = NEUTRAL_DIR; | 2568 | it->paragraph_embedding = NEUTRAL_DIR; |
| 2567 | bidi_init_it (charpos, bytepos, &it->bidi_it); | 2569 | bidi_init_it (charpos, bytepos, FRAME_WINDOW_P (it->f), &it->bidi_it); |
| 2568 | } | 2570 | } |
| 2569 | 2571 | ||
| 2570 | /* If a buffer position was specified, set the iterator there, | 2572 | /* If a buffer position was specified, set the iterator there, |
| @@ -3086,37 +3088,54 @@ next_overlay_change (EMACS_INT pos) | |||
| 3086 | } | 3088 | } |
| 3087 | 3089 | ||
| 3088 | /* Return the character position of a display string at or after CHARPOS. | 3090 | /* Return the character position of a display string at or after CHARPOS. |
| 3089 | If no display string exist at or after CHARPOS, return ZV. A | 3091 | If no display string exists at or after CHARPOS, return ZV. A |
| 3090 | display string is either an overlay with `display' property whose | 3092 | display string is either an overlay with `display' property whose |
| 3091 | value is a string or a `display' text property whose value is a | 3093 | value is a string, or a `display' text property whose value is a |
| 3092 | string. */ | 3094 | string. FRAME_WINDOW_P is non-zero when we are displaying a window |
| 3095 | on a GUI frame. */ | ||
| 3093 | EMACS_INT | 3096 | EMACS_INT |
| 3094 | compute_display_string_pos (EMACS_INT charpos) | 3097 | compute_display_string_pos (EMACS_INT charpos, int frame_window_p) |
| 3095 | { | 3098 | { |
| 3096 | /* FIXME: Support display properties on strings (object = Qnil means | 3099 | /* FIXME: Support display properties on strings (object = Qnil means |
| 3097 | current buffer). */ | 3100 | current buffer). */ |
| 3098 | Lisp_Object object = Qnil; | 3101 | Lisp_Object object = Qnil; |
| 3099 | Lisp_Object pos = make_number (charpos); | 3102 | Lisp_Object pos, spec; |
| 3103 | struct text_pos position; | ||
| 3104 | EMACS_INT bufpos; | ||
| 3100 | 3105 | ||
| 3101 | if (charpos >= ZV) | 3106 | if (charpos >= ZV) |
| 3102 | return ZV; | 3107 | return ZV; |
| 3103 | 3108 | ||
| 3104 | /* If the character at CHARPOS is where the display string begins, | 3109 | /* If the character at CHARPOS is where the display string begins, |
| 3105 | return CHARPOS. */ | 3110 | return CHARPOS. */ |
| 3106 | if (!NILP (Fget_char_property (pos, Qdisplay, object)) | 3111 | pos = make_number (charpos); |
| 3112 | CHARPOS (position) = charpos; | ||
| 3113 | BYTEPOS (position) = CHAR_TO_BYTE (charpos); | ||
| 3114 | bufpos = charpos; /* FIXME! support strings as well */ | ||
| 3115 | if (!NILP (spec = Fget_char_property (pos, Qdisplay, object)) | ||
| 3107 | && (charpos <= BEGV | 3116 | && (charpos <= BEGV |
| 3108 | || NILP (Fget_char_property (make_number (charpos - 1), Qdisplay, | 3117 | || !EQ (Fget_char_property (make_number (charpos - 1), Qdisplay, |
| 3109 | object)))) | 3118 | object), |
| 3119 | spec))) | ||
| 3120 | && handle_display_spec (NULL, spec, object, Qnil, &position, bufpos, | ||
| 3121 | frame_window_p)) | ||
| 3110 | return charpos; | 3122 | return charpos; |
| 3111 | 3123 | ||
| 3112 | /* Look forward for the first character where the `display' property | 3124 | /* Look forward for the first character with a `display' property |
| 3113 | changes from nil to non-nil. */ | 3125 | that will replace the underlying text when displayed. */ |
| 3114 | do { | 3126 | do { |
| 3115 | pos = Fnext_single_char_property_change (pos, Qdisplay, object, Qnil); | 3127 | pos = Fnext_single_char_property_change (pos, Qdisplay, object, Qnil); |
| 3116 | } while (XFASTINT (pos) < ZV | 3128 | CHARPOS (position) = XFASTINT (pos); |
| 3117 | && NILP (Fget_char_property (pos, Qdisplay, object))); | 3129 | BYTEPOS (position) = CHAR_TO_BYTE (CHARPOS (position)); |
| 3130 | if (CHARPOS (position) >= ZV) | ||
| 3131 | break; | ||
| 3132 | spec = Fget_char_property (pos, Qdisplay, object); | ||
| 3133 | bufpos = CHARPOS (position); /* FIXME! support strings as well */ | ||
| 3134 | } while (NILP (spec) | ||
| 3135 | || !handle_display_spec (NULL, spec, object, Qnil, &position, bufpos, | ||
| 3136 | frame_window_p)); | ||
| 3118 | 3137 | ||
| 3119 | return XFASTINT (pos); | 3138 | return CHARPOS (position); |
| 3120 | } | 3139 | } |
| 3121 | 3140 | ||
| 3122 | /* Return the character position of the end of the display string that | 3141 | /* Return the character position of the end of the display string that |
| @@ -3802,8 +3821,9 @@ setup_for_ellipsis (struct it *it, int len) | |||
| 3802 | static enum prop_handled | 3821 | static enum prop_handled |
| 3803 | handle_display_prop (struct it *it) | 3822 | handle_display_prop (struct it *it) |
| 3804 | { | 3823 | { |
| 3805 | Lisp_Object prop, object, overlay; | 3824 | Lisp_Object propval, object, overlay; |
| 3806 | struct text_pos *position; | 3825 | struct text_pos *position; |
| 3826 | EMACS_INT bufpos; | ||
| 3807 | /* Nonzero if some property replaces the display of the text itself. */ | 3827 | /* Nonzero if some property replaces the display of the text itself. */ |
| 3808 | int display_replaced_p = 0; | 3828 | int display_replaced_p = 0; |
| 3809 | 3829 | ||
| @@ -3811,11 +3831,13 @@ handle_display_prop (struct it *it) | |||
| 3811 | { | 3831 | { |
| 3812 | object = it->string; | 3832 | object = it->string; |
| 3813 | position = &it->current.string_pos; | 3833 | position = &it->current.string_pos; |
| 3834 | bufpos = CHARPOS (it->current.pos); | ||
| 3814 | } | 3835 | } |
| 3815 | else | 3836 | else |
| 3816 | { | 3837 | { |
| 3817 | XSETWINDOW (object, it->w); | 3838 | XSETWINDOW (object, it->w); |
| 3818 | position = &it->current.pos; | 3839 | position = &it->current.pos; |
| 3840 | bufpos = CHARPOS (*position); | ||
| 3819 | } | 3841 | } |
| 3820 | 3842 | ||
| 3821 | /* Reset those iterator values set from display property values. */ | 3843 | /* Reset those iterator values set from display property values. */ |
| @@ -3830,9 +3852,9 @@ handle_display_prop (struct it *it) | |||
| 3830 | if (!it->string_from_display_prop_p) | 3852 | if (!it->string_from_display_prop_p) |
| 3831 | it->area = TEXT_AREA; | 3853 | it->area = TEXT_AREA; |
| 3832 | 3854 | ||
| 3833 | prop = get_char_property_and_overlay (make_number (position->charpos), | 3855 | propval = get_char_property_and_overlay (make_number (position->charpos), |
| 3834 | Qdisplay, object, &overlay); | 3856 | Qdisplay, object, &overlay); |
| 3835 | if (NILP (prop)) | 3857 | if (NILP (propval)) |
| 3836 | return HANDLED_NORMALLY; | 3858 | return HANDLED_NORMALLY; |
| 3837 | /* Now OVERLAY is the overlay that gave us this property, or nil | 3859 | /* Now OVERLAY is the overlay that gave us this property, or nil |
| 3838 | if it was a text property. */ | 3860 | if it was a text property. */ |
| @@ -3840,59 +3862,88 @@ handle_display_prop (struct it *it) | |||
| 3840 | if (!STRINGP (it->string)) | 3862 | if (!STRINGP (it->string)) |
| 3841 | object = it->w->buffer; | 3863 | object = it->w->buffer; |
| 3842 | 3864 | ||
| 3843 | if (CONSP (prop) | 3865 | display_replaced_p = handle_display_spec (it, propval, object, overlay, |
| 3844 | /* Simple properties. */ | 3866 | position, bufpos, |
| 3845 | && !EQ (XCAR (prop), Qimage) | 3867 | FRAME_WINDOW_P (it->f)); |
| 3846 | && !EQ (XCAR (prop), Qspace) | 3868 | |
| 3847 | && !EQ (XCAR (prop), Qwhen) | 3869 | return display_replaced_p ? HANDLED_RETURN : HANDLED_NORMALLY; |
| 3848 | && !EQ (XCAR (prop), Qslice) | 3870 | } |
| 3849 | && !EQ (XCAR (prop), Qspace_width) | 3871 | |
| 3850 | && !EQ (XCAR (prop), Qheight) | 3872 | /* Subroutine of handle_display_prop. Returns non-zero if the display |
| 3851 | && !EQ (XCAR (prop), Qraise) | 3873 | specification in SPEC is a replacing specification, i.e. it would |
| 3874 | replace the text covered by `display' property with something else, | ||
| 3875 | such as an image or a display string. | ||
| 3876 | |||
| 3877 | See handle_single_display_spec for documentation of arguments. | ||
| 3878 | frame_window_p is non-zero if the window being redisplayed is on a | ||
| 3879 | GUI frame; this argument is used only if IT is NULL, see below. | ||
| 3880 | |||
| 3881 | IT can be NULL, if this is called by the bidi reordering code | ||
| 3882 | through compute_display_string_pos, which see. In that case, this | ||
| 3883 | function only examines SPEC, but does not otherwise "handle" it, in | ||
| 3884 | the sense that it doesn't set up members of IT from the display | ||
| 3885 | spec. */ | ||
| 3886 | static int | ||
| 3887 | handle_display_spec (struct it *it, Lisp_Object spec, Lisp_Object object, | ||
| 3888 | Lisp_Object overlay, struct text_pos *position, | ||
| 3889 | EMACS_INT bufpos, int frame_window_p) | ||
| 3890 | { | ||
| 3891 | int replacing_p = 0; | ||
| 3892 | |||
| 3893 | if (CONSP (spec) | ||
| 3894 | /* Simple specerties. */ | ||
| 3895 | && !EQ (XCAR (spec), Qimage) | ||
| 3896 | && !EQ (XCAR (spec), Qspace) | ||
| 3897 | && !EQ (XCAR (spec), Qwhen) | ||
| 3898 | && !EQ (XCAR (spec), Qslice) | ||
| 3899 | && !EQ (XCAR (spec), Qspace_width) | ||
| 3900 | && !EQ (XCAR (spec), Qheight) | ||
| 3901 | && !EQ (XCAR (spec), Qraise) | ||
| 3852 | /* Marginal area specifications. */ | 3902 | /* Marginal area specifications. */ |
| 3853 | && !(CONSP (XCAR (prop)) && EQ (XCAR (XCAR (prop)), Qmargin)) | 3903 | && !(CONSP (XCAR (spec)) && EQ (XCAR (XCAR (spec)), Qmargin)) |
| 3854 | && !EQ (XCAR (prop), Qleft_fringe) | 3904 | && !EQ (XCAR (spec), Qleft_fringe) |
| 3855 | && !EQ (XCAR (prop), Qright_fringe) | 3905 | && !EQ (XCAR (spec), Qright_fringe) |
| 3856 | && !NILP (XCAR (prop))) | 3906 | && !NILP (XCAR (spec))) |
| 3857 | { | 3907 | { |
| 3858 | for (; CONSP (prop); prop = XCDR (prop)) | 3908 | for (; CONSP (spec); spec = XCDR (spec)) |
| 3859 | { | 3909 | { |
| 3860 | if (handle_single_display_spec (it, XCAR (prop), object, overlay, | 3910 | if (handle_single_display_spec (it, XCAR (spec), object, overlay, |
| 3861 | position, display_replaced_p)) | 3911 | position, bufpos, replacing_p, |
| 3912 | frame_window_p)) | ||
| 3862 | { | 3913 | { |
| 3863 | display_replaced_p = 1; | 3914 | replacing_p = 1; |
| 3864 | /* If some text in a string is replaced, `position' no | 3915 | /* If some text in a string is replaced, `position' no |
| 3865 | longer points to the position of `object'. */ | 3916 | longer points to the position of `object'. */ |
| 3866 | if (STRINGP (object)) | 3917 | if (!it || STRINGP (object)) |
| 3867 | break; | 3918 | break; |
| 3868 | } | 3919 | } |
| 3869 | } | 3920 | } |
| 3870 | } | 3921 | } |
| 3871 | else if (VECTORP (prop)) | 3922 | else if (VECTORP (spec)) |
| 3872 | { | 3923 | { |
| 3873 | int i; | 3924 | int i; |
| 3874 | for (i = 0; i < ASIZE (prop); ++i) | 3925 | for (i = 0; i < ASIZE (spec); ++i) |
| 3875 | if (handle_single_display_spec (it, AREF (prop, i), object, overlay, | 3926 | if (handle_single_display_spec (it, AREF (spec, i), object, overlay, |
| 3876 | position, display_replaced_p)) | 3927 | position, bufpos, replacing_p, |
| 3928 | frame_window_p)) | ||
| 3877 | { | 3929 | { |
| 3878 | display_replaced_p = 1; | 3930 | replacing_p = 1; |
| 3879 | /* If some text in a string is replaced, `position' no | 3931 | /* If some text in a string is replaced, `position' no |
| 3880 | longer points to the position of `object'. */ | 3932 | longer points to the position of `object'. */ |
| 3881 | if (STRINGP (object)) | 3933 | if (!it || STRINGP (object)) |
| 3882 | break; | 3934 | break; |
| 3883 | } | 3935 | } |
| 3884 | } | 3936 | } |
| 3885 | else | 3937 | else |
| 3886 | { | 3938 | { |
| 3887 | if (handle_single_display_spec (it, prop, object, overlay, | 3939 | if (handle_single_display_spec (it, spec, object, overlay, |
| 3888 | position, 0)) | 3940 | position, bufpos, 0, frame_window_p)) |
| 3889 | display_replaced_p = 1; | 3941 | replacing_p = 1; |
| 3890 | } | 3942 | } |
| 3891 | 3943 | ||
| 3892 | return display_replaced_p ? HANDLED_RETURN : HANDLED_NORMALLY; | 3944 | return replacing_p; |
| 3893 | } | 3945 | } |
| 3894 | 3946 | ||
| 3895 | |||
| 3896 | /* Value is the position of the end of the `display' property starting | 3947 | /* Value is the position of the end of the `display' property starting |
| 3897 | at START_POS in OBJECT. */ | 3948 | at START_POS in OBJECT. */ |
| 3898 | 3949 | ||
| @@ -3916,10 +3967,12 @@ display_prop_end (struct it *it, Lisp_Object object, struct text_pos start_pos) | |||
| 3916 | 3967 | ||
| 3917 | /* Set up IT from a single `display' property specification SPEC. OBJECT | 3968 | /* Set up IT from a single `display' property specification SPEC. OBJECT |
| 3918 | is the object in which the `display' property was found. *POSITION | 3969 | is the object in which the `display' property was found. *POSITION |
| 3919 | is the position at which it was found. DISPLAY_REPLACED_P non-zero | 3970 | is the position in OBJECT at which the `display' property was found. |
| 3920 | means that we previously saw a display specification which already | 3971 | BUFPOS is the buffer position of OBJECT (different from POSITION if |
| 3921 | replaced text display with something else, for example an image; | 3972 | OBJECT is not a buffer). DISPLAY_REPLACED_P non-zero means that we |
| 3922 | we ignore such properties after the first one has been processed. | 3973 | previously saw a display specification which already replaced text |
| 3974 | display with something else, for example an image; we ignore such | ||
| 3975 | properties after the first one has been processed. | ||
| 3923 | 3976 | ||
| 3924 | OVERLAY is the overlay this `display' property came from, | 3977 | OVERLAY is the overlay this `display' property came from, |
| 3925 | or nil if it was a text property. | 3978 | or nil if it was a text property. |
| @@ -3928,17 +3981,22 @@ display_prop_end (struct it *it, Lisp_Object object, struct text_pos start_pos) | |||
| 3928 | cases too, set *POSITION to the position where the `display' | 3981 | cases too, set *POSITION to the position where the `display' |
| 3929 | property ends. | 3982 | property ends. |
| 3930 | 3983 | ||
| 3984 | If IT is NULL, only examine the property specification in SPEC, but | ||
| 3985 | don't set up IT. In that case, FRAME_WINDOW_P non-zero means SPEC | ||
| 3986 | is intended to be displayed in a window on a GUI frame. | ||
| 3987 | |||
| 3931 | Value is non-zero if something was found which replaces the display | 3988 | Value is non-zero if something was found which replaces the display |
| 3932 | of buffer or string text. */ | 3989 | of buffer or string text. */ |
| 3933 | 3990 | ||
| 3934 | static int | 3991 | static int |
| 3935 | handle_single_display_spec (struct it *it, Lisp_Object spec, Lisp_Object object, | 3992 | handle_single_display_spec (struct it *it, Lisp_Object spec, Lisp_Object object, |
| 3936 | Lisp_Object overlay, struct text_pos *position, | 3993 | Lisp_Object overlay, struct text_pos *position, |
| 3937 | int display_replaced_p) | 3994 | EMACS_INT bufpos, int display_replaced_p, |
| 3995 | int frame_window_p) | ||
| 3938 | { | 3996 | { |
| 3939 | Lisp_Object form; | 3997 | Lisp_Object form; |
| 3940 | Lisp_Object location, value; | 3998 | Lisp_Object location, value; |
| 3941 | struct text_pos start_pos; | 3999 | struct text_pos start_pos = *position; |
| 3942 | int valid_p; | 4000 | int valid_p; |
| 3943 | 4001 | ||
| 3944 | /* If SPEC is a list of the form `(when FORM . VALUE)', evaluate FORM. | 4002 | /* If SPEC is a list of the form `(when FORM . VALUE)', evaluate FORM. |
| @@ -3962,11 +4020,12 @@ handle_single_display_spec (struct it *it, Lisp_Object spec, Lisp_Object object, | |||
| 3962 | buffer or string. Bind `position' to the position in the | 4020 | buffer or string. Bind `position' to the position in the |
| 3963 | object where the property was found, and `buffer-position' | 4021 | object where the property was found, and `buffer-position' |
| 3964 | to the current position in the buffer. */ | 4022 | to the current position in the buffer. */ |
| 4023 | |||
| 4024 | if (NILP (object)) | ||
| 4025 | XSETBUFFER (object, current_buffer); | ||
| 3965 | specbind (Qobject, object); | 4026 | specbind (Qobject, object); |
| 3966 | specbind (Qposition, make_number (CHARPOS (*position))); | 4027 | specbind (Qposition, make_number (CHARPOS (*position))); |
| 3967 | specbind (Qbuffer_position, | 4028 | specbind (Qbuffer_position, make_number (bufpos)); |
| 3968 | make_number (STRINGP (object) | ||
| 3969 | ? IT_CHARPOS (*it) : CHARPOS (*position))); | ||
| 3970 | GCPRO1 (form); | 4029 | GCPRO1 (form); |
| 3971 | form = safe_eval (form); | 4030 | form = safe_eval (form); |
| 3972 | UNGCPRO; | 4031 | UNGCPRO; |
| @@ -3981,63 +4040,66 @@ handle_single_display_spec (struct it *it, Lisp_Object spec, Lisp_Object object, | |||
| 3981 | && EQ (XCAR (spec), Qheight) | 4040 | && EQ (XCAR (spec), Qheight) |
| 3982 | && CONSP (XCDR (spec))) | 4041 | && CONSP (XCDR (spec))) |
| 3983 | { | 4042 | { |
| 3984 | if (!FRAME_WINDOW_P (it->f)) | 4043 | if (it) |
| 3985 | return 0; | ||
| 3986 | |||
| 3987 | it->font_height = XCAR (XCDR (spec)); | ||
| 3988 | if (!NILP (it->font_height)) | ||
| 3989 | { | 4044 | { |
| 3990 | struct face *face = FACE_FROM_ID (it->f, it->face_id); | 4045 | if (!FRAME_WINDOW_P (it->f)) |
| 3991 | int new_height = -1; | 4046 | return 0; |
| 3992 | 4047 | ||
| 3993 | if (CONSP (it->font_height) | 4048 | it->font_height = XCAR (XCDR (spec)); |
| 3994 | && (EQ (XCAR (it->font_height), Qplus) | 4049 | if (!NILP (it->font_height)) |
| 3995 | || EQ (XCAR (it->font_height), Qminus)) | ||
| 3996 | && CONSP (XCDR (it->font_height)) | ||
| 3997 | && INTEGERP (XCAR (XCDR (it->font_height)))) | ||
| 3998 | { | ||
| 3999 | /* `(+ N)' or `(- N)' where N is an integer. */ | ||
| 4000 | int steps = XINT (XCAR (XCDR (it->font_height))); | ||
| 4001 | if (EQ (XCAR (it->font_height), Qplus)) | ||
| 4002 | steps = - steps; | ||
| 4003 | it->face_id = smaller_face (it->f, it->face_id, steps); | ||
| 4004 | } | ||
| 4005 | else if (FUNCTIONP (it->font_height)) | ||
| 4006 | { | 4050 | { |
| 4007 | /* Call function with current height as argument. | 4051 | struct face *face = FACE_FROM_ID (it->f, it->face_id); |
| 4008 | Value is the new height. */ | 4052 | int new_height = -1; |
| 4009 | Lisp_Object height; | 4053 | |
| 4010 | height = safe_call1 (it->font_height, | 4054 | if (CONSP (it->font_height) |
| 4011 | face->lface[LFACE_HEIGHT_INDEX]); | 4055 | && (EQ (XCAR (it->font_height), Qplus) |
| 4012 | if (NUMBERP (height)) | 4056 | || EQ (XCAR (it->font_height), Qminus)) |
| 4013 | new_height = XFLOATINT (height); | 4057 | && CONSP (XCDR (it->font_height)) |
| 4014 | } | 4058 | && INTEGERP (XCAR (XCDR (it->font_height)))) |
| 4015 | else if (NUMBERP (it->font_height)) | 4059 | { |
| 4016 | { | 4060 | /* `(+ N)' or `(- N)' where N is an integer. */ |
| 4017 | /* Value is a multiple of the canonical char height. */ | 4061 | int steps = XINT (XCAR (XCDR (it->font_height))); |
| 4018 | struct face *f; | 4062 | if (EQ (XCAR (it->font_height), Qplus)) |
| 4063 | steps = - steps; | ||
| 4064 | it->face_id = smaller_face (it->f, it->face_id, steps); | ||
| 4065 | } | ||
| 4066 | else if (FUNCTIONP (it->font_height)) | ||
| 4067 | { | ||
| 4068 | /* Call function with current height as argument. | ||
| 4069 | Value is the new height. */ | ||
| 4070 | Lisp_Object height; | ||
| 4071 | height = safe_call1 (it->font_height, | ||
| 4072 | face->lface[LFACE_HEIGHT_INDEX]); | ||
| 4073 | if (NUMBERP (height)) | ||
| 4074 | new_height = XFLOATINT (height); | ||
| 4075 | } | ||
| 4076 | else if (NUMBERP (it->font_height)) | ||
| 4077 | { | ||
| 4078 | /* Value is a multiple of the canonical char height. */ | ||
| 4079 | struct face *f; | ||
| 4019 | 4080 | ||
| 4020 | f = FACE_FROM_ID (it->f, | 4081 | f = FACE_FROM_ID (it->f, |
| 4021 | lookup_basic_face (it->f, DEFAULT_FACE_ID)); | 4082 | lookup_basic_face (it->f, DEFAULT_FACE_ID)); |
| 4022 | new_height = (XFLOATINT (it->font_height) | 4083 | new_height = (XFLOATINT (it->font_height) |
| 4023 | * XINT (f->lface[LFACE_HEIGHT_INDEX])); | 4084 | * XINT (f->lface[LFACE_HEIGHT_INDEX])); |
| 4024 | } | 4085 | } |
| 4025 | else | 4086 | else |
| 4026 | { | 4087 | { |
| 4027 | /* Evaluate IT->font_height with `height' bound to the | 4088 | /* Evaluate IT->font_height with `height' bound to the |
| 4028 | current specified height to get the new height. */ | 4089 | current specified height to get the new height. */ |
| 4029 | int count = SPECPDL_INDEX (); | 4090 | int count = SPECPDL_INDEX (); |
| 4030 | 4091 | ||
| 4031 | specbind (Qheight, face->lface[LFACE_HEIGHT_INDEX]); | 4092 | specbind (Qheight, face->lface[LFACE_HEIGHT_INDEX]); |
| 4032 | value = safe_eval (it->font_height); | 4093 | value = safe_eval (it->font_height); |
| 4033 | unbind_to (count, Qnil); | 4094 | unbind_to (count, Qnil); |
| 4034 | 4095 | ||
| 4035 | if (NUMBERP (value)) | 4096 | if (NUMBERP (value)) |
| 4036 | new_height = XFLOATINT (value); | 4097 | new_height = XFLOATINT (value); |
| 4037 | } | 4098 | } |
| 4038 | 4099 | ||
| 4039 | if (new_height > 0) | 4100 | if (new_height > 0) |
| 4040 | it->face_id = face_with_height (it->f, it->face_id, new_height); | 4101 | it->face_id = face_with_height (it->f, it->face_id, new_height); |
| 4102 | } | ||
| 4041 | } | 4103 | } |
| 4042 | 4104 | ||
| 4043 | return 0; | 4105 | return 0; |
| @@ -4048,12 +4110,15 @@ handle_single_display_spec (struct it *it, Lisp_Object spec, Lisp_Object object, | |||
| 4048 | && EQ (XCAR (spec), Qspace_width) | 4110 | && EQ (XCAR (spec), Qspace_width) |
| 4049 | && CONSP (XCDR (spec))) | 4111 | && CONSP (XCDR (spec))) |
| 4050 | { | 4112 | { |
| 4051 | if (!FRAME_WINDOW_P (it->f)) | 4113 | if (it) |
| 4052 | return 0; | 4114 | { |
| 4115 | if (!FRAME_WINDOW_P (it->f)) | ||
| 4116 | return 0; | ||
| 4053 | 4117 | ||
| 4054 | value = XCAR (XCDR (spec)); | 4118 | value = XCAR (XCDR (spec)); |
| 4055 | if (NUMBERP (value) && XFLOATINT (value) > 0) | 4119 | if (NUMBERP (value) && XFLOATINT (value) > 0) |
| 4056 | it->space_width = value; | 4120 | it->space_width = value; |
| 4121 | } | ||
| 4057 | 4122 | ||
| 4058 | return 0; | 4123 | return 0; |
| 4059 | } | 4124 | } |
| @@ -4064,20 +4129,23 @@ handle_single_display_spec (struct it *it, Lisp_Object spec, Lisp_Object object, | |||
| 4064 | { | 4129 | { |
| 4065 | Lisp_Object tem; | 4130 | Lisp_Object tem; |
| 4066 | 4131 | ||
| 4067 | if (!FRAME_WINDOW_P (it->f)) | 4132 | if (it) |
| 4068 | return 0; | ||
| 4069 | |||
| 4070 | if (tem = XCDR (spec), CONSP (tem)) | ||
| 4071 | { | 4133 | { |
| 4072 | it->slice.x = XCAR (tem); | 4134 | if (!FRAME_WINDOW_P (it->f)) |
| 4073 | if (tem = XCDR (tem), CONSP (tem)) | 4135 | return 0; |
| 4136 | |||
| 4137 | if (tem = XCDR (spec), CONSP (tem)) | ||
| 4074 | { | 4138 | { |
| 4075 | it->slice.y = XCAR (tem); | 4139 | it->slice.x = XCAR (tem); |
| 4076 | if (tem = XCDR (tem), CONSP (tem)) | 4140 | if (tem = XCDR (tem), CONSP (tem)) |
| 4077 | { | 4141 | { |
| 4078 | it->slice.width = XCAR (tem); | 4142 | it->slice.y = XCAR (tem); |
| 4079 | if (tem = XCDR (tem), CONSP (tem)) | 4143 | if (tem = XCDR (tem), CONSP (tem)) |
| 4080 | it->slice.height = XCAR (tem); | 4144 | { |
| 4145 | it->slice.width = XCAR (tem); | ||
| 4146 | if (tem = XCDR (tem), CONSP (tem)) | ||
| 4147 | it->slice.height = XCAR (tem); | ||
| 4148 | } | ||
| 4081 | } | 4149 | } |
| 4082 | } | 4150 | } |
| 4083 | } | 4151 | } |
| @@ -4090,36 +4158,43 @@ handle_single_display_spec (struct it *it, Lisp_Object spec, Lisp_Object object, | |||
| 4090 | && EQ (XCAR (spec), Qraise) | 4158 | && EQ (XCAR (spec), Qraise) |
| 4091 | && CONSP (XCDR (spec))) | 4159 | && CONSP (XCDR (spec))) |
| 4092 | { | 4160 | { |
| 4093 | if (!FRAME_WINDOW_P (it->f)) | 4161 | if (it) |
| 4094 | return 0; | 4162 | { |
| 4163 | if (!FRAME_WINDOW_P (it->f)) | ||
| 4164 | return 0; | ||
| 4095 | 4165 | ||
| 4096 | #ifdef HAVE_WINDOW_SYSTEM | 4166 | #ifdef HAVE_WINDOW_SYSTEM |
| 4097 | value = XCAR (XCDR (spec)); | 4167 | value = XCAR (XCDR (spec)); |
| 4098 | if (NUMBERP (value)) | 4168 | if (NUMBERP (value)) |
| 4099 | { | 4169 | { |
| 4100 | struct face *face = FACE_FROM_ID (it->f, it->face_id); | 4170 | struct face *face = FACE_FROM_ID (it->f, it->face_id); |
| 4101 | it->voffset = - (XFLOATINT (value) | 4171 | it->voffset = - (XFLOATINT (value) |
| 4102 | * (FONT_HEIGHT (face->font))); | 4172 | * (FONT_HEIGHT (face->font))); |
| 4103 | } | 4173 | } |
| 4104 | #endif /* HAVE_WINDOW_SYSTEM */ | 4174 | #endif /* HAVE_WINDOW_SYSTEM */ |
| 4175 | } | ||
| 4105 | 4176 | ||
| 4106 | return 0; | 4177 | return 0; |
| 4107 | } | 4178 | } |
| 4108 | 4179 | ||
| 4109 | /* Don't handle the other kinds of display specifications | 4180 | /* Don't handle the other kinds of display specifications |
| 4110 | inside a string that we got from a `display' property. */ | 4181 | inside a string that we got from a `display' property. */ |
| 4111 | if (it->string_from_display_prop_p) | 4182 | if (it && it->string_from_display_prop_p) |
| 4112 | return 0; | 4183 | return 0; |
| 4113 | 4184 | ||
| 4114 | /* Characters having this form of property are not displayed, so | 4185 | /* Characters having this form of property are not displayed, so |
| 4115 | we have to find the end of the property. */ | 4186 | we have to find the end of the property. */ |
| 4116 | start_pos = *position; | 4187 | if (it) |
| 4117 | *position = display_prop_end (it, object, start_pos); | 4188 | { |
| 4189 | start_pos = *position; | ||
| 4190 | *position = display_prop_end (it, object, start_pos); | ||
| 4191 | } | ||
| 4118 | value = Qnil; | 4192 | value = Qnil; |
| 4119 | 4193 | ||
| 4120 | /* Stop the scan at that end position--we assume that all | 4194 | /* Stop the scan at that end position--we assume that all |
| 4121 | text properties change there. */ | 4195 | text properties change there. */ |
| 4122 | it->stop_charpos = position->charpos; | 4196 | if (it) |
| 4197 | it->stop_charpos = position->charpos; | ||
| 4123 | 4198 | ||
| 4124 | /* Handle `(left-fringe BITMAP [FACE])' | 4199 | /* Handle `(left-fringe BITMAP [FACE])' |
| 4125 | and `(right-fringe BITMAP [FACE])'. */ | 4200 | and `(right-fringe BITMAP [FACE])'. */ |
| @@ -4128,12 +4203,16 @@ handle_single_display_spec (struct it *it, Lisp_Object spec, Lisp_Object object, | |||
| 4128 | || EQ (XCAR (spec), Qright_fringe)) | 4203 | || EQ (XCAR (spec), Qright_fringe)) |
| 4129 | && CONSP (XCDR (spec))) | 4204 | && CONSP (XCDR (spec))) |
| 4130 | { | 4205 | { |
| 4131 | int face_id = lookup_basic_face (it->f, DEFAULT_FACE_ID); | ||
| 4132 | int fringe_bitmap; | 4206 | int fringe_bitmap; |
| 4133 | 4207 | ||
| 4134 | if (!FRAME_WINDOW_P (it->f)) | 4208 | if (it) |
| 4135 | /* If we return here, POSITION has been advanced | 4209 | { |
| 4136 | across the text with this property. */ | 4210 | if (!FRAME_WINDOW_P (it->f)) |
| 4211 | /* If we return here, POSITION has been advanced | ||
| 4212 | across the text with this property. */ | ||
| 4213 | return 0; | ||
| 4214 | } | ||
| 4215 | else if (!frame_window_p) | ||
| 4137 | return 0; | 4216 | return 0; |
| 4138 | 4217 | ||
| 4139 | #ifdef HAVE_WINDOW_SYSTEM | 4218 | #ifdef HAVE_WINDOW_SYSTEM |
| @@ -4144,42 +4223,47 @@ handle_single_display_spec (struct it *it, Lisp_Object spec, Lisp_Object object, | |||
| 4144 | across the text with this property. */ | 4223 | across the text with this property. */ |
| 4145 | return 0; | 4224 | return 0; |
| 4146 | 4225 | ||
| 4147 | if (CONSP (XCDR (XCDR (spec)))) | 4226 | if (it) |
| 4148 | { | 4227 | { |
| 4149 | Lisp_Object face_name = XCAR (XCDR (XCDR (spec))); | 4228 | int face_id = lookup_basic_face (it->f, DEFAULT_FACE_ID);; |
| 4150 | int face_id2 = lookup_derived_face (it->f, face_name, | ||
| 4151 | FRINGE_FACE_ID, 0); | ||
| 4152 | if (face_id2 >= 0) | ||
| 4153 | face_id = face_id2; | ||
| 4154 | } | ||
| 4155 | 4229 | ||
| 4156 | /* Save current settings of IT so that we can restore them | 4230 | if (CONSP (XCDR (XCDR (spec)))) |
| 4157 | when we are finished with the glyph property value. */ | 4231 | { |
| 4158 | push_it (it, position); | 4232 | Lisp_Object face_name = XCAR (XCDR (XCDR (spec))); |
| 4233 | int face_id2 = lookup_derived_face (it->f, face_name, | ||
| 4234 | FRINGE_FACE_ID, 0); | ||
| 4235 | if (face_id2 >= 0) | ||
| 4236 | face_id = face_id2; | ||
| 4237 | } | ||
| 4159 | 4238 | ||
| 4160 | it->area = TEXT_AREA; | 4239 | /* Save current settings of IT so that we can restore them |
| 4161 | it->what = IT_IMAGE; | 4240 | when we are finished with the glyph property value. */ |
| 4162 | it->image_id = -1; /* no image */ | 4241 | push_it (it, position); |
| 4163 | it->position = start_pos; | ||
| 4164 | it->object = NILP (object) ? it->w->buffer : object; | ||
| 4165 | it->method = GET_FROM_IMAGE; | ||
| 4166 | it->from_overlay = Qnil; | ||
| 4167 | it->face_id = face_id; | ||
| 4168 | 4242 | ||
| 4169 | /* Say that we haven't consumed the characters with | 4243 | it->area = TEXT_AREA; |
| 4170 | `display' property yet. The call to pop_it in | 4244 | it->what = IT_IMAGE; |
| 4171 | set_iterator_to_next will clean this up. */ | 4245 | it->image_id = -1; /* no image */ |
| 4172 | *position = start_pos; | 4246 | it->position = start_pos; |
| 4247 | it->object = NILP (object) ? it->w->buffer : object; | ||
| 4248 | it->method = GET_FROM_IMAGE; | ||
| 4249 | it->from_overlay = Qnil; | ||
| 4250 | it->face_id = face_id; | ||
| 4173 | 4251 | ||
| 4174 | if (EQ (XCAR (spec), Qleft_fringe)) | 4252 | /* Say that we haven't consumed the characters with |
| 4175 | { | 4253 | `display' property yet. The call to pop_it in |
| 4176 | it->left_user_fringe_bitmap = fringe_bitmap; | 4254 | set_iterator_to_next will clean this up. */ |
| 4177 | it->left_user_fringe_face_id = face_id; | 4255 | *position = start_pos; |
| 4178 | } | 4256 | |
| 4179 | else | 4257 | if (EQ (XCAR (spec), Qleft_fringe)) |
| 4180 | { | 4258 | { |
| 4181 | it->right_user_fringe_bitmap = fringe_bitmap; | 4259 | it->left_user_fringe_bitmap = fringe_bitmap; |
| 4182 | it->right_user_fringe_face_id = face_id; | 4260 | it->left_user_fringe_face_id = face_id; |
| 4261 | } | ||
| 4262 | else | ||
| 4263 | { | ||
| 4264 | it->right_user_fringe_bitmap = fringe_bitmap; | ||
| 4265 | it->right_user_fringe_face_id = face_id; | ||
| 4266 | } | ||
| 4183 | } | 4267 | } |
| 4184 | #endif /* HAVE_WINDOW_SYSTEM */ | 4268 | #endif /* HAVE_WINDOW_SYSTEM */ |
| 4185 | return 1; | 4269 | return 1; |
| @@ -4222,12 +4306,16 @@ handle_single_display_spec (struct it *it, Lisp_Object spec, Lisp_Object object, | |||
| 4222 | 4306 | ||
| 4223 | valid_p = (STRINGP (value) | 4307 | valid_p = (STRINGP (value) |
| 4224 | #ifdef HAVE_WINDOW_SYSTEM | 4308 | #ifdef HAVE_WINDOW_SYSTEM |
| 4225 | || (FRAME_WINDOW_P (it->f) && valid_image_p (value)) | 4309 | || ((it ? FRAME_WINDOW_P (it->f) : frame_window_p) |
| 4310 | && valid_image_p (value)) | ||
| 4226 | #endif /* not HAVE_WINDOW_SYSTEM */ | 4311 | #endif /* not HAVE_WINDOW_SYSTEM */ |
| 4227 | || (CONSP (value) && EQ (XCAR (value), Qspace))); | 4312 | || (CONSP (value) && EQ (XCAR (value), Qspace))); |
| 4228 | 4313 | ||
| 4229 | if (valid_p && !display_replaced_p) | 4314 | if (valid_p && !display_replaced_p) |
| 4230 | { | 4315 | { |
| 4316 | if (!it) | ||
| 4317 | return 1; | ||
| 4318 | |||
| 4231 | /* Save current settings of IT so that we can restore them | 4319 | /* Save current settings of IT so that we can restore them |
| 4232 | when we are finished with the glyph property value. */ | 4320 | when we are finished with the glyph property value. */ |
| 4233 | push_it (it, position); | 4321 | push_it (it, position); |
| @@ -18080,6 +18168,8 @@ See also `bidi-paragraph-direction'. */) | |||
| 18080 | bytepos--; | 18168 | bytepos--; |
| 18081 | itb.charpos = pos; | 18169 | itb.charpos = pos; |
| 18082 | itb.bytepos = bytepos; | 18170 | itb.bytepos = bytepos; |
| 18171 | itb.nchars = -1; | ||
| 18172 | itb.frame_window_p = FRAME_WINDOW_P (SELECTED_FRAME ()); /* guesswork */ | ||
| 18083 | itb.first_elt = 1; | 18173 | itb.first_elt = 1; |
| 18084 | itb.separator_limit = -1; | 18174 | itb.separator_limit = -1; |
| 18085 | itb.paragraph_dir = NEUTRAL_DIR; | 18175 | itb.paragraph_dir = NEUTRAL_DIR; |