Overview
Comment: | better footnotes, update syntax def, delete broken old span |
---|---|
Downloads: | Tarball | ZIP archive | SQL archive |
Timelines: | family | ancestors | descendants | both | trunk |
Files: | files | file ages | folders |
SHA3-256: |
a8358d587d209c4a3690fcda3edda8bb |
User & Date: | lexi on 2022-09-10 13:31:23 |
Other Links: | manifest | tags |
Context
2022-09-10
| ||
17:28 | add remote fetch via curl, shim native bindings check-in: ee086767f3 user: lexi tags: trunk | |
13:31 | better footnotes, update syntax def, delete broken old span check-in: a8358d587d user: lexi tags: trunk | |
03:16 | defuck xref structure check-in: 0ef3dd0c77 user: lexi tags: trunk | |
Changes
Modified cortav.ct from [fb6019b4ad] to [fe93ee725b].
104 104 *[*definition] ([^def-ex tab]): a line [^def-tab-enc beginning with a tab] is a multipurpose metadata syntax. the tab may be followed by an identifier, a colon, and a value string, in which case it opens a new definition; alternatively, a second tab character turns the line into a [*definition continuation], adding the remaining characters as a new line to the definition value on the previous line. when a new definition is opened on a line immediately following certain kinds of objects, such as resources, embeds, or multiline macro expansions, it attaches key-value metadata to that object. when a definition is not preceded by such an object, an independent [*reference] is created instad. 105 105 ** a [*reference] is a general mechanism for out-of-line metadata, and references are used in many different ways -- e.g. to specify link destinations, footnote contents, abbreviations, or macro bodies. to ensure that a definition is interpreted as a reference, rather than as metadata for an object, precede it with a blank line. 106 106 def-tab-enc: in encodings without tab characters, a definition is opened by a line beginning with two blanks, and continued by a line beginning with four blanks. 107 107 def-ex: [*open a new reference]: [`[!\\t][$key]: [$value]] 108 108 [*continue a reference]: [`[!\\t\\t][$value]] 109 109 * [*quotation] ([`<]): a line of the form [`<[$name]> [$quote]] denotes an utterance by [$name]. 110 110 * [*blockquote] ([`>]): alternate blockquote syntax. can be nested by repeating the [`>] character. 111 -* [*subtitle/caption] ([`\--]): attaches a subtitle to the previous header, or caption to the previous object 111 +* [*subtitle/caption] (["--]): attaches a subtitle to the previous header, or caption to the previous object 112 112 * [*embed] ([`&]): embeds a referenced object. can be used to show images or repeat previously defined objects like lists or tables, optionally with a caption. an embed line can be followed immediately by a sequence of [*definitions] in the same way that resource definitions can, to override resource properties on a per-instance basis. note that only presentation-related properties like [$desc] can be meaningful overridden, as embed does not trigger a re-render of the parse tree; if you want to override e.g. context variables, use a multiline macro invocation instead. 113 113 ** [`&[$image]] embeds an image or other block-level object. [!image] can be a reference with a url or file path, or it can be an embed section (e.g. for SVG files) 114 114 ***[`&myimg All that remained of the unfortunate blood magic pageant contestants and audience (police photo)] 115 115 ** [`&-[$ident] [$styled-text]] embeds a closed disclosure element containing the text of the named object (a nonprinting section or cortav resource should usually be used to store the content; it can also name an image or video, of course). in interactive outputs, this will display as a block which can be clicked on to view the full contents of the referenced object [$ident]; if [$styled-text] is present, it overrides the title of the section you are embedding (if any). in static outputs, the disclosure object will display as an enclosed box with [$styled-text] as the title text 116 116 *** [`&-ex-a Prosecution Exhibit A (GRAPHIC CONTENT)] 117 117 ** [`&+[$section] [$styled-text]] is like the above, but the disclosure element is open by default 118 118 * [`$[$macro] [$arg1]|[$arg2]|[$argn]…] invokes a block-level macro with the supplied arguments, and can be followed by a property override definition list the same way embed and resource lines can. note that while both [`$[$id]] and [`&[$id]] can be used to instantiate resources of type [`text/x.cortav], there is a critical difference: [`$[$id]] renders out the sub-document separately each time it is named, allowing for parameter expansion and for context variables to be overridden for each invocation. by contrast, [`&[$id]] can only insert copies of the same render; no parameters can be passed and context variables will be expanded to their value at the time the resource was defined. 119 119 ** [`$mymacro arg 1|arg 2|arg 3] 120 -* [*horizontal rule] ([`\---]): inserts a horizontal rule or other context break; does not end the section. must be followed by newline. underlines can also be used in place of dashes ([`___], [`-_-], [`__-__-__] etc), as can horizontal unicode box drawing characters ([`─ ━ ┈] etc). 121 -* [*page break] ([`\^^]): for formats that support pagination, like EPUB or HTML (when printed), indicates that the rest of the current page should be blank. for formats that do not, extra margins will be inserted. does not create a new section 122 -* [*page rule] ([`\^-^]): inserts a page break for formats that support them, and a horizontal rule for formats that do not. does not create a new section. comprised of any number of horizontal rule characters surrounded by a pair of carets (e.g. [`^-^] [`^_^] [`^----^] [`^__--^] [`^┈┈┈┈┈^]) 120 +* [*horizontal rule] (["---]): inserts a horizontal rule or other context break; does not end the section. must be followed by newline. underlines can also be used in place of dashes ([`___], [`-_-], [`__-__-__] etc), as can horizontal unicode box drawing characters ([`─ ━ ┈] etc). 121 +* [*page break] (["^^]): for formats that support pagination, like EPUB or HTML (when printed), indicates that the rest of the current page should be blank. for formats that do not, extra margins will be inserted. does not create a new section 122 +* [*page rule] (["^-^]): inserts a page break for formats that support them, and a horizontal rule for formats that do not. does not create a new section. comprised of any number of horizontal rule characters surrounded by a pair of carets (e.g. [`^-^] [`^_^] [`^----^] [`^__--^] [`^┈┈┈┈┈^]) 123 123 * [*table cells] ([`+ |]): see [>ex.tab table examples]. 124 124 * [*equations] ([`=]): block-level equations can be inserted with the [`=] sequence 125 125 * [*cross-references] ([`=>] [`⇒]): inserts a block-level link. has two forms for the sake of gemtext compatibility. [$styled-text] is a descriptive text of the destination. especially useful for menus and gemtext output. 126 -** the cortav syntax is [`=>[$ident] [$styled-text]], where [$ident] is an identifier; links to the same destination as [` \[>[$ident] [$styled-text]\]] would 126 +** the cortav syntax is [`=>[$ident] [$styled-text]], where [$ident] is an identifier; links to the same destination as [`\[>[$ident] [$styled-text]\]] would 127 127 ** the compatibility syntax is [`=> [$uri] [$styled-text]] (note the space before [$uri]!). instead of taking an identifier for an object in the document, it directly accepts a URI. note that this is not formally equivalent to gemtext's link syntax, which also allows paths in place of URIs; [`cortav] does not. the gemtext line ["=> /somewhere] would need to be expressed as ["=> file:/somewhere], and ["=> /somewhere?key=val] as ["http:/somewhere?key=val] (or ["gemini:/somewhere?key=val], if the result is to be served over a gemini server). 128 128 * [*empty lines] (that is, lines consisting of nothing but whitespace) constitute a [!break], which terminates multiline objects that do not have a dedicated termination sequence, for example lists and asides. 129 129 130 130 ##onspans styled text 131 131 most blocks contain a sequence of spans. these spans are produced by interpreting a stream of [*styled-text] following the control sequence. styled-text is a sequence of codepoints potentially interspersed with escapes. an escape is formed by an open square bracket [`\[] followed by a [*span control sequence], and arguments for that sequence like more styled-text. escapes can be nested. 132 132 133 133 * strong {obj *|styled-text}: causes its text to stand out from the narrative, generally rendered as bold or a brighter color. ................................................................................ 134 134 * emphatic {obj !|styled-text}: indicates that its text should be spoken with emphasis, generally rendered as italics 135 135 * custom style {span .|id|[$styled-text]}: applies a specially defined font style. for example, if you have defined [`caution] to mean "demibold italic underline", cortav will try to apply the proper weight and styling within the constraints of the current font to the span [$styled-text]. see the [>fonts-sty fonts section] for more information about this mechanism. 136 136 * literal {obj `|styled-text}: indicates that its text is a reference to a literal sequence of characters or other discrete token. generally rendered in monospace 137 137 * variable {obj $|styled-text}: indicates to the reader that its text is a placeholder, rather than a literal representation. generally rendered in italic monospace, ideally of a different color 138 138 * underline {obj _|styled-text}: underlines the text. use sparingly on text intended for webpages -- underlined text [!is] distinct from links, but underlining non-links is still a violation of convention. 139 139 * strikeout {obj ~|styled-text}: indicates that its text should be struck through or otherwise indicated for deletion 140 140 * insertion {obj +|styled-text}: indicates that its text should be indicated as a new addition to the text body. 141 -** consider using a macro definition [`\edit: [~[#1]][+[#2]]] to save typing if you are doing editing work 142 -* link [` \[>[$ref] [$styled-text]\]]: produces a hyperlink or cross-reference denoted by [$ref], which may be either a URL specified with a reference or the name of an object like an image or section elsewhere in the document. the unicode characters [`→] and [`🔗] can also be used instead of [`>] to denote a link. 143 -* footnote {span ^|ref|[$styled-text]}: annotates the text with a defined footnote. in interactive output media [`\[^citations.qtheo Quantum Theosophy: A Neophyte's Catechism\]] will insert a link with the text [`Quantum Theosophy: A Neophyte's Catechism] that, when clicked, causes a footnote to pop up on the screen. for static output media, the text will simply have a superscript integer after it denoting where the footnote is to be found. 141 +** consider using a macro definition ["edit: [~[#1]][+[#2]]] to save typing if you are doing editing work 142 +* link [`\[>[$ref] [$styled-text]\]]: produces a hyperlink or cross-reference denoted by [$ref], which may be either a URL specified with a reference or the name of an object like an image or section elsewhere in the document. the unicode characters [`→] and [`🔗] can also be used instead of [`>] to denote a link. 143 +* footnote {span ^|[$ref]|[$styled-text]}: annotates the text with a defined footnote. in interactive output media ["[^citations.qtheo Quantum Theosophy: A Neophyte's Catechism]] will insert a link with the text [`Quantum Theosophy: A Neophyte's Catechism] that, when clicked, causes a footnote to pop up on the screen. for static output media, the text will simply have a superscript integer after it denoting where the footnote is to be found. [$ref] can be the ID of a reference, in which case the reference value is parsed as [`cortav] markup to form the body of the footnote; it can also be the ID of a resource, which can be of any MIME type compatible with the current renderer, as as [`text/x.cortav], [`text/plain], or [`image/png]. 144 144 * superscript {obj '|[$styled-text]} 145 145 * subscript {obj ,|[$styled-text]} 146 146 * raw {obj \\ |[$raw-text]}: causes all characters within to be interpreted literally, without expansion. the only special characters are square brackets, which must have a matching closing bracket, and backslashes. 147 147 * raw literal [` \["[$raw-text]\]]: shorthand for a raw inside a literal, that is ["[`[\\…]]] 148 148 * macro [` \{[$name] [$arguments]}]: invokes a [>ex.mac macro] inline, specified with a reference. if the result of macro expansion contains newlines, they will be treated as line breaks, rather than paragraph breaks as they would be in a multiline context. 149 149 * argument {obj #|var}: in macros only, inserts the [$var]-th argument. otherwise, inserts a context variable provided by the renderer. 150 150 * raw argument {obj ##|var}: like above, but does not evaluate [$var]. ................................................................................ 645 645 .pos: n 646 646 .meaning: speech 647 647 648 648 %% context variables are useful because they inherit from the enclosing context 649 649 %% thus, we can exploit resource syntax to create templates with default values 650 650 651 651 @agent { 652 - + CODENAME :| [#1] 653 - + CIVILIAN IDENTITY :| [#civil] 652 + + CODENAME :| [#1] 653 + + CIVILIAN IDENTITY :| [#civil] 654 654 + RULES of ENGAGEMENT :| [#roe] 655 - + DANGER LEVEL :| [#danger] 655 + + DANGER LEVEL :| [#danger] 656 656 } 657 657 .civil: (unknown) 658 658 .roe: Monitor; do not engage 659 659 .danger: (unknown) 660 660 661 661 $agent ZUCCHINI PARABLE 662 662 .civil: Zephram "Rolodex" Goldberg ................................................................................ 672 672 + english :+ ranuir + zia ţai + thaliste + 673 673 | honor :| tef | pang | mbecheve | 674 674 | rakewyrm:| hirvag | hi phang | nache umwelinde | 675 675 | eat :| fese | dzia | rotechqa | 676 676 677 677 and now the other way around! 678 678 679 -+:english :| honor | 680 -+:ranuir :| tef | 681 -+:zia ţai :| pang | 679 ++:english :| honor | 680 ++:ranuir :| tef | 681 ++:zia ţai :| pang | 682 682 +:thalishte:| mbecheve | 683 683 ~~~ 684 684 685 685 ##extns extensions 686 686 the cortav specification also specifies a number of extensions that do not have to be supported for a renderer to be compliant. the extension mechanism supports the following directives. 687 687 688 688 * inhibits: prevents an extension from being used even where available ................................................................................ 752 752 753 753 the highlighter should make use of semantic HTML tags like [`<var>] where possible. 754 754 755 755 ###lua lua 756 756 renderers with a lua interpreter available can evaluate lua code: 757 757 * [`%lua use [!file]]: evaluates [$file] and makes its definitions available 758 758 * [`\[%lua raw [!script]\]]: evaluates [$script] and emits the string it returns (if any) in raw span context. 759 -* [` \[%lua exp [!script]\]]: evaluates [$script] and emits the string it returns (if any) in expanded span context. 759 +* [`\[%lua exp [!script]\]]: evaluates [$script] and emits the string it returns (if any) in expanded span context. 760 760 * [`%lua raw [!script]]: evaluates [$script] and emits the string array it returns (if any) in raw block context. 761 761 * [`%lua exp [!script]]: evaluates [$script] and emits the string array it returns (if any) in expanded block context. 762 762 763 763 the interpreter should provide a [`cortav] table with the objects: 764 764 * [`ctx]: contains context variables 765 765 766 766 used files should return a table with the following members ................................................................................ 774 774 [`ts] enables the directives: 775 775 * [`%[*ts] class [$scope level] ([$styled-text])]: indicates a classification level for either the whole document (scope [$doc]) or the next section (scope [$sec]). if the ts level is below [$level], the section will be redacted or rendering will fail with an error, as appropriate. if styled-text is included, this will be treated as the name of the classification level. 776 776 * [`%[*ts] word [$scope word] ([$styled-text])]: indicates a codeword clearance that must be present for the text to render. if styled-text is present, this will be used to render the name of the codeword instead of [$word]. 777 777 * [`%[*when] ts level [$level]] 778 778 * [`%[*when] ts word [$word]] 779 779 780 780 [`ts] enables the spans: 781 -* [` \[🔒#[$level] [$styled-text]\]]: redacts the span if the security level is below that specified. 782 -* [` \[🔒.[$word] [$styled-text]\]]: redacts the span if the specified codeword clearance is not enabled. 781 +* [`\[🔒#[$level] [$styled-text]\]]: redacts the span if the security level is below that specified. 782 +* [`\[🔒.[$word] [$styled-text]\]]: redacts the span if the specified codeword clearance is not enabled. 783 783 (the padlock emoji is shorthand for [`%[*ts]].) 784 784 785 785 [`ts] redacts spans securely; that is, they are simply replaced with an indicator that they have been redacted, without visually leaking the length of the redacted text. redacted sections are simply omitted. 786 786 787 787 ~~~#ts-example example [cortav] ~~~ 788 788 %ts word doc sorrowful-pines SORROWFUL PINES 789 789 ................................................................................ 945 945 [*do note] that no cortav implementation needs to concern itself with character class data. this functionality is provided in the reference implementation strictly as an (optional) extension to the spec to improve usability, not as a normative requirement. 946 946 947 947 corran: http://ʞ.cc/fic/spirals/society 948 948 tengwar: https://en.wikipedia.org/wiki/Tengwar 949 949 950 950 ###refimpl-switches switches 951 951 [`cortav.lua] offers various switches to control its behavior. 952 -+ long + short + function + 952 ++ long + short + function + 953 953 | [`--out [$file]] :|:[`-o]:| sets the output file (default stdout) | 954 954 | [`--log [$file]] :|:[`-l]:| sets the log file (default stderr) | 955 955 | [`--define [$var] [$val]] :|:[`-d]:| sets the context variable [$var] to [$val] | 956 956 | [`--mode-set [$mode]] :|:[`-y]:| activates the [>refimpl-mode mode] with ID [!mode] 957 957 | [`--mode-clear [$mode]] :|:[`-n]:| disables the mode with ID [!mode] | 958 958 | [`--mode [$id] [$val]] :|:[`-m]:| configures mode [$id] with the value [$val] | 959 959 | [`--mode-set-weak [$mode]] :|:[`-Y]:| activates the [>refimpl-mode mode] with ID [$mode] if the source file does not specify otherwise
Modified cortav.lua from [c03c132cce] to [648cf1722d].
738 738 } 739 739 end 740 740 ct.spanctls = { 741 741 {seq = '!', parse = formatter 'emph'}; 742 742 {seq = '*', parse = formatter 'strong'}; 743 743 {seq = '~', parse = formatter 'strike'}; 744 744 {seq = '+', parse = formatter 'insert'}; 745 - {seq = '"', parse = rawcode}; 746 - -- deprecated 747 - {seq = '`\\', parse = rawcode}; 748 - {seq = '\\\\', parse = rawcode}; 749 745 {seq = '\\', parse = function(s, c) -- raw 750 746 return { 751 747 kind = 'raw'; 752 748 spans = {s}; 753 749 origin = c:clone(); 754 750 } 755 751 end}; 756 752 {seq = '`', parse = formatter 'literal'}; 753 + {seq = '"', parse = rawcode}; 757 754 {seq = '$', parse = formatter 'variable'}; 758 - {seq = '^', parse = function(s,c) --footnotes 759 - local r, t = s:match '^([^%s]+)%s*(.-)$' 755 + {seq = '^', parse = function(s, c) 756 + -- TODO support for footnote sections 757 + local fn, t = s:match '^([^%s]+)%s*(.-)$' 760 758 return { 761 759 kind = 'footnote'; 762 - ref = r; 763 - spans = ct.parse_span(t, c); 760 + spans = (t and t~='') and ct.parse_span(t, c) or {}; 761 + ref = fn; 764 762 origin = c:clone(); 765 763 } 766 - -- TODO support for footnote sections 767 764 end}; 768 765 {seq = '=', parse = function(s,c) --math mode 769 766 local tx = { 770 767 ['%*'] = '×'; 771 768 ['/'] = '÷'; 772 769 } 773 770 for k,v in pairs(tx) do s = s:gsub(k,v) end ................................................................................ 789 786 end}; 790 787 {seq = '&', parse = function(s, c) 791 788 local r, t = s:match '^([^%s]+)%s*(.-)$' 792 789 return { 793 790 kind = 'deref'; 794 791 spans = (t and t ~= "") and ct.parse_span(t, c) or {}; 795 792 ref = r; 796 - origin = c:clone(); 797 - } 798 - end}; 799 - {seq = '^', parse = function(s, c) 800 - local fn, t = s:match '^([^%s]+)%s*(.-)$' 801 - return { 802 - kind = 'footnote'; 803 - spans = (t and t~='') and ct.parse_span(t, c) or {}; 804 - ref = fn; 805 793 origin = c:clone(); 806 794 } 807 795 end}; 808 796 {seq = '>', parse = insert_link}; 809 797 {seq = '→', parse = insert_link}; 810 798 {seq = '🔗', parse = insert_link}; 811 799 {seq = '##', parse = insert_var_ref(true)};
Modified desk/cortav.xml from [dc63948a6a] to [a3601c692e].
6 6 ? Kate/kwrite-compatible syntax definition for the cortav markup format 7 7 > ln cortav.xml $HOME/.local/share/org.kde.syntax-highlighting/syntax/ 8 8 ! NOTE: the Kate syntax engine cannot capture all the syntactic properties 9 9 of Cortav. we do the best we can, but note the following important 10 10 discrepancies: 11 11 12 12 1) the inline resource syntax allows a wide range of complex 13 - brackets pairs such as <!--:[ ]:--!>; the Kate syntax only 13 + brackets pairs such as <!-:[ ]:-!>; the Kate syntax only 14 14 accounts for the pair { } 15 15 --> 16 -<language name='Cortav' version='1' kateversion='2.4' section='Markup' extensions='*.ct'> 16 +<language name='Cortav' 17 + section='Markup' 18 + extensions='*.ct' 19 + version='1' 20 + kateversion='2.4'> 17 21 <highlighting> 18 22 <list name='extension-directives'> 19 23 <item>uses</item> 20 24 <item>needs</item> 21 25 <item>inhibits</item> 22 26 </list> 23 27 <list name='meta-directives'> ................................................................................ 158 162 </context> 159 163 160 164 <context name='span-del' attribute='Deleted Text' lineEndContext='#pop'> 161 165 <IncludeRules context='span'/> 162 166 </context> 163 167 164 168 <context name='span-cue' attribute='Span Cue' lineEndContext='#pop' fallthroughContext="error"> 165 - <StringDetect attribute='Span Cue' String='`\' context='#pop!flat-span' /> 166 169 <StringDetect attribute='Span Cue' String='"' context='#pop!flat-span' /> 167 170 168 171 <DetectChar attribute='Span Cue' char='!' context='#pop!span-emph' /> 169 172 <DetectChar attribute='Span Cue' char='*' context='#pop!span-strong' /> 170 173 <DetectChar attribute='Span Cue' char='~' context='#pop!span-del' /> 171 174 172 175 <AnyChar attribute='Span Cue' String='`$+🔒' context='#pop!span' />
Modified ext/toc.lua from [38c6bac1b2] to [823e0f174d].
221 221 local sec = secptr.ref 222 222 if sec.heading_node then -- does this section have a label? 223 223 local ent = tag('li',nil, 224 224 catenate{tag('a', {href='#'..getSafeID(sec)}, 225 225 sr.htmlSpan(sec.heading_node.spans, sec.heading_node, sec))}) 226 226 if secptr.depth > #stack then 227 227 local n = {tag = 'ol', attrs={}, nodes={ent}} 228 - table.insert(top().nodes[#top().nodes].nodes, n) 228 + if top() then 229 + table.insert(top().nodes[#top().nodes].nodes, n) 230 + end 229 231 table.insert(stack, n) 230 232 else 231 233 if secptr.depth < #stack then 232 234 for j=#stack,secptr.depth+1,-1 do stack[j] = nil end 233 235 end 234 - table.insert(top().nodes, ent) 236 + if top() then 237 + table.insert(top().nodes, ent) 238 + end 235 239 end 236 240 237 241 -- now we need to assemble a list of items within the 238 242 -- section worthy of an entry on their own. currently 239 243 -- this is only anchors created with %toc mark|name 240 244 local innerlinks = {} 241 245 local noteworthy = { anchor = true }
Modified render/html.lua from [4a60de4c59] to [e235e554e3].
55 55 li { 56 56 padding: 0.1em 0; 57 57 } 58 58 ]]; 59 59 list_ordered = [[]]; 60 60 list_unordered = [[]]; 61 61 footnote = [[ 62 + @media screen { 63 + a[href].fnref { 64 + text-decoration-style: dashed; 65 + color: @tone(0.7 45); 66 + text-decoration-color: @tone/0.4(0.7 45); 67 + } 68 + a[href]:hover.fnref { 69 + color: @tone(0.9 45); 70 + text-decoration-color: @tone/0.7(0.7 45); 71 + } 72 + } 62 73 aside.footnote { 63 74 font-family: 90%; 64 75 grid-template-columns: 1em 1fr min-content; 65 76 grid-template-rows: 1fr min-content; 66 77 position: fixed; 67 78 padding: 1em; 68 79 background: @tone(0.03); ................................................................................ 98 109 backdrop-filter: blur(0px); 99 110 } 100 111 aside.footnote:target ~ #cover { 101 112 opacity: 100%; 102 113 pointer-events: all; 103 114 backdrop-filter: blur(5px); 104 115 } 116 + } 117 + @media screen and (max-width: calc(@width + 20em)) { 118 + aside.footnote { 119 + left: 1em; 120 + right: 1em; 121 + } 105 122 } 106 123 @media print { 107 124 aside.footnote { 108 125 display: grid; 109 126 position: relative; 110 127 } 111 128 aside.footnote:first-of-type { ................................................................................ 145 162 } 146 163 } 147 164 aside.footnote > div.number { 148 165 text-align:right; 149 166 grid-row: 1/2; 150 167 grid-column: 1/2; 151 168 } 152 - aside.footnote > div.text { 169 + aside.footnote > .text { 153 170 grid-row: 1/2; 154 171 grid-column: 2/4; 155 172 padding-left: 1em; 156 173 overflow-y: auto; 174 + margin-top: 0; 157 175 } 158 - aside.footnote > div.text > p:first-child { 176 + aside.footnote > .text > :first-child { 159 177 margin-top: 0; 160 178 } 161 179 ]]; 162 180 header = [[ 163 181 body { padding: 0 2.5em !important } 164 182 h1,h2,h3,h4,h5,h6 { border-bottom: 1px solid @tone(0.7); } 165 183 h1 { font-size: 200%; border-bottom-style: double !important; border-bottom-width: 3px !important; margin: 0em -1em; } ................................................................................ 761 779 end 762 780 function span_renderers.footnote(f,b,s) 763 781 local linkattr = {} 764 782 if opts.epub then 765 783 linkattr['epub:type'] = 'noteref' 766 784 else 767 785 addStyle 'footnote' 786 + linkattr.class = 'fnref' 768 787 end 769 788 local source, sid, ssec = b.origin:ref(f.ref) 770 789 local cnc = getSafeID(ssec) .. ' ' .. sid 771 790 local fn 772 791 if footnotes[cnc] then 773 792 fn = footnotes[cnc] 774 793 else ................................................................................ 893 912 table.insert(secnodes, block_renderers[bl.kind](bl,sec)) 894 913 end 895 914 end 896 915 if next(secnodes) then 897 916 if doc.secorder[2] then --#secs>1? 898 917 -- only wrap in a section if >1 section 899 918 table.insert(ir, tag('section', 900 - {id = getSafeID(sec)}, 901 - secnodes)) 919 + {id = getSafeID(sec)}, 920 + secnodes)) 902 921 else 903 922 ir = secnodes 904 923 end 905 924 end 906 925 end 907 926 return ir 908 927 end ................................................................................ 1189 1208 do local fnsorted = {} 1190 1209 for _, fn in pairs(footnotes) do 1191 1210 fnsorted[fn.num] = fn 1192 1211 end 1193 1212 1194 1213 for _, fn in ipairs(fnsorted) do 1195 1214 local tag = tagproc.toIR.tag 1196 - local body = {nodes={}} 1197 - local ftir = {} 1198 - for l in fn.source:gmatch('([^\n]*)') do 1199 - ct.parse_line(l, fn.origin, ftir) 1215 + local body 1216 + if type(fn.source) == 'table' then 1217 + if fn.source.kind == 'resource' then 1218 + local fake_embed = { 1219 + kind = 'embed'; 1220 + rsrc = fn.source; 1221 + origin = fn.origin; 1222 + mode = 'inline'; 1223 + } 1224 + local rendered = astproc.toIR.block_renderers.embed( 1225 + fake_embed, fn.origin.sec 1226 + ) 1227 + if not rendered then 1228 + fn.origin:fail('unacceptable resource mime type “%s” for footnote target “%s”', fn.source.mime, fn.source.id or '(anonymous)') 1229 + end 1230 + body = rendered 1231 + else 1232 + fn.origin:fail('footnote span links to block “%s” of unacceptable kind “%s”', fn.source.kind) 1233 + end 1234 + else 1235 + body = {tag='div',nodes={}} 1236 + local ftir = {} 1237 + for l in fn.source:gmatch('([^\n]*)') do 1238 + ct.parse_line(l, fn.origin, ftir) 1239 + end 1240 + renderBlocks(ftir,body) 1200 1241 end 1201 - renderBlocks(ftir,body) 1202 1242 local fattr = {id=fn.id} 1203 1243 if opts.epub then 1204 1244 ---UUUUUUGHHH 1205 1245 local npfx = string.format('(%u) ', fn.num) 1206 1246 if next(body.nodes) then 1207 1247 local n = body.nodes[1] 1208 1248 repeat ................................................................................ 1215 1255 else 1216 1256 n.nodes[1] = {tag='p',attrs={},nodes={npfx}} 1217 1257 break 1218 1258 end 1219 1259 until false 1220 1260 1221 1261 else 1222 - body.nodes[1] = {tag='p',attrs={},nodes={npfx}} 1262 + if body.tag == 'div' then 1263 + body.nodes[1] = {tag='p',attrs={},nodes={npfx}} 1264 + elseif body.tag == 'pre' then 1265 + body.nodes[1] = npfx .. body.nodes[1] 1266 + else 1267 + body = {tag='div', nodes = {npfx, body}} 1268 + end 1223 1269 end 1224 1270 fattr['epub:type'] = 'footnote' 1225 1271 else 1226 1272 fattr.class = 'footnote' 1227 1273 end 1274 + body.attrs = body.attrs or {} 1275 + body.attrs.class = 'text' 1228 1276 local note = tag('aside', fattr, opts.epub and body.nodes or { 1229 1277 tag('div',{class='number'}, tostring(fn.num)), 1230 - tag('div',{class='text'}, body.nodes), 1278 + body, 1279 +-- tag('div',{class='text'}, body.nodes), 1231 1280 tag('a',{href='#0'},'⤫') 1232 1281 }) 1233 1282 table.insert(ir, note) 1234 1283 end 1235 1284 end 1236 1285 if next(footnotes) and not opts.epub then 1237 1286 table.insert(ir, tagproc.toIR.tag('div',{id='cover'},''))