"use strict"; const Promise = require("bluebird"); const React = require("react"); const create = require("create-react-class"); const sanitize = require("sanitize-html"); const Event = require("./events/Event.js"); const Info = require("./info.js"); const Input = require("./input.js"); const User = require("./events/user.js"); const Loading = require("./loading.js"); const generateJdenticon = require("../lib/generate-jdenticon"); const groupEvents = require("../lib/group-events"); let eventFunctions = { plaintext: function() { if (this.type == "m.room.message") { if (this.content.format == "org.matrix.custom.html") { return sanitize(this.content.formatted_body, {allowedTags: []}); } else { return this.content.body; } } else if (this.type == "m.room.member") { if (this.content.membership == "invite") { return `${this.sender} invited ${this.state_key}`; } else if (this.content.membership == "join") { return `${this.state_key} joined the room`; } else if (this.content.membership == "leave") { return `${this.state_key} left the room`; } else if (this.content.membership == "kick") { return `${this.sender} kicked ${this.state_key}`; } else if (this.content.membership == "ban") { return `${this.sender} banned ${this.state_key}`; } else { return "unknown member event"; } } else if (this.type == "m.room.avatar") { if (this.content.url.length > 0) { return `${this.sender} changed the room avatar`; } } else if (this.type == "m.room.name") { return `${this.sender} changed the room name to ${this.content.name}`; } else { return "unknown event"; } } }; let chat = create({ displayName: "Chat", getInitialState: function() { return { ref: null, loading: false }; }, getSnapshotBeforeUpdate: function(_oldProps, _oldState) { let ref = this.state.ref; if (ref != null && (ref.scrollHeight - ref.offsetHeight) - ref.scrollTop < 100) { // Less than 100px from bottom return true; } else { return null; } }, componentDidUpdate(prevProps, prevState, snapshot) { let ref = this.state.ref; if (ref != null && snapshot) { // scroll to bottom ref.scrollTop = (ref.scrollHeight - ref.offsetHeight); } }, setRef: function(ref) { if (ref != null) { this.setState({ ref: ref }); } }, onReplyClick: function(e) { this.setState({ replyEvent: e }); }, paginateBackwards: function() { if (!this.state.loading) { let client = this.props.client; let timeline = client.getRoom(this.props.roomId).getLiveTimeline(); this.setState({loading: true}); return Promise.try(() => { return client.paginateEventTimeline(timeline, {backwards: true}); }).then(() => { this.setState({loading: false}); }); } }, render: function() { let client = this.props.client; let empty =
; if (this.props.roomId == null) { //empty screen return empty; } else { let room = client.getRoom(this.props.roomId); if (room == null) { return empty; } else { let liveTimeline = room.getLiveTimeline(); let liveTimelineEvents = liveTimeline.getEvents(); let events = liveTimelineEvents.map((item) => { let event = item.event; return Object.assign( event, eventFunctions, (event.sender == null) /* Whether this event is a local echo */ ? { local: true, sender: event.user_id } : null ); }); let eventGroups = groupEvents(events); //TODO: replace with something that only renders events in view return (
{this.state.loading ? : load older messages }
{(eventGroups.map((group) => { return ; }))}
); } } } }); let EventGroup = create({ displayName: "EventGroup", getInitialState: function() { let user = this.props.client.getUser(this.props.events[0].sender); let avatar = ; if (user.avatarUrl != null) { let hs = this.props.client.baseUrl; let media_mxc = user.avatarUrl.slice(6); let url = `${hs}/_matrix/media/v1/thumbnail/${media_mxc}?width=128&height=128&method=scale`; avatar = ; } return { user: user, avatar: avatar }; }, avatarRef: function(ref) { generateJdenticon(this.state.user.userId).update(ref); }, render: function() { let events = this.props.events.map((event, key) => { return ; }); return
{this.state.avatar}
{events}
; } }); module.exports = chat;