1+ <?xml version =" 1.0" encoding =" UTF-8" ?>
2+ <xsl : stylesheet
3+ xmlns : xsl =" http://www.w3.org/1999/XSL/Transform"
4+ xmlns : xs =" http://www.w3.org/2001/XMLSchema"
5+ xmlns : tei =" http://www.tei-c.org/ns/1.0"
6+ xmlns : t2m =" http://tei-2-markdown"
7+ exclude-result-prefixes =" xs"
8+ version =" 2.0" >
9+
10+ <!--
11+ Convert TEI to Markdown for manuForma forms
12+ @author Adam Retter
13+ -->
14+
15+ <xsl : output method =" xml" version =" 1.0" omit-xml-declaration =" no" encoding =" UTF-8" indent =" yes" />
16+
17+
18+ <xsl : template name =" tei-to-markdown" >
19+ <xsl : apply-templates select =" ." mode =" tei-to-markdown" />
20+ </xsl : template >
21+
22+ <!-- Replace tei:hi h1 Elements with heading 1 Markdown -->
23+ <xsl : template match =" tei:hi[@rend eq 'h1']" mode =" tei-to-markdown" >
24+ <xsl : variable name =" children" as =" node()*" >
25+ <xsl : apply-templates select =" node()" mode =" #current" />
26+ </xsl : variable >
27+ <xsl : text ># </xsl : text ><xsl : sequence select =" t2m:trim-text($children)" /><xsl : text >
 </xsl : text >
28+ </xsl : template >
29+
30+ <!-- Replace tei:hi h2 Elements with heading 2 Markdown -->
31+ <xsl : template match =" tei:hi[@rend eq 'h2']" mode =" tei-to-markdown" >
32+ <xsl : variable name =" children" as =" node()*" >
33+ <xsl : apply-templates select =" node()" mode =" #current" />
34+ </xsl : variable >
35+ <xsl : text >## </xsl : text ><xsl : apply-templates select =" t2m:trim-text($children)" mode =" #current" /><xsl : text >
 </xsl : text >
36+ </xsl : template >
37+
38+ <!-- Replace tei:hi h3 Elements with heading 3 Markdown -->
39+ <xsl : template match =" tei:hi[@rend eq 'h3']" mode =" tei-to-markdown" >
40+ <xsl : variable name =" children" as =" node()*" >
41+ <xsl : apply-templates select =" node()" mode =" #current" />
42+ </xsl : variable >
43+ <xsl : text >### </xsl : text ><xsl : apply-templates select =" t2m:trim-text($children)" mode =" #current" /><xsl : text >
 </xsl : text >
44+ </xsl : template >
45+
46+ <!-- Replace tei:hi h1, h2, h3 Elements that contain only whitespace with a single space character -->
47+ <xsl : template match =" tei:hi[@rend = ('h1', 'h2', 'h3')][matches(., '^\s+$')]" mode =" tei-to-markdown" >
48+ <xsl : text > </xsl : text >
49+ </xsl : template >
50+
51+ <!-- Drop empty tei:hi Elements -->
52+ <xsl : template match =" tei:hi[empty(child::node())]" mode =" tei-to-markdown" />
53+
54+ <!-- Replace tei:emph bold Elements with bold Markdown -->
55+ <xsl : template match =" tei:emph[@rend eq 'bold']" mode =" tei-to-markdown" >
56+ <xsl : text >**</xsl : text ><xsl : apply-templates select =" node()" mode =" #current" /><xsl : text >**</xsl : text >
57+ </xsl : template >
58+
59+ <!-- Replace tei:emph italic Elements with bold Markdown -->
60+ <xsl : template match =" tei:emph[@rend eq 'italic']" mode =" tei-to-markdown" >
61+ <xsl : text >*</xsl : text ><xsl : apply-templates select =" node()" mode =" #current" /><xsl : text >*</xsl : text >
62+ </xsl : template >
63+
64+ <!-- Replace tei:emph bold or italic Elements that contain only whitespace with a single space character -->
65+ <xsl : template match =" tei:emph[@rend = ('bold', 'italic')][matches(., '^\s+$')]" mode =" tei-to-markdown" >
66+ <xsl : text > </xsl : text >
67+ </xsl : template >
68+
69+ <!-- Drop empty tei:emph Elements -->
70+ <xsl : template match =" tei:emph[empty(child::node())]" mode =" tei-to-markdown" />
71+
72+ <!-- Replace runs of whitespace between tei:emph Elements with a single space character -->
73+ <xsl : template match =" text()[preceding-sibling::tei:emph][following-sibling::tei:emph][matches(., '^\s+$')]" mode =" tei-to-markdown" >
74+ <xsl : text > </xsl : text >
75+ </xsl : template >
76+
77+ <!-- Remove space characters in text that occurs before tei:lb Elements -->
78+ <xsl : template match =" text()[ends-with(., ' ')][following-sibling::tei:lb]" mode =" tei-to-markdown" >
79+ <xsl : value-of select =" replace(replace(., '^(.*)\s+$', '$1'), '^\s+(.*)$', '$1')" />
80+ </xsl : template >
81+
82+ <!-- Remove space characters in text that occurs after tei:lb Elements -->
83+ <xsl : template match =" text()[starts-with(., ' ')][preceding-sibling::tei:lb]" mode =" tei-to-markdown" >
84+ <xsl : value-of select =" replace(replace(., '^\s+(.*)$', '$1'), '^(.*)\s+$', '$1')" />
85+ </xsl : template >
86+
87+ <!-- Replace tei:lb Elements with a line-break character when they have a following sibling (that is not a tei:lb) -->
88+ <xsl : template match =" tei:lb[following-sibling::node()[not(self::tei:lb)]]" mode =" tei-to-markdown" >
89+ <xsl : text >
 </xsl : text >
90+ </xsl : template >
91+
92+ <!-- Drop tei:lb Elements when they do not have a following sibling -->
93+ <xsl : template match =" tei:lb[empty(following-sibling::node())]" mode =" tei-to-markdown" />
94+
95+ <!-- Separate tei:p Elements with a single line-break character (i.e.: '\n') -->
96+ <xsl : template match =" tei:p[following-sibling::tei:p]" mode =" tei-to-markdown" >
97+ <xsl : apply-templates select =" node()|@*" mode =" #current" />
98+ <xsl : text >

 </xsl : text >
99+ </xsl : template >
100+
101+ <!-- Remove unknown Element tags -->
102+ <xsl : template match =" element()" mode =" tei-to-markdown" >
103+ <xsl : apply-templates select =" node()|@*" mode =" #current" />
104+ </xsl : template >
105+
106+ <!-- Convert unknown Attributes into Text -->
107+ <xsl : template match =" attribute()" mode =" tei-to-markdown" >
108+ <xsl : value-of select =" name(.)" /><xsl : text >: </xsl : text ><xsl : value-of select =" ." />
109+ </xsl : template >
110+
111+ <!-- Default: Identity trasform everything except Elements (which will be dealt with above) -->
112+ <xsl : template match =" node()[not(. instance of element())]|@*" mode =" tei-to-markdown" priority =" -1" >
113+ <xsl : copy >
114+ <xsl : apply-templates select =" node()" mode =" #current" />
115+ </xsl : copy >
116+ </xsl : template >
117+
118+ <xsl : function name =" t2m:trim-text" as =" node()*" >
119+ <xsl : param name =" input" required =" yes" as =" node()*" />
120+ <xsl : variable name =" length" select =" count($input)" />
121+ <xsl : choose >
122+ <xsl : when test =" $length eq 1" >
123+ <xsl : value-of select =" normalize-space($input)" />
124+ </xsl : when >
125+ <xsl : otherwise >
126+ <xsl : sequence select =" t2m:trim-text-replace(head($input), '^\s*(.+)$')" />
127+ <xsl : sequence select =" subsequence($input, 2, $length - 1)" />
128+ <xsl : sequence select =" t2m:trim-text-replace($input[$length], '^(.+)\s*$')" />
129+ </xsl : otherwise >
130+ </xsl : choose >
131+ </xsl : function >
132+
133+ <xsl : function name =" t2m:trim-text-replace" as =" node()?" >
134+ <xsl : param name =" node" as =" node()?" />
135+ <xsl : param name =" extract-pattern" as =" xs:string" />
136+ <xsl : choose >
137+ <xsl : when test =" $node instance of text()" >
138+ <xsl : value-of select =" replace($node, $extract-pattern, '$1')" />
139+ </xsl : when >
140+ <xsl : otherwise >
141+ <xsl : sequence select =" $node" />
142+ </xsl : otherwise >
143+ </xsl : choose >
144+ </xsl : function >
145+
146+ </xsl : stylesheet >
0 commit comments