From 49a3cb8edeacd7a82f5c4c4e7b6053b5ad94a170 Mon Sep 17 00:00:00 2001 From: Jeremy Ruston Date: Mon, 28 May 2012 15:51:52 +0100 Subject: [PATCH] Allow for macros and classes at both run level and block level Involving a bit of a refactoring of the parameters to the $tw.Tree.Macro constructor --- core/modules/macros/chooser.js | 1 - core/modules/macros/slider.js | 9 ++--- core/modules/macros/story/story.js | 16 ++++---- core/modules/macros/view.js | 9 +++-- core/modules/macros/zoomer.js | 1 - .../newwikitextparser/blockrules/class.js | 2 +- .../newwikitextparser/blockrules/heading.js | 2 +- .../newwikitextparser/blockrules/html.js | 2 +- .../newwikitextparser/blockrules/list.js | 2 +- .../newwikitextparser/blockrules/rule.js | 2 +- .../newwikitextparser/newwikitextparser.js | 4 +- .../newwikitextparser/runrules/macro.js | 8 +++- .../newwikitextparser/runrules/prettylink.js | 8 +++- .../newwikitextparser/runrules/wikilink.js | 8 +++- core/modules/parsers/tiddlytextparser.js | 10 +++-- .../wikitextparser/rules/wikitextrules.js | 8 +++- core/modules/treenodes/macro.js | 39 ++++++++++++------- tw5.com/tiddlers/TestingNewWikiText.tid | 8 ++++ 18 files changed, 89 insertions(+), 50 deletions(-) diff --git a/core/modules/macros/chooser.js b/core/modules/macros/chooser.js index de42e3393..35c2c889d 100644 --- a/core/modules/macros/chooser.js +++ b/core/modules/macros/chooser.js @@ -14,7 +14,6 @@ Zooming chooser macro exports.info = { name: "chooser", - wrapperTag: "div", params: { }, events: ["touchstart","touchmove","touchend","mouseover","mousemove","mouseup","mouseout"] diff --git a/core/modules/macros/slider.js b/core/modules/macros/slider.js index 865bec845..32d0093a5 100644 --- a/core/modules/macros/slider.js +++ b/core/modules/macros/slider.js @@ -79,11 +79,10 @@ exports.getSliderChildren = function() { if(this.hasParameter("content")) { return this.wiki.parseText("text/x-tiddlywiki",this.params.content).tree; } else if(this.hasParameter("target")) { - return [$tw.Tree.Macro( - "tiddler", - {target: this.params.target}, - null, - this.wiki)]; + return [$tw.Tree.Macro("tiddler",{ + srcParams: {target: this.params.target}, + wiki: this.wiki + })]; } else { return [$tw.Tree.errorNode("No content specified for slider")]; } diff --git a/core/modules/macros/story/story.js b/core/modules/macros/story/story.js index d269c6b77..409edf316 100644 --- a/core/modules/macros/story/story.js +++ b/core/modules/macros/story/story.js @@ -148,10 +148,10 @@ exports.executeMacro = function() { var storyJson = JSON.parse(this.wiki.getTiddlerText(this.params.story)), storyNode = $tw.Tree.Element("div",{},[]); for(var t=0; t]*)>/mg, reAttr = /\s*([A-Za-z\-_]+)(?:\s*=\s*(?:("[^"]*")|('[^']*')|([^"'\s]+)))?/mg; reStart.lastIndex = this.pos; diff --git a/core/modules/parsers/newwikitextparser/blockrules/list.js b/core/modules/parsers/newwikitextparser/blockrules/list.js index 33bddd64f..01450d803 100644 --- a/core/modules/parsers/newwikitextparser/blockrules/list.js +++ b/core/modules/parsers/newwikitextparser/blockrules/list.js @@ -30,7 +30,7 @@ var listTypes = { /* */ -exports.parse = function(match) { +exports.parse = function(match,isBlock) { var listStack = [], // Array containing list elements for the previous row in the list t, listInfo, listElement, itemElement, previousRootListTag; // Cycle through the rows in the list diff --git a/core/modules/parsers/newwikitextparser/blockrules/rule.js b/core/modules/parsers/newwikitextparser/blockrules/rule.js index a41797be8..a7d8a7d93 100644 --- a/core/modules/parsers/newwikitextparser/blockrules/rule.js +++ b/core/modules/parsers/newwikitextparser/blockrules/rule.js @@ -18,7 +18,7 @@ exports.blockParser = true; exports.regExpString = "-{3,}\r?\n"; -exports.parse = function(match) { +exports.parse = function(match,isBlock) { this.pos = match.index + match[0].length; return [$tw.Tree.Element("hr",{},[])]; }; diff --git a/core/modules/parsers/newwikitextparser/newwikitextparser.js b/core/modules/parsers/newwikitextparser/newwikitextparser.js index db0dea00f..d12ff56ae 100644 --- a/core/modules/parsers/newwikitextparser/newwikitextparser.js +++ b/core/modules/parsers/newwikitextparser/newwikitextparser.js @@ -54,7 +54,7 @@ WikiTextRenderer.prototype.parseBlock = function() { rule = this.parser.blockRules[t]; } } - return rule ? rule.parse.call(this,match) : []; + return rule ? rule.parse.call(this,match,true) : []; } else { // Treat it as a paragraph if we didn't find a block rule return [$tw.Tree.Element("p",{},this.parseRun())]; @@ -111,7 +111,7 @@ WikiTextRenderer.prototype.parseRun = function(terminatorRegExp) { } } if(rule) { - tree.push.apply(tree,rule.parse.call(this,runRuleMatch)); + tree.push.apply(tree,rule.parse.call(this,runRuleMatch,false)); } // Look for the next run rule this.parser.runRegExp.lastIndex = this.pos; diff --git a/core/modules/parsers/newwikitextparser/runrules/macro.js b/core/modules/parsers/newwikitextparser/runrules/macro.js index 6c40e269a..5b6a3f05c 100644 --- a/core/modules/parsers/newwikitextparser/runrules/macro.js +++ b/core/modules/parsers/newwikitextparser/runrules/macro.js @@ -19,13 +19,17 @@ exports.blockParser = true; exports.regExpString = "<<"; -exports.parse = function(match) { +exports.parse = function(match,isBlock) { var regExp = /<<(?:([!@£\$%\^\&\*\(\)`\~'"\|\\\/;\:\.\,\+\=\-\_\{\}])|([^>\s]+))(?:\s*)((?:[^>]|(?:>(?!>)))*)>>/mg; regExp.lastIndex = this.pos; match = regExp.exec(this.source); if(match && match.index === this.pos) { this.pos = match.index + match[0].length; - var macroNode = $tw.Tree.Macro(match[1] || match[2],match[3],[],this.wiki); + var macroNode = $tw.Tree.Macro(match[1] || match[2],{ + srcParams: match[3], + isBlock: isBlock, + wiki: this.wiki + }); this.dependencies.mergeDependencies(macroNode.dependencies); return [macroNode]; } diff --git a/core/modules/parsers/newwikitextparser/runrules/prettylink.js b/core/modules/parsers/newwikitextparser/runrules/prettylink.js index 1d20d0c68..7ec25cad6 100644 --- a/core/modules/parsers/newwikitextparser/runrules/prettylink.js +++ b/core/modules/parsers/newwikitextparser/runrules/prettylink.js @@ -18,7 +18,7 @@ exports.runParser = true; exports.regExpString = "\\[\\["; -exports.parse = function(match) { +exports.parse = function(match,isBlock) { var regExp = /\[\[(.*?)(?:\|(~)?(.*?))?\]\]/mg; regExp.lastIndex = this.pos; match = regExp.exec(this.source); @@ -26,7 +26,11 @@ exports.parse = function(match) { var text = match[1], link = match[3] || text; this.pos = match.index + match[0].length; - var macroNode = $tw.Tree.Macro("link",{to: link},[$tw.Tree.Text(text)],this.wiki); + var macroNode = $tw.Tree.Macro("link",{ + srcParams: {to: link}, + content: [$tw.Tree.Text(text)], + wiki: this.wiki + }); this.dependencies.mergeDependencies(macroNode.dependencies); return [macroNode]; } diff --git a/core/modules/parsers/newwikitextparser/runrules/wikilink.js b/core/modules/parsers/newwikitextparser/runrules/wikilink.js index 526b7e706..d78b44796 100644 --- a/core/modules/parsers/newwikitextparser/runrules/wikilink.js +++ b/core/modules/parsers/newwikitextparser/runrules/wikilink.js @@ -33,7 +33,7 @@ textPrimitives.wikiLink = "(?:(?:" + textPrimitives.upperLetter + "+" + exports.regExpString = textPrimitives.unWikiLink + "?" + textPrimitives.wikiLink; -exports.parse = function(match) { +exports.parse = function(match,isBlock) { this.pos = match.index + match[0].length; // If the link starts with the unwikilink character then just output it as plain text if(match[0].substr(0,1) === textPrimitives.unWikiLink) { @@ -48,7 +48,11 @@ exports.parse = function(match) { return [$tw.Tree.Text(match[0])]; } } - var macroNode = $tw.Tree.Macro("link",{to: match[0]},[$tw.Tree.Text(match[0])],this.wiki); + var macroNode = $tw.Tree.Macro("link",{ + srcParams: {to: match[0]}, + content: [$tw.Tree.Text(match[0])], + wiki: this.wiki + }); this.dependencies.mergeDependencies(macroNode.dependencies); return [macroNode]; }; diff --git a/core/modules/parsers/tiddlytextparser.js b/core/modules/parsers/tiddlytextparser.js index 88ef1a740..5a39ec45c 100644 --- a/core/modules/parsers/tiddlytextparser.js +++ b/core/modules/parsers/tiddlytextparser.js @@ -38,10 +38,14 @@ TiddlyTextParser.prototype.parse = function(type,text) { var macroName = match[2] || match[3]; if(match[1]) { // Transclusion macroNode = $tw.Tree.Macro("tiddler",{ - target: match[1] - },[],this.wiki); + srcParams: {target: match[1]}, + wiki: this.wiki + }); } else if(macroName) { // Macro call - macroNode = $tw.Tree.Macro(macroName,match[4],[],this.wiki); + macroNode = $tw.Tree.Macro(macroName,{ + srcParams: match[4], + wiki: this.wiki + }); } output.push(macroNode); dependencies.mergeDependencies(macroNode.dependencies); diff --git a/core/modules/parsers/wikitextparser/rules/wikitextrules.js b/core/modules/parsers/wikitextparser/rules/wikitextrules.js index 525637f24..10d701c19 100755 --- a/core/modules/parsers/wikitextparser/rules/wikitextrules.js +++ b/core/modules/parsers/wikitextparser/rules/wikitextrules.js @@ -103,9 +103,13 @@ var enclosedTextHelper = function(w) { } }; -var insertMacroCall = function(w,output,name,params,children) { +var insertMacroCall = function(w,output,name,params,content) { if(name in w.wiki.macros) { - var macroNode = $tw.Tree.Macro(name,params,children,w.wiki); + var macroNode = $tw.Tree.Macro(name,{ + srcParams: params, + content: content, + wiki: w.wiki + }); w.dependencies.mergeDependencies(macroNode.dependencies); output.push(macroNode); } diff --git a/core/modules/treenodes/macro.js b/core/modules/treenodes/macro.js index 1bf95ad49..6df636818 100644 --- a/core/modules/treenodes/macro.js +++ b/core/modules/treenodes/macro.js @@ -17,32 +17,39 @@ var Node = require("./node.js").Node; /* Construct a renderer node representing a macro invocation macroName: name of the macro + options: see below + +The options available are: + srcParams: a string or a hashmap of parameters (each can be a string, or a fn(tiddler,wiki) for evaluated parameters) - children: optional array of child nodes - store: reference to the WikiStore associated with this macro + content: optional array of child nodes + wiki: reference to the WikiStore associated with this macro dependencies: optional Dependencies object representing the dependencies of this macro + isBlock: true if this macro is being used as an HTML block Note that the dependencies will be evaluated if not provided. */ -var Macro = function(macroName,srcParams,content,wiki,dependencies) { - var MacroClass = wiki ? wiki.macros[macroName] : null; // Get the macro class +var Macro = function(macroName,options) { + options = options || {}; + var MacroClass = options.wiki ? options.wiki.macros[macroName] : null; // Get the macro class if(this instanceof Macro) { // Save the details this.macroName = macroName; - this.srcParams = srcParams || {}; - this.content = content || []; - this.wiki = wiki; - this.dependencies = dependencies; + this.srcParams = options.srcParams || {}; + this.content = options.content || []; + this.wiki = options.wiki; + this.dependencies = options.dependencies; + this.isBlock = options.isBlock; // Parse the macro parameters if required if(typeof this.srcParams === "string") { - this.srcParams = this.parseMacroParamString(srcParams); + this.srcParams = this.parseMacroParamString(this.srcParams); } // Evaluate the dependencies if required if(macroName && !this.dependencies) { this.dependencies = this.evaluateDependencies(); } // Get a reference to the static information about this macro - if(wiki && wiki.macros[macroName]) { + if(MacroClass) { this.MacroClass = MacroClass; this.info = MacroClass.prototype.info; } @@ -51,7 +58,7 @@ var Macro = function(macroName,srcParams,content,wiki,dependencies) { if(!MacroClass) { throw "Unknown macro '" + macroName + "'"; } - return new MacroClass(macroName,srcParams,content,wiki,dependencies); + return new MacroClass(macroName,options); } }; @@ -129,7 +136,13 @@ Macro.prototype.cloneContent = function() { }; Macro.prototype.clone = function() { - return new this.MacroClass(this.macroName,this.srcParams,this.cloneContent(),this.wiki,this.dependencies); + return new this.MacroClass(this.macroName,{ + srcParams: this.srcParams, + content: this.cloneContent(), + wiki: this.wiki, + isBlock: this.isBlock, + dependencies: this.dependencies + }); }; Macro.prototype.execute = function(parents,tiddlerTitle) { @@ -164,7 +177,7 @@ Macro.prototype.render = function(type) { Macro.prototype.renderInDom = function(parentDomNode,insertBefore) { // Create the wrapper node for the macro - var domNode = document.createElement(this.info.wrapperTag || "span"); + var domNode = document.createElement(this.isBlock ? "div" : "span"); this.domNode = domNode; if(insertBefore) { parentDomNode.insertBefore(domNode,insertBefore); diff --git a/tw5.com/tiddlers/TestingNewWikiText.tid b/tw5.com/tiddlers/TestingNewWikiText.tid index c9f9bfa0f..1691f31f7 100644 --- a/tw5.com/tiddlers/TestingNewWikiText.tid +++ b/tw5.com/tiddlers/TestingNewWikiText.tid @@ -82,3 +82,11 @@ This is my nice and simple block of text. HelloThere And another:
This time the text is all squashed up, without line breaks
+ +--- + +Macro calls can be inline like this: <> + +Or, at paragraph block level: + +<>