Parse formatted message bodies in addition to plain ones.
This commit is contained in:
parent
cfa686867c
commit
e56b15237e
4 changed files with 43 additions and 15 deletions
|
@ -21,26 +21,30 @@ export class BaseTextTile extends BaseMessageTile {
|
||||||
constructor(options) {
|
constructor(options) {
|
||||||
super(options);
|
super(options);
|
||||||
this._messageBody = null;
|
this._messageBody = null;
|
||||||
|
this._messageFormat = null
|
||||||
}
|
}
|
||||||
|
|
||||||
get shape() {
|
get shape() {
|
||||||
return "message";
|
return "message";
|
||||||
}
|
}
|
||||||
|
|
||||||
_parseBody(bodyString) {
|
_parseBody(body) {
|
||||||
return stringAsBody(bodyString);
|
return stringAsBody(body.string);
|
||||||
}
|
}
|
||||||
|
|
||||||
get body() {
|
get body() {
|
||||||
const body = this._getBodyAsString();
|
const body = this._getBody();
|
||||||
// body is a string, so we can check for difference by just
|
// body.string is a string, so we can check for difference by just
|
||||||
// doing an equality check
|
// doing an equality check
|
||||||
if (!this._messageBody || this._messageBody.sourceString !== body) {
|
// Even if the body hasn't changed, but the format has, we need
|
||||||
|
// to re-fill our cache.
|
||||||
|
if (!this._messageBody || this._messageBody.sourceString !== body.string || this._messageFormat !== body.format) {
|
||||||
// body with markup is an array of parts,
|
// body with markup is an array of parts,
|
||||||
// so we should not recreate it for the same body string,
|
// so we should not recreate it for the same body string,
|
||||||
// or else the equality check in the binding will always fail.
|
// or else the equality check in the binding will always fail.
|
||||||
// So cache it here.
|
// So cache it here.
|
||||||
this._messageBody = this._parseBody(body);
|
this._messageBody = this._parseBody(body);
|
||||||
|
this._messageFormat = body.format;
|
||||||
}
|
}
|
||||||
return this._messageBody;
|
return this._messageBody;
|
||||||
}
|
}
|
||||||
|
|
|
@ -33,13 +33,15 @@ export class EncryptedEventTile extends BaseTextTile {
|
||||||
return "message-status"
|
return "message-status"
|
||||||
}
|
}
|
||||||
|
|
||||||
_getBodyAsString() {
|
_getBody() {
|
||||||
const decryptionError = this._entry.decryptionError;
|
const decryptionError = this._entry.decryptionError;
|
||||||
const code = decryptionError?.code;
|
const code = decryptionError?.code;
|
||||||
|
let string;
|
||||||
if (code === "MEGOLM_NO_SESSION") {
|
if (code === "MEGOLM_NO_SESSION") {
|
||||||
return this.i18n`The sender hasn't sent us the key for this message yet.`;
|
string = this.i18n`The sender hasn't sent us the key for this message yet.`;
|
||||||
} else {
|
} else {
|
||||||
return decryptionError?.message || this.i18n`Could not decrypt message because of unknown reason.`;
|
string = decryptionError?.message || this.i18n`Could not decrypt message because of unknown reason.`;
|
||||||
}
|
}
|
||||||
|
return { string, format: "plain" };
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -16,18 +16,39 @@ limitations under the License.
|
||||||
|
|
||||||
import {BaseTextTile} from "./BaseTextTile.js";
|
import {BaseTextTile} from "./BaseTextTile.js";
|
||||||
import {parsePlainBody} from "../MessageBody.js";
|
import {parsePlainBody} from "../MessageBody.js";
|
||||||
|
import {parseHTMLBody} from "../../../../../platform/web/dom/deserialize.js";
|
||||||
|
|
||||||
export class TextTile extends BaseTextTile {
|
export class TextTile extends BaseTextTile {
|
||||||
_getBodyAsString() {
|
_getContentString(key, format, fallback = null) {
|
||||||
const content = this._getContent();
|
const content = this._getContent();
|
||||||
let body = content?.body || "";
|
let val = content?.[key] || fallback;
|
||||||
if (content.msgtype === "m.emote") {
|
if (!val && val !== "") { // empty string is falsy, but OK here.
|
||||||
body = `* ${this.displayName} ${body}`;
|
return null;
|
||||||
}
|
}
|
||||||
return body;
|
if (content.msgtype === "m.emote") {
|
||||||
|
val = `* ${this.displayName} ${body}`;
|
||||||
|
}
|
||||||
|
return { string: val, format };
|
||||||
}
|
}
|
||||||
|
|
||||||
_parseBody(bodyString) {
|
_getPlainBody() {
|
||||||
return parsePlainBody(bodyString);
|
return this._getContentString("body", "plain", "");
|
||||||
|
}
|
||||||
|
|
||||||
|
_getFormattedBody() {
|
||||||
|
return this._getContentString("formatted_body", "html");
|
||||||
|
}
|
||||||
|
|
||||||
|
_getBody() {
|
||||||
|
return this._getFormattedBody() || this._getPlainBody();
|
||||||
|
}
|
||||||
|
|
||||||
|
_parseBody(body) {
|
||||||
|
const string = body.string;
|
||||||
|
if (body.format === "html") {
|
||||||
|
return parseHTMLBody(this.platform, string);
|
||||||
|
} else {
|
||||||
|
return parsePlainBody(string);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -42,6 +42,7 @@ const formatFunction = {
|
||||||
code: codePart => tag.code({}, text(codePart.text)),
|
code: codePart => tag.code({}, text(codePart.text)),
|
||||||
text: textPart => text(textPart.text),
|
text: textPart => text(textPart.text),
|
||||||
link: linkPart => tag.a({ href: linkPart.url, target: "_blank", rel: "noopener" }, renderParts(linkPart.inlines)),
|
link: linkPart => tag.a({ href: linkPart.url, target: "_blank", rel: "noopener" }, renderParts(linkPart.inlines)),
|
||||||
|
format: formatPart => tag[formatPart.format]({}, renderParts(formatPart.children)),
|
||||||
newline: () => tag.br()
|
newline: () => tag.br()
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
Reference in a new issue