Files
jitsi-meet/react/features/toolbox/functions.native.ts

126 lines
4.8 KiB
TypeScript
Raw Normal View History

import { IReduxState } from '../app/types';
import { IStateful } from '../base/app/types';
import { hasAvailableDevices } from '../base/devices/functions.native';
import { TOOLBOX_ALWAYS_VISIBLE, TOOLBOX_ENABLED } from '../base/flags/constants';
import { getFeatureFlag } from '../base/flags/functions';
import { getParticipantCountWithFake } from '../base/participants/functions';
import { toState } from '../base/redux/functions';
import { isLocalVideoTrackDesktop } from '../base/tracks/functions.native';
2019-03-12 17:45:53 +00:00
import { MAIN_TOOLBAR_BUTTONS_PRIORITY, VISITORS_MODE_BUTTONS } from './constants';
import { isButtonEnabled } from './functions.any';
import { IGetVisibleNativeButtonsParams, IToolboxNativeButton } from './types';
export * from './functions.any';
/**
* Indicates if the desktop share button is disabled or not.
*
* @param {IReduxState} state - The state from the Redux store.
* @returns {boolean}
*/
export function isDesktopShareButtonDisabled(state: IReduxState) {
const { muted, unmuteBlocked } = state['features/base/media'].video;
const videoOrShareInProgress = !muted || isLocalVideoTrackDesktop(state);
return unmuteBlocked && !videoOrShareInProgress;
}
2019-03-12 17:45:53 +00:00
/**
* Returns true if the toolbox is visible.
*
* @param {IStateful} stateful - A function or object that can be
2019-03-12 17:45:53 +00:00
* resolved to Redux state by the function {@code toState}.
* @returns {boolean}
*/
export function isToolboxVisible(stateful: IStateful) {
const state = toState(stateful);
const { toolbarConfig } = state['features/base/config'];
const { alwaysVisible } = toolbarConfig || {};
const { enabled, visible } = state['features/toolbox'];
feat: Participants optimisations (#9515) * fix(participants): Change from array to Map * fix(unload): optimise * feat: Introduces new states for e2ee feature. Stores everyoneSupportsE2EE and everyoneEnabledE2EE to minimize looping through participants list. squash: Uses participants map and go over the elements only once. * feat: Optimizes isEveryoneModerator to do less frequent checks in all participants. * fix: Drops deep equal from participants pane and uses the map. * fix(SharedVideo): isVideoPlaying * fix(participants): Optimise isEveryoneModerator * fix(e2e): Optimise everyoneEnabledE2EE * fix: JS errors. * ref(participants): remove getParticipants * fix(participants): Prepare for PR. * fix: Changes participants pane to be component. The functional component was always rendered: `prev props: {} !== {} :next props`. * feat: Optimization to skip participants list on pane closed. * fix: The participants list shows and the local participant. * fix: Fix wrong action name for av-moderation. * fix: Minimizes the number of render calls of av moderation notification. * fix: Fix iterating over remote participants. * fix: Fixes lint error. * fix: Reflects participant updates for av-moderation. * fix(ParticipantPane): to work with IDs. * fix(av-moderation): on PARTCIPANT_UPDATE * fix(ParticipantPane): close delay. * fix: address code review comments * fix(API): mute-everyone * fix: bugs * fix(Thumbnail): on mobile. * fix(ParticipantPane): Close context menu on click. * fix: Handles few error when local participant is undefined. * feat: Hides AV moderation if not supported. * fix: Show mute all video. * fix: Fixes updating participant for av moderation. Co-authored-by: damencho <damencho@jitsi.org>
2021-07-09 07:36:19 -05:00
const participantCount = getParticipantCountWithFake(state);
const alwaysVisibleFlag = getFeatureFlag(state, TOOLBOX_ALWAYS_VISIBLE, false);
const enabledFlag = getFeatureFlag(state, TOOLBOX_ENABLED, true);
2019-03-12 17:45:53 +00:00
return enabledFlag && enabled
&& (alwaysVisible || visible || participantCount === 1 || alwaysVisibleFlag);
2019-03-12 17:45:53 +00:00
}
/**
* Indicates if the video mute button is disabled or not.
*
* @param {IReduxState} state - The state from the Redux store.
* @returns {boolean}
*/
export function isVideoMuteButtonDisabled(state: IReduxState) {
const { muted, unmuteBlocked } = state['features/base/media'].video;
return !hasAvailableDevices(state, 'videoInput')
|| (unmuteBlocked && Boolean(muted));
}
/**
* Returns all buttons that need to be rendered.
*
* @param {IGetVisibleButtonsParams} params - The parameters needed to extract the visible buttons.
* @returns {Object} - The visible buttons arrays .
*/
export function getVisibleNativeButtons(
{ allButtons, clientWidth, iAmVisitor, mainToolbarButtonsThresholds, toolbarButtons }: IGetVisibleNativeButtonsParams) {
let filteredButtons = Object.keys(allButtons).filter(key =>
typeof key !== 'undefined' // filter invalid buttons that may be coming from config.mainToolbarButtons override
&& isButtonEnabled(key, toolbarButtons));
if (iAmVisitor) {
filteredButtons = VISITORS_MODE_BUTTONS.filter(button => filteredButtons.indexOf(button) > -1);
}
const { order } = mainToolbarButtonsThresholds.find(({ width }) => clientWidth > width)
|| mainToolbarButtonsThresholds[mainToolbarButtonsThresholds.length - 1];
const mainToolbarButtonKeysOrder = [
...order.filter(key => filteredButtons.includes(key)),
...MAIN_TOOLBAR_BUTTONS_PRIORITY.filter(key => !order.includes(key) && filteredButtons.includes(key)),
...filteredButtons.filter(key => !order.includes(key) && !MAIN_TOOLBAR_BUTTONS_PRIORITY.includes(key))
];
const mainButtonsKeys = mainToolbarButtonKeysOrder.slice(0, order.length);
const overflowMenuButtons = filteredButtons.reduce((acc, key) => {
if (!mainButtonsKeys.includes(key)) {
acc.push(allButtons[key]);
}
return acc;
}, [] as IToolboxNativeButton[]);
// if we have 1 button in the overflow menu it is better to directly display it in the main toolbar by replacing
// the "More" menu button with it.
if (overflowMenuButtons.length === 1) {
const button = overflowMenuButtons.shift()?.key;
button && mainButtonsKeys.push(button);
}
const mainMenuButtons
= mainButtonsKeys.map(key => allButtons[key]).sort((a, b) => {
// Native toolbox includes hangup and overflowmenu button keys, too
// hangup goes last, overflowmenu goes second-to-last
if (a.key === 'hangup' || a.key === 'overflowmenu') {
return 1;
}
if (b.key === 'hangup' || b.key === 'overflowmenu') {
return -1;
}
return 0; // other buttons are sorted by priority
});
return {
mainMenuButtons,
overflowMenuButtons
};
}