【问题标题】:HTML Canvas: Scaling image to fit without stretching?HTML Canvas:缩放图像以适应而不拉伸?
【发布时间】:2015-01-20 23:23:30
【问题描述】:

我使用下面的代码在画布内绘制和缩放图像。问题是内部渲染的图像被拉伸以适应。

如果可能的话,我希望它根据宽度进行缩放,但要保持其纵横比。

有什么想法吗?

//IMAGE LOADER
var canvas = document.getElementById('image-canvas');
var canvas2 = document.getElementById('image-canvas2');
ctx = canvas.getContext('2d');
ctx2 = canvas2.getContext('2d');

// Trigger the imageLoader function when a file has been selected
var fileInput = document.getElementById('fileInput');
fileInput.addEventListener('change', imageLoader, false);

function imageLoader() {
    var reader = new FileReader();
    reader.onload = function(event) {
        img = new Image();
        img.onload = function(){
            ctx.drawImage(img,0,0,canvas.width, canvas.height);
            ctx2.drawImage(img,0,0,canvas.width, canvas.height);
        }
        img.src = reader.result;
    }
    reader.readAsDataURL(fileInput.files[0]);
}

【问题讨论】:

  • 你知道正确的比例是什么吗?您可以在绘图时应用正确的比例。如果你不知道,你可以在 DOM 上渲染它并查询图像的宽度/高度

标签: javascript html canvas


【解决方案1】:

您可以通过将图像添加到 DOM 来计算图像的尺寸。知道比例后,您可以缩放图像以适应画布。

ratio = width / height;
width = height * ratio;
height = width / ratio;

无论图像是横向还是纵向,以下都应该有效。

var canvas = document.getElementById('image-canvas');
var canvas2 = document.getElementById('image-canvas2');
var ctx = canvas.getContext('2d');
document.getElementById('fileInput').addEventListener('change', imageLoader, false);

function imageLoader() {
    var reader = new FileReader();
    reader.onload = function(event) {
        var img = new Image();
        img.onload = function(){
            var ct = document.getElementById('measure'); 
            ct.appendChild(img);
            var wrh = img.width / img.height;
            var newWidth = canvas.width;
            var newHeight = newWidth / wrh;
            if (newHeight > canvas.height) {
                newHeight = canvas.height;
                newWidth = newHeight * wrh;
            }
            ct.removeChild(img);
            ctx.drawImage(img,0,0, newWidth , newHeight);
        }
        img.src = reader.result;
    }
    reader.readAsDataURL(fileInput.files[0]);
}
/* Add image to the DOM here so user can't see it */
#measure { position: absolute; left: -10000px; top: -100000px;}
canvas { border: 1px solid red; }
<canvas id="image-canvas" width="300" height="300"></canvas>
<input type="file" id="fileInput" />
<div id="measure"></div>

你可以play with it here

【讨论】:

  • 很棒的反应。非常感谢!
  • 很好的解决方案!为我节省了很多工作,谢谢伙计!
  • 当我在烟花的响应视图中尝试时,效果很好,但是当我在手机上尝试时,它没有。有什么想法吗?
  • @galeonweb 您应该提出一个与此问题相关的新问题,发布您尝试使用的代码、错误是什么以及您的预期。请不要在现有问题下提出新问题,这会增加太多噪音
  • 好的,抱歉。我不确定我是否可以重复提问,以及如何
猜你喜欢
  • 1970-01-01
  • 2013-08-22
  • 2010-11-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2010-10-13
  • 2014-03-13
  • 1970-01-01
相关资源
最近更新 更多