diff --git a/packages/common/components/MediaViewer/sub-components/duration.js b/packages/common/components/MediaViewer/sub-components/duration.js deleted file mode 100644 index 85ae296596..0000000000 --- a/packages/common/components/MediaViewer/sub-components/duration.js +++ /dev/null @@ -1,24 +0,0 @@ -import React from "react"; - -export default function Duration({ className, seconds }) { - return ( - - ); -} - -function format(seconds) { - const date = new Date(seconds * 1000); - const hh = date.getUTCHours(); - const mm = date.getUTCMinutes(); - const ss = pad(date.getUTCSeconds()); - if (hh) { - return `${hh}:${pad(mm)}:${ss}`; - } - return `${mm}:${ss}`; -} - -function pad(string) { - return ("0" + string).slice(-2); -} diff --git a/packages/common/components/MediaViewer/sub-components/image-viewer.js b/packages/common/components/MediaViewer/sub-components/image-viewer.js deleted file mode 100644 index 5de161772f..0000000000 --- a/packages/common/components/MediaViewer/sub-components/image-viewer.js +++ /dev/null @@ -1,415 +0,0 @@ -import React from "react"; -import PropTypes from "prop-types"; -import styled from "styled-components"; - -import MediaZoomInIcon from "PUBLIC_DIR/images/media.zoomin.react.svg"; -import MediaZoomOutIcon from "PUBLIC_DIR/images/media.zoomout.react.svg"; -import MediaRotateLeftIcon from "PUBLIC_DIR/images/media.rotateleft.react.svg"; -import MediaRotateRightIcon from "PUBLIC_DIR/images/media.rotateright.react.svg"; -import MediaDeleteIcon from "PUBLIC_DIR/images/media.delete.react.svg"; -import MediaDownloadIcon from "PUBLIC_DIR/images/download.react.svg"; -import commonIconsStyles from "@docspace/components/utils/common-icons-style"; -import MediaFavoriteIcon from "PUBLIC_DIR/images/favorite.react.svg"; - -import ViewerSeparator from "PUBLIC_DIR/images/viewer.separator.react.svg"; -import MediaShare from "PUBLIC_DIR/images/share.react.svg"; - -import DropDownItem from "@docspace/components/drop-down-item"; -import DropDown from "@docspace/components/drop-down"; -import equal from "fast-deep-equal/react"; -import { Base } from "@docspace/components/themes"; -import { Viewer } from "@docspace/components/viewer"; - -const StyledViewer = styled(Viewer)` - .react-viewer-footer { - bottom: 5px !important; - z-index: 301 !important; - overflow: visible; - } - .react-viewer-canvas { - z-index: 300 !important; - margin-top: 50px; - } - .react-viewer-navbar, - .react-viewer-mask, - .react-viewer-attribute, - .react-viewer-close { - display: none; - } - .react-viewer-toolbar { - position: relative; - overflow: visible; - bottom: 4px; - } - .react-viewer-toolbar li { - width: 40px; - height: 30px; - margin-top: 4px; - border-radius: 2px; - cursor: pointer; - line-height: 24px; - -webkit-tap-highlight-color: rgba(0, 0, 0, 0); - } - .react-viewer-btn { - background-color: transparent; - &:hover { - background-color: ${(props) => - props.theme.mediaViewer.imageViewer.backgroundColor}; - } - } - .react-viewer-image-transition { - transition-duration: 0s; - } - li[data-key="prev"] { - left: 20px; - } - li[data-key="next"] { - right: 20px; - } - li[data-key="prev"], - li[data-key="next"] { - position: fixed; - top: calc(50% - 20px); - - height: auto; - background: none; - - &:hover { - background: none; - } - } - li[data-key="delete"], - li[data-key="customDownload"] { - position: fixed; - @media (max-width: 600px) { - position: initial; - } - bottom: 9px; - .controlBtn { - margin: 0; - } - } - li[data-key="delete"] { - right: 62px; - } - li[data-key="customDownload"] { - right: 12px; - } - .iconContainer { - width: 24px; - height: 24px; - line-height: 20px; - margin: 3px auto; - - &.reset { - width: 18px; - } - - path, - rect { - fill: ${(props) => props.theme.mediaViewer.imageViewer.fill}; - } - } - - .btnContainer { - display: block; - width: 16px; - height: 16px; - margin: 4px 12px; - line-height: 19px; - - path, - rect { - fill: ${(props) => props.theme.mediaViewer.imageViewer.fill}; - } - } - .scrollBtn { - cursor: ${(props) => (props.inactive ? "default" : "pointer")}; - opacity: ${(props) => (props.inactive ? "0.2" : "1")}; - &:hover { - background-color: ${(props) => - !props.inactive - ? props.theme.mediaViewer.imageViewer.backgroundColor - : props.theme.mediaViewer.imageViewer.inactiveBackgroundColor}; - } - } -`; - -const StyledDropDown = styled(DropDown)` - background: #333; -`; - -const StyledDropDownItem = styled(DropDownItem)` - color: #fff; - - .drop-down-item_icon svg { - path { - fill: #fff !important; - } - } - - /* .is-separator { - height: 1px; - background: #474747; - } */ - - &:hover { - background: #444; - } -`; - -StyledViewer.defaultProps = { theme: Base }; - -class ImageViewer extends React.Component { - // componentDidUpdate() { - // document.getElementsByClassName("iconContainer reset").length > 0 && - // document.getElementsByClassName("iconContainer reset")[0].click(); - // } - - shouldComponentUpdate(nextProps) { - return !equal(this.props, nextProps); - } - render() { - const { - className, - visible, - images, - inactive, - onClose, - userAccess, - title, - errorTitle, - onPrevClick, - onNextClick, - playlist, - playlistPos, - isImage, - isAudio, - isVideo, - isPreviewFile, - archiveRoom, - contextModel, - audioIcon, - headerIcon, - onSetSelectionFile, - onDownloadClick, - } = this.props; - - const generateContextMenu = (isOpen, right, bottom) => { - const model = contextModel(); - - const onItemClick = (e, item) => { - const { action, onClick } = item; - - return onClick({ originalEvent: e, action: action, item }); - }; - - return ( - - {model.map((item) => { - if (item.disabled) return; - - const onClick = (e) => { - onClose(); - onItemClick(e, item); - }; - return ( - - ); - })} - - ); - }; - - var customToolbar = [ - { - key: "zoomOut", - percent: true, - actionType: 2, - render: ( -
- -
- ), - }, - { - key: "percent", - actionType: 999, - }, - { - key: "zoomIn", - actionType: 1, - render: ( -
- -
- ), - }, - { - key: "rotateLeft", - actionType: 5, - render: ( -
- -
- ), - }, - { - key: "rotateRight", - actionType: 6, - render: ( -
- -
- ), - }, - { - key: "separator download-separator", - actionType: -1, - noHover: true, - render: ( -
- -
- ), - }, - // { - // key: "share", - // actionType: 101, - // render: ( - //
- // - //
- // ), - // }, - { - key: "download", - actionType: 102, - render: ( -
- -
- ), - }, - { - key: "context-separator", - actionType: -1, - noHover: true, - render: ( -
- -
- ), - }, - { - key: "context-menu", - actionType: -1, - }, - { - key: "delete", - actionType: 103, - render: ( -
- -
- ), - }, - { - key: "favorite", - actionType: 104, - render: ( -
- -
- ), - }, - ]; - - customToolbar.forEach((button) => { - switch (button.key) { - case "prev": - button.onClick = this.props.onPrevClick; - break; - case "next": - button.onClick = this.props.onNextClick; - break; - case "delete": - button.onClick = this.props.onDeleteClick; - break; - case "download": - button.onClick = onDownloadClick; - break; - default: - break; - } - }); - - const canShare = playlist[playlistPos].canShare; - const toolbars = - !canShare && userAccess - ? customToolbar.filter( - (x) => x.key !== "share" && x.key !== "share-separator" - ) - : customToolbar.filter((x) => x.key !== "delete"); - - return ( -
- toolbars} - images={images} - /> -
- ); - } -} - -ImageViewer.propTypes = { - className: PropTypes.string, - visible: PropTypes.bool, - inactive: PropTypes.bool, - images: PropTypes.arrayOf(PropTypes.object), - onNextClick: PropTypes.func, - onPrevClick: PropTypes.func, - onDeleteClick: PropTypes.func, - onDownloadClick: PropTypes.func, - onClose: PropTypes.func, -}; - -export default ImageViewer; diff --git a/packages/common/components/MediaViewer/sub-components/progress.js b/packages/common/components/MediaViewer/sub-components/progress.js deleted file mode 100644 index 3c4ed0cd40..0000000000 --- a/packages/common/components/MediaViewer/sub-components/progress.js +++ /dev/null @@ -1,138 +0,0 @@ -import React from "react"; -import styled from "styled-components"; -import PropTypes from "prop-types"; -import { Base } from "@docspace/components/themes"; - -const StyledProgress = styled.div` - display: inline-block; - - .slider-container { - display: inline-block; - border-radius: 2px; - position: relative; - width: ${(props) => props.width}px; - height: 6px; - background: ${(props) => - props.theme.mediaViewer.progressBar.backgroundColor}; - margin: 15px 0; - vertical-align: middle; - } - .fill { - cursor: pointer; - width: ${(props) => 100 * props.value}%; - position: absolute; - - top: calc(50% - 3px); - height: 6px; - background: ${(props) => props.theme.mediaViewer.progressBar.background}; - border-radius: 2px; - } - input[type="range"] { - display: block; - overflow: visible; - background: transparent; - width: ${(props) => props.width}px; - height: 6px; - outline: none; - margin: 0; - -webkit-appearance: none; - position: relative; - cursor: pointer; - } - - input[type="range"]::-webkit-slider-thumb { - position: relative; - appearance: none; - box-sizing: content-box; - width: 12px; - height: 12px; - margin-top: -3px; - background: white; - border-radius: 50%; - - cursor: pointer; - } - input[type="range"]::-moz-range-thumb { - position: relative; - appearance: none; - box-sizing: content-box; - width: 12px; - height: 12px; - background: white; - border-radius: 50%; - margin-top: -3px; - cursor: pointer; - } - input[type="range"]::-ms-thumb { - position: relative; - appearance: none; - box-sizing: content-box; - width: 12px; - height: 12px; - background: white; - border-radius: 50%; - margin-top: -3px; - cursor: pointer; - } - - input[type="range"]::-webkit-slider-runnable-track { - margin: 12px 0; - height: 6px; - border-radius: 2px; - cursor: pointer; - -webkit-appearance: none; - text-align: right; - pointer-events: none; - } - input[type="range"]::-moz-range-track { - margin: 12px 0; - height: 6px; - border-radius: 2px; - cursor: pointer; - -webkit-appearance: none; - text-align: right; - pointer-events: none; - } - input[type="range"]::-ms-track { - border-color: transparent; - color: transparent; - - margin: 12px 0; - height: 6px; - border-radius: 2px; - cursor: pointer; - -webkit-appearance: none; - text-align: right; - pointer-events: none; - } -`; - -StyledProgress.defaultProps = { theme: Base }; -const Progress = (props) => { - return ( - -
-
- props.handleSeekChange(event)} - onMouseUp={props.handleSeekMouseUp} - /> -
-
- ); -}; - -Progress.propTypes = { - value: PropTypes.number, - handleSeekMouseDown: PropTypes.func, - handleSeekChange: PropTypes.func, - handleSeekMouseUp: PropTypes.func, -}; - -export default Progress; diff --git a/packages/common/components/MediaViewer/sub-components/video-viewer.js b/packages/common/components/MediaViewer/sub-components/video-viewer.js deleted file mode 100644 index 95f18ed8f1..0000000000 --- a/packages/common/components/MediaViewer/sub-components/video-viewer.js +++ /dev/null @@ -1,579 +0,0 @@ -import React, { Component } from "react"; -import PropTypes from "prop-types"; -import styled, { css } from "styled-components"; -import { findDOMNode } from "react-dom"; -import screenfull from "screenfull"; -import ReactPlayer from "react-player"; - -import Duration from "./duration"; -import Progress from "./progress"; -import MediaPauseIcon from "PUBLIC_DIR/images/media.pause.react.svg"; -import MediaPlayIcon from "PUBLIC_DIR/images/media.play.react.svg"; -import MediaFullScreenIcon from "PUBLIC_DIR/images/media.fullscreen.video.react.svg"; -import MediaMuteIcon from "PUBLIC_DIR/images/media.mute.react.svg"; -import MediaMuteOffIcon from "PUBLIC_DIR/images/media.muteoff.react.svg"; -import commonIconsStyles from "@docspace/components/utils/common-icons-style"; -import { Base } from "@docspace/components/themes"; - -const iconsStyles = css` - path, - stroke, - rect { - fill: ${(props) => props.theme.mediaViewer.videoViewer.fill}; - } -`; - -const controlsHeight = 40; -const StyledControls = styled.div` - height: ${(props) => props.height}px; - display: block; - position: fixed; - z-index: 301; - ${(props) => - !props.isVideo && - `background-color: ${props.theme.mediaViewer.videoViewer.backgroundColor};`} - top: calc(50% + ${(props) => props.top}px); - left: ${(props) => props.left}px; -`; - -StyledControls.defaultProps = { theme: Base }; -const StyledVideoControlBtn = styled.div` - display: inline-block; - height: 26px; - line-height: 30px; - margin: 5px 2px; - width: 38px; - border-radius: 2px; - cursor: pointer; - text-align: center; - vertical-align: top; - &:hover { - background-color: ${(props) => - props.theme.mediaViewer.videoViewer.background}; - } - - .playBtnContainer { - width: 16px; - height: 16px; - line-height: 0; - margin: 5px auto; - } - .pauseBtnContainer { - display: block; - width: 16px; - height: 16px; - margin: 3px 10px; - line-height: 19px; - } - .muteBtnContainer { - display: block; - width: 16px; - height: 16px; - margin: 3px 11px; - line-height: 19px; - } - .fullscreenBtnContainer { - display: block; - width: 16px; - height: 16px; - margin: 3px 11px; - line-height: 19px; - } -`; - -StyledVideoControlBtn.defaultProps = { theme: Base }; -const StyledMediaPauseIcon = styled(MediaPauseIcon)` - ${commonIconsStyles} - ${iconsStyles} -`; -StyledMediaPauseIcon.defaultProps = { theme: Base }; -const StyledMediaPlayIcon = styled(MediaPlayIcon)` - ${commonIconsStyles} - ${iconsStyles} -`; -StyledMediaPlayIcon.defaultProps = { theme: Base }; -const StyledMediaFullScreenIcon = styled(MediaFullScreenIcon)` - ${commonIconsStyles} - ${iconsStyles} -`; -StyledMediaFullScreenIcon.defaultProps = { theme: Base }; -const StyledMediaMuteIcon = styled(MediaMuteIcon)` - ${commonIconsStyles} - - path:first-child { - stroke: ${(props) => props.theme.mediaViewer.videoViewer.stroke}; - } - - path:last-child { - fill: ${(props) => props.theme.mediaViewer.videoViewer.fill}; - } -`; -const StyledMediaMuteOffIcon = styled(MediaMuteOffIcon)` - ${commonIconsStyles} - - path, rect { - fill: ${(props) => props.theme.mediaViewer.videoViewer.fill}; - } -`; - -StyledMediaMuteIcon.defaultProps = { theme: Base }; -const VideoControlBtn = (props) => { - return ( - {props.children} - ); -}; -VideoControlBtn.propTypes = { - children: PropTypes.any, -}; -const Controls = (props) => { - return {props.children}; -}; -Controls.propTypes = { - children: PropTypes.any, -}; -const PlayBtn = (props) => { - return ( - - {props.playing ? ( -
- -
- ) : ( -
- -
- )} -
- ); -}; -PlayBtn.propTypes = { - playing: PropTypes.bool, - onClick: PropTypes.func, -}; -const FullScreenBtn = (props) => { - return ( - -
- -
-
- ); -}; -FullScreenBtn.propTypes = { - onClick: PropTypes.func, -}; - -const StyledValumeContainer = styled.div` - display: inline-block; - vertical-align: top; - line-height: 39px; - position: relative; - - .muteConteiner { - display: none; - position: absolute; - width: 40px; - height: 80px; - border-radius: 5px; - top: -76px; - left: 5px; - background: black; - } - &:hover { - .muteConteiner { - display: inline-block; - } - } - .mute { - display: inline-block; - transform: rotate(-90deg); - margin: 22px -14px; - } -`; -const StyledDuration = styled.div` - display: inline-block; - height: 26px; - line-height: 26px; - margin: 5px; - width: 60px; - text-align: center; - vertical-align: top; - border-radius: 2px; - cursor: pointer; - - &:hover { - background-color: ${(props) => - props.theme.mediaViewer.videoViewer.background}; - } -`; - -StyledValumeContainer.defaultProps = { theme: Base }; -const StyledVideoViewer = styled.div` - color: ${(props) => props.theme.mediaViewer.videoViewer.color}; - - .playerWrapper { - display: ${(props) => (props.isVideo ? "block" : "none")}; - width: ${(props) => props.width}px; - height: ${(props) => props.height}px; - left: ${(props) => props.left}px; - top: calc(50% - ${(props) => props.top / 2}px); - z-index: 301; - position: fixed; - padding-bottom: 40px; - background-color: ${(props) => - props.theme.mediaViewer.videoViewer.backgroundColor}; - - video { - z-index: 300; - } - } -`; - -StyledVideoViewer.defaultProps = { theme: Base }; - -const ErrorContainer = styled.div` - z-index: 301; - display: block; - position: fixed; - left: calc(50% - 110px); - top: calc(50% - 40px); - background-color: ${(props) => - props.theme.mediaViewer.videoViewer.backgroundColorError}; - color: ${(props) => props.theme.mediaViewer.videoViewer.colorError}; - border-radius: 10px; - padding: 20px; - text-align: center; -`; - -ErrorContainer.defaultProps = { theme: Base }; - -class ValumeBtn extends Component { - constructor(props) { - super(props); - } - - render() { - return ( - -
- -
- - -
- {this.props.muted ? ( - - ) : ( - - )} -
-
-
- ); - } -} -ValumeBtn.propTypes = { - width: PropTypes.number, - volume: PropTypes.number, - muted: PropTypes.bool, - onMouseDown: PropTypes.func, - onChange: PropTypes.func, - handleSeekMouseUp: PropTypes.func, - onChangeMute: PropTypes.func, -}; - -class VideoViewer extends Component { - state = { - url: this.props.url, - pip: false, - playing: false, - controls: false, - light: false, - volume: 0.3, - muted: false, - played: 0, - loaded: 0, - duration: 0, - playbackRate: 1.0, - loop: false, - isNew: false, - error: false, - isLoaded: false, - }; - - componentDidMount() { - document.addEventListener("keydown", this.onKeydown, false); - } - - componentWillUnmount() { - document.removeEventListener("keydown", this.onKeydown, false); - } - - componentDidUpdate(prevProps) { - if (this.props.url !== prevProps.url) { - this.setState({ - url: this.props.url, - isNew: true, - error: false, - }); - } - } - - onKeydown = (e) => { - if (e.keyCode === 32) this.handlePlayPause(); - }; - - handlePlayPause = () => { - this.setState({ playing: !this.state.playing, isNew: false }); - }; - - handleStop = () => { - this.setState({ url: null, playing: false }); - }; - - handleVolumeChange = (e) => { - this.setState({ - volume: parseFloat(e.target.value), - muted: false, - }); - }; - - handleToggleMuted = () => { - this.setState({ muted: !this.state.muted }); - }; - - handlePlay = () => { - this.setState({ playing: true }); - }; - - handleEnablePIP = () => { - this.setState({ pip: true }); - }; - - handleDisablePIP = () => { - this.setState({ pip: false }); - }; - - handlePause = () => { - this.setState({ playing: false }); - }; - - handleSeekMouseDown = (e) => { - this.setState({ seeking: true }); - }; - - handleSeekChange = (e) => { - this.setState({ played: parseFloat(e.target.value) }); - }; - - handleSeekMouseUp = (e) => { - console.log(!isNaN(parseFloat(e.target.value)), parseFloat(e.target.value)); - if (!isNaN(parseFloat(e.target.value))) { - this.setState({ seeking: false }); - this.player.seekTo(parseFloat(e.target.value)); - } - }; - - handleProgress = (state) => { - if (!this.state.seeking) { - this.setState(state); - } - }; - - handleEnded = () => { - this.setState({ playing: this.state.loop }); - }; - - handleDuration = (duration) => { - this.setState({ duration }); - }; - - handleClickFullscreen = () => { - screenfull.request(findDOMNode(this.player)); - }; - - ref = (player) => { - this.player = player; - }; - - resizePlayer = (videoSize, screenSize) => { - var ratio = videoSize.h / videoSize.w; - - if (videoSize.h > screenSize.h) { - videoSize.h = screenSize.h; - videoSize.w = videoSize.h / ratio; - } - if (videoSize.w > screenSize.w) { - videoSize.w = screenSize.w; - videoSize.h = videoSize.w * ratio; - } - - return { - width: videoSize.w, - height: videoSize.h, - }; - }; - - onError = (e) => { - console.log("onError", e); - this.setState({ error: true }); - }; - - onPlay = () => { - this.setState({ playing: !this.state.isNew, isNew: false, isLoaded: true }); - }; - - render() { - const { - url, - playing, - controls, - light, - volume, - muted, - loop, - played, - loaded, - duration, - playbackRate, - pip, - error, - isLoaded, - } = this.state; - const { errorLabel } = this.props; - - const parentOffset = this.props.getOffset() || 0; - var screenSize = { - w: window.innerWidth, - h: window.innerHeight, - }; - screenSize.h -= parentOffset + controlsHeight; - - let width = screenSize.w; - let height = screenSize.h; - - let centerAreaOx = screenSize.w / 2 + document.documentElement.scrollLeft; - let centerAreaOy = screenSize.h / 2 + document.documentElement.scrollTop; - - let videoElement = document.getElementsByTagName("video")[0]; - if (videoElement) { - width = this.props.isVideo - ? videoElement.videoWidth || 480 - : screenSize.w - 150; - height = this.props.isVideo ? videoElement.videoHeight || 270 : 0; - - let resize = this.resizePlayer( - { - w: width, - h: height, - }, - screenSize - ); - width = resize.width; - height = resize.height; - } - - let left = this.props.isVideo - ? centerAreaOx - width / 2 - : centerAreaOx - width / 2; - - const videoControlBtnWidth = 220; - const audioControlBtnWidth = 170; - let progressWidth = this.props.isVideo - ? width - videoControlBtnWidth - : width - audioControlBtnWidth; - - if (error) { - return ( - -

{errorLabel}

-
- ); - } - - return ( - -
-
- -
- - - - - - - - - {this.props.isVideo && ( - - )} - -
-
- ); - } -} - -VideoViewer.propTypes = { - isVideo: PropTypes.bool, - url: PropTypes.string, - getOffset: PropTypes.func, - errorLabel: PropTypes.string, -}; - -export default VideoViewer;