1 package org.opencv.test.features2d; 2 3 import java.util.Arrays; 4 import java.util.List; 5 6 import org.opencv.core.Core; 7 import org.opencv.core.CvException; 8 import org.opencv.core.CvType; 9 import org.opencv.core.Mat; 10 import org.opencv.core.MatOfDMatch; 11 import org.opencv.core.MatOfKeyPoint; 12 import org.opencv.core.Point; 13 import org.opencv.core.Scalar; 14 import org.opencv.core.DMatch; 15 import org.opencv.features2d.DescriptorExtractor; 16 import org.opencv.features2d.DescriptorMatcher; 17 import org.opencv.features2d.FeatureDetector; 18 import org.opencv.core.KeyPoint; 19 import org.opencv.test.OpenCVTestCase; 20 import org.opencv.test.OpenCVTestRunner; 21 import org.opencv.imgproc.Imgproc; 22 23 public class FlannBasedDescriptorMatcherTest extends OpenCVTestCase { 24 25 static final String xmlParamsDefault = "<?xml version=\"1.0\"?>\n" 26 + "<opencv_storage>\n" 27 + "<indexParams>\n" 28 + " <_>\n" 29 + " <name>algorithm</name>\n" 30 + " <type>23</type>\n" 31 + " <value>1</value></_>\n" 32 + " <_>\n" 33 + " <name>trees</name>\n" 34 + " <type>4</type>\n" 35 + " <value>4</value></_></indexParams>\n" 36 + "<searchParams>\n" 37 + " <_>\n" 38 + " <name>checks</name>\n" 39 + " <type>4</type>\n" 40 + " <value>32</value></_>\n" 41 + " <_>\n" 42 + " <name>eps</name>\n" 43 + " <type>5</type>\n" 44 + " <value>0.</value></_>\n" 45 + " <_>\n" 46 + " <name>sorted</name>\n" 47 + " <type>15</type>\n" 48 + " <value>1</value></_></searchParams>\n" 49 + "</opencv_storage>\n"; 50 static final String ymlParamsDefault = "%YAML:1.0\n" 51 + "indexParams:\n" 52 + " -\n" 53 + " name: algorithm\n" 54 + " type: 23\n" 55 + " value: 1\n" 56 + " -\n" 57 + " name: trees\n" 58 + " type: 4\n" 59 + " value: 4\n" 60 + "searchParams:\n" 61 + " -\n" 62 + " name: checks\n" 63 + " type: 4\n" 64 + " value: 32\n" 65 + " -\n" 66 + " name: eps\n" 67 + " type: 5\n" 68 + " value: 0.\n" 69 + " -\n" 70 + " name: sorted\n" 71 + " type: 15\n" 72 + " value: 1\n"; 73 static final String ymlParamsModified = "%YAML:1.0\n" 74 + "indexParams:\n" 75 + " -\n" 76 + " name: algorithm\n" 77 + " type: 23\n" 78 + " value: 6\n"// this line is changed! 79 + " -\n" 80 + " name: trees\n" 81 + " type: 4\n" 82 + " value: 4\n" 83 + "searchParams:\n" 84 + " -\n" 85 + " name: checks\n" 86 + " type: 4\n" 87 + " value: 32\n" 88 + " -\n" 89 + " name: eps\n" 90 + " type: 5\n" 91 + " value: 4.\n"// this line is changed! 92 + " -\n" 93 + " name: sorted\n" 94 + " type: 15\n" 95 + " value: 1\n"; 96 97 DescriptorMatcher matcher; 98 99 int matSize; 100 101 DMatch[] truth; 102 getMaskImg()103 private Mat getMaskImg() { 104 return new Mat(5, 2, CvType.CV_8U, new Scalar(0)) { 105 { 106 put(0, 0, 1, 1, 1, 1); 107 } 108 }; 109 } 110 111 private Mat getQueryDescriptors() { 112 Mat img = getQueryImg(); 113 MatOfKeyPoint keypoints = new MatOfKeyPoint(); 114 Mat descriptors = new Mat(); 115 116 FeatureDetector detector = FeatureDetector.create(FeatureDetector.SURF); 117 DescriptorExtractor extractor = DescriptorExtractor.create(DescriptorExtractor.SURF); 118 119 String filename = OpenCVTestRunner.getTempFileName("yml"); 120 writeFile(filename, "%YAML:1.0\nhessianThreshold: 8000.\noctaves: 3\noctaveLayers: 4\nupright: 0\n"); 121 detector.read(filename); 122 123 detector.detect(img, keypoints); 124 extractor.compute(img, keypoints, descriptors); 125 126 return descriptors; 127 } 128 129 private Mat getQueryImg() { 130 Mat cross = new Mat(matSize, matSize, CvType.CV_8U, new Scalar(255)); 131 Imgproc.line(cross, new Point(30, matSize / 2), new Point(matSize - 31, matSize / 2), new Scalar(100), 3); 132 Imgproc.line(cross, new Point(matSize / 2, 30), new Point(matSize / 2, matSize - 31), new Scalar(100), 3); 133 134 return cross; 135 } 136 137 private Mat getTrainDescriptors() { 138 Mat img = getTrainImg(); 139 MatOfKeyPoint keypoints = new MatOfKeyPoint(new KeyPoint(50, 50, 16, 0, 20000, 1, -1), new KeyPoint(42, 42, 16, 160, 10000, 1, -1)); 140 Mat descriptors = new Mat(); 141 142 DescriptorExtractor extractor = DescriptorExtractor.create(DescriptorExtractor.SURF); 143 144 extractor.compute(img, keypoints, descriptors); 145 146 return descriptors; 147 } 148 149 private Mat getTrainImg() { 150 Mat cross = new Mat(matSize, matSize, CvType.CV_8U, new Scalar(255)); 151 Imgproc.line(cross, new Point(20, matSize / 2), new Point(matSize - 21, matSize / 2), new Scalar(100), 2); 152 Imgproc.line(cross, new Point(matSize / 2, 20), new Point(matSize / 2, matSize - 21), new Scalar(100), 2); 153 154 return cross; 155 } 156 157 protected void setUp() throws Exception { 158 super.setUp(); 159 matcher = DescriptorMatcher.create(DescriptorMatcher.FLANNBASED); 160 matSize = 100; 161 truth = new DMatch[] { 162 new DMatch(0, 0, 0, 0.6211397f), 163 new DMatch(1, 1, 0, 0.9177120f), 164 new DMatch(2, 1, 0, 0.3112163f), 165 new DMatch(3, 1, 0, 0.2925075f), 166 new DMatch(4, 1, 0, 0.9309179f) 167 }; 168 } 169 170 public void testAdd() { 171 matcher.add(Arrays.asList(new Mat())); 172 assertFalse(matcher.empty()); 173 } 174 175 public void testClear() { 176 matcher.add(Arrays.asList(new Mat())); 177 178 matcher.clear(); 179 180 assertTrue(matcher.empty()); 181 } 182 183 public void testClone() { 184 Mat train = new Mat(1, 1, CvType.CV_8U, new Scalar(123)); 185 matcher.add(Arrays.asList(train)); 186 187 try { 188 matcher.clone(); 189 fail("Expected CvException (CV_StsNotImplemented)"); 190 } catch (CvException cverr) { 191 // expected 192 } 193 } 194 195 public void testCloneBoolean() { 196 matcher.add(Arrays.asList(new Mat())); 197 198 DescriptorMatcher cloned = matcher.clone(true); 199 200 assertNotNull(cloned); 201 assertTrue(cloned.empty()); 202 } 203 204 public void testCreate() { 205 assertNotNull(matcher); 206 } 207 208 public void testEmpty() { 209 assertTrue(matcher.empty()); 210 } 211 212 public void testGetTrainDescriptors() { 213 Mat train = new Mat(1, 1, CvType.CV_8U, new Scalar(123)); 214 Mat truth = train.clone(); 215 matcher.add(Arrays.asList(train)); 216 217 List<Mat> descriptors = matcher.getTrainDescriptors(); 218 219 assertEquals(1, descriptors.size()); 220 assertMatEqual(truth, descriptors.get(0)); 221 } 222 223 public void testIsMaskSupported() { 224 assertFalse(matcher.isMaskSupported()); 225 } 226 227 public void testKnnMatchMatListOfListOfDMatchInt() { 228 fail("Not yet implemented"); 229 } 230 231 public void testKnnMatchMatListOfListOfDMatchIntListOfMat() { 232 fail("Not yet implemented"); 233 } 234 235 public void testKnnMatchMatListOfListOfDMatchIntListOfMatBoolean() { 236 fail("Not yet implemented"); 237 } 238 239 public void testKnnMatchMatMatListOfListOfDMatchInt() { 240 fail("Not yet implemented"); 241 } 242 243 public void testKnnMatchMatMatListOfListOfDMatchIntMat() { 244 fail("Not yet implemented"); 245 } 246 247 public void testKnnMatchMatMatListOfListOfDMatchIntMatBoolean() { 248 fail("Not yet implemented"); 249 } 250 251 public void testMatchMatListOfDMatch() { 252 Mat train = getTrainDescriptors(); 253 Mat query = getQueryDescriptors(); 254 MatOfDMatch matches = new MatOfDMatch(); 255 matcher.add(Arrays.asList(train)); 256 matcher.train(); 257 258 matcher.match(query, matches); 259 260 assertArrayDMatchEquals(truth, matches.toArray(), EPS); 261 } 262 263 public void testMatchMatListOfDMatchListOfMat() { 264 Mat train = getTrainDescriptors(); 265 Mat query = getQueryDescriptors(); 266 Mat mask = getMaskImg(); 267 MatOfDMatch matches = new MatOfDMatch(); 268 matcher.add(Arrays.asList(train)); 269 matcher.train(); 270 271 matcher.match(query, matches, Arrays.asList(mask)); 272 273 assertArrayDMatchEquals(truth, matches.toArray(), EPS); 274 } 275 276 public void testMatchMatMatListOfDMatch() { 277 Mat train = getTrainDescriptors(); 278 Mat query = getQueryDescriptors(); 279 MatOfDMatch matches = new MatOfDMatch(); 280 281 matcher.match(query, train, matches); 282 283 assertArrayDMatchEquals(truth, matches.toArray(), EPS); 284 285 // OpenCVTestRunner.Log(matches.toString()); 286 // OpenCVTestRunner.Log(matches); 287 } 288 289 public void testMatchMatMatListOfDMatchMat() { 290 Mat train = getTrainDescriptors(); 291 Mat query = getQueryDescriptors(); 292 Mat mask = getMaskImg(); 293 MatOfDMatch matches = new MatOfDMatch(); 294 295 matcher.match(query, train, matches, mask); 296 297 assertListDMatchEquals(Arrays.asList(truth), matches.toList(), EPS); 298 } 299 300 public void testRadiusMatchMatListOfListOfDMatchFloat() { 301 fail("Not yet implemented"); 302 } 303 304 public void testRadiusMatchMatListOfListOfDMatchFloatListOfMat() { 305 fail("Not yet implemented"); 306 } 307 308 public void testRadiusMatchMatListOfListOfDMatchFloatListOfMatBoolean() { 309 fail("Not yet implemented"); 310 } 311 312 public void testRadiusMatchMatMatListOfListOfDMatchFloat() { 313 fail("Not yet implemented"); 314 } 315 316 public void testRadiusMatchMatMatListOfListOfDMatchFloatMat() { 317 fail("Not yet implemented"); 318 } 319 320 public void testRadiusMatchMatMatListOfListOfDMatchFloatMatBoolean() { 321 fail("Not yet implemented"); 322 } 323 324 public void testRead() { 325 String filenameR = OpenCVTestRunner.getTempFileName("yml"); 326 String filenameW = OpenCVTestRunner.getTempFileName("yml"); 327 writeFile(filenameR, ymlParamsModified); 328 329 matcher.read(filenameR); 330 matcher.write(filenameW); 331 332 assertEquals(ymlParamsModified, readFile(filenameW)); 333 } 334 335 public void testTrain() { 336 Mat train = getTrainDescriptors(); 337 matcher.add(Arrays.asList(train)); 338 matcher.train(); 339 } 340 341 public void testTrainNoData() { 342 try { 343 matcher.train(); 344 fail("Expected CvException - FlannBasedMatcher::train should fail on empty train set"); 345 } catch (CvException cverr) { 346 // expected 347 } 348 } 349 350 public void testWrite() { 351 String filename = OpenCVTestRunner.getTempFileName("xml"); 352 353 matcher.write(filename); 354 355 assertEquals(xmlParamsDefault, readFile(filename)); 356 } 357 358 public void testWriteYml() { 359 String filename = OpenCVTestRunner.getTempFileName("yml"); 360 361 matcher.write(filename); 362 363 assertEquals(ymlParamsDefault, readFile(filename)); 364 } 365 366 } 367