mirror of
https://github.com/zhw2590582/ArtPlayer.git
synced 2026-10-28 18:41:20 -08:00
refactor(vtt-thumbnail): [PKG-VTT-THUMB-04] type runtime data and resource boundaries
This commit is contained in:
1 parent
80588a3046
commit
7f2906ae52
22 files changed
+2940
-75
No files matched your search
@@ -0,0 +1,68 @@
|
||||
import type { Events } from 'artplayer'
|
||||
import type { PreviewOptions, StyleKey, Thumbnail } from './types'
|
||||
import { findThumbnail } from './parseVtt'
|
||||
|
||||
export default function createPreview({ lifetime, thumbnails, progress, duration, setStyle, isMobile }: PreviewOptions) {
|
||||
let timer: ReturnType<typeof setTimeout> | null = null
|
||||
let generation = 0
|
||||
lifetime.own(() => {
|
||||
generation++
|
||||
if (timer !== null) {
|
||||
const previous = timer
|
||||
timer = null
|
||||
clearTimeout(previous)
|
||||
}
|
||||
})
|
||||
function style(control: HTMLElement, key: StyleKey, value: string | number) {
|
||||
if (!lifetime.closed)
|
||||
setStyle<keyof CSSStyleDeclaration>(control, key, value)
|
||||
}
|
||||
function show(control: HTMLElement, cue: Thumbnail, width: number) {
|
||||
style(control, 'backgroundImage', `url(${cue.url})`)
|
||||
style(control, 'height', `${cue.h}px`)
|
||||
style(control, 'width', `${cue.w}px`)
|
||||
style(control, 'backgroundPosition', `-${cue.x}px -${cue.y}px`)
|
||||
if (width <= Number(cue.w) / 2)
|
||||
style(control, 'left', 0)
|
||||
else if (width > progress.clientWidth - Number(cue.w) / 2)
|
||||
style(control, 'left', `${progress.clientWidth - Number(cue.w)}px`)
|
||||
else
|
||||
style(control, 'left', `${width - Number(cue.w) / 2}px`)
|
||||
}
|
||||
return (control: HTMLElement) => async (type: Events['setBar'][0], percentage: number, event?: Event) => {
|
||||
if (lifetime.closed)
|
||||
return
|
||||
const dragging = type === 'played' && event && isMobile
|
||||
if (type !== 'hover' && !dragging)
|
||||
return
|
||||
const width = progress.clientWidth * percentage
|
||||
const second = percentage * duration()
|
||||
style(control, 'display', 'flex')
|
||||
if (lifetime.closed)
|
||||
return
|
||||
const cue = findThumbnail(thumbnails, second)
|
||||
if (!cue)
|
||||
return style(control, 'display', 'none')
|
||||
if (width > 0 && width < progress.clientWidth)
|
||||
show(control, cue, width)
|
||||
else if (!isMobile)
|
||||
style(control, 'display', 'none')
|
||||
if (dragging && !lifetime.closed) {
|
||||
const current = ++generation
|
||||
if (timer !== null)
|
||||
clearTimeout(timer)
|
||||
if (lifetime.closed)
|
||||
return
|
||||
const id = setTimeout(() => {
|
||||
if (current !== generation || lifetime.closed)
|
||||
return
|
||||
timer = null
|
||||
style(control, 'display', 'none')
|
||||
}, 500)
|
||||
if (lifetime.closed || current !== generation)
|
||||
clearTimeout(id)
|
||||
else
|
||||
timer = id
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in new issue
Block a user