cmark

My personal build of CMark ✏️

Commit
d39cd29b8763c248b416bcae15586132be00c686
Parent
8e0f25192e6ece5c77fb69d8f4032761f85a566f
Author
John MacFarlane <jgm@berkeley.edu>
Date

Made closeUnmatchedBlocks a method of DocParser...

instead of a closure. Performance increase and code simplification.

Diffstat

1 file changed, 24 insertions, 26 deletions

Status File Name N° Changes Insertions Deletions
Modified js/lib/blocks.js 50 24 26
diff --git a/js/lib/blocks.js b/js/lib/blocks.js
@@ -215,6 +215,15 @@ var listsMatch = function(list_data, item_data) {
             list_data.bullet_char === item_data.bullet_char);
 };
 
+// Finalize and close any unmatched blocks.
+var closeUnmatchedBlocks = function() {
+    // finalize any blocks not matched
+    while (this.oldtip !== this.last_matched_container) {
+        this.finalize(this.oldtip, this.line_number - 1);
+        this.oldtip = this.oldtip.parent;
+    }
+};
+
 // Analyze a line of text and update the document appropriately.
 // We parse markdown text by calling this on each line of input,
 // then finalizing the document.
@@ -226,12 +235,11 @@ var incorporateLine = function(ln, line_number) {
     var data;
     var blank;
     var indent;
-    var last_matched_container;
     var i;
     var CODE_INDENT = 4;
 
     var container = this.doc;
-    var oldtip = this.tip;
+    this.oldtip = this.tip;
 
     // replace NUL characters for security
     if (ln.indexOf('\u0000') !== -1) {
@@ -335,20 +343,7 @@ var incorporateLine = function(ln, line_number) {
         }
     }
 
-    last_matched_container = container;
-
-    // This function is used to finalize and close any unmatched
-    // blocks.  We aren't ready to do this now, because we might
-    // have a lazy paragraph continuation, in which case we don't
-    // want to close unmatched blocks.  So we store this closure for
-    // use later, when we have more information.
-    var closeUnmatchedBlocks = function(mythis) {
-        // finalize any blocks not matched
-        while (oldtip !== last_matched_container) {
-            mythis.finalize(oldtip, line_number - 1);
-            oldtip = oldtip.parent;
-        }
-    };
+    this.last_matched_container = container;
 
     // Check to see if we've hit 2nd blank line; if so break out of list:
     if (blank && container.last_line_blank) {
@@ -377,7 +372,7 @@ var incorporateLine = function(ln, line_number) {
             // indented code
             if (this.tip.t !== 'Paragraph' && !blank) {
                 offset += CODE_INDENT;
-                closeUnmatchedBlocks(this);
+                this.closeUnmatchedBlocks();
                 container = this.addChild('IndentedCode', line_number, offset);
             } else { // indent > 4 in a lazy paragraph continuation
                 break;
@@ -390,13 +385,13 @@ var incorporateLine = function(ln, line_number) {
             if (ln.charCodeAt(offset) === C_SPACE) {
                 offset++;
             }
-            closeUnmatchedBlocks(this);
+            this.closeUnmatchedBlocks();
             container = this.addChild('BlockQuote', line_number, offset);
 
         } else if ((match = ln.slice(first_nonspace).match(reATXHeaderMarker))) {
             // ATX header
             offset = first_nonspace + match[0].length;
-            closeUnmatchedBlocks(this);
+            this.closeUnmatchedBlocks();
             container = this.addChild('Header', line_number, first_nonspace);
             container.level = match[0].trim().length; // number of #s
             // remove trailing ###s:
@@ -407,7 +402,7 @@ var incorporateLine = function(ln, line_number) {
         } else if ((match = ln.slice(first_nonspace).match(reCodeFence))) {
             // fenced code block
             var fence_length = match[0].length;
-            closeUnmatchedBlocks(this);
+            this.closeUnmatchedBlocks();
             container = this.addChild('FencedCode', line_number, first_nonspace);
             container.fence_length = fence_length;
             container.fence_char = match[0][0];
@@ -417,7 +412,7 @@ var incorporateLine = function(ln, line_number) {
 
         } else if (matchAt(reHtmlBlockOpen, ln, first_nonspace) !== -1) {
             // html block
-            closeUnmatchedBlocks(this);
+            this.closeUnmatchedBlocks();
             container = this.addChild('HtmlBlock', line_number, first_nonspace);
             // note, we don't adjust offset because the tag is part of the text
             break;
@@ -426,21 +421,21 @@ var incorporateLine = function(ln, line_number) {
                    container.strings.length === 1 &&
                    ((match = ln.slice(first_nonspace).match(reSetextHeaderLine)))) {
             // setext header line
-            closeUnmatchedBlocks(this);
+            this.closeUnmatchedBlocks();
             container.t = 'Header'; // convert Paragraph to SetextHeader
             container.level = match[0][0] === '=' ? 1 : 2;
             offset = ln.length;
 
         } else if (matchAt(reHrule, ln, first_nonspace) !== -1) {
             // hrule
-            closeUnmatchedBlocks(this);
+            this.closeUnmatchedBlocks();
             container = this.addChild('HorizontalRule', line_number, first_nonspace);
             offset = ln.length - 1;
             break;
 
         } else if ((data = parseListMarker(ln, first_nonspace))) {
             // list item
-            closeUnmatchedBlocks(this);
+            this.closeUnmatchedBlocks();
             data.marker_offset = indent;
             offset = first_nonspace + data.padding;
 
@@ -480,7 +475,7 @@ var incorporateLine = function(ln, line_number) {
     indent = first_nonspace - offset;
 
     // First check for a lazy paragraph continuation:
-    if (this.tip !== last_matched_container &&
+    if (this.tip !== this.last_matched_container &&
         !blank &&
         this.tip.t === 'Paragraph' &&
         this.tip.strings.length > 0) {
@@ -492,7 +487,7 @@ var incorporateLine = function(ln, line_number) {
     } else { // not a lazy continuation
 
         // finalize any blocks not matched
-        closeUnmatchedBlocks(this);
+        this.closeUnmatchedBlocks();
 
         // Block quote lines are never blank as they start with >
         // and we don't count blanks in fenced code for purposes of tight/loose
@@ -691,6 +686,8 @@ function DocParser(options){
     return {
         doc: new Document(),
         tip: this.doc,
+        oldtip: this.doc,
+        last_matched_container: this.doc,
         refmap: {},
         lastLineLength: 0,
         inlineParser: new InlineParser(),
@@ -700,6 +697,7 @@ function DocParser(options){
         incorporateLine: incorporateLine,
         finalize: finalize,
         processInlines: processInlines,
+        closeUnmatchedBlocks: closeUnmatchedBlocks,
         parse: parse,
         options: options || {}
     };