diff options
Diffstat (limited to 'Master/texmf-dist/tex/generic/babel/babel-bidi-basic-r.lua')
-rw-r--r-- | Master/texmf-dist/tex/generic/babel/babel-bidi-basic-r.lua | 177 |
1 files changed, 177 insertions, 0 deletions
diff --git a/Master/texmf-dist/tex/generic/babel/babel-bidi-basic-r.lua b/Master/texmf-dist/tex/generic/babel/babel-bidi-basic-r.lua new file mode 100644 index 00000000000..2f80775609e --- /dev/null +++ b/Master/texmf-dist/tex/generic/babel/babel-bidi-basic-r.lua @@ -0,0 +1,177 @@ +-- +-- This is file `babel-bidi-basic-r.lua', +-- generated with the docstrip utility. +-- +-- The original source files were: +-- +-- babel.dtx (with options: `basic-r') +-- +-- +-- Copyright (C) 2012-2017 Javier Bezos and Johannes L. Braams. +-- Copyright (C) 1989-2012 Johannes L. Braams and +-- any individual authors listed elsewhere in this file. +-- All rights reserved. +-- +-- This file is part of the Babel system. +-- -------------------------------------- +-- +-- It may be distributed and/or modified under the +-- conditions of the LaTeX Project Public License, either version 1.3 +-- of this license or (at your option) any later version. +-- The latest version of this license is in +-- http://www.latex-project.org/lppl.txt +-- and version 1.3 or later is part of all distributions of LaTeX +-- version 2003/12/01 or later. +-- +-- This work has the LPPL maintenance status "maintained". +-- +-- The Current Maintainer of this work is Javier Bezos. +-- +-- The list of derived (unpacked) files belonging to the distribution +-- and covered by LPPL is defined by the unpacking scripts (with +-- extension |.ins|) which are part of the distribution. +-- +Babel = Babel or {} + +Babel.langdirs = {} + +require('babel-bidi.lua') + +local characters = Babel.characters +local ranges = Babel.ranges + +local DIR = node.id("dir") + +local function dir_mark(head, from, to, outer) + dir = (outer == 'r') and 'TLT' or 'TRT' -- ie, reverse + local d = node.new(DIR) + d.dir = '+' .. dir + node.insert_before(head, from, d) + d = node.new(DIR) + d.dir = '-' .. dir + node.insert_after(head, to, d) +end + +function Babel.pre_otfload(head) + local first_n, last_n = nil, nil -- first and last char with nums + local last_es = nil -- an auxiliary 'last' used with nums + local first_d, last_d = nil, nil -- first and last char in L/R block + local dir = nil + local dir_real = nil + local strong = ('TRT' == tex.pardir) and 'r' or 'l' + local strong_lr = (strong == 'l') and 'l' or 'r' + local outer = strong + + local new_dir = false + local first_dir = false + + local last_lr = nil + + local type_n = '' + + for item in node.traverse(head) do + + -- three cases: glyph, dir, otherwise + if item.id == node.id'glyph' then + + local chardata = characters[item.char] + dir = chardata and chardata.d or nil + if not dir then + for nn, et in ipairs(ranges) do + if item.char < et[1] then + break + elseif item.char <= et[2] then + dir = et[3] + break + end + end + end + dir = dir or 'l' + if new_dir then + strong = Babel.langdirs[item.lang] or 'l' + strong_lr = (strong == 'l') and 'l' or 'r' + outer = strong_lr + new_dir = false + end + if dir == 'nsm' then dir = strong end -- W1 + dir_real = dir -- We need dir_real to set strong below + if dir == 'al' then dir = 'r' end -- W3 + if strong == 'al' then + if dir == 'en' then dir = 'an' end -- W2 + if dir == 'et' or dir == 'es' then dir = 'on' end -- W6 + strong_lr = 'r' -- W3 + end + elseif item.id == node.id'dir' then + new_dir = true + dir = nil + else + dir = nil -- Not a char + end + if dir == 'en' or dir == 'an' or dir == 'et' then + if dir ~= 'et' then + type_n = dir + end + first_n = first_n or item + last_n = last_es or item + last_es = nil + elseif dir == 'es' and last_n then -- W3+W6 + last_es = item + elseif dir == 'cs' then -- it's right - do nothing + elseif first_n then -- & if dir = any but en, et, an, es, cs, inc nil + if strong_lr == 'r' and type_n ~= '' then + dir_mark(head, first_n, last_n, 'r') + elseif strong_lr == 'l' and first_d and type_n == 'an' then + dir_mark(head, first_n, last_n, 'r') + dir_mark(head, first_d, last_d, outer) + first_d, last_d = nil, nil + elseif strong_lr == 'l' and type_n ~= '' then + last_d = last_n + end + type_n = '' + first_n, last_n = nil, nil + end + if dir == 'l' or dir == 'r' then + if dir ~= outer then + first_d = first_d or item + last_d = item + elseif first_d and dir ~= strong_lr then + dir_mark(head, first_d, last_d, outer) + first_d, last_d = nil, nil + end + end + if dir and not last_lr and dir ~= 'l' and outer == 'r' then + item.char = characters[item.char] and + characters[item.char].m or item.char + elseif (dir or new_dir) and last_lr ~= item then + local mir = outer .. strong_lr .. (dir or outer) + if mir == 'rrr' or mir == 'lrr' or mir == 'rrl' or mir == 'rlr' then + for ch in node.traverse(node.next(last_lr)) do + if ch == item then break end + if ch.id == node.id'glyph' then + ch.char = characters[ch.char].m or ch.char + end + end + --last_lr = nil + end + end + if dir == 'l' or dir == 'r' then + last_lr = item + strong = dir_real -- Don't search back - best save now + strong_lr = (strong == 'l') and 'l' or 'r' + elseif new_dir then + last_lr = nil + end + end + if last_lr and outer == 'r' then + for ch in node.traverse_id(node.id'glyph', node.next(last_lr)) do + ch.char = characters[ch.char].m or ch.char + end + end + if first_n then + dir_mark(head, first_n, last_n, outer) + end + if first_d then + dir_mark(head, first_d, last_d, outer) + end + return node.prev(head) or head +end |