jiti-meet/react/features/recording/components/RecordingLabel.web.js

155 lines
4.5 KiB
JavaScript

import PropTypes from 'prop-types';
import React, { Component } from 'react';
import { connect } from 'react-redux';
import { translate } from '../../base/i18n';
/**
* Implements a React {@link Component} which displays the current state of
* conference recording. Currently it uses CSS to display itself automatically
* when there is a recording state update.
*
* @extends {Component}
*/
class RecordingLabel extends Component {
/**
* {@code RecordingLabel} component's property types.
*
* @static
*/
static propTypes = {
/**
* Whether or not the filmstrip is currently visible or toggled to
* hidden. Depending on the filmstrip state, different CSS classes will
* be set to allow for adjusting of {@code RecordingLabel} positioning.
*/
_filmstripVisible: PropTypes.bool,
/**
* An object to describe the {@code RecordingLabel} content. If no
* translation key to display is specified, the label will apply CSS to
* itself so it can be made invisible.
* {{
* centered: boolean,
* key: string,
* showSpinner: boolean
* }}
*/
_labelDisplayConfiguration: PropTypes.object,
/**
* Invoked to obtain translated string.
*/
t: PropTypes.func
};
/**
* Initializes a new {@code RecordingLabel} instance.
*
* @param {Object} props - The read-only properties with which the new
* instance is to be initialized.
*/
constructor(props) {
super(props);
this.state = {
/**
* Whether or not the filmstrip was not visible but has transitioned
* in the latest component update to visible. This boolean is used
* to set a class for position animations.
*
* @type {boolean}
*/
filmstripBecomingVisible: false
};
}
/**
* Updates the state for whether or not the filmstrip is being toggled to
* display after having being hidden.
*
* @inheritdoc
* @param {Object} nextProps - The read-only props which this Component will
* receive.
* @returns {void}
*/
componentWillReceiveProps(nextProps) {
this.setState({
filmstripBecomingVisible: nextProps._filmstripVisible
&& !this.props._filmstripVisible
});
}
/**
* Implements React's {@link Component#render()}.
*
* @inheritdoc
* @returns {ReactElement}
*/
render() {
const { _labelDisplayConfiguration } = this.props;
const { centered, key, showSpinner } = _labelDisplayConfiguration || {};
const isVisible = Boolean(key);
const rootClassName = [
'video-state-indicator centeredVideoLabel',
isVisible ? 'show-inline' : '',
centered ? '' : 'moveToCorner',
this.state.filmstripBecomingVisible ? 'opening' : '',
this.props._filmstripVisible
? 'with-filmstrip' : 'without-filmstrip'
].join(' ');
return (
<span
className = { rootClassName }
id = 'recordingLabel'>
<span id = 'recordingLabelText'>
{ this.props.t(key) }
</span>
{ showSpinner
? <img
className = 'recordingSpinner'
id = 'recordingSpinner'
src = 'images/spin.svg' />
: null }
</span>
);
}
}
/**
* Maps (parts of) the Redux state to the associated {@code RecordingLabel}
* component's props.
*
* @param {Object} state - The Redux state.
* @private
* @returns {{
* _filmstripVisible: boolean,
* _labelDisplayConfiguration: Object
* }}
*/
function _mapStateToProps(state) {
const { visible } = state['features/filmstrip'];
const { labelDisplayConfiguration } = state['features/recording'];
return {
/**
* Whether or not the filmstrip is currently set to be displayed.
*
* @type {boolean}
*/
_filmstripVisible: visible,
/**
* An object describing how {@code RecordingLabel} should display its
* contents.
*
* @type {Object}
*/
_labelDisplayConfiguration: labelDisplayConfiguration
};
}
export default translate(connect(_mapStateToProps)(RecordingLabel));