Created
July 31, 2019 12:14
-
-
Save zr-tex8r/ddaf5bb2f91d9df1be46e10ffa700fc3 to your computer and use it in GitHub Desktop.
Pandoc:“Markdownはデカイ文字を書くのに便利”的なフィルタ
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
-- biggggg.lua | |
-- | |
-- @copyright 2019 Takayuki YATO (aka. "ZR") | |
-- GitHub: https://github.com/zr-tex8r | |
-- Twitter: @zr_tex8r | |
-- This program is distributed under the MIT License. | |
-- | |
local filter_name = 'biggggg' | |
---------------------------------------- 設定 | |
--- デバッグログを出すか | |
local show_log = false | |
--- 拡大倍率 | |
local BIG_BASE = 1.2 | |
local LATEX_PROLOGUE = [==[ | |
\makeatletter | |
\@ifundefined{scalefont}{\DeclareRobustCommand\scalefont[1]{% | |
\dimen@\f@size\p@ \dimen@=#1\dimen@ | |
\fontsize\dimen@\dimen@\selectfont}}{} | |
\@ifundefined{textsmall}{\DeclareRobustCommand\textsmall[1]{% | |
{\scalefont{0.8333}#1}}}{} | |
\makeatother | |
]==] | |
---------------------------------------- 補助 | |
local insert, remove = table.insert, table.remove | |
--- デバッグログを出力する. | |
local function log(fmt, ...) | |
if not show_log then return end | |
io.stderr:write(filter_name..': '..fmt:format(...).."\n") | |
end | |
local function fformat(prec, val) | |
local s = ('%.'..tostring(prec)..'f'):format(val) | |
return s:gsub('0+$', ''):gsub('%.$', '') | |
end | |
---------------------------------------- フィルタ用補助 | |
--- 出力フォーマットがサポート対象であるか. | |
-- @return 真偽値 | |
local function is_format_supported() | |
return FORMAT == 'latex' or FORMAT == 'html' | |
end | |
--- 拡大用のクラス名について, その段階値を返す. | |
-- @return 段階値 (拡大用クラス以外ならnil) | |
local function scale_value(cls) | |
if cls == 'Small' then return cls end | |
if cls == 'smal' then return -0.5 end | |
local big = cls:match('^bi(g+)$') | |
if big then return #big end | |
local small = cls:match('^smal(l+)$') | |
if small then return - #small end | |
return nil | |
end | |
--- 段階値からマークアップへの変換. | |
-- @return 前側のマークアップの文字列 | |
-- @return 後側のマークアップの文字列 | |
local function scale_markup(scl) | |
if FORMAT == 'latex' then | |
if scl == 'Small' then | |
return '\\textsmall{', '}' | |
end | |
local val = fformat(4, BIG_BASE ^ scl) | |
return '{\\scalefont{'..val..'}', '}' | |
elseif FORMAT == 'html' then | |
if scl == 'Small' then | |
return '<small>', '</small>' | |
end | |
local val = fformat(2, 100 * BIG_BASE ^ scl) | |
return '<span style="font-size:'..val..'%">', '</span>' | |
else assert(false) | |
end | |
end | |
--- span要素のクラス群の中から拡大に関する情報を取り出す. | |
-- @return 段階値 (拡大用クラス不指定ならnil) | |
-- @return 拡大用以外のクラスの列 (不指定ならnil) | |
local function scan_bigg_classes(span) | |
local gscl, oclss, clss = 0, {}, span.classes | |
for _, cls in ipairs(clss) do | |
local t = scale_value(cls) | |
if type(t) == 'string' then gscl = t | |
elseif type(t) == 'number' then | |
if type(gscl) == 'number' then gscl = gscl + t end | |
else insert(oclss, cls) | |
end | |
end | |
if #clss == #oclss then return nil end | |
return gscl, oclss | |
end | |
---------------------------------------- フェーズ'mainproc' | |
-- Span要素に対する処理. | |
local function mainproc_Span(span) | |
local scl, clss = scan_bigg_classes(span) | |
if not scl then return end | |
log("bigg span: scale=%s", scl) | |
-- 内容の前後にマークアップのRawInlineを追加する | |
local mb, ma = scale_markup(scl) | |
if mb then | |
insert(span.content, 1, pandoc.RawInline(FORMAT, mb)) | |
end | |
if ma then | |
insert(span.content, pandoc.RawInline(FORMAT, ma)) | |
end | |
span.classes = clss | |
return {span} | |
end | |
-- 文書全体に対する処理. | |
local function mainproc_Pandoc(doc) | |
if FORMAT == 'latex' then | |
insert(doc.blocks, 1, | |
pandoc.RawBlock(FORMAT, LATEX_PROLOGUE)) | |
return doc | |
end | |
end | |
---------------------------------------- フィルタ定義 | |
if is_format_supported() then | |
return { | |
{-- フェーズmainproc | |
Span = mainproc_Span; | |
Pandoc = mainproc_Pandoc; | |
}; | |
} | |
else log("format '%s' in not supported", FORMAT) | |
end | |
---------------------------------------- おしまい |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment