我使用html5 canvas元素在浏览器中调整图像大小.事实证明,质量非常低.我发现:在缩放<canvas>时禁用插值,但它无助于提高质量.
下面是我的css和js代码,以及用Photoshop调整并在画布API中缩放的图像.
在浏览器中缩放图像时,我需要做些什么才能获得最佳质量?
注意:我想将大图像缩小到一个小图像,修改画布中的颜色并将结果从画布发送到服务器.
CSS:
canvas, img {
image-rendering: optimizeQuality;
image-rendering: -moz-crisp-edges;
image-rendering: -webkit-optimize-contrast;
image-rendering: optimize-contrast;
-ms-interpolation-mode: nearest-neighbor;
}
Run Code Online (Sandbox Code Playgroud)
JS:
var $img = $('<img>');
var $originalCanvas = $('<canvas>');
$img.load(function() {
var originalContext = $originalCanvas[0].getContext('2d');
originalContext.imageSmoothingEnabled = false;
originalContext.webkitImageSmoothingEnabled = false;
originalContext.mozImageSmoothingEnabled = false;
originalContext.drawImage(this, 0, 0, 379, 500);
});
Run Code Online (Sandbox Code Playgroud)
使用photoshop调整图像大小:

图像在画布上调整大小:

编辑:
我尝试按照以下方案中提出的多个步骤进行缩减:
调整HTML5画布和 Html5画布中的图像大小drawImage:如何应用抗锯齿
这是我用过的功能:
function resizeCanvasImage(img, canvas, maxWidth, maxHeight) {
var imgWidth = img.width,
imgHeight = img.height;
var ratio = 1, ratio1 …Run Code Online (Sandbox Code Playgroud) 请看下面的例子:
var canvas = document.getElementById("canvas");
var ctx = canvas.getContext("2d");
img = new Image();
img.onload = function(){
canvas.width = 400;
canvas.height = 150;
ctx.drawImage(img, 0, 0, img.width, img.height, 0, 0, 400, 150);
}
img.src = "http://openwalls.com/image/1734/colored_lines_on_blue_background_1920x1200.jpg";
Run Code Online (Sandbox Code Playgroud)
如您所见,虽然据说drawImage会自动应用抗锯齿,但图像不会消除锯齿.我尝试了很多不同的方法,但似乎没有用.你能告诉我如何获得抗锯齿图像吗?谢谢.
如何在画布上打开消除锯齿功能.
以下代码未绘制平滑线:
var context = mainCanv.getContext("2d");
if (context) {
context.moveTo(0,0);
context.lineTo(100,75);
context.strokeStyle = "#df4b26";
context.lineWidth = 3;
context.stroke();
}
Run Code Online (Sandbox Code Playgroud) 可能重复:
如何在没有抗锯齿的情况下拉伸图像
在放大图像时是否可以以任何方式禁用抗锯齿?
现在,我得到的东西看起来像这样:

使用以下css代码:
#bib { width:104px;height:104px;background-image:url(/media/buttonart_back.png);background-size:1132px 1360px;
background-repeat:no-repeat;}
Run Code Online (Sandbox Code Playgroud)
我想要的是这样的:

简而言之,任何CSS标志都可以在放大图像时禁用抗锯齿,保留硬边.
欢迎任何javascript hacks或类似的东西.
(是的,我知道php和imagemagick也可以这样做,但更喜欢基于CSS的解决方案.)
更新 以下建议:
image-rendering: -moz-crisp-edges;
image-rendering: -moz-crisp-edges;
image-rendering: -o-crisp-edges;
image-rendering: -webkit-optimize-contrast;
-ms-interpolation-mode: nearest-neighbor;
Run Code Online (Sandbox Code Playgroud)
但这似乎不适用于背景图像.
首先:我想做什么?
我有一个查看图像的应用程序.它使用canvas元素渲染图像.你可以放大,你可以缩小,你可以拖动它.这部分现在完美运作.
但是,假设我有一个包含大量文本的图像.它的分辨率为1200x1700,我的画布有1200x900.最初,当缩小时,这会导致渲染分辨率为~560x800.
我的实际绘图如下:
drawImage(src, srcOffsetX, srcOffsetY, sourceViewWidth, sourceViewHeight,
destOffsetX, destOffsetY, destWidth, destHeight);
Run Code Online (Sandbox Code Playgroud)
此图像上的小文字看起来非常非常糟糕,特别是与其他图像查看器(例如IrfanView)或甚至html <img>元素相比时.
我发现浏览器插值算法是导致这个问题的原因.比较不同的浏览器显示,Chrome渲染缩放图像效果最佳,但仍然不够好.
好吧,我在Interwebs的每个角落搜索了4-5个小时,没找到我需要的东西.我找到了"imageSmoothingEnabled"选项,"图像渲染"CSS样式,你不能在画布上使用,在浮动位置渲染和插值算法的许多JavaScript实现(这些我的目的很慢).
你可能会问为什么我告诉你这一切:为了节省你给我答案的时间我已经知道了
那么:有没有更好的快速方法来获得更好的插值?我目前的想法是创建一个图像对象,调整大小(因为img在缩放时具有良好的插值!)然后渲染它.不幸的是,应用img.width似乎只会影响显示的宽度......
更新:感谢西蒙,我可以解决我的问题.这是我使用的动态缩放算法.请注意,它保持纵横比,height参数仅用于避免更多的浮点计算.它现在只缩小.
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; …Run Code Online (Sandbox Code Playgroud)