Skip to content

Commit

Permalink
♻️ Use JSS for video (#30298)
Browse files Browse the repository at this point in the history
This is a port of video-autoplay.css.

No CSS def in an AMP component since there's not a PreactBaseElement that uses VideoWrapper yet (see #30280)
  • Loading branch information
alanorozco committed Sep 21, 2020
1 parent 14db3d2 commit 71cd740
Show file tree
Hide file tree
Showing 3 changed files with 118 additions and 27 deletions.
102 changes: 102 additions & 0 deletions extensions/amp-video/1.0/autoplay.jss.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,102 @@
/**
* Copyright 2020 The AMP HTML Authors. All Rights Reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS-IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

import {createUseStyles} from 'react-jss';

const eq = {
pointerEvents: 'none !important',
alignItems: 'flex-end',
bottom: 7,
height: 12,
opacity: 0.8,
overflow: 'hidden',
position: 'absolute',
right: 7,
width: 20,
zIndex: 1,
display: 'flex',
};

const eqCol = {
flex: 1,
height: '100%',
marginRight: 1,
position: 'relative',
'&:before, &:after': {
animation: '0s linear infinite alternate $eq-animation',
backgroundColor: '#FAFAFA',
height: '100%',
position: 'absolute',
width: '100%',
willChange: 'transform',
animationPlayState: 'paused',
},
'&:nth-child(1)': {
'&:before, &:after': {
transform: 'translateY(60%)',
animationDuration: '0.3s',
},
'&:after': {
animationDuration: '0.45s',
},
},
'&:nth-child(2)': {
'&:before, &:after': {
transform: 'translateY(30%)',
animationDuration: '0.5s',
},
'&:after': {
animationDuration: '0.4s',
},
},
'&:nth-child(3)': {
'&:before, &:after': {
transform: 'translateY(70%)',
animationDuration: '0.3s',
},
'&:after': {
animationDuration: '0.35s',
},
},
'&:nth-child(4)': {
'&:before, &:after': {
transform: 'translateY(50%)',
animationDuration: '0.4s',
},
'&:after': {
animationDuration: '0.25s',
},
},
};

const eqPlaying = {
// These are same as `eqCol`
'& > div:before, & > div:after': {animationPlayState: 'running'},
};

const JSS = {
eq,
eqPlaying,
eqCol,
'@keyframes eq-animation': {
'0%': {transform: 'translateY(100%)'},
'100%': {transform: 'translateY(0)'},
},
};

// useStyles gets replaced for AMP builds via `babel-plugin-transform-jss`.
// eslint-disable-next-line local/no-export-side-effect
export const useStyles = createUseStyles(JSS);
12 changes: 8 additions & 4 deletions extensions/amp-video/1.0/test/test-video-wrapper.js
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,8 @@ import {forwardRef} from '../../../../src/preact/compat';
import {mount} from 'enzyme';
import {omit} from '../../../../src/utils/object';

import {useStyles as useAutoplayStyles} from '../autoplay.jss';

describes.sandboxed('VideoWrapper Preact component', {}, (env) => {
let intersectionObserverObserved;
let intersectionObserverCallback;
Expand Down Expand Up @@ -160,27 +162,29 @@ describes.sandboxed('VideoWrapper Preact component', {}, (env) => {
});

describe('Autoplay', () => {
const classes = useAutoplayStyles();

it('should render icon', () => {
const wrapper = mount(
<VideoWrapper component={TestPlayer} controls autoplay />
);
expect(wrapper.exists('.amp-video-eq')).to.be.true;
expect(wrapper.exists(`.${classes.eq}`)).to.be.true;
});

it('should remove icon when clicking autoplay mask', () => {
const wrapper = mount(
<VideoWrapper component={TestPlayer} controls autoplay />
);
expect(wrapper.exists('.amp-video-eq')).to.be.true;
expect(wrapper.exists(`.${classes.eq}`)).to.be.true;
wrapper.find('[role="button"]').simulate('click');
expect(wrapper.exists('.amp-video-eq')).to.be.false;
expect(wrapper.exists(`.${classes.eq}`)).to.be.false;
});

it('should not render icon when setting "noaudio"', () => {
const wrapper = mount(
<VideoWrapper component={TestPlayer} controls noaudio autoplay />
);
expect(wrapper.exists('.amp-video-eq')).to.be.false;
expect(wrapper.exists(`.${classes.eq}`)).to.be.false;
});

it('should not render mask without controls', () => {
Expand Down
31 changes: 8 additions & 23 deletions extensions/amp-video/1.0/video-wrapper.js
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,6 @@ import * as Preact from '../../../src/preact';
import {ContainWrapper} from '../../../src/preact/component';
import {Deferred} from '../../../src/utils/promise';
import {MIN_VISIBILITY_RATIO_FOR_AUTOPLAY} from '../../../src/video-interface';
import {cssText as autoplayCss} from '../../../build/video-autoplay.css';
import {dict} from '../../../src/utils/object';
import {fillContentOverlay, fillStretch} from './video-wrapper.css';
import {once} from '../../../src/utils/function';
Expand All @@ -28,6 +27,7 @@ import {
parseSchemaImage,
setMediaSession,
} from '../../../src/mediasession-helper';
import {useStyles as useAutoplayStyles} from './autoplay.jss';
import {
useCallback,
useLayoutEffect,
Expand Down Expand Up @@ -173,6 +173,8 @@ function Autoplay({
play,
pause,
}) {
const classes = useAutoplayStyles();

useMountEffect(() => {
const observer = new IntersectionObserver(
(entries) => {
Expand All @@ -195,16 +197,7 @@ function Autoplay({
return (
<>
{displayIcon && (
<div
className={`amp-video-eq ${playing ? `amp-video-eq-play` : ''}`}
// Legacy AMP (VideoManager) toggles this icon by a CSS selector.
// We need display: flex here to override VideoManager's default
// styling, since we're rendering this only when necessary, e.g.
// visible.
// TODO(alanorozco): We can simplify by also removing/adding element
// in legacy AMP (or if we no longer need the VideoManager).
style={{'display': 'flex'}}
>
<div className={`${classes.eq} ${playing ? classes.eqPlaying : ''}`}>
<AutoplayIconContent />
</div>
)}
Expand All @@ -216,22 +209,14 @@ function Autoplay({
onClick={onOverlayClick}
></div>
)}

{/* TODO(wg-bento): Global styling.
https://github.com/ampproject/wg-bento/issues/7 */}
<style>{autoplayCss}</style>
</>
);
}

/**
* @return {!PreactDef.Renderable}
*/
const AutoplayIconContent = once(() =>
[1, 2, 3, 4].map((i) => (
<div className="amp-video-eq-col" key={i}>
<div className={`amp-video-eq-filler amp-video-eq-${i}-1`}></div>
<div className={`amp-video-eq-filler amp-video-eq-${i}-2`}></div>
</div>
))
);
const AutoplayIconContent = once(() => {
const classes = useAutoplayStyles();
return [1, 2, 3, 4].map((i) => <div className={classes.eqCol} key={i}></div>);
});

0 comments on commit 71cd740

Please sign in to comment.