我正在尝试将 300dpi 图像绘制到画布对象,但在 Chrome 中显示质量很差。当我使用下面的代码时,它并没有改善,但那是因为devicePixelRatio
与backingStoreRatio
(两者都是1
)相同。
然后我尝试强制更改一些比率并发现以下内容:
- 如果我更改
ratio
为2
并强制缩放代码运行,那么它会以更好的分辨率绘制到画布上。 - 如果我更改
ratio
为大于2
(例如3
,4
,5
,6
等)的任何值,那么它的分辨率很差!
这一切都是在台式计算机上完成的。
如何确保画布以高分辨率绘制?
(代码来自:http ://www.html5rocks.com/en/tutorials/canvas/hidpi/ )
/**
* Writes an image into a canvas taking into
* account the backing store pixel ratio and
* the device pixel ratio.
*
* @author Paul Lewis
* @param {Object} opts The params for drawing an image to the canvas
*/
function drawImage(opts) {
if(!opts.canvas) {
throw("A canvas is required");
}
if(!opts.image) {
throw("Image is required");
}
// get the canvas and context
var canvas = opts.canvas,
context = canvas.getContext('2d'),
image = opts.image,
// now default all the dimension info
srcx = opts.srcx || 0,
srcy = opts.srcy || 0,
srcw = opts.srcw || image.naturalWidth,
srch = opts.srch || image.naturalHeight,
desx = opts.desx || srcx,
desy = opts.desy || srcy,
desw = opts.desw || srcw,
desh = opts.desh || srch,
auto = opts.auto,
// finally query the various pixel ratios
devicePixelRatio = window.devicePixelRatio || 1,
backingStoreRatio = context.webkitBackingStorePixelRatio ||
context.mozBackingStorePixelRatio ||
context.msBackingStorePixelRatio ||
context.oBackingStorePixelRatio ||
context.backingStorePixelRatio || 1,
ratio = devicePixelRatio / backingStoreRatio;
// ensure we have a value set for auto.
// If auto is set to false then we
// will simply not upscale the canvas
// and the default behaviour will be maintained
if (typeof auto === 'undefined') {
auto = true;
}
// upscale the canvas if the two ratios don't match
if (auto && devicePixelRatio !== backingStoreRatio) {
var oldWidth = canvas.width;
var oldHeight = canvas.height;
canvas.width = oldWidth * ratio;
canvas.height = oldHeight * ratio;
canvas.style.width = oldWidth + 'px';
canvas.style.height = oldHeight + 'px';
// now scale the context to counter
// the fact that we've manually scaled
// our canvas element
context.scale(ratio, ratio);
}
context.drawImage(pic, srcx, srcy, srcw, srch, desx, desy, desw, desh);
}
仅进行以下更改会产生高分辨率画布图像(为什么?):
//WE FORCE RATIO TO BE 2
ratio = 2;
//WE FORCE IT TO UPSCALE (event though they're equal)
if (auto && devicePixelRatio === backingStoreRatio) {
如果我们把上面的比例改成3
,就不再是高分辨率了!
编辑:一个额外的观察 - 即使使用 2x 比率,虽然它的分辨率明显更好,但它仍然不如在img
标签中显示图像那么清晰)