require "asciidoctor/extensions"
require "htmlentities"
require "unicode2latex"
require "mime/types"
require "base64"
require "English"
require "latexmath"
module Asciidoctor
module Standoc
module Inline
def refid?(x)
@refids.include? x
end
def inline_anchor(node)
case node.type
when :ref
inline_anchor_ref node
when :xref
inline_anchor_xref node
when :link
inline_anchor_link node
when :bibref
inline_anchor_bibref node
end
end
def inline_anchor_ref(node)
noko do |xml|
xml.bookmark nil, **attr_code(id: node.id)
end.join
end
def inline_anchor_xref(node)
noko do |xml|
attrs = inline_anchor_xref_attrs(node)
c = attrs[:text]
attrs.delete(:text) unless c.nil?
xml.xref **attr_code(attrs) do |x|
x << c
end
end.join
end
def inline_anchor_xref_attrs(node)
m = /^(?droploc%)?(?capital%|lowercase%)?(?droploc%)?
(?fn(:\s*(?.*))?)?$/x.match node.text
casing = m.nil? ? nil : m[:case]&.sub(/%$/, "")
droploc = m.nil? ? nil : ((m[:drop].nil? && m[:drop2].nil?) ? nil: true)
f = (m.nil? || m[:fn].nil?) ? "inline" : "footnote"
c = (!m.nil? && (%i[case fn drop drop2].any? { |x| !m[x].nil? })) ?
m[:text] : node.text
t = node.target.gsub(/^#/, "").gsub(%r{(\.xml|\.adoc)(#.*$)}, "\\2")
{ target: t, type: f, case: casing, droploc: droploc, text: c }
end
def inline_anchor_link(node)
contents = node.text
contents = "" if node.target.gsub(%r{^mailto:}, "") == node.text
attributes = { "target": node.target, "alt": node.attr("title") }
noko do |xml|
xml.link **attr_code(attributes) do |l|
l << contents
end
end.join
end
def inline_anchor_bibref(node)
eref_contents = (node.text || node.target || node.id)&.
sub(/^\[?([^\[\]]+?)\]?$/, "[\\1]")
eref_attributes = { id: node.target || node.id }
@refids << (node.target || node.id)
noko do |xml|
xml.ref **attr_code(eref_attributes) do |r|
r << eref_contents
end
end.join
end
def inline_callout(node)
noko do |xml|
xml.callout node.text
end.join
end
def inline_footnote(node)
@fn_number ||= 0
noko do |xml|
@fn_number += 1
xml.fn **{ reference: @fn_number } do |fn|
fn.p { |p| p << node.text }
end
end.join
end
def inline_break(node)
noko do |xml|
xml << node.text
xml.br
end.join
end
def page_break(node)
attrs = {}
node.option?("landscape") and attrs[:orientation] = "landscape"
node.option?("portrait") and attrs[:orientation] = "portrait"
noko { |xml| xml.pagebreak **attr_code(attrs)}.join
end
def thematic_break(_node)
noko { |xml| xml.hr }.join
end
def xml_encode(text)
HTMLEntities.new.encode(text, :basic, :hexadecimal).
gsub(/>/, ">").gsub(/\</, "<").gsub(/&/, "&").
gsub(/>/, ">").gsub(/</, "<").gsub(/&/, "&").
gsub(/"/, '"').gsub(/
/, "\n").gsub(/&#/, "")
end
def latex_parse(text)
lxm_input = Unicode2LaTeX.unicode2latex(HTMLEntities.new.decode(text))
results = Latexmath.parse(lxm_input).to_mathml
results.nil? and
@log.add('Math', nil,
"latexmlmath failed to process equation:\n#{lxm_input}")
results&.sub(%r{