From be02ac3bc6b3340a8060e7c314c0baf77bdbce26 Mon Sep 17 00:00:00 2001 From: Luke Barnard Date: Fri, 17 Mar 2017 12:06:48 +0000 Subject: [PATCH 1/2] Fix people section again - Alter CSS due to removed mx_RoomDropTarget_avatar. The avatar was removed because it didn't particularly add anything and we needed space for "Drop here to tag as direct chat", which is quite long. - Use guessAndSetDMRoom as a convenience method for guessing the DM member and setting the state. - Do evil hacks to make DNDRoomTile do dragging of RoomTiles to and from the People section. Dragging a DM to and from Rooms/Favourites/Low Priority now works as one would expect. This is still not ideal however because edge cases exist where you have more than one tag set and then you drag a DM from "Favourites" to "Rooms" and the tile ends up in "People". This would require setting multiple tags, and breaks the 1-1 mapping between tags and sections even further. Ultimately the UI needs a rework. --- .../context_menus/RoomTileContextMenu.js | 35 +++-------- src/components/views/rooms/DNDRoomTile.js | 61 ++++++++++++++----- src/components/views/rooms/RoomDropTarget.js | 1 - .../views/rooms/_RoomDropTarget.scss | 11 +--- 4 files changed, 57 insertions(+), 51 deletions(-) diff --git a/src/components/views/context_menus/RoomTileContextMenu.js b/src/components/views/context_menus/RoomTileContextMenu.js index 289121f1d3..5b6cec884d 100644 --- a/src/components/views/context_menus/RoomTileContextMenu.js +++ b/src/components/views/context_menus/RoomTileContextMenu.js @@ -138,31 +138,16 @@ module.exports = React.createClass({ if (MatrixClientPeg.get().isGuest()) return; - let newTarget; - if (newIsDirectMessage) { - const guessedTarget = Rooms.guessDMRoomTarget( - this.props.room, - this.props.room.getMember(MatrixClientPeg.get().credentials.userId), - ); - newTarget = guessedTarget.userId; - } else { - newTarget = null; - } - - // give some time for the user to see the icon change first, since - // this will hide the context menu once it completes - q.delay(500).done(() => { - return Rooms.setDMRoom(this.props.room.roomId, newTarget).finally(() => { - // Close the context menu - if (this.props.onFinished) { - this.props.onFinished(); - }; - }, (err) => { - var ErrorDialog = sdk.getComponent("dialogs.ErrorDialog"); - Modal.createDialog(ErrorDialog, { - title: "Failed to set Direct Message status of room", - description: err.toString() - }); + Rooms.guessAndSetDMRoom(this.props.room, newIsDirectMessage).finally(() => { + // Close the context menu + if (this.props.onFinished) { + this.props.onFinished(); + }; + }, (err) => { + var ErrorDialog = sdk.getComponent("dialogs.ErrorDialog"); + Modal.createDialog(ErrorDialog, { + title: "Failed to set Direct Message status of room", + description: err.toString() }); }); }, diff --git a/src/components/views/rooms/DNDRoomTile.js b/src/components/views/rooms/DNDRoomTile.js index 6296552df1..2fcdb47da3 100644 --- a/src/components/views/rooms/DNDRoomTile.js +++ b/src/components/views/rooms/DNDRoomTile.js @@ -16,14 +16,16 @@ limitations under the License. 'use strict'; -var React = require('react'); -var DragSource = require('react-dnd').DragSource; -var DropTarget = require('react-dnd').DropTarget; +import React from 'react'; +import {DragSource} from 'react-dnd'; +import {DropTarget} from 'react-dnd'; -var dis = require("matrix-react-sdk/lib/dispatcher"); -var MatrixClientPeg = require('matrix-react-sdk/lib/MatrixClientPeg'); -var sdk = require('matrix-react-sdk'); -var RoomTile = require('matrix-react-sdk/lib/components/views/rooms/RoomTile'); +import dis from 'matrix-react-sdk/lib/dispatcher'; +import MatrixClientPeg from 'matrix-react-sdk/lib/MatrixClientPeg'; +import sdk from 'matrix-react-sdk'; +import RoomTile from 'matrix-react-sdk/lib/components/views/rooms/RoomTile'; +import * as Rooms from 'matrix-react-sdk/lib/Rooms'; +import Modal from 'matrix-react-sdk/lib/Modal'; /** * Defines a new Component, DNDRoomTile that wraps RoomTile, making it draggable. @@ -72,22 +74,49 @@ var roomTileSource = { item.targetList.forceUpdate(); // as we're not using state } + const prevTag = item.originalList.props.tagName; + const newTag = item.targetList.props.tagName; + if (monitor.didDrop() && item.targetList.props.editable) { + // Evil hack to get DMs behaving + if ((prevTag === undefined && newTag === 'im.vector.fake.direct') || + (prevTag === 'im.vector.fake.direct' && newTag === undefined) + ) { + Rooms.guessAndSetDMRoom( + item.room, newTag === 'im.vector.fake.direct', + ).done(() => { + item.originalList.removeRoomTile(item.room); + }, (err) => { + const ErrorDialog = sdk.getComponent("dialogs.ErrorDialog"); + console.error("Failed to set direct chat tag " + err); + Modal.createDialog(ErrorDialog, { + title: "Error", + description: "Failed to set direct chat tag", + }); + }); + return; + } + + // More evilness: We will still be dealing with moving to favourites/low prio, + // but we avoid ever doing a request with 'im.vector.fake.direct`. + // if we moved lists, remove the old tag - if (item.targetList !== item.originalList && item.originalList.props.tagName) { + if (prevTag && prevTag !== 'im.vector.fake.direct' && + item.targetList !== item.originalList + ) { // commented out attempts to set a spinner on our target component as component is actually // the original source component being dragged, not our target. To fix we just need to // move all of this to endDrop in the target instead. FIXME later. //component.state.set({ spinner: component.state.spinner ? component.state.spinner++ : 1 }); - MatrixClientPeg.get().deleteRoomTag(item.room.roomId, item.originalList.props.tagName).finally(function() { + MatrixClientPeg.get().deleteRoomTag(item.room.roomId, prevTag).finally(function() { //component.state.set({ spinner: component.state.spinner-- }); }).fail(function(err) { var ErrorDialog = sdk.getComponent("dialogs.ErrorDialog"); - console.error("Failed to remove tag " + item.originalList.props.tagName + " from room: " + err); + console.error("Failed to remove tag " + prevTag + " from room: " + err); Modal.createDialog(ErrorDialog, { title: "Error", - description: "Failed to remove tag " + item.originalList.props.tagName + " from room", + description: "Failed to remove tag " + prevTag + " from room", }); }); } @@ -98,16 +127,18 @@ var roomTileSource = { } // if we moved lists or the ordering changed, add the new tag - if (item.targetList.props.tagName && (item.targetList !== item.originalList || newOrder)) { + if (newTag && newTag !== 'im.vector.fake.direct' && + (item.targetList !== item.originalList || newOrder) + ) { //component.state.set({ spinner: component.state.spinner ? component.state.spinner++ : 1 }); - MatrixClientPeg.get().setRoomTag(item.room.roomId, item.targetList.props.tagName, newOrder).finally(function() { + MatrixClientPeg.get().setRoomTag(item.room.roomId, newTag, newOrder).finally(function() { //component.state.set({ spinner: component.state.spinner-- }); }).fail(function(err) { var ErrorDialog = sdk.getComponent("dialogs.ErrorDialog"); - console.error("Failed to add tag " + item.targetList.props.tagName + " to room: " + err); + console.error("Failed to add tag " + newTag + " to room: " + err); Modal.createDialog(ErrorDialog, { title: "Error", - description: "Failed to add tag " + item.targetList.props.tagName + " to room", + description: "Failed to add tag " + newTag + " to room", }); }); } diff --git a/src/components/views/rooms/RoomDropTarget.js b/src/components/views/rooms/RoomDropTarget.js index 789ba8fa85..1c5eb3c115 100644 --- a/src/components/views/rooms/RoomDropTarget.js +++ b/src/components/views/rooms/RoomDropTarget.js @@ -31,7 +31,6 @@ module.exports = React.createClass({ else { return (
-
{ this.props.label }
diff --git a/src/skins/vector/css/vector-web/views/rooms/_RoomDropTarget.scss b/src/skins/vector/css/vector-web/views/rooms/_RoomDropTarget.scss index e91658e8a8..e0a50a95c7 100644 --- a/src/skins/vector/css/vector-web/views/rooms/_RoomDropTarget.scss +++ b/src/skins/vector/css/vector-web/views/rooms/_RoomDropTarget.scss @@ -38,21 +38,12 @@ limitations under the License. padding-bottom: 1px; } -.mx_RoomDropTarget_avatar { - background-color: $primary-bg-color; - border-radius: 24px; - width: 24px; - height: 24px; - float: left; - margin-left: 7px; - margin-right: 7px; -} - .mx_RoomDropTarget_label { position: relative; margin-top: 3px; line-height: 21px; z-index: 1; + text-align: center; } .collapsed .mx_RoomDropTarget_avatar { From abc5b2d5f401344388c6e819447ff4b21aca44fc Mon Sep 17 00:00:00 2001 From: Luke Barnard Date: Mon, 27 Mar 2017 09:44:33 +0100 Subject: [PATCH 2/2] UI delay in UI --- src/components/views/context_menus/RoomTileContextMenu.js | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/components/views/context_menus/RoomTileContextMenu.js b/src/components/views/context_menus/RoomTileContextMenu.js index 5b6cec884d..d981a36751 100644 --- a/src/components/views/context_menus/RoomTileContextMenu.js +++ b/src/components/views/context_menus/RoomTileContextMenu.js @@ -138,7 +138,9 @@ module.exports = React.createClass({ if (MatrixClientPeg.get().isGuest()) return; - Rooms.guessAndSetDMRoom(this.props.room, newIsDirectMessage).finally(() => { + Rooms.guessAndSetDMRoom( + this.props.room, newIsDirectMessage + ).delay(500).finally(() => { // Close the context menu if (this.props.onFinished) { this.props.onFinished();