diff options
| author | Jules Laplace <julescarbon@gmail.com> | 2020-07-28 00:20:51 +0200 |
|---|---|---|
| committer | Jules Laplace <julescarbon@gmail.com> | 2020-07-28 00:20:51 +0200 |
| commit | f6bc505597463cc8f593e00d74b421175a69f7f3 (patch) | |
| tree | 8e55d423573fcadc0e51f86b67b825c4c619f90e /animism-align/frontend/app/views | |
| parent | 443f0a465c720c9e70a124671872c74bc7e9bbd4 (diff) | |
some fullscreen elements fading in...
Diffstat (limited to 'animism-align/frontend/app/views')
14 files changed, 175 insertions, 19 deletions
diff --git a/animism-align/frontend/app/views/align/align.reducer.js b/animism-align/frontend/app/views/align/align.reducer.js index 1f79180..50498c5 100644 --- a/animism-align/frontend/app/views/align/align.reducer.js +++ b/animism-align/frontend/app/views/align/align.reducer.js @@ -20,7 +20,7 @@ export default function alignReducer(state = initialState, action) { // console.log(action.type, action) switch (action.type) { case types.peaks.loaded: - console.log('peaks duration:', action.data.length / 10) + // console.log('peaks duration:', action.data.length / 10) return state case types.align.set_display_setting: diff --git a/animism-align/frontend/app/views/align/components/annotations/annotationTypes/annotationTypes.utility.js b/animism-align/frontend/app/views/align/components/annotations/annotationTypes/annotationTypes.utility.js index a3c35d4..8b59e18 100644 --- a/animism-align/frontend/app/views/align/components/annotations/annotationTypes/annotationTypes.utility.js +++ b/animism-align/frontend/app/views/align/components/annotations/annotationTypes/annotationTypes.utility.js @@ -33,7 +33,7 @@ export const checkAnnotationMediaNotReady = (annotation, media) => { return (!media) || (!(annotation.settings.media_id in media)) } -export const AnnotationMediaLoading = ({ y, className, onClick, onDoubleClick }) => { +export const AnnotationMediaLoading = ({ y, media, className, onClick, onDoubleClick }) => { if (!media) { return ( <div diff --git a/animism-align/frontend/app/views/audio/audio.actions.js b/animism-align/frontend/app/views/audio/audio.actions.js index 0ee41c6..9d9727d 100644 --- a/animism-align/frontend/app/views/audio/audio.actions.js +++ b/animism-align/frontend/app/views/audio/audio.actions.js @@ -6,7 +6,7 @@ import { session } from 'app/session' const audioPlayer = document.createElement('audio') audioPlayer.src = '/static/data_store/peaks/animismA080720.mp3' audioPlayer.addEventListener('loadedmetadata', () => { - console.log('audio duration:', audioPlayer.duration) + // console.log('audio duration:', audioPlayer.duration) dispatch({ type: types.align.set_display_setting, key: 'duration', value: audioPlayer.duration }) }) audioPlayer.addEventListener('play', () => { diff --git a/animism-align/frontend/app/views/viewer/player/components.fullscreen/fullscreen.image.js b/animism-align/frontend/app/views/viewer/player/components.fullscreen/fullscreen.image.js new file mode 100644 index 0000000..c0e4b0e --- /dev/null +++ b/animism-align/frontend/app/views/viewer/player/components.fullscreen/fullscreen.image.js @@ -0,0 +1,16 @@ +import React from 'react' + +export const Image = ({ element, media, transitionDuration }) => { + const item = media.lookup[element.settings.media_id] + const style = { + transitionDuration, + backgroundImage: 'url(' + item.settings.display.url + ')', + } + return ( + <div + className='fullscreen-element image' + style={style} + > + </div> + ) +} diff --git a/animism-align/frontend/app/views/viewer/player/components.fullscreen/fullscreen.utility.js b/animism-align/frontend/app/views/viewer/player/components.fullscreen/fullscreen.utility.js new file mode 100644 index 0000000..c86236d --- /dev/null +++ b/animism-align/frontend/app/views/viewer/player/components.fullscreen/fullscreen.utility.js @@ -0,0 +1,18 @@ +import React from 'react' + +export const Curtain = ({ element, transitionDuration }) => { + // console.log(element, isEntering) + const { color } = element + const style = { + backgroundColor: color.backgroundColor, + color: color.textColor, + transitionDuration, + } + return ( + <div + className='fullscreen-element curtain' + style={style} + > + </div> + ) +} diff --git a/animism-align/frontend/app/views/viewer/player/components.fullscreen/index.js b/animism-align/frontend/app/views/viewer/player/components.fullscreen/index.js new file mode 100644 index 0000000..3befbde --- /dev/null +++ b/animism-align/frontend/app/views/viewer/player/components.fullscreen/index.js @@ -0,0 +1,19 @@ +import React from 'react' + +// import { +// MediaVideo +// } from './fullscreen.video' + +import { + Image +} from './fullscreen.image' + +import { + Curtain +} from './fullscreen.utility' + +export const fullscreenComponents = { + curtain: React.memo(Curtain), + // video: React.memo(MediaVideo), + image: React.memo(Image), +} diff --git a/animism-align/frontend/app/views/viewer/player/components.inline/index.js b/animism-align/frontend/app/views/viewer/player/components.inline/index.js index ee65641..89d1d42 100644 --- a/animism-align/frontend/app/views/viewer/player/components.inline/index.js +++ b/animism-align/frontend/app/views/viewer/player/components.inline/index.js @@ -2,15 +2,15 @@ import React from 'react' import { Paragraph, ParagraphHeading -} from './elementTypes.text' +} from './inline.text' import { MediaVideo -} from './elementTypes.video' +} from './inline.video' import { MediaImage -} from './elementTypes.image' +} from './inline.image' export const transcriptElementLookup = { paragraph: React.memo(Paragraph), diff --git a/animism-align/frontend/app/views/viewer/player/components.inline/elementTypes.image.js b/animism-align/frontend/app/views/viewer/player/components.inline/inline.image.js index f005fc0..f005fc0 100644 --- a/animism-align/frontend/app/views/viewer/player/components.inline/elementTypes.image.js +++ b/animism-align/frontend/app/views/viewer/player/components.inline/inline.image.js diff --git a/animism-align/frontend/app/views/viewer/player/components.inline/elementTypes.text.js b/animism-align/frontend/app/views/viewer/player/components.inline/inline.text.js index 8825479..8825479 100644 --- a/animism-align/frontend/app/views/viewer/player/components.inline/elementTypes.text.js +++ b/animism-align/frontend/app/views/viewer/player/components.inline/inline.text.js diff --git a/animism-align/frontend/app/views/viewer/player/components.inline/elementTypes.video.js b/animism-align/frontend/app/views/viewer/player/components.inline/inline.video.js index fe821eb..fe821eb 100644 --- a/animism-align/frontend/app/views/viewer/player/components.inline/elementTypes.video.js +++ b/animism-align/frontend/app/views/viewer/player/components.inline/inline.video.js diff --git a/animism-align/frontend/app/views/viewer/player/player.container.js b/animism-align/frontend/app/views/viewer/player/player.container.js index 1ddb5c7..9655955 100644 --- a/animism-align/frontend/app/views/viewer/player/player.container.js +++ b/animism-align/frontend/app/views/viewer/player/player.container.js @@ -1,8 +1,8 @@ import React, { Component } from 'react' import { connect } from 'react-redux' -import { floatInRange } from 'app/utils' import actions from 'app/actions' +import { floatInRange } from 'app/utils' import PlayerTranscript from './player.transcript' import PlayerFullscreen from './player.fullscreen' @@ -38,17 +38,16 @@ class PlayerContainer extends Component { actions.viewer.setCurrentSection(sections[0]) } } - render() { // const { } = this.props - const { currentSection, fullscreenTimeline } = this.props + const { currentSection } = this.props if (!currentSection) { return <div /> } // console.log(currentSection) return ( <div className='viewer-container'> <PlayerTranscript section={currentSection} /> - <PlayerFullscreen timeline={fullscreenTimeline} /> + <PlayerFullscreen /> </div> ) } @@ -57,7 +56,6 @@ class PlayerContainer extends Component { const mapStateToProps = state => ({ audio: state.audio, sections: state.viewer.sections, - fullscreenTimeline: state.viewer.fullscreenTimeline, currentSection: state.viewer.currentSection, }) diff --git a/animism-align/frontend/app/views/viewer/player/player.fullscreen.css b/animism-align/frontend/app/views/viewer/player/player.fullscreen.css index 8041c84..fb4d8af 100644 --- a/animism-align/frontend/app/views/viewer/player/player.fullscreen.css +++ b/animism-align/frontend/app/views/viewer/player/player.fullscreen.css @@ -11,4 +11,39 @@ .viewer-fullscreen.active { pointer-events: auto; user-select: auto; -}
\ No newline at end of file +} + +/* transitions */ + +.viewer-fullscreen .fade-enter { + opacity: 0; +} +.viewer-fullscreen .fade-enter.fade-enter-active { + opacity: 1; + transition-property: opacity; +} +.viewer-fullscreen .fade-exit { + opacity: 1; +} +.viewer-fullscreen .fade-exit-active { + opacity: 0; + transition-property: opacity; +} + +/* elements */ + +.viewer-fullscreen .fullscreen-element { + position: absolute; + width: 100%; + height: 100%; + top: 0; + left: 0; +} + +.viewer-fullscreen .curtain { +} + +.viewer-fullscreen .image { + background-size: cover; + background-position: center center; +} diff --git a/animism-align/frontend/app/views/viewer/player/player.fullscreen.js b/animism-align/frontend/app/views/viewer/player/player.fullscreen.js index 89052ed..47c6cd2 100644 --- a/animism-align/frontend/app/views/viewer/player/player.fullscreen.js +++ b/animism-align/frontend/app/views/viewer/player/player.fullscreen.js @@ -1,22 +1,83 @@ import React, { Component } from 'react' import { connect } from 'react-redux' +import { TransitionGroup, CSSTransition } from 'react-transition-group' import actions from 'app/actions' +import { floatInRange, floatLT } from 'app/utils' + +import { fullscreenComponents } from './components.fullscreen' class PlayerFullscreen extends Component { + state = { + elements: [], + } + componentDidMount() { + this.setCurrentElements() + } + + componentDidUpdate(prevProps) { + if (this.props.audio.play_ts === prevProps.audio.play_ts) return + this.setCurrentElements() } - + + setCurrentElements() { + const { audio, timeline } = this.props + const { play_ts } = audio + const elements = timeline.filter(element => ( + floatInRange(element.start_ts, play_ts, element.fade_out_start_ts + 0.1) + )) + this.setState({ elements }) + } + render() { - const { } = this.props + const { audio, media } = this.props + const { play_ts } = audio + const { elements } = this.state + // console.log(elements, play_ts) return ( <div className="viewer-fullscreen"> + <TransitionGroup> + {elements.map(element => { + if (!(element.type in fullscreenComponents)) { + return null + } + const isEntering = floatInRange(element.start_ts, play_ts, element.fade_in_end_ts) + const FullscreenComponent = fullscreenComponents[element.type] + const transitionDuration = (isEntering ? (1000 * element.fadeInDuration) : (1000 * element.fadeOutDuration)) + 'ms' + return ( + <CSSTransition + key={element.index} + classNames="fade" + timeout={{ + enter: element.fadeInDuration * 1000, + exit: element.fadeOutDuration * 1000, + }} + component={FirstChild} + > + <FullscreenComponent + element={element} + media={media} + transitionDuration={transitionDuration} + /> + </CSSTransition> + ) + })} + </TransitionGroup> </div> ) } } +const FirstChild = (props) => { + const childrenArray = React.Children.toArray(props.children); + return childrenArray[0] || null; +} + const mapStateToProps = state => ({ + audio: state.audio, + media: state.media.index, + timeline: state.viewer.fullscreenTimeline, }) export default connect(mapStateToProps)(PlayerFullscreen) diff --git a/animism-align/frontend/app/views/viewer/viewer.actions.js b/animism-align/frontend/app/views/viewer/viewer.actions.js index 836c677..a456646 100644 --- a/animism-align/frontend/app/views/viewer/viewer.actions.js +++ b/animism-align/frontend/app/views/viewer/viewer.actions.js @@ -3,6 +3,7 @@ import { store, history, dispatch } from 'app/store' import { MEDIA_ANNOTATION_TYPES, MEDIA_LABEL_TYPES, TEXT_ANNOTATION_TYPES, UTILITY_ANNOTATION_TYPES, + CURTAIN_COLOR_LOOKUP, } from 'app/constants' import { buildParagraphs } from 'app/utils/transcript.utils' import { annotationFadeTimings } from 'app/utils/annotation.utils' @@ -26,6 +27,7 @@ export const loadSections = () => dispatch => { // keep tally of all media, so that we can display them with correct IDs in the checklist let mediaIndex = 0 + let eventIndex = 0 // dedupe the labels that we see in each section let currentMediaLabels = {} @@ -96,7 +98,7 @@ export const loadSections = () => dispatch => { // build timeline of fullscreen events if (UTILITY_ANNOTATION_TYPES.has(annotation.type) || annotation.settings.fullscreen) { - const event = makeFullscreenEvent(annotation) + const event = makeFullscreenEvent(eventIndex++, annotation) fullscreenTimeline.push(event) } @@ -121,15 +123,22 @@ export const loadSections = () => dispatch => { } } - console.log(sections) - console.log(fullscreenTimeline) + // console.log(sections) + // console.log(fullscreenTimeline) dispatch({ type: types.viewer.load_sections, sections, fullscreenTimeline }) } -const makeFullscreenEvent = annotation => { +const makeFullscreenEvent = (index, annotation) => { const timing = annotationFadeTimings(annotation) const event = { - annotation, timing + ...timing, + annotation, + index, + settings: annotation.settings, + type: annotation.type, + } + if (event.type === 'curtain') { + event.color = CURTAIN_COLOR_LOOKUP[annotation.settings.color] || CURTAIN_COLOR_LOOKUP.white } return event } |
