Просмотр исходного кода

fix(context-menus) Fix participant context menus/toolbar overflow menu

- on ipads, long touch open dialog now opens the context menu to the left of the thumbnail as expected
- on ipads, now we close context menus on tap out
- fix case when participant context menu's height > tileview videos' height causing scroll on videos pane
- keep toolbox open while the overflow menu is shown
- keep remote participant video thumbnail in filmstrip visible even if toolbox is hidden, if context menu is opened
- Fix bug where toolbox could be completely disabled
master
Horatiu Muresan 4 лет назад
Родитель
Сommit
b801e0115d
Аккаунт пользователя с таким Email не найден

+ 9
- 0
react/features/base/connection/actionTypes.js Просмотреть файл

@@ -54,4 +54,13 @@ export const CONNECTION_WILL_CONNECT = 'CONNECTION_WILL_CONNECT';
54 54
  */
55 55
 export const SET_LOCATION_URL = 'SET_LOCATION_URL';
56 56
 
57
+/**
58
+ * The type of (redux) action which tells whether connection info should be displayed
59
+ * on context menu.
60
+ *
61
+ * {
62
+ *     type: SHOW_CONNECTION_INFO,
63
+ *     showConnectionInfo: boolean
64
+ * }
65
+ */
57 66
 export const SHOW_CONNECTION_INFO = 'SHOW_CONNECTION_INFO';

+ 51
- 3
react/features/base/popover/components/Popover.web.js Просмотреть файл

@@ -113,6 +113,12 @@ class Popover extends Component<Props, State> {
113 113
         id: ''
114 114
     };
115 115
 
116
+    /**
117
+     * Reference to the dialog container.
118
+     */
119
+    _containerRef: Object;
120
+
121
+
116 122
     /**
117 123
      * Initializes a new {@code Popover} instance.
118 124
      *
@@ -130,8 +136,10 @@ class Popover extends Component<Props, State> {
130 136
         this._onHideDialog = this._onHideDialog.bind(this);
131 137
         this._onShowDialog = this._onShowDialog.bind(this);
132 138
         this._onKeyPress = this._onKeyPress.bind(this);
139
+        this._containerRef = React.createRef();
133 140
         this._onEscKey = this._onEscKey.bind(this);
134 141
         this._onThumbClick = this._onThumbClick.bind(this);
142
+        this._onTouchStart = this._onTouchStart.bind(this);
135 143
     }
136 144
 
137 145
     /**
@@ -141,7 +149,27 @@ class Popover extends Component<Props, State> {
141 149
      * @public
142 150
      */
143 151
     showDialog() {
144
-        this.setState({ showDialog: true });
152
+        this._onShowDialog();
153
+    }
154
+
155
+    /**
156
+     * Sets up a touch event listener to attach.
157
+     *
158
+     * @inheritdoc
159
+     * @returns {void}
160
+     */
161
+    componentDidMount() {
162
+        window.addEventListener('touchstart', this._onTouchStart);
163
+    }
164
+
165
+    /**
166
+     * Removes the listener set up in the {@code componentDidMount} method.
167
+     *
168
+     * @inheritdoc
169
+     * @returns {void}
170
+     */
171
+    componentWillUnmount() {
172
+        window.removeEventListener('touchstart', this._onTouchStart);
145 173
     }
146 174
 
147 175
     /**
@@ -178,7 +206,8 @@ class Popover extends Component<Props, State> {
178 206
                 onClick = { this._onThumbClick }
179 207
                 onKeyPress = { this._onKeyPress }
180 208
                 onMouseEnter = { this._onShowDialog }
181
-                onMouseLeave = { this._onHideDialog }>
209
+                onMouseLeave = { this._onHideDialog }
210
+                ref = { this._containerRef }>
182 211
                 <InlineDialog
183 212
                     content = { this._renderContent() }
184 213
                     isOpen = { this.state.showDialog }
@@ -189,6 +218,25 @@ class Popover extends Component<Props, State> {
189 218
         );
190 219
     }
191 220
 
221
+    _onTouchStart: (event: TouchEvent) => void;
222
+
223
+    /**
224
+     * Hide dialog on touch outside of the context menu.
225
+     *
226
+     * @param {TouchEvent} event - The touch event.
227
+     * @private
228
+     * @returns {void}
229
+     */
230
+    _onTouchStart(event) {
231
+        if (this.state.showDialog
232
+            && !this.props.overflowDrawer
233
+            && this._containerRef
234
+            && this._containerRef.current
235
+            && !this._containerRef.current.contains(event.target)) {
236
+            this._onHideDialog();
237
+        }
238
+    }
239
+
192 240
     _onHideDialog: () => void;
193 241
 
194 242
     /**
@@ -216,7 +264,7 @@ class Popover extends Component<Props, State> {
216 264
      * @returns {void}
217 265
      */
218 266
     _onShowDialog(event) {
219
-        event.stopPropagation();
267
+        event && event.stopPropagation();
220 268
         if (!this.props.disablePopover) {
221 269
             this.setState({ showDialog: true });
222 270
 

+ 12
- 0
react/features/base/responsive-ui/actionTypes.js Просмотреть файл

@@ -30,3 +30,15 @@ export const SET_ASPECT_RATIO = 'SET_ASPECT_RATIO';
30 30
  * @public
31 31
  */
32 32
 export const SET_REDUCED_UI = 'SET_REDUCED_UI';
33
+
34
+/**
35
+ * The type of (redux) action which tells whether a local or remote participant
36
+ * context menu is open.
37
+ *
38
+ * {
39
+ *     type: SET_CONTEXT_MENU_OPEN,
40
+ *     showConnectionInfo: boolean
41
+ * }
42
+ */
43
+export const SET_CONTEXT_MENU_OPEN = 'SET_CONTEXT_MENU_OPEN';
44
+

+ 14
- 1
react/features/base/responsive-ui/actions.js Просмотреть файл

@@ -7,7 +7,7 @@ import { CHAT_SIZE } from '../../chat/constants';
7 7
 import { getParticipantsPaneOpen } from '../../participants-pane/functions';
8 8
 import theme from '../../participants-pane/theme.json';
9 9
 
10
-import { CLIENT_RESIZED, SET_ASPECT_RATIO, SET_REDUCED_UI } from './actionTypes';
10
+import { CLIENT_RESIZED, SET_ASPECT_RATIO, SET_CONTEXT_MENU_OPEN, SET_REDUCED_UI } from './actionTypes';
11 11
 import { ASPECT_RATIO_NARROW, ASPECT_RATIO_WIDE } from './constants';
12 12
 
13 13
 /**
@@ -110,3 +110,16 @@ export function setReducedUI(width: number, height: number): Function {
110 110
         }
111 111
     };
112 112
 }
113
+
114
+/**
115
+ * Sets whether the local or remote participant context menu is open.
116
+ *
117
+ * @param {boolean} isOpen - Whether local or remote context menu is open.
118
+ * @returns {Object}
119
+ */
120
+export function setParticipantContextMenuOpen(isOpen: boolean) {
121
+    return {
122
+        type: SET_CONTEXT_MENU_OPEN,
123
+        isOpen
124
+    };
125
+}

+ 6
- 2
react/features/base/responsive-ui/reducer.js Просмотреть файл

@@ -2,7 +2,7 @@
2 2
 
3 3
 import { ReducerRegistry, set } from '../redux';
4 4
 
5
-import { CLIENT_RESIZED, SET_ASPECT_RATIO, SET_REDUCED_UI } from './actionTypes';
5
+import { CLIENT_RESIZED, SET_ASPECT_RATIO, SET_CONTEXT_MENU_OPEN, SET_REDUCED_UI } from './actionTypes';
6 6
 import { ASPECT_RATIO_NARROW } from './constants';
7 7
 
8 8
 const {
@@ -17,7 +17,8 @@ const DEFAULT_STATE = {
17 17
     aspectRatio: ASPECT_RATIO_NARROW,
18 18
     clientHeight: innerHeight,
19 19
     clientWidth: innerWidth,
20
-    reducedUI: false
20
+    reducedUI: false,
21
+    contextMenuOpened: false
21 22
 };
22 23
 
23 24
 ReducerRegistry.register('features/base/responsive-ui', (state = DEFAULT_STATE, action) => {
@@ -34,6 +35,9 @@ ReducerRegistry.register('features/base/responsive-ui', (state = DEFAULT_STATE,
34 35
 
35 36
     case SET_REDUCED_UI:
36 37
         return set(state, 'reducedUI', action.reducedUI);
38
+
39
+    case SET_CONTEXT_MENU_OPEN:
40
+        return set(state, 'contextMenuOpened', action.isOpen);
37 41
     }
38 42
 
39 43
     return state;

+ 6
- 0
react/features/filmstrip/components/web/Filmstrip.js Просмотреть файл

@@ -34,6 +34,11 @@ import ThumbnailWrapper from './ThumbnailWrapper';
34 34
 declare var APP: Object;
35 35
 declare var interfaceConfig: Object;
36 36
 
37
+/**
38
+ * Fixes case in which context menu overflows and creates a scroll on the whole filmstrip videos pane.
39
+ */
40
+const TILEVIEW_VIDEO_PANES_STYLE = { overflow: 'visible' };
41
+
37 42
 /**
38 43
  * The type of the React {@code Component} props of {@link Filmstrip}.
39 44
  */
@@ -386,6 +391,7 @@ class Filmstrip extends PureComponent <Props> {
386 391
                     overscanRowCount = { 1 }
387 392
                     rowCount = { _rows }
388 393
                     rowHeight = { _thumbnailHeight + TILE_VERTICAL_MARGIN }
394
+                    style = { TILEVIEW_VIDEO_PANES_STYLE }
389 395
                     width = { _filmstripWidth }>
390 396
                     {
391 397
                         ThumbnailWrapper

+ 3
- 1
react/features/filmstrip/functions.web.js Просмотреть файл

@@ -70,9 +70,11 @@ export function shouldRemoteVideosBeVisible(state: Object) {
70 70
     const participantCount = getParticipantCountWithFake(state);
71 71
     let pinnedParticipant;
72 72
     const { disable1On1Mode } = state['features/base/config'];
73
+    const { contextMenuOpened } = state['features/base/responsive-ui'];
73 74
 
74 75
     return Boolean(
75
-        participantCount > 2
76
+        contextMenuOpened
77
+            || participantCount > 2
76 78
 
77 79
             // Always show the filmstrip when there is another participant to
78 80
             // show and the  local video is pinned, or the toolbar is displayed.

+ 14
- 10
react/features/toolbox/actions.web.js Просмотреть файл

@@ -13,8 +13,7 @@ import {
13 13
     clearToolboxTimeout,
14 14
     setToolboxTimeout,
15 15
     setToolboxTimeoutMS,
16
-    setToolboxVisible,
17
-    setToolboxEnabled
16
+    setToolboxVisible
18 17
 } from './actions.native';
19 18
 
20 19
 declare var interfaceConfig: Object;
@@ -132,10 +131,13 @@ export function showToolbox(timeout: number = 0): Object {
132 131
             alwaysVisible,
133 132
             enabled,
134 133
             timeoutMS,
135
-            visible
134
+            visible,
135
+            overflowDrawer
136 136
         } = state['features/toolbox'];
137
+        const { contextMenuOpened } = state['features/base/responsive-ui'];
138
+        const contextMenuOpenedInTileview = isLayoutTileView(state) && contextMenuOpened && !overflowDrawer;
137 139
 
138
-        if (enabled && !visible) {
140
+        if (enabled && !visible && !contextMenuOpenedInTileview) {
139 141
             dispatch(setToolboxVisible(true));
140 142
 
141 143
             // If the Toolbox is always visible, there's no need for a timeout
@@ -167,18 +169,20 @@ export function setOverflowDrawer(displayAsDrawer: boolean) {
167 169
     };
168 170
 }
169 171
 
172
+
170 173
 /**
171 174
  * Disables and hides the toolbox on demand when in tile view.
172 175
  *
173 176
  * @returns {void}
174 177
  */
175
-export function disableToolboxOnTileView() {
178
+export function hideToolboxOnTileView() {
176 179
     return (dispatch: Dispatch<any>, getState: Function) => {
177
-        if (!isLayoutTileView(getState())) {
178
-            return;
179
-        }
180
+        const state = getState();
181
+        const { overflowDrawer } = state['features/toolbox'];
182
+
180 183
 
181
-        dispatch(setToolboxEnabled(false));
182
-        dispatch(hideToolbox(true));
184
+        if (!overflowDrawer && isLayoutTileView(state)) {
185
+            dispatch(hideToolbox(true));
186
+        }
183 187
     };
184 188
 }

+ 13
- 12
react/features/toolbox/components/web/Toolbox.js Просмотреть файл

@@ -389,29 +389,27 @@ class Toolbox extends Component<Props, State> {
389 389
      * @inheritdoc
390 390
      */
391 391
     componentDidUpdate(prevProps) {
392
-        // Ensure the dialog is closed when the toolbox becomes hidden.
393
-        if (prevProps._overflowMenuVisible && !this.props._visible) {
394
-            this._onSetOverflowVisible(false);
395
-        }
392
+        const { _dialog, _reactionsEnabled, _participantCount, dispatch, t } = this.props;
393
+
396 394
 
397 395
         if (prevProps._overflowMenuVisible
398 396
             && !prevProps._dialog
399
-            && this.props._dialog) {
397
+            && _dialog) {
400 398
             this._onSetOverflowVisible(false);
401
-            this.props.dispatch(setToolbarHovered(false));
399
+            dispatch(setToolbarHovered(false));
402 400
         }
403 401
 
404 402
         if (!this.state.reactionsShortcutsRegistered
405
-            && (prevProps._reactionsEnabled !== this.props._reactionsEnabled
406
-            || prevProps._participantCount !== this.props._participantCount)) {
407
-            if (this.props._reactionsEnabled && this.props._participantCount > 1) {
403
+            && (prevProps._reactionsEnabled !== _reactionsEnabled
404
+            || prevProps._participantCount !== _participantCount)) {
405
+            if (_reactionsEnabled && _participantCount > 1) {
408 406
                 // eslint-disable-next-line react/no-did-update-set-state
409 407
                 this.setState({
410 408
                     reactionsShortcutsRegistered: true
411 409
                 });
412 410
                 const REACTION_SHORTCUTS = Object.keys(REACTIONS).map(key => {
413 411
                     const onShortcutSendReaction = () => {
414
-                        this.props.dispatch(addReactionToBuffer(key));
412
+                        dispatch(addReactionToBuffer(key));
415 413
                         sendAnalytics(createShortcutEvent(
416 414
                             `reaction.${key}`
417 415
                         ));
@@ -420,7 +418,7 @@ class Toolbox extends Component<Props, State> {
420 418
                     return {
421 419
                         character: REACTIONS[key].shortcutChar,
422 420
                         exec: onShortcutSendReaction,
423
-                        helpDescription: this.props.t(`toolbar.reaction${key.charAt(0).toUpperCase()}${key.slice(1)}`),
421
+                        helpDescription: t(`toolbar.reaction${key.charAt(0).toUpperCase()}${key.slice(1)}`),
424 422
                         altKey: true
425 423
                     };
426 424
                 });
@@ -911,7 +909,9 @@ class Toolbox extends Component<Props, State> {
911 909
      * @returns {void}
912 910
      */
913 911
     _onMouseOut() {
914
-        this.props.dispatch(setToolbarHovered(false));
912
+        const { _overflowMenuVisible, dispatch } = this.props;
913
+
914
+        !_overflowMenuVisible && dispatch(setToolbarHovered(false));
915 915
     }
916 916
 
917 917
     _onMouseOver: () => void;
@@ -939,6 +939,7 @@ class Toolbox extends Component<Props, State> {
939 939
      */
940 940
     _onSetOverflowVisible(visible) {
941 941
         this.props.dispatch(setOverflowMenuVisible(visible));
942
+        this.props.dispatch(setToolbarHovered(visible));
942 943
     }
943 944
 
944 945
     _onShortcutToggleChat: () => void;

+ 15
- 22
react/features/video-menu/components/web/LocalVideoMenuTriggerButton.js Просмотреть файл

@@ -1,6 +1,7 @@
1 1
 // @flow
2 2
 
3 3
 import React, { Component } from 'react';
4
+import { batch } from 'react-redux';
4 5
 
5 6
 import { isMobileBrowser } from '../../../base/environment/utils';
6 7
 import { translate } from '../../../base/i18n';
@@ -10,10 +11,10 @@ import {
10 11
 } from '../../../base/participants';
11 12
 import { Popover } from '../../../base/popover';
12 13
 import { connect } from '../../../base/redux';
14
+import { setParticipantContextMenuOpen } from '../../../base/responsive-ui/actions';
13 15
 import { getLocalVideoTrack } from '../../../base/tracks';
14 16
 import ConnectionIndicatorContent from '../../../connection-indicator/components/web/ConnectionIndicatorContent';
15
-import { setToolboxEnabled, disableToolboxOnTileView } from '../../../toolbox/actions';
16
-import { isToolboxEnabled } from '../../../toolbox/functions';
17
+import { hideToolboxOnTileView } from '../../../toolbox/actions';
17 18
 import { getCurrentLayout, LAYOUTS } from '../../../video-layout';
18 19
 import { renderConnectionStatus } from '../../actions.web';
19 20
 
@@ -65,11 +66,6 @@ type Props = {
65 66
      */
66 67
     _showLocalVideoFlipButton: boolean,
67 68
 
68
-    /**
69
-     * Whether the toolbox is enabled or not.
70
-     */
71
-    _toolboxEnabled: boolean,
72
-
73 69
     /**
74 70
      * Invoked to obtain translated strings.
75 71
      */
@@ -83,11 +79,6 @@ type Props = {
83 79
  * @extends {Component}
84 80
  */
85 81
 class LocalVideoMenuTriggerButton extends Component<Props> {
86
-    /**
87
-     * Preserve the intial toolbox state.
88
-     */
89
-     initialToolboxEnabled: boolean;
90
-
91 82
     /**
92 83
      * Reference to the Popover instance.
93 84
      */
@@ -103,7 +94,6 @@ class LocalVideoMenuTriggerButton extends Component<Props> {
103 94
         super(props);
104 95
 
105 96
         this.popoverRef = React.createRef();
106
-        this.initialToolboxEnabled = true;
107 97
         this._onPopoverClose = this._onPopoverClose.bind(this);
108 98
         this._onPopoverOpen = this._onPopoverOpen.bind(this);
109 99
     }
@@ -129,8 +119,6 @@ class LocalVideoMenuTriggerButton extends Component<Props> {
129 119
         if (this.props.getRef) {
130 120
             this.props.getRef(this);
131 121
         }
132
-
133
-        this.initialToolboxEnabled = this.props._toolboxEnabled;
134 122
     }
135 123
 
136 124
     /**
@@ -181,16 +169,17 @@ class LocalVideoMenuTriggerButton extends Component<Props> {
181 169
                     overflowDrawer = { _overflowDrawer }
182 170
                     position = { _menuPosition }
183 171
                     ref = { this.popoverRef }>
184
-                    {!isMobileBrowser() && (
172
+                    {!_overflowDrawer && (
185 173
                         <span
186 174
                             className = 'popover-trigger local-video-menu-trigger'>
187
-                            <Icon
175
+                            {!isMobileBrowser() && <Icon
188 176
                                 ariaLabel = { t('dialog.localUserControls') }
189 177
                                 role = 'button'
190 178
                                 size = '1em'
191 179
                                 src = { IconMenuThumb }
192 180
                                 tabIndex = { 0 }
193 181
                                 title = { t('dialog.localUserControls') } />
182
+                            }
194 183
                         </span>
195 184
                     )}
196 185
                 </Popover>
@@ -206,7 +195,8 @@ class LocalVideoMenuTriggerButton extends Component<Props> {
206 195
      * @returns {void}
207 196
      */
208 197
     _onPopoverOpen() {
209
-        this.props.dispatch(disableToolboxOnTileView());
198
+        this.props.dispatch(setParticipantContextMenuOpen(true));
199
+        this.props.dispatch(hideToolboxOnTileView());
210 200
     }
211 201
 
212 202
     _onPopoverClose: () => void;
@@ -217,8 +207,12 @@ class LocalVideoMenuTriggerButton extends Component<Props> {
217 207
      * @returns {void}
218 208
      */
219 209
     _onPopoverClose() {
220
-        this.props.dispatch(setToolboxEnabled(this.initialToolboxEnabled));
221
-        this.props.dispatch(renderConnectionStatus(false));
210
+        const { dispatch } = this.props;
211
+
212
+        batch(() => {
213
+            dispatch(setParticipantContextMenuOpen(false));
214
+            dispatch(renderConnectionStatus(false));
215
+        });
222 216
     }
223 217
 }
224 218
 
@@ -258,8 +252,7 @@ function _mapStateToProps(state) {
258 252
         _showLocalVideoFlipButton: !disableLocalVideoFlip && videoTrack?.videoType !== 'desktop',
259 253
         _overflowDrawer: overflowDrawer,
260 254
         _localParticipantId: localParticipant.id,
261
-        _showConnectionInfo: showConnectionInfo,
262
-        _toolboxEnabled: isToolboxEnabled(state)
255
+        _showConnectionInfo: showConnectionInfo
263 256
     };
264 257
 }
265 258
 

+ 18
- 24
react/features/video-menu/components/web/RemoteVideoMenuTriggerButton.js Просмотреть файл

@@ -1,6 +1,7 @@
1 1
 // @flow
2 2
 
3 3
 import React, { Component } from 'react';
4
+import { batch } from 'react-redux';
4 5
 
5 6
 import ConnectionIndicatorContent from
6 7
     '../../../../features/connection-indicator/components/web/ConnectionIndicatorContent';
@@ -10,9 +11,9 @@ import { Icon, IconMenuThumb } from '../../../base/icons';
10 11
 import { getLocalParticipant, getParticipantById, PARTICIPANT_ROLE } from '../../../base/participants';
11 12
 import { Popover } from '../../../base/popover';
12 13
 import { connect } from '../../../base/redux';
14
+import { setParticipantContextMenuOpen } from '../../../base/responsive-ui/actions';
13 15
 import { requestRemoteControl, stopController } from '../../../remote-control';
14
-import { setToolboxEnabled, disableToolboxOnTileView } from '../../../toolbox/actions';
15
-import { isToolboxEnabled } from '../../../toolbox/functions';
16
+import { hideToolboxOnTileView } from '../../../toolbox/actions';
16 17
 import { getCurrentLayout, LAYOUTS } from '../../../video-layout';
17 18
 import { renderConnectionStatus } from '../../actions.web';
18 19
 
@@ -78,11 +79,6 @@ type Props = {
78 79
      */
79 80
     _remoteControlState: number,
80 81
 
81
-    /**
82
-     * Whether the toolbox is enabled or not.
83
-     */
84
-    _toolboxEnabled: boolean,
85
-
86 82
     /**
87 83
      * The redux dispatch function.
88 84
      */
@@ -133,11 +129,6 @@ type Props = {
133 129
  * @extends {Component}
134 130
  */
135 131
 class RemoteVideoMenuTriggerButton extends Component<Props> {
136
-    /**
137
-     * Preserve the intial toolbox state.
138
-     */
139
-     initialToolboxEnabled: boolean;
140
-
141 132
     /**
142 133
      * Reference to the Popover instance.
143 134
      */
@@ -153,7 +144,6 @@ class RemoteVideoMenuTriggerButton extends Component<Props> {
153 144
         super(props);
154 145
 
155 146
         this.popoverRef = React.createRef();
156
-        this.initialToolboxEnabled = true;
157 147
         this._onPopoverClose = this._onPopoverClose.bind(this);
158 148
         this._onPopoverOpen = this._onPopoverOpen.bind(this);
159 149
     }
@@ -179,8 +169,6 @@ class RemoteVideoMenuTriggerButton extends Component<Props> {
179 169
         if (this.props.getRef) {
180 170
             this.props.getRef(this);
181 171
         }
182
-
183
-        this.initialToolboxEnabled = this.props._toolboxEnabled;
184 172
     }
185 173
 
186 174
     /**
@@ -202,7 +190,7 @@ class RemoteVideoMenuTriggerButton extends Component<Props> {
202 190
      * @returns {ReactElement}
203 191
      */
204 192
     render() {
205
-        const { _showConnectionInfo, _participantDisplayName, participantID } = this.props;
193
+        const { _overflowDrawer, _showConnectionInfo, _participantDisplayName, participantID } = this.props;
206 194
         const content = _showConnectionInfo
207 195
             ? <ConnectionIndicatorContent participantId = { participantID } />
208 196
             : this._renderRemoteVideoMenu();
@@ -218,18 +206,19 @@ class RemoteVideoMenuTriggerButton extends Component<Props> {
218 206
                 content = { content }
219 207
                 onPopoverClose = { this._onPopoverClose }
220 208
                 onPopoverOpen = { this._onPopoverOpen }
221
-                overflowDrawer = { this.props._overflowDrawer }
209
+                overflowDrawer = { _overflowDrawer }
222 210
                 position = { this.props._menuPosition }
223 211
                 ref = { this.popoverRef }>
224
-                {!isMobileBrowser() && (
212
+                {!_overflowDrawer && (
225 213
                     <span className = 'popover-trigger remote-video-menu-trigger'>
226
-                        <Icon
214
+                        {!isMobileBrowser() && <Icon
227 215
                             ariaLabel = { this.props.t('dialog.remoteUserControls', { username }) }
228 216
                             role = 'button'
229 217
                             size = '1.4em'
230 218
                             src = { IconMenuThumb }
231 219
                             tabIndex = { 0 }
232 220
                             title = { this.props.t('dialog.remoteUserControls', { username }) } />
221
+                        }
233 222
                     </span>
234 223
                 )}
235 224
             </Popover>
@@ -244,7 +233,8 @@ class RemoteVideoMenuTriggerButton extends Component<Props> {
244 233
      * @returns {void}
245 234
      */
246 235
     _onPopoverOpen() {
247
-        this.props.dispatch(disableToolboxOnTileView());
236
+        this.props.dispatch(setParticipantContextMenuOpen(true));
237
+        this.props.dispatch(hideToolboxOnTileView());
248 238
     }
249 239
 
250 240
     _onPopoverClose: () => void;
@@ -255,8 +245,12 @@ class RemoteVideoMenuTriggerButton extends Component<Props> {
255 245
      * @returns {void}
256 246
      */
257 247
     _onPopoverClose() {
258
-        this.props.dispatch(setToolboxEnabled(this.initialToolboxEnabled));
259
-        this.props.dispatch(renderConnectionStatus(false));
248
+        const { dispatch } = this.props;
249
+
250
+        batch(() => {
251
+            dispatch(setParticipantContextMenuOpen(false));
252
+            dispatch(renderConnectionStatus(false));
253
+        });
260 254
     }
261 255
 
262 256
     /**
@@ -349,6 +343,7 @@ class RemoteVideoMenuTriggerButton extends Component<Props> {
349 343
         if (isMobileBrowser()) {
350 344
             buttons.push(
351 345
                 <ConnectionStatusButton
346
+                    key = 'conn-status'
352 347
                     participantId = { participantID } />
353 348
             );
354 349
         }
@@ -435,8 +430,7 @@ function _mapStateToProps(state, ownProps) {
435 430
         _overflowDrawer: overflowDrawer,
436 431
         _participantDisplayName,
437 432
         _disableGrantModerator: Boolean(disableGrantModerator),
438
-        _showConnectionInfo: showConnectionInfo,
439
-        _toolboxEnabled: isToolboxEnabled(state)
433
+        _showConnectionInfo: showConnectionInfo
440 434
     };
441 435
 }
442 436
 

Загрузка…
Отмена
Сохранить