diff options
author | Akira Kakuto <kakuto@fuk.kindai.ac.jp> | 2018-02-03 22:51:52 +0000 |
---|---|---|
committer | Akira Kakuto <kakuto@fuk.kindai.ac.jp> | 2018-02-03 22:51:52 +0000 |
commit | b2bd23ad17f82aad5776427229b915e7c8e5bb35 (patch) | |
tree | 328707d56ad98a29f6400bc9df6f3f2a1b4ef91f /Build/source | |
parent | 859bc2f0c7457e00be54366b2b2a5f627b90b5b3 (diff) |
xetex.web: Jonathan fixes #137
git-svn-id: svn://tug.org/texlive/trunk@46532 c570f23f-e606-0410-a88d-b1316a301751
Diffstat (limited to 'Build/source')
-rw-r--r-- | Build/source/texk/web2c/xetexdir/ChangeLog | 10 | ||||
-rw-r--r-- | Build/source/texk/web2c/xetexdir/xetex.web | 96 |
2 files changed, 73 insertions, 33 deletions
diff --git a/Build/source/texk/web2c/xetexdir/ChangeLog b/Build/source/texk/web2c/xetexdir/ChangeLog index f1cc12e7ae9..76b77d0e513 100644 --- a/Build/source/texk/web2c/xetexdir/ChangeLog +++ b/Build/source/texk/web2c/xetexdir/ChangeLog @@ -25,6 +25,16 @@ depend on XeTeX choosing the appropriate face for a given size: the boundaries at which face selection changes will be slightly shifted (corrected) from how earlier versions behaved. + * xetex.web: Avoid prematurely merging following text with the + no-break text of a \discretionary. We don't want to combine + text after \discretionary{A}{B}{C} into the same node as the + (trailing node of the) no-break parameter {C}, because this + would result in following text being lost in the case where + the discretionary break is taken. When this happens, its + no-break text (recorded as a count of nodes) is supposed + to be skipped over, but if we've combined following characters + with the trailing node, they will also be (incorrectly) + skipped. Fixes #137. 2018-01-17 Akira Kakuto <kakuto@fuk.kindai.ac.jp> diff --git a/Build/source/texk/web2c/xetexdir/xetex.web b/Build/source/texk/web2c/xetexdir/xetex.web index e9b793c2b71..acd2069aa8f 100644 --- a/Build/source/texk/web2c/xetexdir/xetex.web +++ b/Build/source/texk/web2c/xetexdir/xetex.web @@ -3331,7 +3331,14 @@ than size and length fields, and there's no subsidiary C pointer. @d native_word_node=40 {|subtype| of whatsits that hold |native_font| words} @d native_word_node_AT=41 {a |native_word_node| that should output ActualText} -@d glyph_node=42 {|subtype| in whatsits that hold glyph numbers} +@d native_word_node_disc_flag=2 {flag added to the |subtype| when the node is the trailing node + of the no-break text of a discretionary, so we can avoid + merging it with following chars} +@d native_word_node_MIN=native_word_node +@d native_word_node_MAX=native_word_node_AT+native_word_node_disc_flag +@d is_native_word_subtype(#)==((subtype(#)>=native_word_node_MIN) and (subtype(#)<=native_word_node_MAX)) + +@d glyph_node=44 {|subtype| in whatsits that hold glyph numbers} @d native_node_size=6 {size of a |native_word| node (plus the actual chars) -- see also \.{xetex.h}} @d glyph_node_size=5 @@ -3373,8 +3380,8 @@ So |pic_node_size|, which does not include any space for the picture file pathna A |pdf_node| is just like |pic_node|, but generate a different \.{XDV} file code. -@d pic_node=43 {|subtype| in whatsits that hold picture file references} -@d pdf_node=44 {|subtype| in whatsits that hold PDF page references} +@d pic_node=45 {|subtype| in whatsits that hold picture file references} +@d pdf_node=46 {|subtype| in whatsits that hold PDF page references} @# @d pic_node_size=9 {must sync with \.{xetex.h}} @d pic_path_length(#)==mem[#+4].hh.b0 @@ -3967,7 +3974,10 @@ hlist_node,vlist_node,ins_node,mark_node,adjust_node, unset_node: print("[]"); whatsit_node: case subtype(p) of - native_word_node, native_word_node_AT: begin + native_word_node, native_word_node_AT, + native_word_node+native_word_node_disc_flag, + native_word_node_AT+native_word_node_disc_flag: + begin if native_font(p)<>font_in_short_display then begin print_esc(font_id_text(native_font(p))); print_char(" "); @@ -13995,7 +14005,10 @@ end; @ Extra stuff for justifiable AAT text; need to merge runs of words and normal spaces. -@d is_native_word_node(#) == (((#)<>null and (not is_char_node(#)) and (type(#) = whatsit_node) and ((subtype(#) = native_word_node) or (subtype(#) = native_word_node_AT)))) +@d is_native_word_node(#) == (((#)<>null) + and (not is_char_node(#)) + and (type(#) = whatsit_node) + and (is_native_word_subtype(#))) @d is_glyph_node(#) == (((#)<>null and (not is_char_node(#)) and (type(#) = whatsit_node) and (subtype(#) = glyph_node))) @d node_is_invisible_to_interword_space(#)== @@ -14061,7 +14074,7 @@ end_node_run: {now |r| points to first |native_word_node| of the run, and |p| to q:=r; loop begin if type(q) = whatsit_node then begin - if (subtype(q) = native_word_node) or (subtype(q) = native_word_node_AT) then begin + if (is_native_word_subtype(q)) then begin for j:=0 to native_length(q)-1 do append_char(get_native_char(q, j)); k:=k + width(q); @@ -19608,8 +19621,7 @@ else case type(v) of hlist_node,vlist_node,rule_node,kern_node: break_width[1]:=break_width[1]-width(v); whatsit_node: - if (subtype(v)=native_word_node) - or (subtype(v)=native_word_node_AT) + if (is_native_word_subtype(v)) or (subtype(v)=glyph_node) or (subtype(v)=pic_node) or (subtype(v)=pdf_node) @@ -19633,8 +19645,7 @@ else case type(s) of hlist_node,vlist_node,rule_node,kern_node: break_width[1]:=break_width[1]+width(s); whatsit_node: - if (subtype(s)=native_word_node) - or (subtype(s)=native_word_node_AT) + if (is_native_word_subtype(s)) or (subtype(s)=glyph_node) or (subtype(s)=pic_node) or (subtype(s)=pdf_node) @@ -20220,8 +20231,7 @@ else case type(s) of hlist_node,vlist_node,rule_node,kern_node: disc_width:=disc_width+width(s); whatsit_node: - if (subtype(s)=native_word_node) - or (subtype(s)=native_word_node_AT) + if (is_native_word_subtype(s)) or (subtype(s)=glyph_node) or (subtype(s)=pic_node) or (subtype(s)=pdf_node) @@ -20245,8 +20255,7 @@ else case type(s) of hlist_node,vlist_node,rule_node,kern_node: act_width:=act_width+width(s); whatsit_node: - if (subtype(s)=native_word_node) - or (subtype(s)=native_word_node_AT) + if (is_native_word_subtype(s)) or (subtype(s)=glyph_node) or (subtype(s)=pic_node) or (subtype(s)=pdf_node) @@ -20835,7 +20844,7 @@ loop@+ begin if is_char_node(s) then else if (type(s)=math_node)and(subtype(s)>=L_code) then goto continue else if type(s)=whatsit_node then begin - if (subtype(s) = native_word_node) or (subtype(s) = native_word_node_AT) then begin + if (is_native_word_subtype(s)) then begin { we only consider the node if it contains at least one letter, otherwise we'll skip it } for l:=0 to native_length(s) - 1 do begin c:=get_native_usv(s, l); @@ -23669,7 +23678,12 @@ collected: repeat if main_h = 0 then main_h:=main_k; - if is_native_word_node(main_pp) + {If |main_pp| is the [last node of the] no-break text of a discretionary, + we do not want to merge following text into it, as that would swallow + the following text in the case where the discretionary break is used + and its no-break list is discarded. Hence, we do this only when the + |native_word_node_disc_flag| was NOT set on the |main_pp| node.} + if (is_native_word_node(main_pp) and (subtype(main_pp)<=native_word_node_AT)) and (native_font(main_pp)=main_f) and (main_ppp<>main_pp) and (not is_char_node(main_ppp)) @@ -25171,7 +25185,7 @@ begin if tail<>head then begin if is_char_node(tail) then p:=tail else if type(tail)=ligature_node then p:=lig_char(tail) else if (type(tail)=whatsit_node) then begin - if (subtype(tail)=native_word_node) or (subtype(tail)=native_word_node_AT) then begin + if is_native_word_subtype(tail) then begin tail_append(new_kern(get_native_italic_correction(tail))); subtype(tail):=explicit; end else if (subtype(tail)=glyph_node) then begin @@ -25262,7 +25276,11 @@ else begin print_err("Discretionary list is too long"); ("You can't seriously need such a huge discretionary list?"); error; end; -if n>0 then tail:=q; +if n>0 then begin + tail:=q; + if (is_native_word_node(tail)) then + subtype(tail):=subtype(tail)+native_word_node_disc_flag; + end; decr(save_ptr); return; end @@ -25273,8 +25291,8 @@ q:=head; p:=link(q); n:=0; while p<>null do begin if not is_char_node(p) then if type(p)>rule_node then if type(p)<>kern_node then if type(p)<>ligature_node then - if (type(p)<>whatsit_node) or ((subtype(p)<>native_word_node) and (subtype(p)<>native_word_node_AT) - and (subtype(p)<>glyph_node)) then + if (type(p)<>whatsit_node) + or (not is_native_word_subtype(p) and (subtype(p)<>glyph_node)) then begin print_err("Improper discretionary list"); @.Improper discretionary list@> help1("Discretionary lists must contain only boxes and kerns.");@/ @@ -29092,7 +29110,10 @@ language_node:begin print_esc("setlanguage"); print_int(what_lhm(p)); print_char(","); print_int(what_rhm(p)); print_char(")"); end; -native_word_node, native_word_node_AT:begin print_esc(font_id_text(native_font(p))); +native_word_node, native_word_node_AT, +native_word_node+native_word_node_disc_flag, +native_word_node_AT+native_word_node_disc_flag: +begin print_esc(font_id_text(native_font(p))); print_char(" "); print_native_word(p); end; @@ -29125,7 +29146,10 @@ write_node,special_node: begin r:=get_node(write_node_size); close_node,language_node: begin r:=get_node(small_node_size); words:=small_node_size; end; -native_word_node, native_word_node_AT: begin words:=native_size(p); +native_word_node, native_word_node_AT, +native_word_node+native_word_node_disc_flag, +native_word_node_AT+native_word_node_disc_flag: +begin words:=native_size(p); r:=get_node(words); while words > 0 do begin decr(words); mem[r+words]:=mem[p+words]; end; @@ -29151,7 +29175,10 @@ write_node,special_node: begin delete_token_ref(write_tokens(p)); free_node(p,write_node_size); goto done; end; close_node,language_node: free_node(p,small_node_size); -native_word_node, native_word_node_AT: begin free_native_glyph_info(p); free_node(p,native_size(p)); end; +native_word_node, native_word_node_AT, +native_word_node+native_word_node_disc_flag, +native_word_node_AT+native_word_node_disc_flag: +begin free_native_glyph_info(p); free_node(p,native_size(p)); end; glyph_node: free_node(p,glyph_node_size); pic_node,pdf_node: free_node(p,total_pic_node_size(p)); pdf_save_pos_node: @@ -29176,7 +29203,10 @@ end @ @<Incorporate a whatsit node into an hbox@>= begin case subtype(p) of - native_word_node, native_word_node_AT: begin + native_word_node, native_word_node_AT, + native_word_node+native_word_node_disc_flag, + native_word_node_AT+native_word_node_disc_flag: + begin { merge with any following word fragments in same font, discarding discretionary breaks } if (q <> r+list_offset) and (type(q) = disc_node) then k:=replace_count(q) else k:=0; while (link(q) <> p) do begin @@ -29188,7 +29218,7 @@ begin restart: if (k <= 0) and (pp <> null) and (not is_char_node(pp)) then begin if (type(pp) = whatsit_node) - and ((subtype(pp) = native_word_node) or (subtype(pp) = native_word_node_AT)) + and (is_native_word_subtype(pp)) and (native_font(pp) = native_font(p)) then begin pp:=link(pp); goto restart; @@ -29261,8 +29291,7 @@ begin end @ @<Let |d| be the width of the whatsit |p|, and |goto found| if ``visible''@>= -if (subtype(p)=native_word_node) -or (subtype(p)=native_word_node_AT) +if (is_native_word_subtype(p)) or (subtype(p)=glyph_node) or (subtype(p)=pic_node) or (subtype(p)=pdf_node) @@ -29276,8 +29305,7 @@ end else begin cur_lang:=what_lang(#); l_hyf:=what_lhm(#); r_hyf:=what_rhm(#); set_hyph_index; end - else if (subtype(#)=native_word_node) - or (subtype(#)=native_word_node_AT) + else if (is_native_word_subtype(#)) or (subtype(#)=glyph_node) or (subtype(#)=pic_node) or (subtype(#)=pdf_node) @@ -29373,7 +29401,10 @@ else @ @<Output the whatsit node |p| in an hlist@>= begin case subtype(p) of - native_word_node, native_word_node_AT, glyph_node: begin + native_word_node, native_word_node_AT, + native_word_node+native_word_node_disc_flag, + native_word_node_AT+native_word_node_disc_flag, + glyph_node: begin synch_h; synch_v; {Sync DVI state to TeX state} f:=native_font(p); if f<>dvi_f then @<Change font |dvi_f| to |f|@>; @@ -29386,7 +29417,7 @@ begin dvi_two(native_glyph(p)); cur_h:=cur_h + width(p); end else begin - if subtype(p) = native_word_node_AT then begin + if (subtype(p)=native_word_node_AT) or (subtype(p)=native_word_node_AT+native_word_node_disc_flag) then begin if (native_length(p) > 0) or (native_glyph_info_ptr(p) <> null_ptr) then begin dvi_out(set_text_and_glyphs); len:=native_length(p); @@ -31452,8 +31483,7 @@ end @ Need to measure |native_word| and picture nodes when reversing! @<Cases of |reverse|...@>= whatsit_node: - if (subtype(p)=native_word_node) - or (subtype(p)=native_word_node_AT) + if (is_native_word_subtype(p)) or (subtype(p)=glyph_node) or (subtype(p)=pic_node) or (subtype(p)=pdf_node) |