diff --git a/res/css/_components.scss b/res/css/_components.scss index 4986ca837f..d30684993d 100644 --- a/res/css/_components.scss +++ b/res/css/_components.scss @@ -61,6 +61,7 @@ @import "./views/dialogs/_EncryptedEventDialog.scss"; @import "./views/dialogs/_GroupAddressPicker.scss"; @import "./views/dialogs/_IncomingSasDialog.scss"; +@import "./views/dialogs/_MessageEditHistoryDialog.scss"; @import "./views/dialogs/_RestoreKeyBackupDialog.scss"; @import "./views/dialogs/_RoomSettingsDialog.scss"; @import "./views/dialogs/_RoomUpgradeDialog.scss"; diff --git a/res/css/views/dialogs/_MessageEditHistoryDialog.scss b/res/css/views/dialogs/_MessageEditHistoryDialog.scss new file mode 100644 index 0000000000..ad51f4237f --- /dev/null +++ b/res/css/views/dialogs/_MessageEditHistoryDialog.scss @@ -0,0 +1,38 @@ +/* +Copyright 2019 The Matrix.org Foundation C.I.C. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +.mx_MessageEditHistoryDialog ul { + list-style-type: none; + + &>li.edit { + display: flex; + + &>strong { + flex: 0 0 100px; + font-weight: bold; + } + + &>p { + + } + + } + + ul, ol { + list-style-type: circle; + } +} + diff --git a/src/components/views/dialogs/MessageEditHistoryDialog.js b/src/components/views/dialogs/MessageEditHistoryDialog.js new file mode 100644 index 0000000000..958c7457e0 --- /dev/null +++ b/src/components/views/dialogs/MessageEditHistoryDialog.js @@ -0,0 +1,80 @@ +/* +Copyright 2019 The Matrix.org Foundation C.I.C. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +import React from 'react'; +import PropTypes from 'prop-types'; +import MatrixClientPeg from "../../../MatrixClientPeg"; +import { _t } from '../../../languageHandler'; +import sdk from "../../../index"; +import * as HtmlUtils from '../../../HtmlUtils'; +import {wantsDateSeparator, formatTime} from '../../../DateUtils'; + +export default class MessageEditHistoryDialog extends React.Component { + static propTypes = { + mxEvent: PropTypes.object.isRequired, + }; + + componentWillMount() { + this.setState({edits: [this.props.mxEvent], isLoading: true}); + } + + async componentDidMount() { + const roomId = this.props.mxEvent.getRoomId(); + const eventId = this.props.mxEvent.getId(); + let edits = await MatrixClientPeg.get(). + relations(roomId, eventId, "m.replace", "m.room.message"); + edits = edits.slice().reverse(); + edits.unshift(this.props.mxEvent); + this.setState({edits, isLoading: false}); + } + + _renderEdit(event) { + const timestamp = formatTime(new Date(event.getTs()), true); + const content = event.event.content["m.new_content"] || event.event.content; + return
  • {timestamp}

    {HtmlUtils.bodyToHtml(content)}

  • ; + } + + _renderEdits() { + const DateSeparator = sdk.getComponent('messages.DateSeparator'); + const nodes = []; + let lastEvent; + this.state.edits.forEach(e => { + if (!lastEvent || wantsDateSeparator(lastEvent.getDate(), e.getDate())) { + nodes.push(
  • ); + } + nodes.push(this._renderEdit(e)); + lastEvent = e; + }); + return nodes; + } + + render() { + const BaseDialog = sdk.getComponent('views.dialogs.BaseDialog'); + let spinner; + const edits = this._renderEdits(); + if (this.state.isLoading) { + const Spinner = sdk.getComponent("elements.Spinner"); + spinner = ; + } + return ( + + + {spinner} + + ); + } +} diff --git a/src/i18n/strings/en_EN.json b/src/i18n/strings/en_EN.json index 010ad29da0..01d84324ce 100644 --- a/src/i18n/strings/en_EN.json +++ b/src/i18n/strings/en_EN.json @@ -1199,6 +1199,7 @@ "Manually export keys": "Manually export keys", "You'll lose access to your encrypted messages": "You'll lose access to your encrypted messages", "Are you sure you want to sign out?": "Are you sure you want to sign out?", + "Message edits": "Message edits", "If you run into any bugs or have feedback you'd like to share, please let us know on GitHub.": "If you run into any bugs or have feedback you'd like to share, please let us know on GitHub.", "To help avoid duplicate issues, please view existing issues first (and add a +1) or create a new issue if you can't find it.": "To help avoid duplicate issues, please view existing issues first (and add a +1) or create a new issue if you can't find it.", "Report bugs & give feedback": "Report bugs & give feedback",