chore: add fallback loading strategy for video previews
This commit is contained in:
@@ -10,6 +10,7 @@ import { PreviewableTextFileTypes, RequiresNativeFilePreview } from './isFilePre
|
||||
import TextPreview from './TextPreview'
|
||||
import { parseFileName } from '@standardnotes/filepicker'
|
||||
import { sanitizeFileName } from '@standardnotes/ui-services'
|
||||
import VideoPreview from './VideoPreview'
|
||||
|
||||
type Props = {
|
||||
application: WebApplication
|
||||
@@ -89,11 +90,7 @@ const PreviewComponent: FunctionComponent<Props> = ({
|
||||
}
|
||||
|
||||
if (file.mimeType.startsWith('video/')) {
|
||||
return (
|
||||
<video className="h-full w-full" controls autoPlay>
|
||||
<source src={objectUrl} type={file.mimeType} />
|
||||
</video>
|
||||
)
|
||||
return <VideoPreview file={file} filesController={application.filesController} objectUrl={objectUrl} />
|
||||
}
|
||||
|
||||
if (file.mimeType.startsWith('audio/')) {
|
||||
|
||||
@@ -0,0 +1,78 @@
|
||||
import { FilesController } from '@/Controllers/FilesController'
|
||||
import { NoPreviewIllustration } from '@standardnotes/icons'
|
||||
import { FileItem } from '@standardnotes/snjs'
|
||||
import { useState } from 'react'
|
||||
import Button from '../Button/Button'
|
||||
import { FileItemActionType } from '../AttachedFilesPopover/PopoverFileItemAction'
|
||||
|
||||
type Props = {
|
||||
file: FileItem
|
||||
filesController: FilesController
|
||||
objectUrl: string
|
||||
}
|
||||
|
||||
/**
|
||||
* Some formats require using the <source/> tag with the type attribute
|
||||
* because we use object URLs. However some formats seem to only work
|
||||
* when not using the <source/> tag.
|
||||
* We show an error message if neither works.
|
||||
*/
|
||||
const VideoPreview = ({ file, filesController, objectUrl }: Props) => {
|
||||
const [showError, setShowError] = useState(false)
|
||||
const [shouldTryFallback, setShouldTryFallback] = useState(false)
|
||||
|
||||
if (showError) {
|
||||
return (
|
||||
<div className="flex flex-grow flex-col items-center justify-center">
|
||||
<NoPreviewIllustration className="mb-4 h-30 w-30" />
|
||||
<div className="mb-2 text-base font-bold">This video can't be previewed.</div>
|
||||
<div className="mb-4 max-w-[35ch] text-center text-sm text-passive-0">
|
||||
To view this file, download it and open it using another application.
|
||||
</div>
|
||||
<Button
|
||||
primary
|
||||
onClick={() => {
|
||||
filesController
|
||||
.handleFileAction({
|
||||
type: FileItemActionType.DownloadFile,
|
||||
payload: { file },
|
||||
})
|
||||
.catch(console.error)
|
||||
}}
|
||||
>
|
||||
Download
|
||||
</Button>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
if (shouldTryFallback) {
|
||||
return (
|
||||
<video
|
||||
className="h-full w-full"
|
||||
controls
|
||||
autoPlay
|
||||
src={objectUrl}
|
||||
onError={() => {
|
||||
setShowError(true)
|
||||
setShouldTryFallback(false)
|
||||
}}
|
||||
/>
|
||||
)
|
||||
}
|
||||
|
||||
return (
|
||||
<video
|
||||
className="h-full w-full"
|
||||
controls
|
||||
autoPlay
|
||||
onError={() => {
|
||||
setShouldTryFallback(true)
|
||||
}}
|
||||
>
|
||||
<source src={objectUrl} type={file.mimeType} />
|
||||
</video>
|
||||
)
|
||||
}
|
||||
|
||||
export default VideoPreview
|
||||
Reference in New Issue
Block a user