/*
 * Copyright (c) 2011-2016, Peter Abeles. All Rights Reserved.
 *
 * This file is part of BoofCV (http://boofcv.org).
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *   http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package boofcv.demonstrations.feature.describe;

import boofcv.abst.feature.associate.AssociateDescription;
import boofcv.abst.feature.associate.ScoreAssociation;
import boofcv.abst.feature.describe.ConvertTupleDesc;
import boofcv.abst.feature.describe.DescribeRegionPoint;
import boofcv.abst.feature.describe.DescribeRegionPointConvert;
import boofcv.abst.feature.detect.interest.ConfigFastHessian;
import boofcv.abst.feature.detect.interest.InterestPointDetector;
import boofcv.factory.feature.associate.FactoryAssociation;
import boofcv.factory.feature.describe.FactoryConvertTupleDesc;
import boofcv.factory.feature.describe.FactoryDescribeRegionPoint;
import boofcv.factory.feature.detect.interest.FactoryInterestPoint;
import boofcv.gui.feature.AssociationPanel;
import boofcv.gui.image.ShowImages;
import boofcv.io.UtilIO;
import boofcv.io.image.ConvertBufferedImage;
import boofcv.io.image.UtilImageIO;
import boofcv.struct.feature.AssociatedIndex;
import boofcv.struct.feature.TupleDesc;
import boofcv.struct.feature.TupleDesc_F64;
import boofcv.struct.feature.TupleDesc_S8;
import boofcv.struct.image.GrayF32;
import georegression.struct.point.Point2D_F64;
import org.ddogleg.struct.FastQueue;

import java.awt.image.BufferedImage;
import java.util.ArrayList;
import java.util.List;

/**
 * Visualizes the difference between two "equivalent" descriptions after conversion by associating image features.
 * If the descriptions are truly equivalent then they will generate the same set of associations.
 *
 * @author Peter Abeles
 */
public class CompareConvertedDescriptionsApp {

	public static 
	void visualize( String title ,
					BufferedImage image1, BufferedImage image2,
					InterestPointDetector detector ,
					DescribeRegionPoint describe ,
					ScoreAssociation scorer ) {

		AssociateDescription assoc = FactoryAssociation.greedy(scorer,Double.MAX_VALUE,false);

		List locationSrc = new ArrayList();
		List locationDst = new ArrayList();

		GrayF32 input1 = ConvertBufferedImage.convertFrom(image1,(GrayF32)null);
		GrayF32 input2 = ConvertBufferedImage.convertFrom(image2,(GrayF32)null);

		FastQueue listSrc = describeImage(input1,detector,describe,locationSrc);
		FastQueue listDst = describeImage(input2,detector,describe,locationDst);

		assoc.setSource(listSrc);
		assoc.setDestination(listDst);
		assoc.associate();

		FastQueue matches = assoc.getMatches();

		AssociationPanel panel = new AssociationPanel(20);
		panel.setImages(image1,image2);
		panel.setAssociation(locationSrc,locationDst,matches);

		ShowImages.showWindow(panel,title);
	}

	public static 
	FastQueue  describeImage( GrayF32 input ,
								  InterestPointDetector detector ,
								  DescribeRegionPoint describe ,
								  List location )
	{
		FastQueue list = new FastQueue(100,describe.getDescriptionType(),false);

		System.out.println("Detecting");
		detector.detect(input);
		System.out.println("Describing");
		describe.setImage(input);

		for( int i = 0; i < detector.getNumberOfFeatures(); i++ ) {
			Point2D_F64 p = detector.getLocation(i);
			double radius = detector.getRadius(i);
			double ori = detector.getOrientation(i);

			TD d = describe.createDescription();
			if( describe.process(p.x,p.y,ori,radius,d) ) {
				list.add( d );
				location.add( p.copy() );
			}
		}

		return list;
	}

	public static void main( String args[] ) {
		String file1 = UtilIO.pathExample("stitch/kayak_01.jpg");
		String file2 = UtilIO.pathExample("stitch/kayak_02.jpg");

		InterestPointDetector detector =
				FactoryInterestPoint.fastHessian(new ConfigFastHessian(1,10,-1,2,9,4,4));

		DescribeRegionPoint describeA =
				(DescribeRegionPoint)FactoryDescribeRegionPoint.surfStable(null, GrayF32.class);

		ConvertTupleDesc converter =
				FactoryConvertTupleDesc.real_F64_S8(describeA.createDescription().size());

		DescribeRegionPoint describeB =
				new DescribeRegionPointConvert(describeA,converter);

		ScoreAssociation scoreA = FactoryAssociation.scoreSad(TupleDesc_F64.class);
		ScoreAssociation scoreB = FactoryAssociation.scoreSad(TupleDesc_S8.class);

		BufferedImage image1 = UtilImageIO.loadImage(file1);
		BufferedImage image2 = UtilImageIO.loadImage(file2);

		visualize("Original",image1,image2,detector,describeA,scoreA);
		visualize("Modified",image1,image2,detector,describeB,scoreB);

		System.out.println("Done");
	}
}

 

Ads help maintain this website.