-
Notifications
You must be signed in to change notification settings - Fork 17
/
publish.js
346 lines (279 loc) · 10.2 KB
/
publish.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
// This is the orginial function from Stuart Langridge at http://www.kryogenix.org/
// This is the update function from Jeff Minard - http://www.jrm.cc/
function superTextile(s) {
// CAJ - First, strip out extra newlines and whitespace at the start
// of comments. This will yield more appropriate text for formatting.
s = s.split("\n").map(function(l) { return ((l=='') || (l.match(/^\s+$/))) ? "" : l.replace(/^\s+/,'') ; }).join("\n") ;
var r = s;
// quick tags first
qtags = [ ['\\*', '\\*', 'strong'],
['\\?\\?', '\\?\\?', 'cite'],
['\\+', '\\+', 'ins'], //fixed
['~', '~', 'sub'],
['\\^', '\\^', 'sup'], // me
['{{{', '}}}', 'code'],
['@', '@', 'code']];
for (var i=0;i<qtags.length;i++) {
var ttag_o = qtags[i][0], ttag_c = qtags[i][1], htag = qtags[i][2];
re = new RegExp(ttag_o+'\\b(.+?)\\b'+ttag_c,'g');
r = r.replace(re,'<'+htag+'>'+'$1'+'</'+htag+'>');
};
// underscores count as part of a word, so do them separately
re = new RegExp('\\b_(.+?)_\\b','g');
r = r.replace(re,'<em>$1</em>');
//jeff: so do dashes
re = new RegExp('[\s\n]-(.+?)-[\s\n]','g');
r = r.replace(re,'<del>$1</del>');
// links
re = new RegExp('"\\b(.+?)\\(\\b(.+?)\\b\\)":([^\\s]+)','g');
r = r.replace(re,'<a href="$3" title="$2">$1</a>');
re = new RegExp('"\\b(.+?)\\b":([^\\s]+)','g');
r = r.replace(re,'<a href="$2">$1</a>');
// images
re = new RegExp('!\\b(.+?)\\(\\b(.+?)\\b\\)!','g');
r = r.replace(re,'<img src="$1" alt="$2">');
re = new RegExp('!\\b(.+?)\\b!','g');
r = r.replace(re,'<img src="$1">');
// block level formatting
lines = r.split('\n');
out = [] ;
nr = '';
var incode = 0 ;
var cur_block = [] ; // collect lines into a block before processing them.
for (var i=0;i<lines.length;i++) {
var line = lines[i].replace(/\s*$/,'');
changed = 0;
// handle incode behavior.
if (incode) {
// Look for end closing bracket and process it.
if (line.match(/^\s*}}}\s*$/)) {
incode = 0 ;
out.push("<p class=\"code\"><code>" + cur_block.join("<br />") + "</code></p>") ;
cur_block = [] ;
// otherwise, just add the line to the current block, escaping HTML entities
} else {
cur_block.push(line.split("&").join("&").split("<").join("<").split(">").join(">")) ;
}
// for normal text, look for line-level items to replace. If no
// replacement is found, then add the line to the current block.
} else {
// an empty line means we should end the current paragraph
if ((line == '') || line.match(/^\s+$/)) {
changed = 1 ;
line = '' ;
// convert bq. => blockquote.
} else if (line.search(/^\s*bq\.\s+/) != -1) {
line = line.replace(/^\s*bq\.\s+/,'\t<blockquote>')+'</blockquote>';
changed = 1;
// convert h* => heading
} else if (line.search(/^\s*h[1|2|3|4|5|6]\.\s+/) != -1) {
line = line.replace(/^\s*h([1|2|3|4|5|6])\.(.+)/, '<h$1>$2</h$1>');
changed = 1;
// convert - to bulletted list. liu tag will be fixed later.
} else if (line.search(/^\s*-\s+/) != -1) {
line = line.replace(/^\s*-\s+/,'\t<liu>') + '</liu>'; changed = 1;
changed = 1;
// convert * to bulletted list. liu tag will be fixed later.
} else if (line.search(/^\s*\*\s+/) != -1) {
line = line.replace(/^\s*\*\s+/,'\t<liu>') + '</liu>'; changed = 1;
changed = 1;
// convert # to numbered list. lio tag will be fixed later.
} else if (line.search(/^\s*#\s+/) != -1) {
line = line.replace(/^\s*#\s+/,'\t<lio>') + '</lio>'; changed = 1;
changed = 1;
// open code tag will start code
} else if (line.match(/^\s*\{\{\{\s*$/)) {
incode++ ;
line = '' ;
changed = 1;
}
// if the line was changed, the emit the current block as a paragraph
// and emit the line itself. Otherwise, just push the line into the
// current block.
if (changed > 0) {
if (cur_block.length > 0) {
out.push("<p>" + cur_block.join(" ") + '</p>') ;
cur_block = [] ;
}
out.push(line) ;
} else {
cur_block.push(line) ;
}
}
}
// done. if there are any lines left, in the current block, emit it.
if (cur_block.length > 0) {
out.push("<p>" + cur_block.join(" ") + '</p>') ;
cur_block = [] ;
}
// Second pass to do lists. This will wrap the lists in <li> | <ol> tags.
inlist = 0;
listtype = '';
for (var i=0;i<out.length;i++) {
line = out[i];
var addin = null ;
if (inlist && listtype == 'ul' && !line.match(/^\t<liu/)) {
addin = '</ul>\n'; inlist = 0;
}
if (inlist && listtype == 'ol' && !line.match(/^\t<lio/)) {
addin = '</ol>\n'; inlist = 0;
}
if (!inlist && line.match(/^\t<liu/)) {
line = '<ul>' + line; inlist = 1; listtype = 'ul';
}
if (!inlist && line.match(/^\t<lio/)) {
line = '<ol>' + line; inlist = 1; listtype = 'ol';
}
if (addin) line = addin + line ;
out[i] = line;
}
// Now we can join the string. Yay!
r = out.join('\n');
// jeff added : will correctly replace <li(o|u)> AND </li(o|u)>
r = r.replace(/li[o|u]>/g,'li>');
return r;
};
function publish(symbolSet) {
publish.conf = { // trailing slash expected for dirs
ext: ".html",
outDir: JSDOC.opt.d || SYS.pwd+"../out/jsdoc/",
templatesDir: JSDOC.opt.t || SYS.pwd+"../templates/sproutcore/",
symbolsDir: "symbols/",
srcDir: "symbols/src/"
};
if (!publish.conf.templatesDir.match(/\/$/)) {
publish.conf.templatesDir += '/'; // add trailing slash
}
if (JSDOC.opt.s && defined(Link) && Link.prototype._makeSrcLink) {
Link.prototype._makeSrcLink = function(srcFilePath) {
return "<"+srcFilePath+">";
}
}
IO.mkPath((publish.conf.outDir+"symbols/src").split("/"));
// used to check the details of things being linked to
Link.symbolSet = symbolSet;
try {
var classTemplate = new JSDOC.JsPlate(publish.conf.templatesDir+"class.tmpl");
var classesTemplate = new JSDOC.JsPlate(publish.conf.templatesDir+"allclasses.tmpl");
}
catch(e) {
print(e.message);
quit();
}
// filters
function hasNoParent($) {return ($.memberOf == "")}
function isaFile($) {return ($.is("FILE"))}
function isaClass($) {return ($.is("CONSTRUCTOR") || $.isNamespace)}
var symbols = symbolSet.toArray();
var files = JSDOC.opt.srcFiles;
for (var i = 0, l = files.length; i < l; i++) {
var file = files[i];
var srcDir = publish.conf.outDir + "symbols/src/";
makeSrcFile(file, srcDir);
}
var classes = symbols.filter(isaClass).sort(makeSortby("alias"));
Link.base = "../";
publish.classesIndex = classesTemplate.process(classes); // kept in memory
for (var i = 0, l = classes.length; i < l; i++) {
var symbol = classes[i];
var output = "";
output = classTemplate.process(symbol);
IO.saveFile(publish.conf.outDir+"symbols/", symbol.alias+publish.conf.ext, output);
}
// regenrate the index with different relative links
Link.base = "";
publish.classesIndex = classesTemplate.process(classes);
try {
var classesindexTemplate = new JSDOC.JsPlate(publish.conf.templatesDir+"classes-json.tmpl");
}
catch(e) { print(e.message); quit(); }
var classesIndex = classesindexTemplate.process(classes);
// IO.saveFile(publish.conf.outDir, "index"+publish.conf.ext, classesIndex);
IO.saveFile(publish.conf.outDir, "classes.json", classesIndex);
classesindexTemplate = classesIndex = null;
try {
var classesindexTemplate = new JSDOC.JsPlate(publish.conf.templatesDir+"index.tmpl");
}
catch(e) { print(e.message); quit(); }
var classesIndex = classesindexTemplate.process(classes);
IO.saveFile(publish.conf.outDir, "index"+publish.conf.ext, classesIndex);
classesindexTemplate = classesIndex = classes = null;
try {
var fileindexTemplate = new JSDOC.JsPlate(publish.conf.templatesDir+"allfiles.tmpl");
}
catch(e) { print(e.message); quit(); }
var documentedFiles = symbols.filter(isaFile);
var allFiles = [];
for (var i = 0; i < files.length; i++) {
allFiles.push(new JSDOC.Symbol(files[i], [], "FILE", new JSDOC.DocComment("/** */")));
}
for (var i = 0; i < documentedFiles.length; i++) {
var offset = files.indexOf(documentedFiles[i].alias);
allFiles[offset] = documentedFiles[i];
}
allFiles = allFiles.sort(makeSortby("name"));
var filesIndex = fileindexTemplate.process(allFiles);
IO.saveFile(publish.conf.outDir, "files"+publish.conf.ext, filesIndex);
fileindexTemplate = filesIndex = files = null;
}
/** Just the first sentence. */
function summarize(desc) {
if (typeof desc != "undefined")
return desc.match(/([\w\W]+?\.)[^a-z0-9]/i)? RegExp.$1 : desc;
}
/** make a symbol sorter by some attribute */
function makeSortby(attribute) {
return function(a, b) {
if (a[attribute] != undefined && b[attribute] != undefined) {
a = a[attribute].toLowerCase();
b = b[attribute].toLowerCase();
if (a < b) return -1;
if (a > b) return 1;
return 0;
}
}
}
function include(path) {
var path = publish.conf.templatesDir+path;
return IO.readFile(path);
}
function makeSrcFile(path, srcDir, name) {
if (JSDOC.opt.s) return;
if (!name) {
name = path.replace(/\.\.?[\\\/]/g, "").replace(/[\\\/]/g, "_");
name = name.replace(/\:/g, "_");
}
var src = {path: path, name:name, charset: IO.encoding, hilited: ""};
if (defined(JSDOC.PluginManager)) {
JSDOC.PluginManager.run("onPublishSrc", src);
}
if (src.hilited) {
IO.saveFile(srcDir, name+publish.conf.ext, src.hilited);
}
}
function makeSignature(params) {
if (!params) return "()";
var signature = "("
+
params.filter(
function($) {
return $.name.indexOf(".") == -1; // don't show config params in signature
}
).map(
function($) {
return $.name;
}
).join(", ")
+
")";
return signature;
}
/** Find symbol {@link ...} strings in text and turn into html links */
function resolveLinks(str, from) {
str = str.replace(/\{@link ([^} ]+) ?\}/gi,
function(match, symbolName) {
return new Link().toSymbol(symbolName);
}
);
return str;
}