-
介绍
- 发现谷歌浏览器默认可以直接预览部分格式的文件,例如pdf,png,txt...但是开发的时候发现一个问题,给的二进制流文件需要加一个Blob对应的type才能预览,后端提供的接口并没有给文件Blob对应的type,所以只能前端加上type,才能正常预览
-
实现步骤
- 步骤一:获取文件后缀,获取正确的Blob对应的type
- 步骤二:谷歌浏览器是否支持预览,不支持预览则下载该文件
-
代码解释
获取Blob对应的type
/**
* 可预览列表
* 谷歌浏览器 可以直接预览部分文件
* 但是转化的 blob 对象 需要提供正确的type
* @param name 带后缀的文件名
* @returns
*/
export const fileNameViewer = (name: string): string => {
let type = getFileExtension(name)
const typeMap = {
pdf: 'application/pdf',
png: 'image/png',
jpg: 'image/jpeg',
jpeg: 'image/jpeg',
txt: 'text/plain;charset=utf-8',
json: 'application/json',
mp3: 'audio/mpeg'
}
return typeMap[type] || 'Unknown'
}
/**
* 获取文件名后缀
* @param fileName 文件名
* @returns 后缀
*/
function getFileExtension(fileName: string): string {
const lastDotIndex = fileName.lastIndexOf('.')
// 检查是否存在点号,且不在字符串的开头
if (lastDotIndex !== -1 && lastDotIndex < fileName.length - 1) {
return fileName.slice(lastDotIndex + 1)
} else {
return '' // 文件名中没有后缀
}
}
预览文件
/**
* @param data 二进制流文件
* @param name 文件名
*/
export const fileView = (data, name) => {
let type = fileNameViewer(name)
// 预览 如果 文件后缀不支持预览,则直接下载
if (type !== 'Unknown') {
// 加 type, 没有类型的话,
const blob = new Blob([data], { type })
let url = URL.createObjectURL(blob)
window.open(url, '_blank')
} else {
fileDownLoad(data, name)
}
}
/**
* 文件下载
* @param data blob二进制流
* @param name 文件名
* @returns
*/
export const fileDownLoad = (data, name) => {
if (!data) {
console.log('data不能为空')
return
}
if (!name) {
console.log('name不能为空')
return
}
const a = document.createElement('a')
a.download = name
a.style.display = 'none'
let url = URL.createObjectURL(data)
a.href = url
document.body.appendChild(a)
a.click()
URL.revokeObjectURL(a.href)
document.body.removeChild(a)
elMessage('导出成功...')
}
-
实际应用
const onPreview = async (UploadFile) => {
try {
let name = UploadFile.fileName || UploadFile.name
let id = UploadFile.response.data.id
// 这边接口获取的就是blob文件流
let { data } = await fileDownloadFile({ id })
// 调用预览方法
fileView(data, name)
} catch (error) {
console.log('🐷 🐽 onPreview 🐽 error👉👉👉', error)
}
}