mirror of
https://github.com/zoriya/v10.git
synced 2026-08-16 02:45:09 +00:00
feat: add media API + HLS video components (#507)
This commit is contained in:
@@ -0,0 +1,27 @@
|
||||
import { HlsMedia } from '@videojs/core/dom/media/hls';
|
||||
import type { PropsWithChildren, VideoHTMLAttributes } from 'react';
|
||||
import { forwardRef, useEffect, useMemo } from 'react';
|
||||
import { useMediaRegistration } from '../../player/context';
|
||||
import { attachMediaElement } from '../../utils/attach-media-element';
|
||||
import { mediaProps } from '../../utils/media-props';
|
||||
import { useComposedRefs } from '../../utils/use-composed-refs';
|
||||
|
||||
export type HlsVideoProps = PropsWithChildren<VideoHTMLAttributes<HTMLVideoElement>>;
|
||||
|
||||
export const HlsVideo = forwardRef<HTMLVideoElement, HlsVideoProps>(({ children, ...props }, ref) => {
|
||||
const mediaApi = useMemo(() => new HlsMedia(), []);
|
||||
const setMedia = useMediaRegistration();
|
||||
|
||||
useEffect(() => {
|
||||
setMedia?.(mediaApi);
|
||||
}, [mediaApi, setMedia]);
|
||||
|
||||
const composedRef = useComposedRefs(attachMediaElement(mediaApi), ref);
|
||||
return (
|
||||
<video ref={composedRef} {...mediaProps(mediaApi, props)}>
|
||||
{children}
|
||||
</video>
|
||||
);
|
||||
});
|
||||
|
||||
export default HlsVideo;
|
||||
@@ -0,0 +1,13 @@
|
||||
import type { MediaApiProxy } from '@videojs/core/dom';
|
||||
|
||||
export function attachMediaElement<T extends HTMLVideoElement>(media: MediaApiProxy): (element: T | null) => void {
|
||||
return (element: T | null) => {
|
||||
if (element) {
|
||||
media.attach(element);
|
||||
} else {
|
||||
media.detach();
|
||||
}
|
||||
// React 19+ accepts a cleanup function as the return value
|
||||
return () => media.detach();
|
||||
};
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
import type { MediaApi } from '@videojs/core/dom';
|
||||
import type { VideoHTMLAttributes } from 'react';
|
||||
|
||||
interface VideoProps extends VideoHTMLAttributes<HTMLVideoElement> {}
|
||||
|
||||
export function mediaProps(media: MediaApi, props: VideoProps) {
|
||||
const { src, ...remainingProps } = props;
|
||||
|
||||
// Preload can still be passed as a prop to the native media element
|
||||
if (props.preload && media.preload !== props.preload) {
|
||||
media.preload = props.preload as '' | 'none' | 'metadata' | 'auto';
|
||||
}
|
||||
|
||||
if (media.src !== src) {
|
||||
media.src = src ?? '';
|
||||
}
|
||||
|
||||
// The remaining props are passed to the native media element
|
||||
return remainingProps;
|
||||
}
|
||||
Reference in New Issue
Block a user