source: stylesheets/lfs-xsl/docbook-xsl-1.78.1/extensions/docbook.py@ 67f507c

10.0 10.0-rc1 10.1 10.1-rc1 11.0 11.0-rc1 11.0-rc2 11.0-rc3 11.1 11.1-rc1 11.2 11.2-rc1 11.3 11.3-rc1 12.0 12.0-rc1 12.1 12.1-rc1 8.4 9.0 9.1 arm bdubbs/gcc13 ml-11.0 multilib renodr/libudev-from-systemd s6-init trunk xry111/arm64 xry111/arm64-12.0 xry111/clfs-ng xry111/lfs-next xry111/loongarch xry111/loongarch-12.0 xry111/loongarch-12.1 xry111/mips64el xry111/pip3 xry111/rust-wip-20221008 xry111/update-glibc
Last change on this file since 67f507c was 15c7d39, checked in by Matthew Burgess <matthew@…>, 11 years ago

Update stylesheets to docbook-xsl-1.78.1.

git-svn-id: http://svn.linuxfromscratch.org/LFS/trunk/BOOK@10355 4aa44e1e-78dd-0310-a6d2-fbcd4c07a689

  • Property mode set to 100644
File size: 7.1 KB
Line 
1# docbook.py: extension module
2# $Id: docbook.py 8353 2009-03-17 16:57:50Z mzjn $
3
4import sys
5import string
6import libxml2
7import libxslt
8import re
9import math
10
11# Some globals
12pixelsPerInch = 96.0
13unitHash = { 'in': pixelsPerInch,
14 'cm': pixelsPerInch / 2.54,
15 'mm': pixelsPerInch / 25.4,
16 'pc': (pixelsPerInch / 72.0) * 12,
17 'pt': pixelsPerInch / 72.0,
18 'px': 1 }
19
20# ======================================================================
21
22def adjustColumnWidths(ctx, nodeset):
23 #
24 # Small check to verify the context is correcly accessed
25 #
26 try:
27 pctxt = libxslt.xpathParserContext(_obj=ctx)
28 ctxt = pctxt.context()
29 tctxt = ctxt.transformContext()
30 except:
31 pass
32
33 # Get the nominal table width
34 varString = lookupVariable(tctxt, "nominal.table.width", None)
35 if varString == None:
36 nominalWidth = 6 * pixelsPerInch;
37 else:
38 nominalWidth = convertLength(varString);
39
40 # Get the requested table width
41 tableWidth = lookupVariable(tctxt, "table.width", "100%")
42
43 foStylesheet = (tctxt.variableLookup("stylesheet.result.type", None) == "fo")
44
45 relTotal = 0
46 relParts = []
47
48 absTotal = 0
49 absParts = []
50
51 colgroup = libxml2.xmlNode(_obj = nodeset[0])
52 # If this is an foStylesheet, we've been passed a list of fo:table-columns.
53 # Otherwise we've been passed a colgroup that contains a list of cols.
54 if foStylesheet:
55 colChildren = colgroup
56 else:
57 colChildren = colgroup.children
58
59 col = colChildren
60 while col != None:
61 if foStylesheet:
62 width = col.prop("column-width")
63 else:
64 width = col.prop("width")
65
66 if width == None:
67 width = "1*"
68
69 relPart = 0.0
70 absPart = 0.0
71 starPos = string.find(width, "*")
72 if starPos >= 0:
73 relPart, absPart = string.split(width, "*", 2)
74 relPart = float(relPart)
75 relTotal = relTotal + float(relPart)
76 else:
77 absPart = width
78
79 pixels = convertLength(absPart)
80 absTotal = absTotal + pixels
81
82 relParts.append(relPart)
83 absParts.append(pixels)
84
85 col = col.next
86
87 # Ok, now we have the relative widths and absolute widths in
88 # two parallel arrays.
89 #
90 # - If there are no relative widths, output the absolute widths
91 # - If there are no absolute widths, output the relative widths
92 # - If there are a mixture of relative and absolute widths,
93 # - If the table width is absolute, turn these all into absolute
94 # widths.
95 # - If the table width is relative, turn these all into absolute
96 # widths in the nominalWidth and then turn them back into
97 # percentages.
98
99 widths = []
100
101 if relTotal == 0:
102 for absPart in absParts:
103 if foStylesheet:
104 inches = absPart / pixelsPerInch
105 widths.append("%4.2fin" % inches)
106 else:
107 widths.append("%d" % absPart)
108 elif absTotal == 0:
109 for relPart in relParts:
110 rel = relPart / relTotal * 100
111 widths.append(rel)
112 widths = correctRoundingError(widths)
113 else:
114 pixelWidth = nominalWidth
115 if string.find(tableWidth, "%") < 0:
116 pixelWidth = convertLength(tableWidth)
117
118 if pixelWidth <= absTotal:
119 print "Table is wider than table width"
120 else:
121 pixelWidth = pixelWidth - absTotal
122
123 absTotal = 0
124 for count in range(len(relParts)):
125 rel = relParts[count] / relTotal * pixelWidth
126 relParts[count] = rel + absParts[count]
127 absTotal = absTotal + rel + absParts[count]
128
129 if string.find(tableWidth, "%") < 0:
130 for count in range(len(relParts)):
131 if foStylesheet:
132 pixels = relParts[count]
133 inches = pixels / pixelsPerInch
134 widths.append("%4.2fin" % inches)
135 else:
136 widths.append(relParts[count])
137 else:
138 for count in range(len(relParts)):
139 rel = relParts[count] / absTotal * 100
140 widths.append(rel)
141 widths = correctRoundingError(widths)
142
143 # Danger, Will Robinson! In-place modification of the result tree!
144 # Side-effect free? We don' need no steenkin' side-effect free!
145 count = 0
146 col = colChildren
147 while col != None:
148 if foStylesheet:
149 col.setProp("column-width", widths[count])
150 else:
151 col.setProp("width", widths[count])
152
153 count = count+1
154 col = col.next
155
156 return nodeset
157
158def convertLength(length):
159 # Given "3.4in" return the width in pixels
160 global pixelsPerInch
161 global unitHash
162
163 m = re.search('([+-]?[\d\.]+)(\S+)', length)
164 if m != None and m.lastindex > 1:
165 unit = pixelsPerInch
166 if unitHash.has_key(m.group(2)):
167 unit = unitHash[m.group(2)]
168 else:
169 print "Unrecognized length: " + m.group(2)
170
171 pixels = unit * float(m.group(1))
172 else:
173 pixels = 0
174
175 return pixels
176
177def correctRoundingError(floatWidths):
178 # The widths are currently floating point numbers, we have to truncate
179 # them back to integers and then distribute the error so that they sum
180 # to exactly 100%.
181
182 totalWidth = 0
183 widths = []
184 for width in floatWidths:
185 width = math.floor(width)
186 widths.append(width)
187 totalWidth = totalWidth + math.floor(width)
188
189 totalError = 100 - totalWidth
190 columnError = totalError / len(widths)
191 error = 0
192 for count in range(len(widths)):
193 width = widths[count]
194 error = error + columnError
195 if error >= 1.0:
196 adj = math.floor(error)
197 error = error - adj
198 widths[count] = "%d%%" % (width + adj)
199 else:
200 widths[count] = "%d%%" % width
201
202 return widths
203
204def lookupVariable(tctxt, varName, default):
205 varString = tctxt.variableLookup(varName, None)
206 if varString == None:
207 return default
208
209 # If it's a list, get the first element
210 if type(varString) == type([]):
211 varString = varString[0]
212
213 # If it's not a string, it must be a node, get its content
214 if type(varString) != type(""):
215 varString = varString.content
216
217 return varString
218
219# ======================================================================
220# Random notes...
221
222#once you have a node which is a libxml2 python xmlNode wrapper all common
223#operations are possible:
224# .children .last .parent .next .prev .doc for navigation
225# .content .type for introspection
226# .prop("attribute_name") to lookup attribute values
227
228# # Now make a nodeset to return
229# # Danger, Will Robinson! This creates a memory leak!
230# newDoc = libxml2.newDoc("1.0")
231# newColGroup = newDoc.newDocNode(None, "colgroup", None)
232# newDoc.addChild(newColGroup)
233# col = colgroup.children
234# while col != None:
235# newCol = newDoc.newDocNode(None, "col", None)
236# newCol.copyPropList(col);
237# newCol.setProp("width", "4")
238# newColGroup.addChild(newCol)
239# col = col.next
Note: See TracBrowser for help on using the repository browser.