From 96c867b34bbee417620ffbdb38a14585528198d4 Mon Sep 17 00:00:00 2001 From: David Baker Date: Wed, 26 Apr 2017 19:00:07 +0100 Subject: [PATCH 1/8] Make left panel more friendly to new users https://github.com/vector-im/riot-web/issues/3609 --- src/components/structures/RoomSubList.js | 14 +++++++----- .../views/rooms/_RoomList.scss | 22 +++++++++++++++++++ 2 files changed, 30 insertions(+), 6 deletions(-) diff --git a/src/components/structures/RoomSubList.js b/src/components/structures/RoomSubList.js index 577dac9c..fde35b12 100644 --- a/src/components/structures/RoomSubList.js +++ b/src/components/structures/RoomSubList.js @@ -82,6 +82,7 @@ var RoomSubList = React.createClass({ incomingCall: React.PropTypes.object, onShowMoreRooms: React.PropTypes.func, searchFilter: React.PropTypes.string, + emptyContent: React.PropTypes.node, // content shown if the list is empty }, getInitialState: function() { @@ -468,16 +469,18 @@ var RoomSubList = React.createClass({ render: function() { var connectDropTarget = this.props.connectDropTarget; - var RoomDropTarget = sdk.getComponent('rooms.RoomDropTarget'); var TruncatedList = sdk.getComponent('elements.TruncatedList'); var label = this.props.collapsed ? null : this.props.label; //console.log("render: " + JSON.stringify(this.state.sortedList)); - var target; - if (this.state.sortedList.length == 0 && this.props.editable) { - target = ; + let content; + if (this.state.sortedList.length == 0) { + //content = ; + content = this.props.emptyContent; + } else { + content = this.makeRoomTiles(); } var roomCount = this.props.list.length > 0 ? this.props.list.length : ''; @@ -497,8 +500,7 @@ var RoomSubList = React.createClass({ if (!this.state.hidden) { subList = - { target } - { this.makeRoomTiles() } + { content } ; } else { diff --git a/src/skins/vector/css/matrix-react-sdk/views/rooms/_RoomList.scss b/src/skins/vector/css/matrix-react-sdk/views/rooms/_RoomList.scss index 110dcd5b..bc699ae7 100644 --- a/src/skins/vector/css/matrix-react-sdk/views/rooms/_RoomList.scss +++ b/src/skins/vector/css/matrix-react-sdk/views/rooms/_RoomList.scss @@ -1,5 +1,6 @@ /* Copyright 2015, 2016 OpenMarket Ltd +Copyright 2107 Vector Creations Ltd Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. @@ -37,3 +38,24 @@ limitations under the License. .mx_RoomList_scrollbar .gm-scrollbar.-vertical { z-index: 6; } + +.mx_RoomList_greyedSubListLabel { + color: #a2a2a2; +} + +.mx_RoomList_emptySubListTip { + font-size: 13px; + margin-left: 18px; + margin-right: 18px; + margin-top: 8px; + margin-bottom: 7px; + padding: 5px; + border: 1px solid $accent-color; + color: $primary-fg-color; + background-color: $droptarget-bg-color; + border-radius: 4px; +} + +.mx_RoomList_butonPreview { + float: right; +} From 095da68aace2e59355346fc2f8e620e04e181e53 Mon Sep 17 00:00:00 2001 From: David Baker Date: Thu, 4 May 2017 13:58:17 +0100 Subject: [PATCH 2/8] Add buttons to room sub list headers --- src/components/structures/RoomSubList.js | 4 ++ .../structures/RoomSubListHeader.js | 42 +++++++++---------- src/skins/vector/css/_components.scss | 1 + .../views/elements/_RoleButton.scss | 26 ++++++++++++ .../views/rooms/_RoomList.scss | 11 ++--- 5 files changed, 54 insertions(+), 30 deletions(-) create mode 100644 src/skins/vector/css/matrix-react-sdk/views/elements/_RoleButton.scss diff --git a/src/components/structures/RoomSubList.js b/src/components/structures/RoomSubList.js index fde35b12..4d2a3927 100644 --- a/src/components/structures/RoomSubList.js +++ b/src/components/structures/RoomSubList.js @@ -1,4 +1,5 @@ /* +Copyright 2017 Vector Creations Ltd Copyright 2015, 2016 OpenMarket Ltd Licensed under the Apache License, Version 2.0 (the "License"); @@ -83,6 +84,7 @@ var RoomSubList = React.createClass({ onShowMoreRooms: React.PropTypes.func, searchFilter: React.PropTypes.string, emptyContent: React.PropTypes.node, // content shown if the list is empty + headerItems: React.PropTypes.node, // content shown in the sublist header }, getInitialState: function() { @@ -522,6 +524,7 @@ var RoomSubList = React.createClass({ roomNotificationCount={ this.roomNotificationCount() } onClick={ this.onClick } onHeaderClick={ this.props.onHeaderClick } + headerItems={this.props.headerItems} /> { subList } @@ -543,6 +546,7 @@ var RoomSubList = React.createClass({ roomNotificationCount={ this.roomNotificationCount() } onClick={ this.onClick } onHeaderClick={ this.props.onHeaderClick } + headerItems={this.props.headerItems} /> : undefined } { (this.props.showSpinner && !this.state.hidden) ? : undefined } diff --git a/src/components/structures/RoomSubListHeader.js b/src/components/structures/RoomSubListHeader.js index ad9aff5f..3ad7547c 100644 --- a/src/components/structures/RoomSubListHeader.js +++ b/src/components/structures/RoomSubListHeader.js @@ -14,16 +14,11 @@ See the License for the specific language governing permissions and limitations under the License. */ -'use strict'; - -var React = require('react'); -var ReactDOM = require('react-dom'); -var classNames = require('classnames'); -var sdk = require('matrix-react-sdk') -var FormattingUtils = require('matrix-react-sdk/lib/utils/FormattingUtils'); -var RoomNotifs = require('matrix-react-sdk/lib/RoomNotifs'); -var AccessibleButton = require('matrix-react-sdk/lib/components/views/elements/AccessibleButton'); -var ConstantTimeDispatcher = require('matrix-react-sdk/lib/ConstantTimeDispatcher'); +import React from 'react'; +import classNames from 'classnames'; +import sdk from 'matrix-react-sdk'; +import FormattingUtils from 'matrix-react-sdk/lib/utils/FormattingUtils'; +import AccessibleButton from 'matrix-react-sdk/lib/components/views/elements/AccessibleButton'; module.exports = React.createClass({ displayName: 'RoomSubListHeader', @@ -42,6 +37,7 @@ module.exports = React.createClass({ hidden: React.PropTypes.bool, onClick: React.PropTypes.func, onHeaderClick: React.PropTypes.func, + headerItems: React.PropTypes.node, // content shown in the sublist header }, getDefaultProps: function() { @@ -63,35 +59,34 @@ module.exports = React.createClass({ // }, render: function() { - var TintableSvg = sdk.getComponent("elements.TintableSvg"); + const TintableSvg = sdk.getComponent("elements.TintableSvg"); - var subListNotifications = this.props.roomNotificationCount; - var subListNotifCount = subListNotifications[0]; - var subListNotifHighlight = subListNotifications[1]; + const subListNotifications = this.props.roomNotificationCount; + const subListNotifCount = subListNotifications[0]; + const subListNotifHighlight = subListNotifications[1]; - var chevronClasses = classNames({ + const chevronClasses = classNames({ 'mx_RoomSubList_chevron': true, 'mx_RoomSubList_chevronRight': this.props.hidden, 'mx_RoomSubList_chevronDown': !this.props.hidden, }); - var badgeClasses = classNames({ + const badgeClasses = classNames({ 'mx_RoomSubList_badge': true, 'mx_RoomSubList_badgeHighlight': subListNotifHighlight, }); - var badge; + let badge; if (subListNotifCount > 0) { badge =
{ FormattingUtils.formatCount(subListNotifCount) }
; - } - else if (subListNotifHighlight) { + } else if (subListNotifHighlight) { badge =
!
; } // When collapsed, allow a long hover on the header to show user // the full tag name and room count - var title; - var roomCount = this.props.roomCount; + let title; + const roomCount = this.props.roomCount; if (this.props.collapsed) { title = this.props.label; if (roomCount !== '') { @@ -99,9 +94,9 @@ module.exports = React.createClass({ } } - var incomingCall; + let incomingCall; if (this.props.isIncomingCallRoom) { - var IncomingCallBox = sdk.getComponent("voip.IncomingCallBox"); + const IncomingCallBox = sdk.getComponent("voip.IncomingCallBox"); incomingCall = ; } @@ -109,6 +104,7 @@ module.exports = React.createClass({
{ this.props.collapsed ? '' : this.props.label } + {this.props.headerItems}
{ roomCount }
{ badge } diff --git a/src/skins/vector/css/_components.scss b/src/skins/vector/css/_components.scss index df3c4600..5b23bb82 100644 --- a/src/skins/vector/css/_components.scss +++ b/src/skins/vector/css/_components.scss @@ -27,6 +27,7 @@ @import "./matrix-react-sdk/views/elements/_MemberEventListSummary.scss"; @import "./matrix-react-sdk/views/elements/_ProgressBar.scss"; @import "./matrix-react-sdk/views/elements/_RichText.scss"; +@import "./matrix-react-sdk/views/elements/_RoleButton.scss"; @import "./matrix-react-sdk/views/login/_InteractiveAuthEntryComponents.scss"; @import "./matrix-react-sdk/views/login/_ServerConfig.scss"; @import "./matrix-react-sdk/views/messages/_MEmoteBody.scss"; diff --git a/src/skins/vector/css/matrix-react-sdk/views/elements/_RoleButton.scss b/src/skins/vector/css/matrix-react-sdk/views/elements/_RoleButton.scss new file mode 100644 index 00000000..04503346 --- /dev/null +++ b/src/skins/vector/css/matrix-react-sdk/views/elements/_RoleButton.scss @@ -0,0 +1,26 @@ +/* +Copyright 2107 Vector Creations Ltd + +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_RoleButton { + margin-left: 4px; + margin-right: 4px; + cursor: pointer; + display: inline-block; +} + +.mx_RoleButton object { + pointer-events: none; +} diff --git a/src/skins/vector/css/matrix-react-sdk/views/rooms/_RoomList.scss b/src/skins/vector/css/matrix-react-sdk/views/rooms/_RoomList.scss index bc699ae7..77df1f8f 100644 --- a/src/skins/vector/css/matrix-react-sdk/views/rooms/_RoomList.scss +++ b/src/skins/vector/css/matrix-react-sdk/views/rooms/_RoomList.scss @@ -39,10 +39,6 @@ limitations under the License. z-index: 6; } -.mx_RoomList_greyedSubListLabel { - color: #a2a2a2; -} - .mx_RoomList_emptySubListTip { font-size: 13px; margin-left: 18px; @@ -50,12 +46,13 @@ limitations under the License. margin-top: 8px; margin-bottom: 7px; padding: 5px; - border: 1px solid $accent-color; + border: 1px dashed $accent-color; color: $primary-fg-color; background-color: $droptarget-bg-color; border-radius: 4px; } -.mx_RoomList_butonPreview { - float: right; +.mx_RoomList_headerButtons { + position: absolute; + right: 60px; } From ff709ed8b126c3f9c96ebebb815730b12a62e31d Mon Sep 17 00:00:00 2001 From: David Baker Date: Thu, 4 May 2017 14:53:13 +0100 Subject: [PATCH 3/8] Fix import --- src/components/structures/RoomSubListHeader.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/components/structures/RoomSubListHeader.js b/src/components/structures/RoomSubListHeader.js index 3ad7547c..74094ae0 100644 --- a/src/components/structures/RoomSubListHeader.js +++ b/src/components/structures/RoomSubListHeader.js @@ -17,7 +17,7 @@ limitations under the License. import React from 'react'; import classNames from 'classnames'; import sdk from 'matrix-react-sdk'; -import FormattingUtils from 'matrix-react-sdk/lib/utils/FormattingUtils'; +import { formatCount } from 'matrix-react-sdk/lib/utils/FormattingUtils'; import AccessibleButton from 'matrix-react-sdk/lib/components/views/elements/AccessibleButton'; module.exports = React.createClass({ @@ -78,7 +78,7 @@ module.exports = React.createClass({ let badge; if (subListNotifCount > 0) { - badge =
{ FormattingUtils.formatCount(subListNotifCount) }
; + badge =
{ formatCount(subListNotifCount) }
; } else if (subListNotifHighlight) { badge =
!
; } From 2bf007495331542c49ff6a9fc98002cee947dac6 Mon Sep 17 00:00:00 2001 From: David Baker Date: Thu, 4 May 2017 15:38:53 +0100 Subject: [PATCH 4/8] Make bottom left menu buttons use RoleButton too --- src/components/structures/BottomLeftMenu.js | 122 ++---------------- .../views/elements/_RoleButton.scss | 7 + .../css/vector-web/structures/_LeftPanel.scss | 34 ++--- 3 files changed, 25 insertions(+), 138 deletions(-) diff --git a/src/components/structures/BottomLeftMenu.js b/src/components/structures/BottomLeftMenu.js index f378cac6..1195a6f3 100644 --- a/src/components/structures/BottomLeftMenu.js +++ b/src/components/structures/BottomLeftMenu.js @@ -14,13 +14,8 @@ See the License for the specific language governing permissions and limitations under the License. */ -'use strict'; - -var React = require('react'); -var ReactDOM = require('react-dom'); -var sdk = require('matrix-react-sdk') -var dis = require('matrix-react-sdk/lib/dispatcher'); -var AccessibleButton = require('matrix-react-sdk/lib/components/views/elements/AccessibleButton'); +import React from 'react'; +import sdk from 'matrix-react-sdk'; module.exports = React.createClass({ displayName: 'BottomLeftMenu', @@ -30,121 +25,24 @@ module.exports = React.createClass({ teamToken: React.PropTypes.string, }, - getInitialState: function() { - return({ - directoryHover : false, - roomsHover : false, - homeHover: false, - peopleHover : false, - settingsHover : false, - }); - }, - - // Room events - onDirectoryClick: function() { - dis.dispatch({ action: 'view_room_directory' }); - }, - - onDirectoryMouseEnter: function() { - this.setState({ directoryHover: true }); - }, - - onDirectoryMouseLeave: function() { - this.setState({ directoryHover: false }); - }, - - onRoomsClick: function() { - dis.dispatch({ action: 'view_create_room' }); - }, - - onRoomsMouseEnter: function() { - this.setState({ roomsHover: true }); - }, - - onRoomsMouseLeave: function() { - this.setState({ roomsHover: false }); - }, - - // Home button events - onHomeClick: function() { - dis.dispatch({ action: 'view_home_page' }); - }, - - onHomeMouseEnter: function() { - this.setState({ homeHover: true }); - }, - - onHomeMouseLeave: function() { - this.setState({ homeHover: false }); - }, - - // People events - onPeopleClick: function() { - dis.dispatch({ action: 'view_create_chat' }); - }, - - onPeopleMouseEnter: function() { - this.setState({ peopleHover: true }); - }, - - onPeopleMouseLeave: function() { - this.setState({ peopleHover: false }); - }, - - // Settings events - onSettingsClick: function() { - dis.dispatch({ action: 'view_user_settings' }); - }, - - onSettingsMouseEnter: function() { - this.setState({ settingsHover: true }); - }, - - onSettingsMouseLeave: function() { - this.setState({ settingsHover: false }); - }, - - // Get the label/tooltip to show - getLabel: function(label, show) { - if (show) { - var RoomTooltip = sdk.getComponent("rooms.RoomTooltip"); - return ; - } - }, - render: function() { - var TintableSvg = sdk.getComponent('elements.TintableSvg'); + const RoleButton = sdk.getComponent('elements.RoleButton'); var homeButton; if (this.props.teamToken) { - homeButton = ( - - - { this.getLabel("Welcome page", this.state.homeHover) } - - ); + homeButton = ; } return (
{ homeButton } - - - { this.getLabel("Start chat", this.state.peopleHover) } - - - - { this.getLabel("Room directory", this.state.directoryHover) } - - - - { this.getLabel("Create new room", this.state.roomsHover) } - - - - { this.getLabel("Settings", this.state.settingsHover) } - + + + + + +
); diff --git a/src/skins/vector/css/matrix-react-sdk/views/elements/_RoleButton.scss b/src/skins/vector/css/matrix-react-sdk/views/elements/_RoleButton.scss index 04503346..094e0b9b 100644 --- a/src/skins/vector/css/matrix-react-sdk/views/elements/_RoleButton.scss +++ b/src/skins/vector/css/matrix-react-sdk/views/elements/_RoleButton.scss @@ -24,3 +24,10 @@ limitations under the License. .mx_RoleButton object { pointer-events: none; } + +.mx_RoleButton_tooltip { + display: inline-block; + position: relative; + top: -25px; + left: 6px; +} diff --git a/src/skins/vector/css/vector-web/structures/_LeftPanel.scss b/src/skins/vector/css/vector-web/structures/_LeftPanel.scss index d3bbce1b..f171591c 100644 --- a/src/skins/vector/css/vector-web/structures/_LeftPanel.scss +++ b/src/skins/vector/css/vector-web/structures/_LeftPanel.scss @@ -64,43 +64,25 @@ limitations under the License. pointer-events: none; } -.mx_LeftPanel .mx_BottomLeftMenu_homePage, -.mx_LeftPanel .mx_BottomLeftMenu_directory, -.mx_LeftPanel .mx_BottomLeftMenu_createRoom, -.mx_LeftPanel .mx_BottomLeftMenu_people, -.mx_LeftPanel .mx_BottomLeftMenu_settings { - display: inline-block; - cursor: pointer; -} - -.collapsed .mx_BottomLeftMenu_homePage, -.collapsed .mx_BottomLeftMenu_directory, -.collapsed .mx_BottomLeftMenu_createRoom, -.collapsed .mx_BottomLeftMenu_people, -.collapsed .mx_BottomLeftMenu_settings { +.collapsed .mx_RoleButton { margin-right: 0px ! important; padding-top: 3px ! important; padding-bottom: 3px ! important; } -.mx_LeftPanel .mx_BottomLeftMenu_homePage, -.mx_LeftPanel .mx_BottomLeftMenu_directory, -.mx_LeftPanel .mx_BottomLeftMenu_createRoom, -.mx_LeftPanel .mx_BottomLeftMenu_people { +.mx_BottomLeftMenu_options .mx_RoleButton { + margin-left: 0px; margin-right: 10px; } -.mx_LeftPanel .mx_BottomLeftMenu_settings { +.mx_BottomLeftMenu_options .mx_BottomLeftMenu_settings { float: right; } +.mx_BottomLeftMenu_options .mx_BottomLeftMenu_settings .mx_RoleButton { + margin-right: 0px; +} + .mx_LeftPanel.collapsed .mx_BottomLeftMenu_settings { float: none; } - -.mx_LeftPanel .mx_BottomLeftMenu_tooltip { - display: inline-block; - position: relative; - top: -25px; - left: 6px; -} From da960e776dde215aaf20885fbc7faf22ae905f7a Mon Sep 17 00:00:00 2001 From: David Baker Date: Thu, 4 May 2017 17:45:11 +0100 Subject: [PATCH 5/8] Remove commented code --- src/components/structures/RoomSubList.js | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/components/structures/RoomSubList.js b/src/components/structures/RoomSubList.js index 4d2a3927..bac87bc4 100644 --- a/src/components/structures/RoomSubList.js +++ b/src/components/structures/RoomSubList.js @@ -475,8 +475,6 @@ var RoomSubList = React.createClass({ var label = this.props.collapsed ? null : this.props.label; - //console.log("render: " + JSON.stringify(this.state.sortedList)); - let content; if (this.state.sortedList.length == 0) { //content = ; From 23a141c5ad390cb8d6cf4aede5fd32c9f2463949 Mon Sep 17 00:00:00 2001 From: David Baker Date: Thu, 4 May 2017 17:46:44 +0100 Subject: [PATCH 6/8] Remove slightly misleading commented code --- src/components/structures/RoomSubList.js | 1 - 1 file changed, 1 deletion(-) diff --git a/src/components/structures/RoomSubList.js b/src/components/structures/RoomSubList.js index bac87bc4..adeb3651 100644 --- a/src/components/structures/RoomSubList.js +++ b/src/components/structures/RoomSubList.js @@ -477,7 +477,6 @@ var RoomSubList = React.createClass({ let content; if (this.state.sortedList.length == 0) { - //content = ; content = this.props.emptyContent; } else { content = this.makeRoomTiles(); From 1001c98a3c8fca82d264a54d5a433845a2e36fe9 Mon Sep 17 00:00:00 2001 From: David Baker Date: Thu, 4 May 2017 18:23:04 +0100 Subject: [PATCH 7/8] Align buttons better with the text --- .../vector/css/matrix-react-sdk/views/rooms/_RoomList.scss | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/skins/vector/css/matrix-react-sdk/views/rooms/_RoomList.scss b/src/skins/vector/css/matrix-react-sdk/views/rooms/_RoomList.scss index 77df1f8f..35787ca0 100644 --- a/src/skins/vector/css/matrix-react-sdk/views/rooms/_RoomList.scss +++ b/src/skins/vector/css/matrix-react-sdk/views/rooms/_RoomList.scss @@ -52,6 +52,10 @@ limitations under the License. border-radius: 4px; } +.mx_RoomList_emptySubListTip .mx_RoleButton { + vertical-align: -3px; +} + .mx_RoomList_headerButtons { position: absolute; right: 60px; From c27f39714a66bbcb0fb6bee95638f7bb67e20637 Mon Sep 17 00:00:00 2001 From: David Baker Date: Fri, 5 May 2017 14:26:13 +0100 Subject: [PATCH 8/8] Dedicated classes for the buttons --- src/components/structures/BottomLeftMenu.js | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-) diff --git a/src/components/structures/BottomLeftMenu.js b/src/components/structures/BottomLeftMenu.js index 1195a6f3..63dfac60 100644 --- a/src/components/structures/BottomLeftMenu.js +++ b/src/components/structures/BottomLeftMenu.js @@ -1,5 +1,6 @@ /* Copyright 2015, 2016 OpenMarket Ltd +Copyright 2017 Vector Creations Ltd Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. @@ -26,22 +27,26 @@ module.exports = React.createClass({ }, render: function() { - const RoleButton = sdk.getComponent('elements.RoleButton'); + const HomeButton = sdk.getComponent('elements.HomeButton'); + const StartChatButton = sdk.getComponent('elements.StartChatButton'); + const RoomDirectoryButton = sdk.getComponent('elements.RoomDirectoryButton'); + const CreateRoomButton = sdk.getComponent('elements.CreateRoomButton'); + const SettingsButton = sdk.getComponent('elements.SettingsButton'); var homeButton; if (this.props.teamToken) { - homeButton = ; + homeButton = ; } return (
{ homeButton } - - - + + + - +