support compare for ImageMagick

fix tests that fail on Linux
master
longlho 11 years ago committed by Long Ho
parent 3af88a772a
commit 66b93161ce
  1. 1
      .gitignore
  2. 3
      index.js
  3. 100
      lib/compare.js
  4. 31
      test/compareImageMagick.js

1
.gitignore vendored

@ -10,3 +10,4 @@ examples/imgs/*
!examples/imgs/orientation/*\d.jpg
!examples/imgs/orientation/*.correct.jpg
*.sw*
.idea

@ -115,6 +115,7 @@ require("./lib/args")(gm.prototype);
require("./lib/drawing")(gm.prototype);
require("./lib/convenience")(gm.prototype);
require("./lib/command")(gm.prototype);
require("./lib/compare")(gm.prototype);
/**
* Expose.
@ -122,7 +123,7 @@ require("./lib/command")(gm.prototype);
module.exports = exports = gm;
module.exports.utils = require('./lib/utils');
module.exports.compare = require('./lib/compare');
module.exports.compare = require('./lib/compare')();
module.exports.version = JSON.parse(
require('fs').readFileSync(__dirname + '/package.json', 'utf8')
).version;

@ -18,41 +18,77 @@ var utils = require('./utils');
* @param {Function} cb(err, Boolean, equality, rawOutput)
*/
module.exports = exports = function compare (orig, compareTo, tolerance, cb) {
orig = utils.escape(orig);
compareTo = utils.escape(compareTo);
// outputting the diff image
if (typeof tolerance === 'object') {
var diffOptions = tolerance;
if (typeof diffOptions.file !== 'string') {
throw new TypeError('The path for the diff output is invalid');
}
// graphicsmagick defaults to red
var highlightColorOption = diffOptions.highlightColor
? ' -highlight-color ' + diffOptions.highlightColor + ' '
: ' ';
module.exports = exports = function (proto) {
function compare(orig, compareTo, tolerance, cb) {
orig = utils.escape(orig);
compareTo = utils.escape(compareTo);
return exec('gm compare' + highlightColorOption + orig + ' ' + compareTo +
' -file ' + utils.escape(diffOptions.file), cb);
}
var isImageMagick = this._options && this._options.imageMagick;
var bin = isImageMagick ? '' : 'gm ';
// else, output the mean square error (mse)
if ('function' == typeof tolerance) {
cb = tolerance;
tolerance = 0.4;
}
// outputting the diff image
if (typeof tolerance === 'object') {
var diffOptions = tolerance;
if (typeof diffOptions.file !== 'string') {
throw new TypeError('The path for the diff output is invalid');
}
// graphicsmagick defaults to red
var highlightColorOption = diffOptions.highlightColor
? ' -highlight-color ' + diffOptions.highlightColor + ' '
: ' ';
var diffFilename = utils.escape(diffOptions.file);
var diffOpt = isImageMagick ? diffFilename : ('-file ' + diffFilename);
var cmd = bin + 'compare' + highlightColorOption + orig + ' ' + compareTo +
' ' + diffOpt;
exec('gm compare -metric mse ' + orig + ' ' + compareTo, function (err, stdout, stderr) {
if (err) return cb(err);
return exec(cmd, function (err, stdout, stderr) {
if (isImageMagick && err && err.code === 1) {
err = null;
}
return cb(err, stdout, stderr);
});
}
var match = /Total: (\d+\.?\d*)/m.exec(stdout);
if (!match) {
err = new Error('Unable to parse output.\nGot ' + stdout);
return cb(err);
// else, output the mean square error (mse)
if ('function' == typeof tolerance) {
cb = tolerance;
tolerance = 0.4;
}
var equality = parseFloat(match[1]);
cb(null, equality <= tolerance, equality, stdout);
});
}
var execCmd = bin + 'compare -metric mse ' + orig + ' ' + compareTo;
// For ImageMagick diff file is required but we don't care about it, so null it out
isImageMagick && (execCmd += ' null:');
exec(execCmd, function (err, stdout, stderr) {
// ImageMagick returns err code 2 if err, 0 if similar, 1 if dissimilar
if (isImageMagick) {
if (!err) {
return cb(null, 0 <= tolerance, 0, stdout);
}
if (err.code === 1) {
err = null;
stdout = stderr;
}
}
if (err) {
return cb(err);
}
// Since ImageMagick similar gives err code 0 and no stdout, there's really no matching
var regex = isImageMagick ? /\((\d+\.?\d*)\)/m : /Total: (\d+\.?\d*)/m;
var match = regex.exec(stdout);
if (!match) {
err = new Error('Unable to parse output.\nGot ' + stdout);
return cb(err);
}
var equality = parseFloat(match[1]);
cb(null, equality <= tolerance, equality, stdout);
});
}
if (proto) {
proto.compare = compare;
}
return compare;
};

@ -0,0 +1,31 @@
var assert = require('assert');
var fs = require('fs');
module.exports = function (gm, dir, finish, GM) {
// Same image
gm.compare(dir + '/original.jpg', dir + '/original.png', function(err, same) {
if (err) return finish(err);
if (!same) return finish(new Error('Compare should be the same!'));
// Create a new noisy image
gm.noise(0.3).write(dir + '/noise3.png', function (err) {
if (err) return finish(err);
var options = {
highlightColor: 'yellow',
file: dir + '/diff.png'
};
// Compare these images and write to a file.
gm.compare(dir + '/original.jpg', dir + '/noise3.png', options, function(err) {
if (err) return finish(err);
fs.exists(options.file, function(exists) {
if (exists) finish();
else finish(new Error('Diff file does not exist.'));
});
});
})
});
};
Loading…
Cancel
Save