mirror of
https://github.com/vector-im/element-web.git
synced 2024-11-16 05:04:57 +08:00
add basic spoiler support
This commit is contained in:
parent
8844706e5f
commit
d8f4512439
@ -280,6 +280,33 @@ limitations under the License.
|
||||
overflow-y: hidden;
|
||||
}
|
||||
|
||||
/* Spoiler stuff */
|
||||
.mx_EventTile_spoiler {
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.mx_EventTile_spoiler_reason {
|
||||
color: $event-timestamp-color;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
.mx_EventTile_spoiler_content {
|
||||
background-color: black;
|
||||
}
|
||||
|
||||
.mx_EventTile_spoiler_content > span {
|
||||
visibility: hidden;
|
||||
}
|
||||
|
||||
|
||||
.mx_EventTile_spoiler.visible > .mx_EventTile_spoiler_content {
|
||||
background-color: initial;
|
||||
}
|
||||
|
||||
.mx_EventTile_spoiler.visible > .mx_EventTile_spoiler_content > span {
|
||||
visibility: visible;
|
||||
}
|
||||
|
||||
/* End to end encryption stuff */
|
||||
.mx_EventTile:hover .mx_EventTile_e2eIcon {
|
||||
opacity: 1;
|
||||
|
@ -250,7 +250,7 @@ const sanitizeHtmlParams = {
|
||||
allowedAttributes: {
|
||||
// custom ones first:
|
||||
font: ['color', 'data-mx-bg-color', 'data-mx-color', 'style'], // custom to matrix
|
||||
span: ['data-mx-bg-color', 'data-mx-color', 'style'], // custom to matrix
|
||||
span: ['data-mx-bg-color', 'data-mx-color', 'data-mx-spoiler', 'style'], // custom to matrix
|
||||
a: ['href', 'name', 'target', 'rel'], // remote target: custom to matrix
|
||||
img: ['src', 'width', 'height', 'alt', 'title'],
|
||||
ol: ['start'],
|
||||
|
32
src/components/views/elements/Spoiler.js
Normal file
32
src/components/views/elements/Spoiler.js
Normal file
@ -0,0 +1,32 @@
|
||||
'use strict';
|
||||
|
||||
import React from 'react';
|
||||
|
||||
module.exports = React.createClass({
|
||||
displayName: 'Spoiler',
|
||||
|
||||
getInitialState() {
|
||||
return {
|
||||
visible: false,
|
||||
};
|
||||
},
|
||||
|
||||
toggleVisible() {
|
||||
this.setState({ visible: !this.state.visible });
|
||||
},
|
||||
|
||||
render: function() {
|
||||
const reason = this.props.reason ? (
|
||||
<span className="mx_EventTile_spoiler_reason">{"(" + this.props.reason + ")"}</span>
|
||||
) : null;
|
||||
return (
|
||||
<span className={"mx_EventTile_spoiler" + (this.state.visible ? " visible" : "")} onClick={this.toggleVisible.bind(this)}>
|
||||
{ reason }
|
||||
|
||||
<span className="mx_EventTile_spoiler_content">
|
||||
<span dangerouslySetInnerHTML={{ __html: this.props.contentHtml }} />
|
||||
</span>
|
||||
</span>
|
||||
);
|
||||
}
|
||||
})
|
@ -96,6 +96,8 @@ module.exports = React.createClass({
|
||||
},
|
||||
|
||||
_applyFormatting() {
|
||||
this.activateSpoilers(this.refs.content.children);
|
||||
|
||||
// pillifyLinks BEFORE linkifyElement because plain room/user URLs in the composer
|
||||
// are still sent as plaintext URLs. If these are ever pillified in the composer,
|
||||
// we should be pillify them here by doing the linkifying BEFORE the pillifying.
|
||||
@ -184,6 +186,34 @@ module.exports = React.createClass({
|
||||
}
|
||||
},
|
||||
|
||||
activateSpoilers: function(nodes) {
|
||||
let node = nodes[0];
|
||||
while (node) {
|
||||
if (node.tagName === "SPAN" && typeof node.getAttribute("data-mx-spoiler") === "string") {
|
||||
const spoilerContainer = document.createElement('span');
|
||||
|
||||
const reason = node.getAttribute("data-mx-spoiler");
|
||||
const Spoiler = sdk.getComponent('elements.Spoiler');
|
||||
node.removeAttribute("data-mx-spoiler"); // we don't want to recurse
|
||||
const spoiler = <Spoiler
|
||||
reason={reason}
|
||||
contentHtml={node.outerHTML}
|
||||
/>;
|
||||
|
||||
ReactDOM.render(spoiler, spoilerContainer);
|
||||
node.parentNode.replaceChild(spoilerContainer, node);
|
||||
|
||||
node = spoilerContainer;
|
||||
}
|
||||
|
||||
if (node.childNodes && node.childNodes.length) {
|
||||
this.activateSpoilers(node.childNodes);
|
||||
}
|
||||
|
||||
node = node.nextSibling;
|
||||
}
|
||||
},
|
||||
|
||||
pillifyLinks: function(nodes) {
|
||||
const shouldShowPillAvatar = SettingsStore.getValue("Pill.shouldShowPillAvatar");
|
||||
let node = nodes[0];
|
||||
|
Loading…
Reference in New Issue
Block a user