如何在HTML5画布上使用更好的插值来缩放图像?
如何在HTML5画布上使用更好的插值来缩放图像?
首先,我想做什么?
我有一个查看图片的应用程序。它使用canvas元素渲染图像。您可以放大,缩小和拖动图像。这部分目前运行得非常完美。
但是假设我有一张有很多文字的图像。它的分辨率是1200x1700,而我的canvas为1200x900。初始状态下,当缩小时,它导致渲染分辨率约为560x800。
我的实际绘图如下所示:
drawImage(src,srcOffsetX,srcOffsetY,sourceViewWidth,sourceViewHeight, destOffsetX,destOffsetY,destWidth,destHeight);
这张图上的小文字看起来非常糟糕,特别是与其他图片查看器(如IrfanView)或甚至是html 元素相比。
我发现浏览器的插值算法是这个问题的原因。比较不同的浏览器显示,Chrome呈现的缩放图像最好,但仍然不够好。
好吧,我在整个互联网上搜索了4-5个小时,但没有找到我需要的东西。我找到了“imageSmoothingEnabled”选项,“image-rendering”CSS样式,但无法在canvas上使用,以及在浮点位置上进行渲染和许多插值算法的JavaScript实现(这些实现对我的目的来说太慢了)。
您可能会问我为什么告诉您所有这些:为了节省您给我已经知道的答案所需的时间。
那么:有没有任何好的快速方法来改善插值?我目前的想法是创建一个图像对象,重新调整大小(因为缩放时img具有良好的插值!),然后再渲染它。不幸的是,应用img.width似乎只影响显示的宽度...
更新:感谢Simon,我解决了我的问题。
这是我使用的动态缩放算法。请注意,它保持宽高比,高度参数仅用于避免更多的浮点计算。它目前只进行缩小。
scale(destWidth, destHeight){ var start = new Date().getTime(); var scalingSteps = 0; var ctx = this._sourceImageCanvasContext; var curWidth = this._sourceImageWidth; var curHeight = this._sourceImageHeight; var lastWidth = this._sourceImageWidth; var lastHeight = this._sourceImageHeight; var end = false; var scale=0.75; while(end==false){ scalingSteps +=1; curWidth *= scale; curHeight *= scale; if(curWidth < destWidth){ curWidth = destWidth; curHeight = destHeight; end=true; } ctx.drawImage(this._sourceImageCanvas, 0, 0, Math.round(lastWidth), Math.round(lastHeight), 0, 0, Math.round(curWidth), Math.round(curHeight)); lastWidth = curWidth; lastHeight = curHeight; } var endTime =new Date().getTime(); console.log("execution time: "+ ( endTime - start) + "ms. scale per frame: "+scale+ " scaling step count: "+scalingSteps); }