如何使用async/await重构Quill图片文件缩放代码以正确获取处理后的Blob对象
解决Quill编辑器图片缩放后异步获取Blob的问题
我懂你碰到的麻烦了——你的代码里FileReader、图片加载还有canvas.toBlob全都是异步操作,当你执行第二个console.log(newFile)的时候,这些异步任务压根还没跑完,所以才拿不到正确的Blob对象。咱们把这些异步逻辑包装成Promise,就能用async/await来理顺执行顺序,确保能拿到处理好的文件再往下走。
改造后的完整代码
async handleImageAdded(file, Editor, cursorLocation, resetUploader) { // 把图片缩放逻辑封装成返回Promise的函数 const resizeImage = (file) => { return new Promise((resolve, reject) => { const reader = new FileReader(); reader.onload = function (e) { const img = document.createElement("img"); img.onload = function () { const canvas = document.createElement("canvas"); const ctx = canvas.getContext("2d"); // 这里按你需求设置缩放尺寸,也可以改成按比例缩放哦 canvas.width = 300; canvas.height = 300; ctx.drawImage(img, 0, 0, canvas.width, canvas.height); // canvas.toBlob是异步的,所以也要用Promise包裹 canvas.toBlob(blob => { if (!blob) { reject(new Error("Failed to create blob from canvas")); return; } // 把Blob转成File对象,保留原文件的名称和类型,方便服务器处理 const resizedFile = new File([blob], file.name, { type: blob.type }); resolve(resizedFile); }, file.type); // 指定输出的MIME类型,和原文件一致 }; img.onerror = reject; img.src = e.target.result; }; reader.onerror = reject; reader.readAsDataURL(file); }); }; try { // 等待图片缩放完成,拿到处理后的文件 const resizedFile = await resizeImage(file); console.log(resizedFile); // 现在这里能输出正确的Blob/File对象了 // 接下来就可以把resizedFile发送到服务器 // 比如用fetch或者axios: // const formData = new FormData(); // formData.append('image', resizedFile); // const response = await fetch('/your-upload-endpoint', { method: 'POST', body: formData }); // ...处理服务器响应 } catch (error) { console.error("图片处理失败:", error); resetUploader(); // 处理失败时重置上传器 } }
关键改动说明
- 封装Promise:把所有异步回调(FileReader、img.onload、canvas.toBlob)都放进一个Promise里,这样就能用
await等待整个图片处理流程完成。 - 转成File对象:Blob没有文件名、文件类型这些元数据,转成File对象后更方便服务器识别和处理,同时保留原文件的名称和MIME类型。
- 错误处理:加上了
try/catch和onerror回调,能捕捉图片读取、加载或缩放过程中出现的错误,避免程序崩溃。 - 执行顺序保证:通过
await确保只有当图片缩放完成拿到结果后,才会执行后续的控制台日志和服务器上传逻辑。
这样改造后,你就能确保console.log输出正确的处理后文件,再顺利发送到服务器啦。
内容的提问来源于stack exchange,提问作者Pavel Shepelenko
相关产品推荐
相关产品推荐

