diff --git a/demoassets/main.js b/demoassets/main.js
index 7463927..1899a51 100644
--- a/demoassets/main.js
+++ b/demoassets/main.js
@@ -50,15 +50,19 @@ $(function(){
});
function onComplete(data){
+ var time = Date.now();
var diffImage = new Image();
- diffImage.src = data.imageDiffFileData;
+ diffImage.src = data.getImageDataUrl();
+
+ console.log(data.analysisTime);
+
$('#image-diff').html(diffImage);
$(diffImage).click(function(){
window.open(diffImage.src, '_blank');
});
- $('#button').show();
+ $('#buttons').show();
if(data.misMatchPercentage == 0){
$('#thesame').show();
diff --git a/index.html b/index.html
index 4c27892..0c88c43 100644
--- a/index.html
+++ b/index.html
@@ -81,7 +81,7 @@
Diff will appear here.
-
+
diff --git a/resemble.js b/resemble.js
index 8700d3d..a5a5cbc 100644
--- a/resemble.js
+++ b/resemble.js
@@ -1,3 +1,10 @@
+/*
+Author: James Cryer
+Company: Huddle
+Last updated date: 19 Feb 2013
+URL: ...
+*/
+
(function(_this){
_this['resemble'] = function( fileData ){
@@ -16,7 +23,6 @@
var ignoreAntialiasing = false;
var ignoreColors = false;
- var skip = false;
function triggerDataUpdate(){
var len = updateCallbackArray.length;
@@ -30,6 +36,7 @@
function loop(x, y, callback){
var i,j;
+
for (i=0;i tolerance.maxBrightness;
}
- function getHsl(data, offset){
+ function getHue(r,g,b){
- var r = data[offset] / 255;
- var g = data[offset+1] / 255;
- var b = data[offset+2] / 255;
+ var r = r / 255;
+ var g = g / 255;
+ var b = b / 255;
var max = Math.max(r, g, b), min = Math.min(r, g, b);
var h;
- var s;
- var l = (max + min) / 2;
var d;
if (max == min){
- h = s = 0; // achromatic
+ h = 0; // achromatic
} else{
d = max - min;
- s = l > 0.5 ? d / (2 - max - min) : d / (max + min);
switch(max){
case r: h = (g - b) / d + (g < b ? 6 : 0); break;
case g: h = (b - r) / d + 2; break;
@@ -171,11 +175,7 @@
h /= 6;
}
- return { // values between 0 and 1
- hue: h,
- saturation: s,
- lightness: l
- };
+ return h;
}
function isAntialiased(sourcePix, data, cacheSet, verticalPos, horizontalPos, width){
@@ -188,6 +188,8 @@
var hasSiblingWithDifferentHue = 0;
var hasEquivilantSibling = 0;
+ addHueInfo(sourcePix);
+
for (i = distance*-1; i <= distance; i++){
for (j = distance*-1; j <= distance; j++){
@@ -196,12 +198,15 @@
} else {
offset = ((verticalPos+j)*width + (horizontalPos+i)) * 4;
- targetPix = getRGBAndHSL(data, offset, cacheSet);
+ targetPix = getPixelInfo(data, offset, cacheSet);
if(targetPix === null){
continue;
}
+ addBrightnessInfo(targetPix);
+ addHueInfo(targetPix);
+
if( isContrasting(sourcePix, targetPix) ){
hasHighContrastSibling++;
}
@@ -214,13 +219,17 @@
hasSiblingWithDifferentHue++;
}
- if( hasSiblingWithDifferentHue > 1 || hasHighContrastSibling > 1 || hasEquivilantSibling === 0){
+ if( hasSiblingWithDifferentHue > 1 || hasHighContrastSibling > 1){
return true;
}
}
}
}
+ if(hasEquivilantSibling < 2){
+ return true;
+ }
+
return false;
}
@@ -245,42 +254,37 @@
px[offset + 3] = 255; //a
}
- var cache = [];
- function getRGBAndHSL(data, offset, cacheSet){
- var hsl;
+
+ function getPixelInfo(data, offset, cacheSet){
var r;
var g;
var b;
var d;
- if(cache[cacheSet] && cache[cacheSet][offset]){
- return cache[cacheSet][offset];
+ if(typeof data[offset] !== 'undefined'){
+ r = data[offset];
+ g = data[offset+1];
+ b = data[offset+2];
+ d = {
+ r: r,
+ g: g,
+ b: b
+ };
+
+ return d;
} else {
- if(typeof data[offset] !== 'undefined'){
- hsl = getHsl(data, offset);
- r = data[offset];
- g = data[offset+1];
- b = data[offset+2];
- d = {
- r: r,
- g: g,
- b: b,
- h: hsl.hue,
- s: hsl.saturation,
- l: hsl.lightness,
- brightness: getBrightness(r,g,b) // 'corrected' lightness
- };
- if(!cache[cacheSet]){
- cache[cacheSet] = [];
- }
- cache[cacheSet][offset] = d;
- return d;
- } else {
- return null;
- }
+ return null;
}
}
+ function addBrightnessInfo(data){
+ data.brightness = getBrightness(data.r,data.g,data.b); // 'corrected' lightness
+ }
+
+ function addHueInfo(data){
+ data.h = getHue(data.r,data.g,data.b);
+ }
+
function analyseImages(img1, img2, width, height){
var hiddenCanvas = document.createElement('canvas');
@@ -296,28 +300,36 @@
var targetPix = imgd.data;
var mismatchCount = 0;
- var isAntialiasedCount = 0;
- var isBrightnessCount = 0;
- loop(height, width, function(verticalPos, horizontalPos){
+ var time = Date.now();
- var offset = (verticalPos*width + horizontalPos) * 4;
- var pixel1 = getRGBAndHSL(data1, offset, 1);
+ var skip;
+
+ if( (width > 1200 || height > 1200) && ignoreAntialiasing){
+ skip = 6;
+ }
- if(skip){
+ loop(height, width, function(verticalPos, horizontalPos){
+
+ if(skip){ // only skip if the image isn't small
if(verticalPos % skip === 0 || horizontalPos % skip === 0){
- copyGrayScalePixel(targetPix, offset, pixel1);
return;
}
}
- var pixel2 = getRGBAndHSL(data2, offset, 2);
+ var offset = (verticalPos*width + horizontalPos) * 4;
+ var pixel1 = getPixelInfo(data1, offset, 1);
+ var pixel2 = getPixelInfo(data2, offset, 2);
if(pixel1 === null || pixel2 === null){
return;
}
if (ignoreColors){
+
+ addBrightnessInfo(pixel1);
+ addBrightnessInfo(pixel2);
+
if( isPixelBrightnessSimilar(pixel1, pixel2) ){
copyGrayScalePixel(targetPix, offset, pixel2);
} else {
@@ -330,14 +342,14 @@
if( isRGBSimilar(pixel1, pixel2) ){
copyPixel(targetPix, offset, pixel2);
- } else if( ignoreAntialiasing &&
- (isAntialiased(pixel1, data1, 1, verticalPos, horizontalPos, width) ||
- isAntialiased(pixel2, data2, 2, verticalPos, horizontalPos, width)) ){
-
- isAntialiasedCount++;
+ } else if( ignoreAntialiasing && (
+ addBrightnessInfo(pixel1), // jit pixel info augmentation looks a little weird, sorry.
+ addBrightnessInfo(pixel2),
+ isAntialiased(pixel1, data1, 1, verticalPos, horizontalPos, width) ||
+ isAntialiased(pixel2, data2, 2, verticalPos, horizontalPos, width)
+ )){
if( isPixelBrightnessSimilar(pixel1, pixel2) ){
- isBrightnessCount++;
copyGrayScalePixel(targetPix, offset, pixel2);
} else {
errorPixel(targetPix, offset);
@@ -350,12 +362,13 @@
});
- context.putImageData(imgd, 0,0);
-
- cache = [];
-
data.misMatchPercentage = (mismatchCount / (height*width) * 100).toFixed(2);
- data.imageDiffFileData = hiddenCanvas.toDataURL("image/png");
+ data.analysisTime = Date.now() - time;
+
+ data.getImageDataUrl = function(){
+ context.putImageData(imgd, 0,0);
+ return hiddenCanvas.toDataURL("image/png");
+ };
}
function compare(one, two){
@@ -405,8 +418,6 @@
ignoreAntialiasing = false;
ignoreColors = false;
- skip = false;
-
if(hasMethod) { param(); }
return self;
},
@@ -420,7 +431,6 @@
ignoreAntialiasing = true;
ignoreColors = false;
- skip = 4;
if(hasMethod) { param(); }
return self;
@@ -433,8 +443,6 @@
ignoreAntialiasing = false;
ignoreColors = true;
- skip = false;
-
if(hasMethod) { param(); }
return self;
},