mirror of
https://github.com/strapi/strapi.git
synced 2025-11-02 02:44:55 +00:00
Merge pull request #10663 from strapi/chore/tutorial-box
Remove outdated tutorials videos
This commit is contained in:
commit
4622909f5c
@ -168,6 +168,7 @@ class StrapiApp {
|
||||
addSettingsLinks: this.addSettingsLinks,
|
||||
getPlugin: this.getPlugin,
|
||||
injectContentManagerComponent: this.injectContentManagerComponent,
|
||||
injectAdminComponent: this.injectAdminComponent,
|
||||
registerHook: this.registerHook,
|
||||
});
|
||||
}
|
||||
@ -183,6 +184,7 @@ class StrapiApp {
|
||||
addSettingsLinks: this.addSettingsLinks,
|
||||
getPlugin: this.getPlugin,
|
||||
injectContentManagerComponent: this.injectContentManagerComponent,
|
||||
injectAdminComponent: this.injectAdminComponent,
|
||||
registerHook: this.registerHook,
|
||||
});
|
||||
}
|
||||
@ -299,6 +301,16 @@ class StrapiApp {
|
||||
this.admin.injectionZones.contentManager[containerName][blockName].push(component);
|
||||
};
|
||||
|
||||
injectAdminComponent = (containerName, blockName, component) => {
|
||||
invariant(
|
||||
this.admin.injectionZones.admin[containerName]?.[blockName],
|
||||
`The ${containerName} ${blockName} zone is not defined in the admin`
|
||||
);
|
||||
invariant(component, 'A Component must be provided');
|
||||
|
||||
this.admin.injectionZones.admin[containerName][blockName].push(component);
|
||||
};
|
||||
|
||||
/**
|
||||
* Load the admin translations
|
||||
* @returns {Object} The imported admin translations
|
||||
|
||||
@ -1,150 +0,0 @@
|
||||
import styled from 'styled-components';
|
||||
|
||||
const Li = styled.li`
|
||||
display: block;
|
||||
padding: 8px 20px;
|
||||
cursor: pointer;
|
||||
margin-top: 0;
|
||||
|
||||
&:hover {
|
||||
background-color: #f7f8f8;
|
||||
.title {
|
||||
color: #0e7de7;
|
||||
}
|
||||
}
|
||||
.txtWrapper,
|
||||
.thumbWrapper {
|
||||
display: inline-block;
|
||||
vertical-align: middle;
|
||||
}
|
||||
.thumbWrapper {
|
||||
position: relative;
|
||||
width: 55px;
|
||||
height: 38px;
|
||||
background-color: #d8d8d8;
|
||||
border-radius: 2px;
|
||||
overflow: hidden;
|
||||
.overlay {
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
z-index: 1;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
background-color: rgba(#0e7de7, 0.8);
|
||||
}
|
||||
img {
|
||||
position: relative;
|
||||
z-index: 0;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
.play {
|
||||
position: absolute;
|
||||
top: calc(50% - 10px);
|
||||
left: calc(50% - 10px);
|
||||
width: 20px;
|
||||
height: 20px;
|
||||
background-color: #0e7de7;
|
||||
border: 1px solid white;
|
||||
text-align: center;
|
||||
line-height: 20px;
|
||||
border-radius: 50%;
|
||||
z-index: 2;
|
||||
&::before {
|
||||
content: '\f04b';
|
||||
display: inline-block;
|
||||
vertical-align: top;
|
||||
height: 100%;
|
||||
font-family: 'FontAwesome';
|
||||
color: white;
|
||||
font-size: 10px;
|
||||
margin-left: 3px;
|
||||
line-height: 18px;
|
||||
}
|
||||
}
|
||||
}
|
||||
&.finished {
|
||||
.title {
|
||||
color: #919bae;
|
||||
}
|
||||
.thumbWrapper {
|
||||
.overlay {
|
||||
background-color: transparent;
|
||||
}
|
||||
img {
|
||||
opacity: 0.6;
|
||||
}
|
||||
.play {
|
||||
background-color: #5a9e06;
|
||||
border-color: #5a9e06;
|
||||
&::before {
|
||||
content: '\f00c';
|
||||
margin-left: 0;
|
||||
font-size: 11px;
|
||||
line-height: 20px;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.txtWrapper {
|
||||
padding: 0 15px;
|
||||
p {
|
||||
font-size: 14px;
|
||||
line-height: 26px;
|
||||
font-family: Lato;
|
||||
font-weight: 600;
|
||||
}
|
||||
.time {
|
||||
color: #919bae;
|
||||
font-family: Lato;
|
||||
font-weight: bold;
|
||||
font-size: 11px;
|
||||
line-height: 11px;
|
||||
}
|
||||
}
|
||||
|
||||
.hiddenPlayerWrapper {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.videoModal {
|
||||
margin-right: auto !important;
|
||||
margin-left: auto !important;
|
||||
.videoModalHeader {
|
||||
padding-bottom: 0;
|
||||
border-bottom: 0;
|
||||
> h5 {
|
||||
font-family: Lato;
|
||||
font-weight: bold !important;
|
||||
font-size: 1.8rem !important;
|
||||
line-height: 3.1rem;
|
||||
color: #333740;
|
||||
}
|
||||
> button {
|
||||
display: flex;
|
||||
position: absolute;
|
||||
right: 0;
|
||||
top: 0;
|
||||
margin-top: 0;
|
||||
margin-right: 0;
|
||||
padding: 10px;
|
||||
cursor: pointer;
|
||||
span {
|
||||
line-height: 0.6em;
|
||||
}
|
||||
}
|
||||
}
|
||||
.videoPlayer {
|
||||
> button {
|
||||
top: 50%;
|
||||
margin-top: -0.75em;
|
||||
left: 50%;
|
||||
margin-left: -1.5em;
|
||||
}
|
||||
}
|
||||
}
|
||||
`;
|
||||
|
||||
export default Li;
|
||||
@ -7,6 +7,7 @@
|
||||
import React from 'react';
|
||||
import { useIntl } from 'react-intl';
|
||||
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
|
||||
import { InjectionZone } from '../../../shared/components';
|
||||
import StyledLink from './StyledLink';
|
||||
|
||||
function StaticLinks() {
|
||||
@ -38,6 +39,7 @@ function StaticLinks() {
|
||||
</li>
|
||||
);
|
||||
})}
|
||||
<InjectionZone area="admin.tutorials.links" />
|
||||
</ul>
|
||||
);
|
||||
}
|
||||
|
||||
@ -1,180 +0,0 @@
|
||||
/**
|
||||
*
|
||||
* OnboardingList
|
||||
*
|
||||
*/
|
||||
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import cn from 'classnames';
|
||||
import { isNaN } from 'lodash';
|
||||
|
||||
import { Modal, ModalHeader, ModalBody } from 'reactstrap';
|
||||
import { Player } from 'video-react';
|
||||
import 'video-react/dist/video-react.css';
|
||||
import Li from './Li';
|
||||
|
||||
/* eslint-disable */
|
||||
|
||||
class OnboardingVideo extends React.Component {
|
||||
componentDidMount() {
|
||||
if (this.hiddenPlayer.current) {
|
||||
this.hiddenPlayer.current.subscribeToStateChange(this.handleChangeState);
|
||||
}
|
||||
}
|
||||
|
||||
hiddenPlayer = React.createRef();
|
||||
|
||||
player = React.createRef();
|
||||
|
||||
handleChangeState = (state, prevState) => {
|
||||
const { duration } = state;
|
||||
const { id } = this.props;
|
||||
|
||||
if (duration !== prevState.duration && !isNaN(duration)) {
|
||||
this.props.setVideoDuration(id, duration);
|
||||
}
|
||||
};
|
||||
|
||||
handleChangeIsPlayingState = (state, prevState) => {
|
||||
const { isActive } = state;
|
||||
const { id } = this.props;
|
||||
|
||||
if (isActive !== prevState.isActive && isActive) {
|
||||
this.props.didPlayVideo(id, this.props.video.startTime);
|
||||
}
|
||||
};
|
||||
|
||||
handleCurrentTimeChange = curr => {
|
||||
this.props.getVideoCurrentTime(this.props.id, curr, this.props.video.duration);
|
||||
};
|
||||
|
||||
handleModalOpen = () => {
|
||||
this.player.current.subscribeToStateChange(this.handleChangeIsPlayingState);
|
||||
|
||||
this.player.current.play();
|
||||
|
||||
if (this.props.video.startTime === 0) {
|
||||
const { player } = this.player.current.getState();
|
||||
player.isActive = true;
|
||||
|
||||
this.props.didPlayVideo(this.props.id, this.props.video.startTime);
|
||||
} else {
|
||||
this.player.current.pause();
|
||||
}
|
||||
};
|
||||
|
||||
handleVideoPause = () => {
|
||||
const { player } = this.player.current.getState();
|
||||
const currTime = player.currentTime;
|
||||
|
||||
this.handleCurrentTimeChange(currTime);
|
||||
this.props.didStopVideo(this.props.id, currTime);
|
||||
};
|
||||
|
||||
handleModalClose = () => {
|
||||
const { player } = this.player.current.getState();
|
||||
const paused = player.paused;
|
||||
|
||||
if (!paused) {
|
||||
this.handleVideoPause();
|
||||
}
|
||||
};
|
||||
|
||||
getVideoTime = (duration, sign) => {
|
||||
const operator = Math.floor(eval(duration + sign + 60));
|
||||
|
||||
if (operator < 10) {
|
||||
return `0${operator}`;
|
||||
}
|
||||
return operator;
|
||||
};
|
||||
|
||||
render() {
|
||||
const { video } = this.props;
|
||||
const time = isNaN(video.duration)
|
||||
? '\xA0'
|
||||
: `${Math.floor(video.duration / 60)}:${this.getVideoTime(video.duration, '%')}`;
|
||||
|
||||
return (
|
||||
<Li
|
||||
key={this.props.id}
|
||||
onClick={this.props.onClick}
|
||||
id={this.props.id}
|
||||
className={cn(video.end && 'finished')}
|
||||
>
|
||||
<div className="thumbWrapper">
|
||||
<img src={video.preview} alt="preview" />
|
||||
<div className="overlay" />
|
||||
<div className="play" />
|
||||
</div>
|
||||
<div className="txtWrapper">
|
||||
<p className="title">{video.title}</p>
|
||||
<p className="time">{time}</p>
|
||||
</div>
|
||||
|
||||
<Modal
|
||||
isOpen={video.isOpen}
|
||||
toggle={this.props.onClick} // eslint-disable-line react/jsx-handler-names
|
||||
className="videoModal"
|
||||
onOpened={this.handleModalOpen}
|
||||
onClosed={this.handleModalClose}
|
||||
>
|
||||
<ModalHeader
|
||||
toggle={this.props.onClick} // eslint-disable-line react/jsx-handler-names
|
||||
className="videoModalHeader"
|
||||
>
|
||||
{video.title}
|
||||
</ModalHeader>
|
||||
<ModalBody className="modalBodyHelper">
|
||||
<div>
|
||||
<Player
|
||||
ref={this.player}
|
||||
className="videoPlayer"
|
||||
src={video.video}
|
||||
startTime={video.startTime}
|
||||
preload="auto"
|
||||
onPause={this.handleVideoPause}
|
||||
onplay={this.videoStart}
|
||||
subscribeToStateChange={this.subscribeToStateChange}
|
||||
/>
|
||||
</div>
|
||||
</ModalBody>
|
||||
</Modal>
|
||||
|
||||
{!this.props.video.duration && (
|
||||
<div className="hiddenPlayerWrapper">
|
||||
<Player
|
||||
ref={this.hiddenPlayer}
|
||||
src={video.video}
|
||||
preload="auto"
|
||||
subscribeToStateChange={this.subscribeToStateChange}
|
||||
/>
|
||||
</div>
|
||||
)}
|
||||
</Li>
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
OnboardingVideo.defaultProps = {
|
||||
didPlayVideo: () => {},
|
||||
didStopVideo: () => {},
|
||||
getVideoCurrentTime: () => {},
|
||||
id: 0,
|
||||
onClick: () => {},
|
||||
setVideoDuration: () => {},
|
||||
video: {},
|
||||
};
|
||||
|
||||
OnboardingVideo.propTypes = {
|
||||
didPlayVideo: PropTypes.func,
|
||||
didStopVideo: PropTypes.func,
|
||||
getVideoCurrentTime: PropTypes.func,
|
||||
id: PropTypes.number,
|
||||
onClick: PropTypes.func,
|
||||
setVideoDuration: PropTypes.func,
|
||||
video: PropTypes.object,
|
||||
};
|
||||
|
||||
export default OnboardingVideo;
|
||||
@ -1,17 +1,10 @@
|
||||
import React, { useEffect, useReducer } from 'react';
|
||||
import { FormattedMessage } from 'react-intl';
|
||||
import axios from 'axios';
|
||||
import React, { useState } from 'react';
|
||||
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
|
||||
import { faQuestion, faTimes } from '@fortawesome/free-solid-svg-icons';
|
||||
import cn from 'classnames';
|
||||
import { useTracking } from '@strapi/helper-plugin';
|
||||
|
||||
import { useConfigurations } from '../../hooks';
|
||||
import formatVideoArray from './utils/formatAndStoreVideoArray';
|
||||
import StaticLinks from './StaticLinks';
|
||||
import Video from './Video';
|
||||
import Wrapper from './Wrapper';
|
||||
import reducer, { initialState } from './reducer';
|
||||
|
||||
const Onboarding = () => {
|
||||
const { showTutorials } = useConfigurations();
|
||||
@ -24,109 +17,15 @@ const Onboarding = () => {
|
||||
};
|
||||
|
||||
const OnboardingVideos = () => {
|
||||
const { trackUsage } = useTracking();
|
||||
|
||||
const [{ isLoading, isOpen, videos }, dispatch] = useReducer(reducer, initialState);
|
||||
|
||||
useEffect(() => {
|
||||
const getData = async () => {
|
||||
try {
|
||||
const { data } = await axios.get('https://strapi.io/videos', {
|
||||
timeout: 1000,
|
||||
});
|
||||
const { didWatchVideos, videos } = formatVideoArray(data);
|
||||
|
||||
dispatch({
|
||||
type: 'GET_DATA_SUCCEEDED',
|
||||
didWatchVideos,
|
||||
videos,
|
||||
});
|
||||
} catch (err) {
|
||||
console.error(err);
|
||||
dispatch({
|
||||
type: 'HIDE_VIDEO_ONBOARDING',
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
getData();
|
||||
}, []);
|
||||
|
||||
// Hide the player in case of request error
|
||||
if (isLoading) {
|
||||
return null;
|
||||
}
|
||||
const [isOpen, setIsOpen] = useState(false);
|
||||
|
||||
const handleClick = () => {
|
||||
const eventName = isOpen
|
||||
? 'didOpenGetStartedVideoContainer'
|
||||
: 'didCloseGetStartedVideoContainer';
|
||||
|
||||
dispatch({ type: 'SET_IS_OPEN' });
|
||||
trackUsage(eventName);
|
||||
setIsOpen(prev => !prev);
|
||||
};
|
||||
const handleClickOpenVideo = videoIndexToOpen => {
|
||||
dispatch({
|
||||
type: 'TOGGLE_VIDEO_MODAL',
|
||||
videoIndexToOpen,
|
||||
});
|
||||
};
|
||||
const handleUpdateVideoStartTime = (videoIndex, elapsedTime) => {
|
||||
dispatch({
|
||||
type: 'UPDATE_VIDEO_STARTED_TIME_AND_PLAYED_INFOS',
|
||||
videoIndex,
|
||||
elapsedTime,
|
||||
});
|
||||
};
|
||||
const setVideoDuration = (videoIndex, duration) => {
|
||||
dispatch({
|
||||
type: 'SET_VIDEO_DURATION',
|
||||
duration,
|
||||
videoIndex,
|
||||
});
|
||||
};
|
||||
|
||||
const hasVideos = videos.length > 0;
|
||||
const className = hasVideos ? 'visible' : 'hidden';
|
||||
|
||||
return (
|
||||
<Wrapper className={className} isOpen={isOpen}>
|
||||
<Wrapper className="visible" isOpen={isOpen}>
|
||||
<div className={cn('videosContent', isOpen ? 'shown' : 'hide')}>
|
||||
<div className="videosHeader">
|
||||
<p>
|
||||
<FormattedMessage id="app.components.Onboarding.title" />
|
||||
</p>
|
||||
<p>
|
||||
{Math.floor((videos.filter(v => v.end).length * 100) / videos.length)}
|
||||
<FormattedMessage id="app.components.Onboarding.label.completed" />
|
||||
</p>
|
||||
</div>
|
||||
<ul className="onboardingList">
|
||||
{videos.map((video, index) => (
|
||||
<Video
|
||||
key={video.id || index}
|
||||
id={index}
|
||||
video={video}
|
||||
onClick={() => handleClickOpenVideo(index)}
|
||||
setVideoDuration={(_, duration) => {
|
||||
setVideoDuration(index, duration);
|
||||
}}
|
||||
getVideoCurrentTime={(_, elapsedTime) => {
|
||||
handleUpdateVideoStartTime(index, elapsedTime);
|
||||
}}
|
||||
didPlayVideo={(_, elapsedTime) => {
|
||||
const eventName = `didPlay${index}GetStartedVideo`;
|
||||
|
||||
trackUsage(eventName, { timestamp: elapsedTime });
|
||||
}}
|
||||
didStopVideo={(_, elapsedTime) => {
|
||||
const eventName = `didStop${index}Video`;
|
||||
|
||||
trackUsage(eventName, { timestamp: elapsedTime });
|
||||
}}
|
||||
/>
|
||||
))}
|
||||
</ul>
|
||||
<StaticLinks />
|
||||
</div>
|
||||
<div className="openBtn">
|
||||
|
||||
@ -1,68 +0,0 @@
|
||||
import produce from 'immer';
|
||||
import set from 'lodash/set';
|
||||
|
||||
const initialState = {
|
||||
isLoading: true,
|
||||
isOpen: false,
|
||||
videos: [],
|
||||
};
|
||||
|
||||
const reducer = (state, action) =>
|
||||
// eslint-disable-next-line consistent-return
|
||||
produce(state, draftState => {
|
||||
switch (action.type) {
|
||||
case 'GET_DATA_SUCCEEDED': {
|
||||
draftState.isOpen = !action.didWatchVideos;
|
||||
draftState.isLoading = false;
|
||||
draftState.videos = action.videos;
|
||||
break;
|
||||
}
|
||||
|
||||
case 'SET_IS_OPEN': {
|
||||
draftState.isOpen = !state.isOpen;
|
||||
break;
|
||||
}
|
||||
case 'SET_VIDEO_DURATION': {
|
||||
set(draftState, ['videos', action.videoIndex, 'duration'], parseFloat(action.duration, 10));
|
||||
break;
|
||||
}
|
||||
case 'TOGGLE_VIDEO_MODAL': {
|
||||
const nextVideos = state.videos.map((video, index) => {
|
||||
if (index === action.videoIndexToOpen) {
|
||||
return { ...video, isOpen: !video.isOpen };
|
||||
}
|
||||
|
||||
return { ...video, isOpen: false };
|
||||
});
|
||||
draftState.videos = nextVideos;
|
||||
break;
|
||||
}
|
||||
case 'UPDATE_VIDEO_STARTED_TIME_AND_PLAYED_INFOS': {
|
||||
const nextVideos = state.videos.map((video, index) => {
|
||||
if (index !== action.videoIndex) {
|
||||
return video;
|
||||
}
|
||||
const elapsedTime = parseFloat(action.elapsedTime, 10);
|
||||
const videoDuration = parseFloat(video.duration, 10);
|
||||
const percentElapsedTime = (elapsedTime * 100) / videoDuration;
|
||||
const end = video.end === true ? video.end : percentElapsedTime > 80;
|
||||
|
||||
return { ...video, startTime: elapsedTime, end };
|
||||
});
|
||||
|
||||
// Update the local storage and make sure that the modal video does not automatically open
|
||||
localStorage.setItem(
|
||||
'videos',
|
||||
JSON.stringify(nextVideos.map(v => ({ ...v, isOpen: false })))
|
||||
);
|
||||
// Update the state
|
||||
draftState.videos = nextVideos;
|
||||
break;
|
||||
}
|
||||
default:
|
||||
return draftState;
|
||||
}
|
||||
});
|
||||
|
||||
export default reducer;
|
||||
export { initialState };
|
||||
@ -1,27 +0,0 @@
|
||||
const formatVideosArray = array => {
|
||||
const alreadyFetchedVideos = JSON.parse(localStorage.getItem('videos')) || [];
|
||||
const didWatchVideos = alreadyFetchedVideos.length === array.length;
|
||||
let videos;
|
||||
|
||||
if (!didWatchVideos) {
|
||||
videos = array.map(video => {
|
||||
return {
|
||||
...video,
|
||||
duration: null,
|
||||
end: false,
|
||||
isOpen: false,
|
||||
key: video.order,
|
||||
startTime: 0,
|
||||
};
|
||||
});
|
||||
|
||||
// Store the videos in the localStorage
|
||||
localStorage.setItem('videos', JSON.stringify(videos));
|
||||
} else {
|
||||
videos = alreadyFetchedVideos;
|
||||
}
|
||||
|
||||
return { didWatchVideos, videos };
|
||||
};
|
||||
|
||||
export default formatVideosArray;
|
||||
@ -5,6 +5,12 @@
|
||||
* @type {Object}
|
||||
*/
|
||||
const injectionZones = {
|
||||
admin: {
|
||||
// Temporary injection zone, support for the react-tour plugin in foodadvisor
|
||||
tutorials: {
|
||||
links: [],
|
||||
},
|
||||
},
|
||||
contentManager: {
|
||||
editView: { informations: [], 'right-links': [] },
|
||||
listView: { actions: [], deleteModalAdditionalInfos: [] },
|
||||
|
||||
@ -38,8 +38,8 @@
|
||||
"@fortawesome/free-brands-svg-icons": "^5.15.3",
|
||||
"@fortawesome/free-solid-svg-icons": "^5.15.3",
|
||||
"@fortawesome/react-fontawesome": "^0.1.14",
|
||||
"@strapi/helper-plugin": "3.6.5",
|
||||
"@strapi/babel-plugin-switch-ee-ce": "1.0.0",
|
||||
"@strapi/helper-plugin": "3.6.5",
|
||||
"@strapi/utils": "3.6.5",
|
||||
"axios": "^0.21.1",
|
||||
"babel-loader": "8.2.2",
|
||||
@ -123,7 +123,6 @@
|
||||
"styled-components": "^5.2.3",
|
||||
"terser-webpack-plugin": "4.2.3",
|
||||
"url-loader": "4.1.1",
|
||||
"video-react": "^0.13.2",
|
||||
"webpack": "5.36.2",
|
||||
"webpack-cli": "4.6.0",
|
||||
"webpack-dev-server": "3.11.2",
|
||||
|
||||
20
yarn.lock
20
yarn.lock
@ -1160,7 +1160,7 @@
|
||||
dependencies:
|
||||
regenerator-runtime "^0.13.4"
|
||||
|
||||
"@babel/runtime@^7.0.0", "@babel/runtime@^7.1.2", "@babel/runtime@^7.10.2", "@babel/runtime@^7.10.5", "@babel/runtime@^7.11.2", "@babel/runtime@^7.12.0", "@babel/runtime@^7.12.1", "@babel/runtime@^7.12.5", "@babel/runtime@^7.13.10", "@babel/runtime@^7.2.0", "@babel/runtime@^7.4.5", "@babel/runtime@^7.5.5", "@babel/runtime@^7.6.2", "@babel/runtime@^7.7.2", "@babel/runtime@^7.8.4", "@babel/runtime@^7.8.7", "@babel/runtime@^7.9.2":
|
||||
"@babel/runtime@^7.0.0", "@babel/runtime@^7.1.2", "@babel/runtime@^7.10.2", "@babel/runtime@^7.10.5", "@babel/runtime@^7.11.2", "@babel/runtime@^7.12.0", "@babel/runtime@^7.12.1", "@babel/runtime@^7.12.5", "@babel/runtime@^7.13.10", "@babel/runtime@^7.2.0", "@babel/runtime@^7.5.5", "@babel/runtime@^7.6.2", "@babel/runtime@^7.7.2", "@babel/runtime@^7.8.4", "@babel/runtime@^7.8.7", "@babel/runtime@^7.9.2":
|
||||
version "7.14.6"
|
||||
resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.14.6.tgz#535203bc0892efc7dec60bdc27b2ecf6e409062d"
|
||||
integrity sha512-/PCB2uJ7oM44tz8YhC4Z/6PeOKXp4K588f+5M3clr1M4zbqztlo0XEfJ2LEzj/FgwfgGcIdl8n7YYjTCI0BYwg==
|
||||
@ -6541,7 +6541,7 @@ class-utils@^0.3.5:
|
||||
isobject "^3.0.0"
|
||||
static-extend "^0.1.1"
|
||||
|
||||
classnames@^2.2.0, classnames@^2.2.3, classnames@^2.2.6, classnames@^2.3.1:
|
||||
classnames@^2.2.0, classnames@^2.2.3, classnames@^2.3.1:
|
||||
version "2.3.1"
|
||||
resolved "https://registry.yarnpkg.com/classnames/-/classnames-2.3.1.tgz#dfcfa3891e306ec1dad105d0e88f4417b8535e8e"
|
||||
integrity sha512-OlQdbZ7gLfGarSqxesMesDa5uz7KFbID8Kpq/SxIoNGDqY8lSYs0D+hhtBXhcdB3rcbXArFr7vlHheLk1voeNA==
|
||||
@ -13609,11 +13609,6 @@ lodash.templatesettings@^4.0.0:
|
||||
dependencies:
|
||||
lodash._reinterpolate "^3.0.0"
|
||||
|
||||
lodash.throttle@^4.1.1:
|
||||
version "4.1.1"
|
||||
resolved "https://registry.yarnpkg.com/lodash.throttle/-/lodash.throttle-4.1.1.tgz#c23e91b710242ac70c37f1e1cda9274cc39bf2f4"
|
||||
integrity sha1-wj6RtxAkKscMN/HhzaknTMOb8vQ=
|
||||
|
||||
lodash.topairs@^4.3.0:
|
||||
version "4.3.0"
|
||||
resolved "https://registry.yarnpkg.com/lodash.topairs/-/lodash.topairs-4.3.0.tgz#3b6deaa37d60fb116713c46c5f17ea190ec48d64"
|
||||
@ -21369,17 +21364,6 @@ vfile@^4.0.0:
|
||||
unist-util-stringify-position "^2.0.0"
|
||||
vfile-message "^2.0.0"
|
||||
|
||||
video-react@^0.13.2:
|
||||
version "0.13.9"
|
||||
resolved "https://registry.yarnpkg.com/video-react/-/video-react-0.13.9.tgz#be397fc5dd7a50908368f0a47124904b87ee3307"
|
||||
integrity sha512-nT8WjOGr3va7zJDR+OfpyqFpMrpMX3LfY3PuVyrt9ZdKDzlHgv9gQc/saAFb/pvImatzOs3+XA2GWrb5hXbTkg==
|
||||
dependencies:
|
||||
"@babel/runtime" "^7.4.5"
|
||||
classnames "^2.2.6"
|
||||
lodash.throttle "^4.1.1"
|
||||
prop-types "^15.7.2"
|
||||
redux "^4.0.1"
|
||||
|
||||
vm-browserify@^1.1.2:
|
||||
version "1.1.2"
|
||||
resolved "https://registry.yarnpkg.com/vm-browserify/-/vm-browserify-1.1.2.tgz#78641c488b8e6ca91a75f511e7a3b32a86e5dda0"
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user