Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
* Initial Commit * Update docs * Add support for elseif blocks * Another test * WIP * Change from `{%if%}` to `<%if%>` See discussion here - https://talk.tiddlywiki.org/t/proposed-if-widget/7882/64 * Don't use the widget body as the template if a list-empty widget is present See discussion here - #7710 (comment) * List widget should search recursively for list-template and list-empty * Allow block mode content within an if/then/else clause * Update docs * Add from-version tag to docs
- Loading branch information
Showing
11 changed files
with
467 additions
and
8 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,120 @@ | ||
/*\ | ||
title: $:/core/modules/parsers/wikiparser/rules/conditional.js | ||
type: application/javascript | ||
module-type: wikirule | ||
Conditional shortcut syntax | ||
``` | ||
This is a <% if [{something}] %>Elephant<% elseif [{else}] %>Pelican<% else %>Crocodile<% endif %> | ||
``` | ||
\*/ | ||
(function(){ | ||
|
||
/*jslint node: true, browser: true */ | ||
/*global $tw: false */ | ||
"use strict"; | ||
|
||
exports.name = "conditional"; | ||
exports.types = {inline: true, block: true}; | ||
|
||
exports.init = function(parser) { | ||
this.parser = parser; | ||
// Regexp to match | ||
this.matchRegExp = /\<\%\s*if\s+/mg; | ||
this.terminateIfRegExp = /\%\>/mg; | ||
}; | ||
|
||
exports.findNextMatch = function(startPos) { | ||
// Look for the next <% if shortcut | ||
this.matchRegExp.lastIndex = startPos; | ||
this.match = this.matchRegExp.exec(this.parser.source); | ||
// If not found then return no match | ||
if(!this.match) { | ||
return undefined; | ||
} | ||
// Check for the next %> | ||
this.terminateIfRegExp.lastIndex = this.match.index; | ||
this.terminateIfMatch = this.terminateIfRegExp.exec(this.parser.source); | ||
// If not found then return no match | ||
if(!this.terminateIfMatch) { | ||
return undefined; | ||
} | ||
// Return the position at which the construction was found | ||
return this.match.index; | ||
}; | ||
|
||
/* | ||
Parse the most recent match | ||
*/ | ||
exports.parse = function() { | ||
// Get the filter condition | ||
var filterCondition = this.parser.source.substring(this.match.index + this.match[0].length,this.terminateIfMatch.index); | ||
// Advance the parser position to past the %> | ||
this.parser.pos = this.terminateIfMatch.index + this.terminateIfMatch[0].length; | ||
// Parse the if clause | ||
return this.parseIfClause(filterCondition); | ||
}; | ||
|
||
exports.parseIfClause = function(filterCondition) { | ||
// Create the list widget | ||
var listWidget = { | ||
type: "list", | ||
tag: "$list", | ||
isBlock: this.is.block, | ||
children: [ | ||
{ | ||
type: "list-template", | ||
tag: "$list-template" | ||
}, | ||
{ | ||
type: "list-empty", | ||
tag: "$list-empty" | ||
} | ||
] | ||
}; | ||
$tw.utils.addAttributeToParseTreeNode(listWidget,"filter",filterCondition); | ||
$tw.utils.addAttributeToParseTreeNode(listWidget,"variable","condition"); | ||
$tw.utils.addAttributeToParseTreeNode(listWidget,"limit","1"); | ||
// Check for an immediately following double linebreak | ||
var hasLineBreak = !!$tw.utils.parseTokenRegExp(this.parser.source,this.parser.pos,/([^\S\n\r]*\r?\n(?:[^\S\n\r]*\r?\n|$))/g); | ||
// Parse the body looking for else or endif | ||
var reEndString = "\\<\\%\\s*(endif)\\s*\\%\\>|\\<\\%\\s*(else)\\s*\\%\\>|\\<\\%\\s*(elseif)\\s+([\\s\\S]+?)\\%\\>", | ||
ex; | ||
if(hasLineBreak) { | ||
ex = this.parser.parseBlocksTerminatedExtended(reEndString); | ||
} else { | ||
var reEnd = new RegExp(reEndString,"mg"); | ||
ex = this.parser.parseInlineRunTerminatedExtended(reEnd,{eatTerminator: true}); | ||
} | ||
// Put the body into the list template | ||
listWidget.children[0].children = ex.tree; | ||
// Check for an else or elseif | ||
if(ex.match) { | ||
if(ex.match[1] === "endif") { | ||
// Nothing to do if we just found an endif | ||
} else if(ex.match[2] === "else") { | ||
// Check for an immediately following double linebreak | ||
hasLineBreak = !!$tw.utils.parseTokenRegExp(this.parser.source,this.parser.pos,/([^\S\n\r]*\r?\n(?:[^\S\n\r]*\r?\n|$))/g); | ||
// If we found an else then we need to parse the body looking for the endif | ||
var reEndString = "\\<\\%\\s*(endif)\\s*\\%\\>", | ||
ex; | ||
if(hasLineBreak) { | ||
ex = this.parser.parseBlocksTerminatedExtended(reEndString); | ||
} else { | ||
var reEnd = new RegExp(reEndString,"mg"); | ||
ex = this.parser.parseInlineRunTerminatedExtended(reEnd,{eatTerminator: true}); | ||
} | ||
// Put the parsed content inside the list empty template | ||
listWidget.children[1].children = ex.tree; | ||
} else if(ex.match[3] === "elseif") { | ||
// Parse the elseif clause by reusing this parser, passing the new filter condition | ||
listWidget.children[1].children = this.parseIfClause(ex.match[4]); | ||
} | ||
} | ||
// Return the parse tree node | ||
return [listWidget]; | ||
}; | ||
|
||
})(); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,26 @@ | ||
title: Conditionals/Basic | ||
description: Basic conditional shortcut syntax | ||
type: text/vnd.tiddlywiki-multiple | ||
tags: [[$:/tags/wiki-test-spec]] | ||
|
||
title: Text | ||
|
||
This is a <% if [<something>match[one]] %>Elephant<% endif %>, I think. | ||
+ | ||
title: Output | ||
|
||
<$let something="one"> | ||
{{Text}} | ||
</$let> | ||
|
||
<$let something="two"> | ||
{{Text}} | ||
</$let> | ||
+ | ||
title: ExpectedResult | ||
|
||
<p> | ||
This is a Elephant, I think. | ||
</p><p> | ||
This is a , I think. | ||
</p> |
37 changes: 37 additions & 0 deletions
37
editions/test/tiddlers/tests/data/conditionals/BlockMode.tid
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,37 @@ | ||
title: Conditionals/BlockMode | ||
description: Basic conditional shortcut syntax in block mode | ||
type: text/vnd.tiddlywiki-multiple | ||
tags: [[$:/tags/wiki-test-spec]] | ||
|
||
title: Output | ||
|
||
\procedure test(animal) | ||
<% if [<animal>match[Elephant]] %> | ||
|
||
! It is an elephant | ||
|
||
<% else %> | ||
|
||
<% if [<animal>match[Giraffe]] %> | ||
|
||
! It is a giraffe | ||
|
||
<% else %> | ||
|
||
! It is completely unknown | ||
|
||
<% endif %> | ||
|
||
<% endif %> | ||
|
||
\end | ||
|
||
<<test "Giraffe">> | ||
|
||
<<test "Elephant">> | ||
|
||
<<test "Antelope">> | ||
+ | ||
title: ExpectedResult | ||
|
||
<h1 class="">It is a giraffe</h1><h1 class="">It is an elephant</h1><h1 class="">It is completely unknown</h1> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,26 @@ | ||
title: Conditionals/Else | ||
description: Else conditional shortcut syntax | ||
type: text/vnd.tiddlywiki-multiple | ||
tags: [[$:/tags/wiki-test-spec]] | ||
|
||
title: Text | ||
|
||
This is a <% if [<something>match[one]] %>Elephant<% else %>Crocodile<% endif %>, I think. | ||
+ | ||
title: Output | ||
|
||
<$let something="one"> | ||
{{Text}} | ||
</$let> | ||
|
||
<$let something="two"> | ||
{{Text}} | ||
</$let> | ||
+ | ||
title: ExpectedResult | ||
|
||
<p> | ||
This is a Elephant, I think. | ||
</p><p> | ||
This is a Crocodile, I think. | ||
</p> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,32 @@ | ||
title: Conditionals/Elseif | ||
description: Elseif conditional shortcut syntax | ||
type: text/vnd.tiddlywiki-multiple | ||
tags: [[$:/tags/wiki-test-spec]] | ||
|
||
title: Text | ||
|
||
This is a <% if [<something>match[one]] %>Elephant<% elseif [<something>match[two]] %>Antelope<% else %>Crocodile<% endif %>, I think. | ||
+ | ||
title: Output | ||
|
||
<$let something="one"> | ||
{{Text}} | ||
</$let> | ||
|
||
<$let something="two"> | ||
{{Text}} | ||
</$let> | ||
|
||
<$let something="three"> | ||
{{Text}} | ||
</$let> | ||
+ | ||
title: ExpectedResult | ||
|
||
<p> | ||
This is a Elephant, I think. | ||
</p><p> | ||
This is a Antelope, I think. | ||
</p><p> | ||
This is a Crocodile, I think. | ||
</p> |
26 changes: 26 additions & 0 deletions
26
editions/test/tiddlers/tests/data/conditionals/MissingEndIf.tid
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,26 @@ | ||
title: Conditionals/MissingEndif | ||
description: Conditional shortcut syntax with missing endif | ||
type: text/vnd.tiddlywiki-multiple | ||
tags: [[$:/tags/wiki-test-spec]] | ||
|
||
title: Text | ||
|
||
This is a <% if [<something>match[one]] %>Elephant | ||
+ | ||
title: Output | ||
|
||
<$let something="one"> | ||
{{Text}} | ||
</$let> | ||
|
||
<$let something="two"> | ||
{{Text}} | ||
</$let> | ||
+ | ||
title: ExpectedResult | ||
|
||
<p> | ||
This is a Elephant | ||
</p><p> | ||
This is a | ||
</p> |
12 changes: 12 additions & 0 deletions
12
editions/test/tiddlers/tests/data/conditionals/MultipleResults.tid
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,12 @@ | ||
title: Conditionals/MultipleResults | ||
description: Check that multiple results from the filter are ignored | ||
type: text/vnd.tiddlywiki-multiple | ||
tags: [[$:/tags/wiki-test-spec]] | ||
|
||
title: Output | ||
|
||
This is a <% if 1 2 3 4 5 6 %>Elephant<% endif %>, I think. | ||
+ | ||
title: ExpectedResult | ||
|
||
<p>This is a Elephant, I think.</p> |
Oops, something went wrong.
b7562f0
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Successfully deployed to the following URLs:
tiddlywiki5 – ./
tiddlywiki5-git-master-jermolene.vercel.app
tiddlywiki5.vercel.app
tiddlywiki5-jermolene.vercel.app