Skip to content

Instantly share code, notes, and snippets.

@aviflax
Created October 26, 2018 18:43
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save aviflax/e4826bf8cf1d618d1e7a2d79a1ec0f88 to your computer and use it in GitHub Desktop.
Save aviflax/e4826bf8cf1d618d1e7a2d79a1ec0f88 to your computer and use it in GitHub Desktop.
Image Diffing with Clojure
(ns image-diff
"Most of this is ported from https://rosettacode.org/wiki/Percentage_difference_between_images#Java"
(:import [java.awt Color]
[java.awt.image BufferedImage]))
(defn pixel-diff
[a b]
(let [a-color-components (.getRGBColorComponents (Color. a) nil)
b-color-components (.getRGBColorComponents (Color. b) nil)]
(->> (map - a-color-components b-color-components)
(map #(Math/abs %))
(reduce +))))
(defn image-pixels
[^BufferedImage img]
(-> img (.getRaster) (.getDataBuffer) (.getData)))
(defn round-dec
"Rounds up, e.g. 0.001 rounded to two places will yield 0.01."
[places d]
(-> (bigdec d)
(.setScale places BigDecimal/ROUND_CEILING)
(double)))
(defn image-diff
[^BufferedImage a ^BufferedImage b]
(let [width (.getWidth a)
height (.getHeight a)
max-diff (* 3 255 width height)]
(when (or (not= width (.getWidth b))
(not= height (.getHeight b)))
(throw (Exception. "Images must have the same dimensions!")))
(as-> (map pixel-diff (image-pixels a) (image-pixels b)) it
(reduce + it)
(/ (* 100.0 it) max-diff)
(round-dec 4 it))))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment