diff --git a/src/components/structures/TagPanel.js b/src/components/structures/TagPanel.js index 49d22d8e52..aa35101197 100644 --- a/src/components/structures/TagPanel.js +++ b/src/components/structures/TagPanel.js @@ -18,7 +18,6 @@ import React from 'react'; import PropTypes from 'prop-types'; import { MatrixClient } from 'matrix-js-sdk'; import FilterStore from '../../stores/FilterStore'; -import FlairStore from '../../stores/FlairStore'; import TagOrderStore from '../../stores/TagOrderStore'; import GroupActions from '../../actions/GroupActions'; @@ -36,17 +35,7 @@ const TagPanel = React.createClass({ getInitialState() { return { - // A list of group profiles for tags that are group IDs. The intention in future - // is to allow arbitrary tags to be selected in the TagPanel, not just groups. - // For now, it suffices to maintain a list of ordered group profiles. - orderedGroupTagProfiles: [ - // { - // groupId: '+awesome:foo.bar',{ - // name: 'My Awesome Community', - // avatarUrl: 'mxc://...', - // shortDescription: 'Some description...', - // }, - ], + orderedTags: [], selectedTags: [], }; }, @@ -67,15 +56,8 @@ const TagPanel = React.createClass({ if (this.unmounted) { return; } - - const orderedTags = TagOrderStore.getOrderedTags() || []; - const orderedGroupTags = orderedTags.filter((t) => t[0] === '+'); - // XXX: One profile lookup failing will bring the whole lot down - Promise.all(orderedGroupTags.map( - (groupId) => FlairStore.getGroupProfileCached(this.context.matrixClient, groupId), - )).then((orderedGroupTagProfiles) => { - if (this.unmounted) return; - this.setState({orderedGroupTagProfiles}); + this.setState({ + orderedTags: TagOrderStore.getOrderedTags() || [], }); }); // This could be done by anything with a matrix client @@ -113,11 +95,11 @@ const TagPanel = React.createClass({ const TintableSvg = sdk.getComponent('elements.TintableSvg'); const DNDTagTile = sdk.getComponent('elements.DNDTagTile'); - const tags = this.state.orderedGroupTagProfiles.map((groupProfile, index) => { + const tags = this.state.orderedTags.map((tag, index) => { return ; }); diff --git a/src/components/views/elements/DNDTagTile.js b/src/components/views/elements/DNDTagTile.js index 4d03534980..539163d0dc 100644 --- a/src/components/views/elements/DNDTagTile.js +++ b/src/components/views/elements/DNDTagTile.js @@ -29,7 +29,7 @@ const tagTileSource = { beginDrag: function(props) { // Return the data describing the dragged item return { - tag: props.groupProfile.groupId, + tag: props.tag, }; }, @@ -55,7 +55,7 @@ const tagTileTarget = { dis.dispatch({ action: 'order_tag', tag: monitor.getItem().tag, - targetTag: props.groupProfile.groupId, + targetTag: props.tag, // Note: we indicate that the tag should be after the target when // it's being dragged over the top half of the target. after: draggedY < targetY, @@ -65,7 +65,7 @@ const tagTileTarget = { drop(props) { // Return the data to be returned by getDropResult return { - tag: props.groupProfile.groupId, + tag: props.tag, }; }, }; diff --git a/src/components/views/elements/TagTile.js b/src/components/views/elements/TagTile.js index 124559a838..eb9a5cbdd9 100644 --- a/src/components/views/elements/TagTile.js +++ b/src/components/views/elements/TagTile.js @@ -22,11 +22,20 @@ import sdk from '../../../index'; import dis from '../../../dispatcher'; import { isOnlyCtrlOrCmdKeyEvent } from '../../../Keyboard'; +import FlairStore from '../../../stores/FlairStore'; + +// A class for a child of TagPanel (possibly wrapped in a DNDTagTile) that represents +// a thing to click on for the user to filter the visible rooms in the RoomList to: +// - Rooms that are part of the group +// - Direct messages with members of the group +// with the intention that this could be expanded to arbitrary tags in future. export default React.createClass({ displayName: 'TagTile', propTypes: { - groupProfile: PropTypes.object, + // A string tag such as "m.favourite" or a group ID such as "+groupid:domain.bla" + // For now, only group IDs are handled. + tag: PropTypes.string, }, contextTypes: { @@ -35,16 +44,38 @@ export default React.createClass({ getInitialState() { return { + // Whether the mouse is over the tile hover: false, + // The profile data of the group if this.props.tag is a group ID + profile: null, }; }, + componentWillMount() { + this.unmounted = false; + if (this.props.tag[0] === '+') { + FlairStore.getGroupProfileCached( + this.context.matrixClient, + this.props.tag, + ).then((profile) => { + if (this.unmounted) return; + this.setState({profile}); + }).catch((err) => { + console.warn('Could not fetch group profile for ' + this.props.tag, err); + }); + } + }, + + componentWillUnmount() { + this.unmounted = true; + }, + onClick: function(e) { e.preventDefault(); e.stopPropagation(); dis.dispatch({ action: 'select_tag', - tag: this.props.groupProfile.groupId, + tag: this.props.tag, ctrlOrCmdKey: isOnlyCtrlOrCmdKeyEvent(e), shiftKey: e.shiftKey, }); @@ -62,8 +93,8 @@ export default React.createClass({ const BaseAvatar = sdk.getComponent('avatars.BaseAvatar'); const AccessibleButton = sdk.getComponent('elements.AccessibleButton'); const RoomTooltip = sdk.getComponent('rooms.RoomTooltip'); - const profile = this.props.groupProfile || {}; - const name = profile.name || profile.groupId; + const profile = this.state.profile || {}; + const name = profile.name || this.props.tag; const avatarHeight = 35; const httpUrl = profile.avatarUrl ? this.context.matrixClient.mxcUrlToHttp(