Skip to content
This repository was archived by the owner on Sep 11, 2024. It is now read-only.

Commit f427695

Browse files
committed
Merge remote-tracking branch 'origin/develop' into dbkr/remove_crypto_migrated_message
2 parents 00f6dee + b68da57 commit f427695

File tree

26 files changed

+2918
-193
lines changed

26 files changed

+2918
-193
lines changed

src/autocomplete/UserProvider.js

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -72,6 +72,7 @@ export default class UserProvider extends AutocompleteProvider {
7272
// updates from pagination will happen when the paginate completes.
7373
if (toStartOfTimeline || !data || !data.liveEvent) return;
7474

75+
// TODO: lazyload if we have no ev.sender room member?
7576
this.onUserSpoke(ev.sender);
7677
}
7778

@@ -147,6 +148,7 @@ export default class UserProvider extends AutocompleteProvider {
147148

148149
onUserSpoke(user: RoomMember) {
149150
if (this.users === null) return;
151+
if (!user) return;
150152
if (user.userId === MatrixClientPeg.get().credentials.userId) return;
151153

152154
// Move the user that spoke to the front of the array

src/components/structures/TimelinePanel.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -624,6 +624,7 @@ var TimelinePanel = React.createClass({
624624
this.props.timelineSet.room.setUnreadNotificationCount('highlight', 0);
625625
dis.dispatch({
626626
action: 'on_room_read',
627+
roomId: this.props.timelineSet.room.roomId,
627628
});
628629
}
629630
}

src/components/views/avatars/RoomAvatar.js

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,12 +48,33 @@ module.exports = React.createClass({
4848
};
4949
},
5050

51+
componentWillMount: function() {
52+
MatrixClientPeg.get().on("RoomState.events", this.onRoomStateEvents);
53+
},
54+
55+
componentWillUnmount: function() {
56+
const cli = MatrixClientPeg.get();
57+
if (cli) {
58+
cli.removeListener("RoomState.events", this.onRoomStateEvents);
59+
}
60+
},
61+
5162
componentWillReceiveProps: function(newProps) {
5263
this.setState({
5364
urls: this.getImageUrls(newProps),
5465
});
5566
},
5667

68+
onRoomStateEvents: function(ev) {
69+
if (ev.getRoomId() !== this.props.room.roomId ||
70+
ev.getType() !== 'm.room.avatar'
71+
) return;
72+
73+
this.setState({
74+
urls: this.getImageUrls(this.props),
75+
});
76+
},
77+
5778
getImageUrls: function(props) {
5879
return [
5980
ContentRepo.getHttpUriForMxc(

src/components/views/rooms/RoomList.js

Lines changed: 0 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -77,9 +77,7 @@ module.exports = React.createClass({
7777

7878
cli.on("Room", this.onRoom);
7979
cli.on("deleteRoom", this.onDeleteRoom);
80-
cli.on("Room.name", this.onRoomName);
8180
cli.on("Room.receipt", this.onRoomReceipt);
82-
cli.on("RoomState.events", this.onRoomStateEvents);
8381
cli.on("RoomMember.name", this.onRoomMemberName);
8482
cli.on("Event.decrypted", this.onEventDecrypted);
8583
cli.on("accountData", this.onAccountData);
@@ -161,12 +159,6 @@ module.exports = React.createClass({
161159
});
162160
}
163161
break;
164-
case 'on_room_read':
165-
// Force an update because the notif count state is too deep to cause
166-
// an update. This forces the local echo of reading notifs to be
167-
// reflected by the RoomTiles.
168-
this.forceUpdate();
169-
break;
170162
}
171163
},
172164

@@ -177,9 +169,7 @@ module.exports = React.createClass({
177169
if (MatrixClientPeg.get()) {
178170
MatrixClientPeg.get().removeListener("Room", this.onRoom);
179171
MatrixClientPeg.get().removeListener("deleteRoom", this.onDeleteRoom);
180-
MatrixClientPeg.get().removeListener("Room.name", this.onRoomName);
181172
MatrixClientPeg.get().removeListener("Room.receipt", this.onRoomReceipt);
182-
MatrixClientPeg.get().removeListener("RoomState.events", this.onRoomStateEvents);
183173
MatrixClientPeg.get().removeListener("RoomMember.name", this.onRoomMemberName);
184174
MatrixClientPeg.get().removeListener("Event.decrypted", this.onEventDecrypted);
185175
MatrixClientPeg.get().removeListener("accountData", this.onAccountData);
@@ -243,14 +233,6 @@ module.exports = React.createClass({
243233
}
244234
},
245235

246-
onRoomName: function(room) {
247-
this._delayedRefreshRoomList();
248-
},
249-
250-
onRoomStateEvents: function(ev, state) {
251-
this._delayedRefreshRoomList();
252-
},
253-
254236
onRoomMemberName: function(ev, member) {
255237
this._delayedRefreshRoomList();
256238
},

src/components/views/rooms/RoomTile.js

Lines changed: 56 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ const React = require('react');
2121
const ReactDOM = require("react-dom");
2222
import PropTypes from 'prop-types';
2323
const classNames = require('classnames');
24+
import dis from '../../../dispatcher';
2425
const MatrixClientPeg = require('../../../MatrixClientPeg');
2526
import DMRoomMap from '../../../utils/DMRoomMap';
2627
const sdk = require('../../../index');
@@ -58,7 +59,9 @@ module.exports = React.createClass({
5859
hover: false,
5960
badgeHover: false,
6061
menuDisplayed: false,
62+
roomName: this.props.room.name,
6163
notifState: RoomNotifs.getRoomNotifsState(this.props.room.roomId),
64+
notificationCount: this.props.room.getUnreadNotificationCount(),
6265
selected: this.props.room.roomId === RoomViewStore.getRoomId(),
6366
});
6467
},
@@ -81,6 +84,20 @@ module.exports = React.createClass({
8184
}
8285
},
8386

87+
onRoomTimeline: function(ev, room) {
88+
if (room !== this.props.room) return;
89+
this.setState({
90+
notificationCount: this.props.room.getUnreadNotificationCount(),
91+
});
92+
},
93+
94+
onRoomName: function(room) {
95+
if (room !== this.props.room) return;
96+
this.setState({
97+
roomName: this.props.room.name,
98+
});
99+
},
100+
84101
onAccountData: function(accountDataEvent) {
85102
if (accountDataEvent.getType() == 'm.push_rules') {
86103
this.setState({
@@ -89,6 +106,21 @@ module.exports = React.createClass({
89106
}
90107
},
91108

109+
onAction: function(payload) {
110+
switch (payload.action) {
111+
// XXX: slight hack in order to zero the notification count when a room
112+
// is read. Ideally this state would be given to this via props (as we
113+
// do with `unread`). This is still better than forceUpdating the entire
114+
// RoomList when a room is read.
115+
case 'on_room_read':
116+
if (payload.roomId !== this.props.room.roomId) break;
117+
this.setState({
118+
notificationCount: this.props.room.getUnreadNotificationCount(),
119+
});
120+
break;
121+
}
122+
},
123+
92124
_onActiveRoomChange: function() {
93125
this.setState({
94126
selected: this.props.room.roomId === RoomViewStore.getRoomId(),
@@ -97,15 +129,37 @@ module.exports = React.createClass({
97129

98130
componentWillMount: function() {
99131
MatrixClientPeg.get().on("accountData", this.onAccountData);
132+
MatrixClientPeg.get().on("Room.timeline", this.onRoomTimeline);
133+
MatrixClientPeg.get().on("Room.name", this.onRoomName);
100134
ActiveRoomObserver.addListener(this.props.room.roomId, this._onActiveRoomChange);
135+
this.dispatcherRef = dis.register(this.onAction);
101136
},
102137

103138
componentWillUnmount: function() {
104139
const cli = MatrixClientPeg.get();
105140
if (cli) {
106141
MatrixClientPeg.get().removeListener("accountData", this.onAccountData);
142+
MatrixClientPeg.get().removeListener("Room.timeline", this.onRoomTimeline);
143+
MatrixClientPeg.get().removeListener("Room.name", this.onRoomName);
107144
}
108145
ActiveRoomObserver.removeListener(this.props.room.roomId, this._onActiveRoomChange);
146+
dis.unregister(this.dispatcherRef);
147+
},
148+
149+
// Do a simple shallow comparison of props and state to avoid unnecessary
150+
// renders. The assumption made here is that only state and props are used
151+
// in rendering this component and children.
152+
//
153+
// RoomList is frequently made to forceUpdate, so this decreases number of
154+
// RoomTile renderings.
155+
shouldComponentUpdate: function(newProps, newState) {
156+
if (Object.keys(newProps).some((k) => newProps[k] !== this.props[k])) {
157+
return true;
158+
}
159+
if (Object.keys(newState).some((k) => newState[k] !== this.state[k])) {
160+
return true;
161+
}
162+
return false;
109163
},
110164

111165
onClick: function(ev) {
@@ -174,7 +228,7 @@ module.exports = React.createClass({
174228
const myUserId = MatrixClientPeg.get().credentials.userId;
175229
const me = this.props.room.currentState.members[myUserId];
176230

177-
const notificationCount = this.props.room.getUnreadNotificationCount();
231+
const notificationCount = this.state.notificationCount;
178232
// var highlightCount = this.props.room.getUnreadNotificationCount("highlight");
179233

180234
const notifBadges = notificationCount > 0 && this._shouldShowNotifBadge();
@@ -202,9 +256,7 @@ module.exports = React.createClass({
202256
'mx_RoomTile_badgeButton': this.state.badgeHover || this.state.menuDisplayed,
203257
});
204258

205-
// XXX: We should never display raw room IDs, but sometimes the
206-
// room name js sdk gives is undefined (cannot repro this -- k)
207-
let name = this.props.room.name || this.props.room.roomId;
259+
let name = this.state.roomName;
208260
name = name.replace(":", ":\u200b"); // add a zero-width space to allow linewrapping after the colon
209261

210262
let badge;

0 commit comments

Comments
 (0)