blob: a196e79095bbf52906cdeb49a82d17a3db701dad [file] [log] [blame]
Tim Peters52cfa332002-04-19 16:09:26 +00001'''
2 Makes the necesary files to convert from plain html of
3 Python 1.5 and 1.5.x Documentation to
4 Microsoft HTML Help format version 1.1
5 Doesn't change the html's docs.
6
7 by hernan.foffani@iname.com
8 no copyright and no responsabilities.
9
10 modified by Dale Nagata for Python 1.5.2
11
12 Renamed from make_chm.py to prechm.py, and checked into the Python
13 project, 19-Apr-2002 by Tim Peters. Assorted modifications by Tim
14 and Fred Drake. Obtained from Robin Dunn's .chm packaging of the
15 Python 2.2 docs, at <http://alldunn.com/python/>.
16'''
17
18import sys
19import os
20import formatter
21import htmllib
22import string
23import getopt
24
25
26
27# moved all the triple_quote up here because my syntax-coloring editor
28# sucks a little bit.
29usage_mode = '''
30Usage: make_chm.py [-c] [-k] [-p] [-v 1.5[.x]] filename
31 -c: does not build filename.hhc (Table of Contents)
32 -k: does not build filename.hhk (Index)
33 -p: does not build filename.hhp (Project File)
34 -v 1.5[.x]: makes help for the python 1.5[.x] docs
35 (default is python 1.5.2 docs)
36'''
37
38# project file (*.hhp) template. there are seven %s
39project_template = '''
40[OPTIONS]
41Compatibility=1.1
42Compiled file=%s.chm
43Contents file=%s.hhc
44Default Window=%s
45Default topic=index.html
46Display compile progress=No
47Full-text search=Yes
48Index file=%s.hhk
49Language=0x409
50Title=Python %s Documentation
51
52[WINDOWS]
53%s="Python %s Documentation","%s.hhc","%s.hhk","index.html","index.html",\
54,,,,0x2520,220,0x384e,,,,,0,,,
55
56[FILES]
57'''
58
59contents_header = '''
60<OBJECT type="text/site properties">
61 <param name="Window Styles" value="0x801227">
62</OBJECT>
63<UL>
64<LI> <OBJECT type="text/sitemap">
65 <param name="Name" value="Python %s Docs">
66 <param name="Local" value="./index.html">
67 </OBJECT>
68<UL>
69'''
70
71contents_footer = '''
72</UL></UL>
73'''
74
75object_sitemap = '''
76 <LI> <OBJECT type="text/sitemap">
77 <param name="Local" value="%s">
78 <param name="Name" value="%s">
79 </OBJECT>
80'''
81
82# Library Doc list of tuples:
83# each 'book' : ( Dir, Title, First page, Content page, Index page)
84#
85supported_libraries = {
86 '2.2': ### Beta!!! fix for actual release
87 [
88 ('.', 'Global Module Index', 'modindex.html', None, None),
89 ('tut','Tutorial','tut.html','node2.html',None),
90 ('lib','Library Reference','lib.html','contents.html','genindex.html'),
91 ('ref','Language Reference','ref.html','contents.html','genindex.html'),
92 ('mac','Macintosh Reference','mac.html','contents.html','genindex.html'),
93 ('ext','Extending and Embedding','ext.html','contents.html',None),
94 ('api','Python/C API','api.html','contents.html','genindex.html'),
95 ('doc','Documenting Python','doc.html','contents.html',None),
96 ('inst','Installing Python Modules', 'inst.html', 'index.html', None),
97 ('dist','Distributing Python Modules', 'dist.html', 'index.html', None),
98 ],
99
100 '2.1.1':
101 [
102 ('.', 'Global Module Index', 'modindex.html', None, None),
103 ('tut','Tutorial','tut.html','node2.html',None),
104 ('lib','Library Reference','lib.html','contents.html','genindex.html'),
105 ('ref','Language Reference','ref.html','contents.html','genindex.html'),
106 ('mac','Macintosh Reference','mac.html','contents.html','genindex.html'),
107 ('ext','Extending and Embedding','ext.html','contents.html',None),
108 ('api','Python/C API','api.html','contents.html','genindex.html'),
109 ('doc','Documenting Python','doc.html','contents.html',None),
110 ('inst','Installing Python Modules', 'inst.html', 'index.html', None),
111 ('dist','Distributing Python Modules', 'dist.html', 'index.html', None),
112 ],
113
114 '2.0.0':
115 [
116 ('.', 'Global Module Index', 'modindex.html', None, None),
117 ('tut','Tutorial','tut.html','node2.html',None),
118 ('lib','Library Reference','lib.html','contents.html','genindex.html'),
119 ('ref','Language Reference','ref.html','contents.html','genindex.html'),
120 ('mac','Macintosh Reference','mac.html','contents.html','genindex.html'),
121 ('ext','Extending and Embedding','ext.html','contents.html',None),
122 ('api','Python/C API','api.html','contents.html','genindex.html'),
123 ('doc','Documenting Python','doc.html','contents.html',None),
124 ('inst','Installing Python Modules', 'inst.html', 'contents.html', None),
125 ('dist','Distributing Python Modules', 'dist.html', 'contents.html', None),
126 ],
127
128 # <dnagata@creo.com> Apr 17/99: library for 1.5.2 version:
129 # <hernan.foffani@iname.com> May 01/99: library for 1.5.2 (04/30/99):
130 '1.5.2':
131 [
132 ('tut','Tutorial','tut.html','node2.html',None),
133 ('lib','Library Reference','lib.html','contents.html','genindex.html'),
134 ('ref','Language Reference','ref.html','contents.html','genindex.html'),
135 ('mac','Macintosh Reference','mac.html','contents.html','genindex.html'),
136 ('ext','Extending and Embedding','ext.html','contents.html',None),
137 ('api','Python/C API','api.html','contents.html','genindex.html'),
138 ('doc','Documenting Python','doc.html','contents.html',None)
139 ],
140
141 # library for 1.5.1 version:
142 '1.5.1':
143 [
144 ('tut','Tutorial','tut.html','contents.html',None),
145 ('lib','Library Reference','lib.html','contents.html','genindex.html'),
146 ('ref','Language Reference','ref-1.html','ref-2.html','ref-11.html'),
147 ('ext','Extending and Embedding','ext.html','contents.html',None),
148 ('api','Python/C API','api.html','contents.html','genindex.html')
149 ],
150
151 # library for 1.5 version:
152 '1.5':
153 [
154 ('tut','Tutorial','tut.html','node1.html',None),
155 ('lib','Library Reference','lib.html','node1.html','node268.html'),
156 ('ref','Language Reference','ref-1.html','ref-2.html','ref-11.html'),
157 ('ext','Extending and Embedding','ext.html','node1.html',None),
158 ('api','Python/C API','api.html','node1.html','node48.html')
159 ]
160}
161
162class AlmostNullWriter(formatter.NullWriter) :
163 savedliteral = ''
164
165 def send_flowing_data(self, data) :
166 # need the text tag for later
167 datastriped = string.strip(data)
168 if self.savedliteral == '':
169 self.savedliteral = datastriped
170 else:
171 self.savedliteral = string.strip(self.savedliteral +
172 ' ' + datastriped)
173
174
175class HelpHtmlParser(htmllib.HTMLParser) :
176 indent = 0 # number of tabs for pritty printing of files
177 ft = None # output file
178 path = None # relative path
179 proc = 0 # if true I process, if false I skip
180 # (some headers, footers, etc.)
181
182 def begin_group(self) :
183 if not self.proc :
184 # first level, start processing
185 self.proc = 1
186 self.indent = self.indent + 1
187
188 def finnish_group(self) :
189 self.indent = self.indent - 1
190 if self.proc and self.indent == 0 :
191 # if processing and back to root, then stop
192 self.proc = 0
193
194 def anchor_bgn(self, href, name, type) :
195 if self.proc :
196 self.formatter.writer.savedliteral = ''
197 self.ft.write('<OBJECT type="text/sitemap">\n')
198 self.ft.write('\t' * self.indent + \
199 '\t<param name="Local" value="' + self.path + \
200 '/' + href + '">\n')
201
202 def anchor_end(self) :
203 if self.proc :
204 self.ft.write('\t' * self.indent + \
205 '\t<param name="Name" value="' + \
206 self.formatter.writer.savedliteral + '">\n')
207 self.ft.write('\t' * self.indent + '\t</OBJECT>\n' )
208
209 def start_dl(self, atr_val) :
210 self.begin_group()
211
212 def end_dl(self) :
213 self.finnish_group()
214
215 def do_dt(self, atr_val) :
216 # no trailing newline on pourpose!
217 self.ft.write("\t" * self.indent + "<LI>")
218
219
220class IdxHlpHtmlParser(HelpHtmlParser) :
221 # nothing special here, seems enough with parent class
222 pass
223
224class TocHlpHtmlParser(HelpHtmlParser) :
225
226 def start_dl(self, atr_val) :
227 self.begin_group()
228 self.ft.write('\t' * self.indent + '<UL>\n')
229
230 def end_dl(self) :
231 self.finnish_group()
232 self.ft.write('</UL>\n')
233
234 def start_ul(self, atr_val) :
235 self.begin_group()
236 self.ft.write('\t' * self.indent + '<UL>\n')
237
238 def end_ul(self) :
239 self.finnish_group()
240 self.ft.write('</UL>\n')
241
242 def do_li(self, atr_val) :
243 # no trailing newline on pourpose!
244 self.ft.write("\t" * self.indent + "<LI>")
245
246
247def index(path, archivo, output) :
248 f = formatter.AbstractFormatter(AlmostNullWriter())
249 parser = IdxHlpHtmlParser(f)
250 parser.path = path
251 parser.ft = output
252 fil = path + '/' + archivo
253 parser.feed(open(fil).read())
254 parser.close()
255
256
257def content(path, archivo, output) :
258 f = formatter.AbstractFormatter(AlmostNullWriter())
259 parser = TocHlpHtmlParser(f)
260 parser.path = path
261 parser.ft = output
262 fil = path + '/' + archivo
263 parser.feed(open(fil).read())
264 parser.close()
265
266
267def do_index(library, output) :
268 output.write('<UL>\n')
269 for book in library :
270 print '\t', book[2]
271 if book[4] :
272 index(book[0], book[4], output)
273 output.write('</UL>\n')
274
275
276def do_content(library, version, output) :
277 output.write(contents_header % version)
278 for book in library :
279 print '\t', book[2]
280 output.write(object_sitemap % (book[0]+"/"+book[2], book[1]))
281 if book[3] :
282 content(book[0], book[3], output)
283 output.write(contents_footer)
284
285
286def do_project( library, output, arch, version) :
287 output.write( project_template % \
288 (arch, arch, arch, arch, version, arch, version, arch, arch) )
289 for book in library :
290 for page in os.listdir(book[0]) :
291 if page[string.rfind(page, '.'):] == '.html' or \
292 page[string.rfind(page, '.'):] == '.css':
293 output.write(book[0]+ '\\' + page + '\n')
294
295
296def openfile(file) :
297 try :
298 p = open(file, "w")
299 except IOError, msg :
300 print file, ":", msg
301 sys.exit(1)
302 return p
303
304def usage() :
305 print usage_mode
306 sys.exit(0)
307
308
309
310def do_it(args = None) :
311 if not args :
312 args = sys.argv[1:]
313
314 if not args :
315 usage()
316
317 try :
318 optlist, args = getopt.getopt(args, 'ckpv:')
319 except getopt.error, msg :
320 print msg
321 usage()
322
323 if not args or len(args) > 1 :
324 usage()
325 arch = args[0]
326
327 version = None
328 for opt in optlist:
329 if opt[0] == '-v':
330 version = opt[1]
331 break
332 if not version:
333 usage()
334
335 library = supported_libraries[ version ]
336
337 if not (('-p','') in optlist) :
338 f = openfile(arch + '.hhp')
339 print "Building Project..."
340 do_project(library, f, arch, version)
341 if version == '2.0.0':
342 for image in os.listdir('icons'):
343 f.write('icons'+ '\\' + image + '\n')
344
345 f.close()
346
347 if not (('-c','') in optlist) :
348 f = openfile(arch + '.hhc')
349 print "Building Table of Content..."
350 do_content(library, version, f)
351 f.close()
352
353 if not (('-k','') in optlist) :
354 f = openfile(arch + '.hhk')
355 print "Building Index..."
356 do_index(library, f)
357 f.close()
358
359if __name__ == '__main__' :
360 do_it()
361
362