1 /* 2 * Copyright (c) 2007, 2017 Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. 8 * 9 * This code is distributed in the hope that it will be useful, but WITHOUT 10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12 * version 2 for more details (a copy is included in the LICENSE file that 13 * accompanied this code). 14 * 15 * You should have received a copy of the GNU General Public License version 16 * 2 along with this work; if not, write to the Free Software Foundation, 17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 18 * 19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 20 * or visit www.oracle.com if you need additional information or have any 21 * questions. 22 */ 23 package org.jemmy.image.pixel; 24 25 /** 26 * Comparator, that implements peak signal to noise ratio, popular and reliable method of measuring 27 * image compression quality or image distortion. 28 * PSNR is used to measure the quality of reconstruction of lossy compression codecs. The signal is 29 * the reference (golden) image, and the noise is actual image. Higher PSNR indicates lesser 30 * difference between images for the most cases. 31 * Comparator is intended to compare images with large amount of very minor differences and one 32 * has to be extremely careful with the range of validity of this metric; it is only conclusively 33 * valid when it is used to compare results from the same content. 34 * 35 * @author andrey.rusakov@oracle.com 36 */ 37 public class PeakSignalNoiseRatioComparator implements RasterComparator { 38 39 public static final String OUTPUT = PeakSignalNoiseRatioComparator.class.getName() + ".OUTPUT"; 40 41 private static final double MAX_CHANNEL = 1.0; 42 private final double minRatio; 43 44 private static double getMeanSquareError(Raster image, Raster original) { 45 double result = 0; 46 double[] colors1 = new double[image.getSupported().length]; 47 double[] colors2 = new double[original.getSupported().length]; 48 49 int w = Math.min(image.getSize().width, original.getSize().width); 50 int h = Math.min(image.getSize().height, original.getSize().height); 51 for (int i = 0; i < w; i++) { 52 for (int j = 0; j < h; j++) { 53 image.getColors(i, j, colors1); 54 original.getColors(i, j, colors2); 55 double distance = AverageDistanceComparator.distance(image.getSupported(), colors1, 56 original.getSupported(), colors2); 57 result += distance * distance / (AverageDistanceComparator.DISTANCE_COMPONENTS.length * w * h); 58 } 59 } 60 return result; 61 } 62 63 private static double getPeakSignalNoiseRatio(Raster image, Raster original) { 64 double mse = getMeanSquareError(image, original); 65 return 20 * Math.log10(MAX_CHANNEL) - 10 * Math.log10(mse); 66 } 67 68 public PeakSignalNoiseRatioComparator(double minRatio) { 69 this.minRatio = minRatio; 70 } 71 72 @Override 73 public boolean compare(Raster image1, Raster image2) { 74 return getPeakSignalNoiseRatio(image1, image2) > minRatio; 75 } 76 77 @Override 78 public String getID() { 79 return getClass().getName() + ":" + minRatio; 80 } 81 82 }