|
|
@@ -14,7 +14,10 @@ var formatText = (function() {
|
|
|
emojiFormatFunction: identity,
|
|
|
|
|
|
/** @type {function(string):string} */
|
|
|
- textFilter: identity
|
|
|
+ textFilter: identity,
|
|
|
+
|
|
|
+ /** @type {function(string):{link: string, text: string}} */
|
|
|
+ linkFilter: linkidentity
|
|
|
};
|
|
|
|
|
|
/**
|
|
|
@@ -160,10 +163,10 @@ var formatText = (function() {
|
|
|
* @return {boolean|MsgBranch}
|
|
|
**/
|
|
|
MsgBranch.prototype.finishWith = function(i) {
|
|
|
- var prevIsAlphadec = isAlphadec(text[i -1]);
|
|
|
- if (this.trigger === '<' && text[i] === '>' && prevIsAlphadec)
|
|
|
+ if (this.trigger === '<' && text[i] === '>')
|
|
|
return true;
|
|
|
|
|
|
+ var prevIsAlphadec = isAlphadec(text[i -1]);
|
|
|
if (!this.isQuote && text.substr(i, this.trigger.length) === this.trigger) {
|
|
|
if (!prevIsAlphadec && (this.isBold || this.isItalic || this.isStrike)) {
|
|
|
// previous char is not compatible with finishing now
|
|
|
@@ -228,31 +231,34 @@ var formatText = (function() {
|
|
|
* @return {string|null}
|
|
|
**/
|
|
|
MsgBranch.prototype.isNewToken = function(i) {
|
|
|
- if (this.isCode || this.isEmoji || this.isCodeBlock)
|
|
|
+ if (this.isCode || this.isEmoji || this.isCodeBlock || this.isLink)
|
|
|
return null;
|
|
|
- var nextIsAlphadec = isAlphadec(text[i +1]);
|
|
|
-
|
|
|
- if (text.substr(i, 3) === '```')
|
|
|
- return '```';
|
|
|
- if (isBeginingOfLine()) {
|
|
|
- if (text.substr(i, 4) === ">")
|
|
|
- return ">";
|
|
|
- if (text[i] === '>')
|
|
|
+ if (!this.lastNode || this.lastNode.terminated || this.lastNode instanceof MsgTextLeaf) {
|
|
|
+ var nextIsAlphadec = isAlphadec(text[i +1]);
|
|
|
+ if (text.substr(i, 3) === '```')
|
|
|
+ return '```';
|
|
|
+ if (isBeginingOfLine()) {
|
|
|
+ if (text.substr(i, 4) === ">")
|
|
|
+ return ">";
|
|
|
+ if (text[i] === '>')
|
|
|
+ return text[i];
|
|
|
+ }
|
|
|
+ if (['`', '\n'].indexOf(text[i]) !== -1)
|
|
|
return text[i];
|
|
|
- }
|
|
|
- if (['`', '\n'].indexOf(text[i]) !== -1)
|
|
|
- return text[i];
|
|
|
- if (['*', '~', '-', '_' ].indexOf(text[i]) !== -1 && (nextIsAlphadec || ['*', '~', '-', '_', '<', '&'].indexOf(text[i+1]) !== -1))
|
|
|
- return text[i];
|
|
|
- if ([':', '<'].indexOf(text[i]) !== -1 && nextIsAlphadec)
|
|
|
- return text[i];
|
|
|
-
|
|
|
- for (var highlightIndex =0, nbHighlight =opts.highlights.length; highlightIndex < nbHighlight; highlightIndex++) {
|
|
|
- var highlight = opts.highlights[highlightIndex];
|
|
|
-
|
|
|
- // TODO compare with collators
|
|
|
- if (text.substr(i, highlight.length) === highlight)
|
|
|
- return highlight;
|
|
|
+ if (['*', '~', '-', '_' ].indexOf(text[i]) !== -1 && (nextIsAlphadec || ['*', '~', '-', '_', '<', '&'].indexOf(text[i+1]) !== -1))
|
|
|
+ return text[i];
|
|
|
+ if ([':'].indexOf(text[i]) !== -1 && nextIsAlphadec)
|
|
|
+ return text[i];
|
|
|
+ if (['<'].indexOf(text[i]) !== -1)
|
|
|
+ return text[i];
|
|
|
+
|
|
|
+ for (var highlightIndex =0, nbHighlight =opts.highlights.length; highlightIndex < nbHighlight; highlightIndex++) {
|
|
|
+ var highlight = opts.highlights[highlightIndex];
|
|
|
+
|
|
|
+ // TODO compare with collators
|
|
|
+ if (text.substr(i, highlight.length) === highlight)
|
|
|
+ return highlight;
|
|
|
+ }
|
|
|
}
|
|
|
return null;
|
|
|
};
|
|
|
@@ -391,15 +397,28 @@ var formatText = (function() {
|
|
|
**/
|
|
|
MsgTextLeaf.prototype.outerHTML = function() {
|
|
|
var tagName = 'span'
|
|
|
- ,classList = [];
|
|
|
+ ,classList = []
|
|
|
+ ,innerHTML
|
|
|
+ ,params = '';
|
|
|
|
|
|
if (this._parent.checkIsCodeBlock()) {
|
|
|
classList.push('codeblock');
|
|
|
+ innerHTML = this.innerHTML();
|
|
|
} else if (this._parent.checkIsCode()) {
|
|
|
classList.push('code');
|
|
|
+ innerHTML = this.innerHTML();
|
|
|
} else {
|
|
|
- if (this.isLink)
|
|
|
+ if (this._parent.isLink) {
|
|
|
+ var link = opts.linkFilter(this.text);
|
|
|
tagName = 'a';
|
|
|
+ params = ' href="' +link.link +'"';
|
|
|
+ if (link.isExternal) {
|
|
|
+ params += ' target="_blank"';
|
|
|
+ }
|
|
|
+ innerHTML = opts.textFilter(link.text);
|
|
|
+ } else {
|
|
|
+ innerHTML = this.innerHTML();
|
|
|
+ }
|
|
|
if (this._parent.checkIsBold())
|
|
|
classList.push('bold');
|
|
|
if (this._parent.checkIsItalic())
|
|
|
@@ -411,7 +430,7 @@ var formatText = (function() {
|
|
|
if (this._parent.checkIsHighlight())
|
|
|
classList.push('highlight');
|
|
|
}
|
|
|
- return '<' +tagName +(classList.length ? ' class="' +classList.join(' ') +'"' : '') +'>' +this.innerHTML() +'</' +tagName +'>';
|
|
|
+ return '<' +tagName +params +(classList.length ? ' class="' +classList.join(' ') +'"' : '') +'>' +innerHTML +'</' +tagName +'>';
|
|
|
};
|
|
|
|
|
|
MsgBranch.prototype.outerHTML = function() {
|
|
|
@@ -504,6 +523,14 @@ var formatText = (function() {
|
|
|
|
|
|
function identity(a) { return a; }
|
|
|
|
|
|
+ function linkidentity(str) {
|
|
|
+ return {
|
|
|
+ link: str,
|
|
|
+ text: str,
|
|
|
+ isInternal: false
|
|
|
+ };
|
|
|
+ };
|
|
|
+
|
|
|
/**
|
|
|
* @param {string} _text
|
|
|
* @param {({
|
|
|
@@ -519,6 +546,7 @@ var formatText = (function() {
|
|
|
opts.highlights = _opts.highlights || [];
|
|
|
opts.emojiFormatFunction = _opts.emojiFormatFunction || identity;
|
|
|
opts.textFilter = _opts.textFilter || identity;
|
|
|
+ opts.linkFilter = _opts.linkFilter || linkidentity;
|
|
|
text = _text;
|
|
|
|
|
|
root = new MsgBranch(this, 0);
|