- 添加批量导入页面支持Excel和图片上传解析 - 实现移动端批量导入功能界面和交互 - 集成图片压缩上传功能提升用户体验 - 增加批量任务状态管理和进度跟踪 - 完善批量数据确认和执行流程 - 配置环境变量支持Docker部署 - 提高文件上传大小限制增强实用性 - 优化系统配置以适应生产环境需求
78 lines
2.3 KiB
JavaScript
78 lines
2.3 KiB
JavaScript
function isImageFile(file) {
|
|
return file && file.type && file.type.indexOf('image/') === 0
|
|
}
|
|
|
|
function canvasToBlob(canvas, type, quality) {
|
|
return new Promise(resolve => {
|
|
if (!canvas.toBlob) {
|
|
resolve(null)
|
|
return
|
|
}
|
|
canvas.toBlob(blob => resolve(blob), type, quality)
|
|
})
|
|
}
|
|
|
|
function loadImage(file) {
|
|
return new Promise((resolve, reject) => {
|
|
const reader = new FileReader()
|
|
reader.onload = event => {
|
|
const image = new Image()
|
|
image.onload = () => resolve(image)
|
|
image.onerror = reject
|
|
image.src = event.target.result
|
|
}
|
|
reader.onerror = reject
|
|
reader.readAsDataURL(file)
|
|
})
|
|
}
|
|
|
|
export async function compressImageForUpload(file, options = {}) {
|
|
const maxSize = options.maxSize || 3 * 1024 * 1024
|
|
const maxWidth = options.maxWidth || 1600
|
|
const maxHeight = options.maxHeight || 1600
|
|
const outputType = options.outputType || 'image/jpeg'
|
|
const minQuality = options.minQuality || 0.55
|
|
|
|
if (!isImageFile(file) || typeof FileReader === 'undefined' || typeof document === 'undefined') {
|
|
return file
|
|
}
|
|
|
|
try {
|
|
const image = await loadImage(file)
|
|
let scale = Math.min(maxWidth / image.width, maxHeight / image.height, 1)
|
|
let quality = options.quality || 0.82
|
|
let bestBlob = null
|
|
|
|
for (let i = 0; i < 7; i++) {
|
|
const width = Math.max(1, Math.round(image.width * scale))
|
|
const height = Math.max(1, Math.round(image.height * scale))
|
|
const canvas = document.createElement('canvas')
|
|
canvas.width = width
|
|
canvas.height = height
|
|
const context = canvas.getContext('2d')
|
|
context.fillStyle = '#ffffff'
|
|
context.fillRect(0, 0, width, height)
|
|
context.drawImage(image, 0, 0, width, height)
|
|
|
|
const blob = await canvasToBlob(canvas, outputType, quality)
|
|
if (!blob) {
|
|
return file
|
|
}
|
|
bestBlob = blob
|
|
if (blob.size <= maxSize) {
|
|
break
|
|
}
|
|
scale = scale * 0.82
|
|
quality = Math.max(minQuality, quality - 0.08)
|
|
}
|
|
|
|
if (!bestBlob || bestBlob.size >= file.size) {
|
|
return file
|
|
}
|
|
const fileName = file.name ? file.name.replace(/\.[^.]+$/, '.jpg') : 'upload.jpg'
|
|
return new File([bestBlob], fileName, { type: outputType, lastModified: Date.now() })
|
|
} catch (error) {
|
|
return file
|
|
}
|
|
}
|