close method

  1. @override
Node? close(
  1. InlineParser parser,
  2. covariant SimpleDelimiter opener,
  3. Delimiter? closer, {
  4. required List<Node> getChildren(),
})
override

Attempts to close this tag at the current position.

If a tag cannot be closed at the current position (for example, if a link reference cannot be found for a link tag's label), then null is returned.

If a tag can be closed at the current position, then this method calls getChildren, in which parser parses any nested text into child nodes. The returned Node incorpororates these child nodes.

Implementation

@override
Node? close(
    InlineParser parser, covariant SimpleDelimiter opener, Delimiter? closer,
    {required List<Node> Function() getChildren}) {
  var text = parser.source.substring(opener.endPos, parser.pos);
  // The current character is the `]` that closed the link text. Examine the
  // next character, to determine what type of link we might have (a '('
  // means a possible inline link; otherwise a possible reference link).
  if (parser.pos + 1 >= parser.source.length) {
    // The `]` is at the end of the document, but this may still be a valid
    // shortcut reference link.
    return _tryCreateReferenceLink(parser, text, getChildren: getChildren);
  }

  // Peek at the next character; don't advance, so as to avoid later stepping
  // backward.
  var char = parser.charAt(parser.pos + 1);

  if (char == $lparen) {
    // Maybe an inline link, like `[text](destination)`.
    parser.advanceBy(1);
    var leftParenIndex = parser.pos;
    var inlineLink = _parseInlineLink(parser);
    if (inlineLink != null) {
      return _tryCreateInlineLink(parser, inlineLink,
          getChildren: getChildren);
    }
    // At this point, we've matched `[...](`, but that `(` did not pan out to
    // be an inline link. We must now check if `[...]` is simply a shortcut
    // reference link.

    // Reset the parser position.
    parser.pos = leftParenIndex;
    parser.advanceBy(-1);
    return _tryCreateReferenceLink(parser, text, getChildren: getChildren);
  }

  if (char == $lbracket) {
    parser.advanceBy(1);
    // At this point, we've matched `[...][`. Maybe a *full* reference link,
    // like `[foo][bar]` or a *collapsed* reference link, like `[foo][]`.
    if (parser.pos + 1 < parser.source.length &&
        parser.charAt(parser.pos + 1) == $rbracket) {
      // That opening `[` is not actually part of the link. Maybe a
      // *shortcut* reference link (followed by a `[`).
      parser.advanceBy(1);
      return _tryCreateReferenceLink(parser, text, getChildren: getChildren);
    }
    var label = _parseReferenceLinkLabel(parser);
    if (label != null) {
      return _tryCreateReferenceLink(parser, label, getChildren: getChildren);
    }
    return null;
  }

  // The link text (inside `[...]`) was not followed with a opening `(` nor
  // an opening `[`. Perhaps just a simple shortcut reference link (`[...]`).
  return _tryCreateReferenceLink(parser, text, getChildren: getChildren);
}