我有一个样本图像和一组其他图像,我想将它们与第一张图像进行比较。因此,我将它们都绘制到画布上并检查它们是否相同。
我在这里使用了这个概念:比较JavaScript中的两个图像
问题在于图像以随机角度旋转。因此图片的base64值似乎彼此不匹配。
注意:我无法计算角度,试错法会浪费资源
match=-1;
for(i=0;i<7;i++)
{
context1.drawImage(img,xPos[i],5,width[i],height,0,0,width[i],height);;
if(canvas1.toDataURL()==samplecanvas.toDataURL()){
match=i+1;
break;
}
context1.clearRect(0, 0, canvas1.width, canvas1.height);
}
在上面的代码中,我正在遍历图像。我在给定的样本图像samplecanvas和canvas1是我画我的图片列表。那我想比较一下 但是我不知道如何。
如何使用JavaScript比较以不同角度以不同方向旋转的两个图像?
我可以比较颜色吗?
假设两个图像均为矩形,并且旋转均未对其进行裁剪,则可以在画布中循环遍历所有像素,以确定最上方,下方,左侧和右侧的像素(*),然后从此处将其旋转到只能“正确旋转”或上下颠倒(或者,对于正方形,是向左或向右90°),这样就可以减少检查的次数。
从那里开始,您可以从另一张图像中“减去”一张图像,并检查差异是否接近零。
(*):从理论上讲,两个角就足够了,但是更多的角有助于提高精度,因为我们正在处理近似值(因为有浮点数)。
var canvas = [];
var ctx = [];
for(var i = 1; i <= 7; i++)
{
canvas[i] = document.getElementById('canvas' + i);
ctx[i] = canvas[i].getContext('2d');
ctx[i].translate(250, 250);
}
var img = new Image();
var result = document.getElementById('result');
var diffCanvases = function(c1, c2)
{
var other = c2.getImageData(0, 0, 500, 500).data;
return c1.getImageData(0, 0, 500, 500).data.map(function(val, i)
{
return Math.abs(val - other[i]);
}).reduce(function(previous, current)
{
return previous + current;
});
};
var drawRotatedImage = function()
{
var angle1 = Math.random() * 2 * Math.PI;
var angle2 = Math.random() * 2 * Math.PI;
ctx[1].rotate(angle1);
ctx[2].rotate(angle2);
ctx[1].drawImage(img, -200, -150);
ctx[2].drawImage(img, -200, -150);
}
var undoRotation = function()
{
var data = [ctx[1].getImageData(0, 0, 500, 500).data, ctx[2].getImageData(0, 0, 500, 500).data];
var extremes = [{}, {}];
for(var i = 0; i < 2; i++)
{
top:
for(var y = 0; y < 500; y++)
{
for(var x = 0; x < 500; x++)
{
if(data[i][(y * 500 + x) * 4] + data[i][(y * 500 + x) * 4 + 1] + data[i][(y * 500 + x) * 4 + 2] + data[i][(y * 500 + x) * 4 + 3] > 0)
{
extremes[i].top = {x: x, y: y};
break top;
}
}
}
bottom:
for(var y = 499; y >= 0; y--)
{
for(var x = 499; x >= 0; x--)
{
if(data[i][(y * 500 + x) * 4] + data[i][(y * 500 + x) * 4 + 1] + data[i][(y * 500 + x) * 4 + 2] + data[i][(y * 500 + x) * 4 + 3] > 0)
{
extremes[i].bottom = {x: x, y: y};
break bottom;
}
}
}
left:
for(var x = 0; x < 500; x++)
{
for(var y = 0; y < 500; y++)
{
if(data[i][(y * 500 + x) * 4] + data[i][(y * 500 + x) * 4 + 1] + data[i][(y * 500 + x) * 4 + 2] + data[i][(y * 500 + x) * 4 + 3] > 0)
{
extremes[i].left = {x: x, y: y};
break left;
}
}
}
right:
for(var x = 499; x >= 0; x--)
{
for(var y = 499; y >= 0; y--)
{
if(data[i][(y * 500 + x) * 4] + data[i][(y * 500 + x) * 4 + 1] + data[i][(y * 500 + x) * 4 + 2] + data[i][(y * 500 + x) * 4 + 3] > 0)
{
extremes[i].right = {x: x, y: y};
break right;
}
}
}
}
var angles = [];
for(var i = 0; i < 2; i++)
{
// Diagonals yield the highest accuracy
var topBottom = Math.atan((extremes[i].bottom.y - extremes[i].top.y) / (extremes[i].bottom.x - extremes[i].top.x));
var leftRight = Math.atan((extremes[i].left.y - extremes[i].right.y) / (extremes[i].left.x - extremes[i].right.x));
angles.push(((topBottom + leftRight + Math.PI) / 2) % (Math.PI / 2));
}
ctx[3].rotate(-angles[0]);
ctx[3].drawImage(canvas[1], -250, -250);
for(var i = 0; i < 4; i++)
{
ctx[4 + i].rotate(-angles[1] + Math.PI * i / 2);
ctx[4 + i].drawImage(canvas[2], -250, -250);
}
result.textContent = 'Canvas 3 vs 4: ' + diffCanvases(ctx[3], ctx[4]) + '\n' +
'Canvas 3 vs 5: ' + diffCanvases(ctx[3], ctx[5]) + '\n' +
'Canvas 3 vs 6: ' + diffCanvases(ctx[3], ctx[6]) + '\n' +
'Canvas 3 vs 7: ' + diffCanvases(ctx[3], ctx[7]) + '\n';
}
img.addEventListener('load', function()
{
drawRotatedImage();
undoRotation();
});
img.crossOrigin = '';
img.src = 'https://i.imgur.com/o2scuuY.jpg';
canvas
{
border: solid 1px #999;
display: block;
}
#result
{
white-space: pre;
}
Original canvases:
<canvas id="canvas1" width="500" height="500"></canvas>
<canvas id="canvas2" width="500" height="500"></canvas>
Canvas 1 "fixed":
<canvas id="canvas3" width="500" height="500"></canvas>
All options for canvas 2 "fixed":
<canvas id="canvas4" width="500" height="500"></canvas>
<canvas id="canvas5" width="500" height="500"></canvas>
<canvas id="canvas6" width="500" height="500"></canvas>
<canvas id="canvas7" width="500" height="500"></canvas>
<div id="result"></div>
在此版本中,单个像素偏移将已经产生巨大的变化。通过检测所有“固定”图像的顶部和左侧偏移量,将第一幅画布与其他四个画布的顶部和左侧偏移进行比较,并调整图像以使差异均匀,可以轻松地将其最小化。
但是我今天对画布和图像已经一无所知。
示例图像取自LoremPixel。
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句