source: other-projects/is-sheet-music-encore/trunk/image-identification-dev-02/image-identification-development/src/MainMorph.java@ 33447

Last change on this file since 33447 was 33447, checked in by cpb16, 5 years ago

starting to implement terminal version of new morphology. need to fix. return bariables always returning null

File size: 57.2 KB
Line 
1/*
2 StartAndEndPoint l1 = parseArray[i];
3 StartAndEndPoint l2 = parseArray[i+ 1];
4 //CHECK WHICH line starts after the other
5 //If l1 is starting after, then comparisons are based around l1.s
6 //System.out.println("l1: " + l1.getP1().x);
7 //System.out.println("l2: " + l2.getP1().x);
8
9 System.out.println("1.0: L1S: " + l1.getP1().x + " larger than L2S: " + l2.getP1().x);
10 if(l1.getP1().x > l2.getP1().x) {
11 System.out.println("1.1: Comparing L1S: " + l1.getP1().x + " less than L2E: " + l2.getP2().x);
12 if (l1.getP1().x < l2.getP2().x) {
13 //AND
14 System.out.println("1.2: Comparing L1S: " + l1.getP1().x + " larger than L2S: " + l2.getP1().x);
15 if (l1.getP1().x > l2.getP1().x) {
16 System.out.println("1: Success. NEXT");
17 //IT IS INTERSECTED
18 continue;
19 }
20 else {
21 //FAILED SECOND COMPARISON
22 System.out.println("1: Fail");
23 }
24 }
25 else {
26 System.out.println("Checking other line");
27 }
28 System.out.println("2.0: L2S: " + l2.getP1().x + " larger than L1S: " + l1.getP1().x);
29 }
30 //If l2 is starting after, then comparisons are based around l2.s
31 else if(l2.getP1().x > l1.getP1().x) {
32 System.out.println("2.1: Comparing L2S: " + l1.getP1().x + " less than L1E: " + l2.getP2().x);
33 if (l2.getP1().x < l1.getP2().x) {
34 //AND
35 System.out.println("2.2: Comparing L2S: " + l2.getP1().x + " larger than L1S: " + l1.getP1().x);
36 if (l2.getP1().x > l1.getP1().x) {
37 System.out.println("2: Success");
38 //IT IS INTERSECTED
39 //continue;
40 }
41 else {
42 //FAILED SECOND COMPARISON
43 System.out.println("2: Fail");
44 //return false;
45 }
46 }
47 else {
48 System.out.println("Failed second comparison RETURN FALSE");
49 return false;
50 }
51 //return false;
52 }
53 else{
54 System.out.println("NEITHER RETURN FALSE");
55 return false;
56 }
57 */
58
59import org.opencv.core.*;
60import org.opencv.core.Point;
61
62import org.opencv.highgui.HighGui;
63import org.opencv.imgcodecs.Imgcodecs;
64import org.opencv.imgproc.Imgproc;
65import org.opencv.imgproc.Moments;
66
67import static org.opencv.core.Core.FILLED;
68import static org.opencv.core.CvType.CV_8UC3;
69import static org.opencv.highgui.HighGui.createJFrame;
70import static org.opencv.highgui.HighGui.imshow;
71import static org.opencv.imgcodecs.Imgcodecs.imwrite;
72
73import java.io.File;
74import java.lang.reflect.Array;
75import java.util.ArrayList;
76
77//REFERENCES:
78//https://docs.opencv.org/3.4.3/d9/db0/tutorial_hough_lines.
79//https://stackoverflow.com/questions/43443309/count-red-pixel-in-a-given-image
80//https://www.wikihow.com/Calculate-Percentage-in-Java
81//https://riptutorial.com/opencv/example/21963/converting-an-mat-object-to-an-bufferedimage-object
82//https://beginnersbook.com/2013/12/java-arraylist-of-object-sort-example-comparable-and-comparator/
83//https://www.programiz.com/java-programming/examples/standard-deviation
84//https://www.geeksforgeeks.org/how-to-remove-duplicates-from-arraylist-in-java/
85//https://stackoverflow.com/questions/7988486/how-do-you-calculate-the-variance-median-and-standard-deviation-in-c-or-java/7988556
86//https://stackoverflow.com/questions/10396970/sort-a-list-that-contains-a-custom-class
87//https://stackoverflow.com/questions/37946482/crop-images-area-with-opencv-java
88//https://docs.opencv.org/3.4/dd/dd7/tutorial_morph_lines_detection.html
89//https://docs.opencv.org/3.4/d0/d49/tutorial_moments.html
90//https://docs.opencv.org/2.4/doc/tutorials/imgproc/shapedescriptors/moments/moments.html
91//https://docs.opencv.org/3.3.1/d3/dc0/group__imgproc__shape.html#ga17ed9f5d79ae97bd4c7cf18403e1689a
92//http://androiderstuffs.blogspot.com/2016/06/detecting-rectangle-using-opencv-java.html
93//https://stackoverflow.com/questions/23327502/opencv-how-to-draw-minarearect-in-java
94//https://stackoverflow.com/questions/30056910/opencv-java-modify-pixel-values
95//https://stackoverflow.com/questions/18345969/how-to-get-the-mass-center-of-a-contour-android-opencv
96//https://docs.opencv.org/3.0-beta/doc/py_tutorials/py_feature2d/py_features_harris/py_features_harris.html
97
98
99//GOAL for 21st
100
101
102//Classifier 01
103//Have args so can call "java image-identification-classifier01 XX XX"
104//args can be parameters in algorthim such as threshold or theta?
105//Run on 5000 images.
106//Record success rates
107//All done with makefile
108
109
110//But first understand houghline transform
111//Know what the algorithm being used is doing.
112//MAke constants for this classifier
113//Make java be able to run on CMD line
114
115public class MainMorph {
116 //CODE VERSIONS
117 static int CODE_VERSION = 8;
118 static int IMAGE_VERSION = 3;
119 //GLOBAL_CONSTANTS
120
121 static double THRESHOLD_C = 4;
122 static double THRESHOLD_AREA_SIZE = 10000;
123 static double THRESHOLD_AREA_COUNT = 10;
124
125 //
126
127 private static void imageViewer(String winName, Mat img) {
128 try {
129 //Internal display - Overview - Will Distort High Res images
130 if(IMAGE_VERSION == 1) {
131 HighGui.namedWindow(winName, HighGui.WINDOW_NORMAL);
132 HighGui.resizeWindow(winName, 1000, 1000);
133 imshow(winName, img);
134
135 HighGui.moveWindow(winName, 500, 0);
136 HighGui.waitKey(0);
137
138 HighGui.destroyWindow(winName);
139 }
140 //Internal display - Segmented - Will _NOT_ Distort High Res images
141 if(IMAGE_VERSION == 2) {
142 HighGui.namedWindow(winName, HighGui.WINDOW_AUTOSIZE);
143 HighGui.resizeWindow(winName, 1000, 1000);
144 imshow(winName, img);
145 HighGui.moveWindow(winName, 500, 0);
146 HighGui.waitKey(0);
147
148 HighGui.destroyWindow(winName);
149 }
150 //External display - Save Images for manual viewing
151 if(IMAGE_VERSION == 3) {
152 //save file (testing purposes)
153 imwrite(winName+".jpg", img);
154 }
155 }
156 catch (Exception e){
157 e.printStackTrace();
158 }
159 }
160
161
162
163 //MAIN
164 public static void main(String[] args) {
165 System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
166 try {
167 //Variables
168 System.out.println("Running Code version: " + CODE_VERSION + " Image Version: " +IMAGE_VERSION);
169 Mat mid = new Mat();
170 Mat edgesDetectedRGB = new Mat();
171 Mat clustersFoundRGB = new Mat();
172
173 String testDirectory = "/Scratch/cpb16/is-sheet-music-encore/image-identification-dev-02/image-identification-development/";
174 String directory = "/Scratch/cpb16/is-sheet-music-encore/download-images/MU/";
175 String hiresDirectory = "/Scratch/cpb16/is-sheet-music-encore/hires-download-images/";
176
177 //!!!!!!!!!!!!!!!!!!!!!!!!!!!NOT!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
178 //mdp.39015097852365-2.png 176 lines Contents page.
179 //mdp.39015097852555-3.png 76 lines
180 //!!!!!!!!!!!!!!!!!!!!!!!!!!!NOTNOT!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
181 //coo.31924062612282-9.png 8 lines
182 //String default_file = directory+"NotSheetMusic/coo.31924062612282-9.png";
183 //String default_file = directory+"NotSheetMusic/mdp.39015097852365-2.png";
184 //String default_file =testDirectory+"TestImages/NotNot/mdp.39015080972303-3.png"; //WHY GREY? DUE TO IMAGE LARGE, ZOOM IN
185 //String default_file =hiresDirectory+"BK/NotSheetMusic/aeu.ark+=13960=t2q53nq6w-6.png";
186 //String default_file =hiresDirectory+"BK/NotSheetMusic/aeu.ark+=13960=t9z03w65z-4.png";
187 //String default_file =hiresDirectory+"MU/NotSheetMusic/aeu.ark+=13960=t0dv28v9r-1.png";
188 //String default_file =hiresDirectory+"MU/SheetMusic/emu.010001066823-9.png";
189 //String default_file =hiresDirectory+"MU/SheetMusic/bc.ark+=13960=t2j72dt1p-10.png";
190 //String default_file =hiresDirectory+"MU/SheetMusic/bc.ark+=13960=t2j72dt1p-7.png";
191 String default_file =hiresDirectory+"MU/SheetMusic/coo.31924062612282-9.png";
192 //String default_file =hiresDirectory+"MU/NotSheetMusic/mdp.39015096363935-1.png";
193 //String default_file =hiresDirectory+"MU/SheetMusic/coo.31924062612282-9.png";
194
195 //System.out.println(default_file);
196 //String default_file = "/Scratch/cpb16/is-sheet-music-encore/image-identification-terminal/TestImages/test-coo.31924062612282-9.png";
197 //String default_file = testDirectory+"TestImages/MorphTester.png";
198 //String default_file = testDirectory+"TestImages/NotSheetMusic01.png";
199 //String default_file = testDirectory+"TestImages/NotSheetMusic02.png";
200 //String default_file = testDirectory+"TestImages/SheetMusic01.png";
201 //String default_file = testDirectory+"TestImages/SheetMusic02.png";
202 //String default_file = testDirectory+"TestImages/vLine.png";
203 String filename = ((args.length > 0) ? args[0] : default_file);
204 File file = new File(filename);
205 if(!file.exists()){System.err.println("Image not found: "+ filename);}
206
207 int horizontalLineCount =0;
208
209 // Load an image
210 Mat original1 = Imgcodecs.imread(filename, Imgcodecs.IMREAD_GRAYSCALE);
211 System.out.println("Width: " + original1.width() + " Height: " + original1.height());
212 Mat original = original1.clone();
213
214 Imgproc.adaptiveThreshold(original1, original,255, Imgproc.ADAPTIVE_THRESH_GAUSSIAN_C,Imgproc.THRESH_BINARY_INV, 15, THRESHOLD_C);
215 //TEST PARAMETERSImgproc.adaptiveThreshold(original, edgesDetected,255, Imgproc.ADAPTIVE_THRESH_GAUSSIAN_C,Imgproc.THRESH_BINARY_INV, 531,1);
216 //Imgproc.threshold(original,original, 127, 255, Imgproc.THRESH_BINARY);
217
218
219 //****************MORPHOLOGY****************************************************************************************
220 //ADDIOTIONAL FILTERING TO STOP STREAKS
221 //LOOK INTO STREAKS MORPHOGOLY.
222 //****************MORPHOLOGY****************************************************************************************
223
224 // Create the images that will use to extract the horizontal and vertical lines
225
226 //dynamic morphology??
227 if(CODE_VERSION == 1) {
228 int hori = original.width();
229 int vert = original.height();
230 //Find ratio between 100 and width and 100 and height
231 int divX = hori/10;
232 int divY = vert/10;
233 int sizeX = (hori/divX) * 10;
234 int sizeY = (vert/divY) * 10;
235
236 Mat test = original.clone();
237 imageViewer("Original", test);
238
239 System.out.println("hori: " + hori + '\t' + "vert: " + vert);
240 System.out.println("sizeX: " + sizeX + '\t' + "sizeY: " + sizeY);
241
242 Mat kernelErode = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(sizeX, (sizeY/100)));
243 Imgproc.erode(test,test,kernelErode);
244 imageViewer("01 Erode", test);
245
246 Mat kernelDialate = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(sizeX,(sizeY/10)));
247 Imgproc.dilate(test, test, kernelDialate);
248 imageViewer("02 Dialate", test);
249
250 Mat kernelErodeAgain = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size((sizeX/10),(sizeY/5)));
251 Imgproc.erode(test,test,kernelErodeAgain);
252 imageViewer(" 03 Erode Again", test);
253
254 Mat kernelClose = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size((sizeX/10)*3,(sizeY/10)*3));
255 Imgproc.morphologyEx(test,test,Imgproc.MORPH_CLOSE, kernelClose);
256 imageViewer("04 Close", test);
257
258 Imgproc.adaptiveThreshold(test, test,255, Imgproc.ADAPTIVE_THRESH_GAUSSIAN_C,Imgproc.THRESH_BINARY_INV, 15, THRESHOLD_C);
259 imageViewer("05 Binarized", test);
260
261 Mat kernelOpen = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size((sizeX/10),(sizeY/20)));
262 Imgproc.morphologyEx(test,test,Imgproc.MORPH_OPEN, kernelOpen);
263 imageViewer(" 06 Open", test);
264
265 Mat kernelDialateAgain = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size((sizeX/5),(sizeY/100)));
266 Imgproc.dilate(test, test, kernelDialateAgain);
267 imageViewer("07 Dialate", test);
268
269
270 Mat kernelCloseAgain = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size((sizeX/10),(sizeY/2)));
271 Imgproc.morphologyEx(test,test,Imgproc.MORPH_CLOSE, kernelCloseAgain);
272 imageViewer(" 08 Close Again (Final)", test);
273 }
274 //Successful hardcode for morhpology
275 if (CODE_VERSION == 2) {
276
277 //MAKE SURE BLACK & WHITE
278 Mat test = original.clone();
279 imageViewer("00 Binarized Original", test);
280
281 Mat kernelErode = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(100,1));
282 Imgproc.erode(test,test,kernelErode);
283 imageViewer("01 Erode", test);
284
285 Mat kernelDialate = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(110,10));
286 Imgproc.dilate(test, test, kernelDialate);
287 imageViewer("02 Dialate", test);
288
289 Mat kernelErodeAgain = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(10,20));
290 Imgproc.erode(test,test,kernelErodeAgain);
291 imageViewer(" 03 Erode Again", test);
292
293 Mat kernelClose = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(35,20));
294 Imgproc.morphologyEx(test,test,Imgproc.MORPH_CLOSE, kernelClose);
295 imageViewer("04 Close", test);
296
297// Imgproc.threshold(test,test, 127, 255, Imgproc.THRESH_BINARY);
298// imageViewer("05 Binarized", test);
299
300 Mat kernelOpen = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(4,4));
301 Imgproc.morphologyEx(test,test,Imgproc.MORPH_OPEN, kernelOpen);
302 imageViewer(" 06 Open", test);
303
304// Mat kernelDialateAgain = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(1,10));
305// Imgproc.dilate(test, test, kernelDialateAgain);
306// imageViewer("07 Dialate", test);
307
308 //FIGURE OUT FLOOD FILL!!
309 Imgproc.floodFill(test,test, new Point(1,1), new Scalar(2));
310
311
312 Mat kernelCloseAgain = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(10,50));
313 Imgproc.morphologyEx(test,test,Imgproc.MORPH_CLOSE, kernelCloseAgain);
314 imageViewer(" 08 Close Again (Final)", test);
315
316 }
317 //Tutorial/Demo Code
318 if (CODE_VERSION == 3) {
319 Mat horizontal = original.clone();
320 Mat vertical = original.clone();
321 // Specify size on horizontal axis
322 int horizontal_size = horizontal.cols() / 50;
323 // Create structure element for extracting horizontal lines through morphology operations
324 Mat horizontalStructure = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(horizontal_size, 2));
325 // Apply morphology operations
326 Imgproc.erode(horizontal, horizontal, horizontalStructure);
327 Imgproc.dilate(horizontal, horizontal, horizontalStructure);
328 // Show extracted horizontal lines
329 imageViewer("horizontal", horizontal);
330 // Specify size on vertical axis
331 int vertical_size = vertical.rows() / 30;
332 // Create structure element for extracting vertical lines through morphology operations
333 Mat verticalStructure = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(1, vertical_size));
334 // Apply morphology operations
335 Imgproc.erode(vertical, vertical, verticalStructure);
336 Imgproc.dilate(vertical, vertical, verticalStructure);
337 // Show extracted vertical lines
338 imageViewer("vertical", vertical);
339 // Inverse vertical image
340 Core.bitwise_not(vertical, vertical);
341 imageViewer("vertical_bit", vertical);
342 // Extract edges and smooth image according to the logic
343 // 1. extract edges
344 // 2. dilate(edges)
345 // 3. src.copyTo(smooth)
346 // 4. blur smooth img
347 // 5. smooth.copyTo(src, edges)
348 // Step 1
349 Mat edges = new Mat();
350 Imgproc.adaptiveThreshold(vertical, edges, 255, Imgproc.ADAPTIVE_THRESH_MEAN_C, Imgproc.THRESH_BINARY, 3, -2);
351 imageViewer("edges", edges);
352 // Step 2
353 Mat kernel = Mat.ones(2, 2, CvType.CV_8UC1);
354 Imgproc.dilate(edges, edges, kernel);
355 imageViewer("dilate", edges);
356 // Step 3
357 Mat smooth = new Mat();
358 vertical.copyTo(smooth);
359 // Step 4
360 Imgproc.blur(smooth, smooth, new Size(2, 2));
361 // Step 5
362 smooth.copyTo(vertical, edges);
363 // Show final result
364 imageViewer("smooth - final", vertical);
365 System.exit(0);
366 }
367 //Better morphology attempt - static
368 if(CODE_VERSION == 4) {
369
370 //Display Original
371 imageViewer("original", original1);
372
373 Mat test = original.clone();
374 Mat pre = original.clone();
375 Mat dst = new Mat();
376
377 imageViewer("00 Inverse Binarized Original", test);
378
379 //remove large items of no interest pre proc
380 //denoize
381 //heal
382 //fnd large images, write to a seperate mat.
383 //draw these onto orignal image(binerized) in red
384 //turn all red pixels in image to black
385
386
387 //denoize
388 Mat denoize = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(3,3));
389 Imgproc.morphologyEx(pre,pre, Imgproc.MORPH_OPEN, denoize);
390 imageViewer("Denoize - PRE", pre);
391
392 //close up gaps
393 Mat gapCloser = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(5,5));
394 Imgproc.morphologyEx(pre,pre,Imgproc.MORPH_CLOSE, gapCloser);
395 imageViewer("gap closer - PRE", pre);
396
397 Mat kernelHighlightLarge = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(10, 10));
398 Imgproc.erode(pre,pre, kernelHighlightLarge);
399 imageViewer("Highlight Large - PRE", pre);
400
401 //change white pixels to red
402 ArrayList<MatOfPoint> contoursPre = new ArrayList<MatOfPoint>();
403 Mat hierarchyPre = new Mat();
404
405 //PARAMETERS: input image, output array of arrays, output array, contour retrieval mode, contour approximation method.
406 //(contours) output array of arrays: Detected contours. Each contour is stored as a vector of points
407 //(hierarchy) output array: Optional output vector, containing information about the image topology.
408 //https://docs.opencv.org/3.3.1/d3/dc0/group__imgproc__shape.html#ga17ed9f5d79ae97bd4c7cf18403e1689a
409
410 Imgproc.findContours(pre, contoursPre, hierarchyPre, Imgproc.RETR_EXTERNAL, Imgproc.CHAIN_APPROX_SIMPLE);
411
412 //Draw contours and record areas
413
414 Mat drawingPre = Mat.zeros(test.size(), CvType.CV_8UC3);
415 Mat mask = new Mat(drawingPre.size(), CV_8UC3,new Scalar(0));
416 Scalar colorPre = new Scalar(255, 255, 255);
417 Imgproc.drawContours(mask, contoursPre, -1, new Scalar(255, 255, 255), FILLED);
418 Imgproc.fillPoly(drawingPre, contoursPre,colorPre);
419 imageViewer("DRAWINGPRE", drawingPre);
420
421
422 //FIIIIIIIIIIIIIIIIIIIIIIIIIIXXXXXXXXXXXX
423 //Remove from main Mat
424 Core.bitwise_not(mask,mask);
425 imageViewer("MASK", mask);
426 imageViewer("TEST", test);
427
428 drawingPre.copyTo(test, mask);
429 imageViewer("COMBINE", test);
430
431 //start staff line detection
432
433 Mat kernelErode = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(10,1));
434 Imgproc.erode(test,test,kernelErode);
435 imageViewer("01 Erode plus pre", test);
436
437 Mat kernelDilate = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(20,3));
438 Imgproc.dilate(test,test,kernelDilate);
439 imageViewer("02 Dilate", test);
440
441 Mat kernelOpening = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(4,4));
442 Imgproc.morphologyEx(test, test, Imgproc.MORPH_CLOSE, kernelOpening);
443 imageViewer("03 Open", test);
444
445 Mat kernelErode02 = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(8,8));
446 Imgproc.erode(test,test,kernelErode02);
447 imageViewer("04 Erode (Final)", test);
448
449
450 //DETECT OUTLINE AND FIND AREA OF THESE LINES.
451 ArrayList<MatOfPoint> contours = new ArrayList<MatOfPoint>();
452 Mat hierarchy = new Mat();
453
454 //PARAMETERS: input image, output array of arrays, output array, contour retrieval mode, contour approximation method.
455 //(contours) output array of arrays: Detected contours. Each contour is stored as a vector of points
456 //(hierarchy) output array: Optional output vector, containing information about the image topology.
457 //https://docs.opencv.org/3.3.1/d3/dc0/group__imgproc__shape.html#ga17ed9f5d79ae97bd4c7cf18403e1689a
458
459 Imgproc.findContours(test, contours, hierarchy, Imgproc.RETR_EXTERNAL, Imgproc.CHAIN_APPROX_SIMPLE);
460
461 //Draw contours and record areas
462 Mat drawing = Mat.zeros(test.size(), CvType.CV_8UC3);
463 Mat drawing2 = Mat.zeros(test.size(), CvType.CV_8UC3);
464 int areaCounter = 0;
465 for (int i = 0; i < contours.size(); i++) {
466 double area = Imgproc.contourArea(contours.get(i));
467 if(area > THRESHOLD_AREA_SIZE ) {
468 areaCounter++;
469 Scalar color = new Scalar(0, 0, 255);
470 Imgproc.drawContours(drawing, contours, i, color, 1);
471 System.out.println("AREA: " + area);
472 }
473 }
474
475 //Classifier Calculation
476 if(areaCounter >= THRESHOLD_AREA_COUNT){
477 System.out.println("THIS IS SHEET MUSIC");
478 System.out.println(areaCounter);
479 }
480
481
482 //Show in a window
483 imageViewer("Contours", drawing);
484 }
485 //Better morphology attempt - dynamic
486 if(CODE_VERSION == 5) {
487 int hori = original.width();
488 int vert = original.height();
489 //Find ratio between 100 and width and 100 and height
490 int sizeX100 = 10 * (hori/68);
491 int sizeY100 = 10 * (vert/46);
492 int sizeX10 = (hori/68);
493 int sizeY10 = (vert/46);
494 int sizeX1 = (hori/68)/10;
495 int sizeY1 = (vert/46)/10;
496
497 //SizeX should always be a 68th * 10. Based off the defualt tester image "coo.*"
498 //SizeT should always be a 46th * 10
499
500 System.out.println(hori + " " + vert + " " + sizeX1 + " " + sizeY1);
501 //Display Original
502 imageViewer("original", original1);
503
504 Mat test = original.clone();
505 imageViewer("00 Inverse Binarized Original", test);
506
507 //Remove very large and wide black spaces (8th of the page)
508 //Mat kernelRemoveLarge = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(hori/8, vert/8));
509 //Imgproc.erode(test,test, kernelRemoveLarge);
510 //imageViewer("Remove Large", test);
511
512 //Eliminate things that are not long and thin
513 Mat kernelErode = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(sizeX10,sizeY1)); //new Size(10,1));
514 Imgproc.erode(test,test,kernelErode);
515 imageViewer("01 Erode", test);
516
517 Mat kernelDilate = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(sizeX10*2,sizeY1*3)); //new Size(20,3));
518 Imgproc.dilate(test,test,kernelDilate);
519 imageViewer("02 Dilate", test);
520
521 Mat kernelClose = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(sizeX1*4,sizeY1*4)); //new Size(4,4));
522 Imgproc.morphologyEx(test, test, Imgproc.MORPH_CLOSE, kernelClose);
523 imageViewer("03 Open", test);
524
525 Mat kernelErode02 = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(sizeX1*8,sizeX1*8)); //new Size(8,8));
526 Imgproc.erode(test,test,kernelErode02);
527 imageViewer("04 Erode (Final)", test);
528
529
530 //DETECT OUTLINE AND FIND AREA OF THESE LINES.
531 ArrayList<MatOfPoint> contours = new ArrayList<MatOfPoint>();
532 Mat hierarchy = new Mat();
533
534 //PARAMETERS: input image, output array of arrays, output array, contour retrieval mode, contour approximation method.
535 //(contours) output array of arrays: Detected contours. Each contour is stored as a vector of points
536 //(hierarchy) output array: Optional output vector, containing information about the image topology.
537 //https://docs.opencv.org/3.3.1/d3/dc0/group__imgproc__shape.html#ga17ed9f5d79ae97bd4c7cf18403e1689a
538
539 Imgproc.findContours(test, contours, hierarchy, Imgproc.RETR_EXTERNAL, Imgproc.CHAIN_APPROX_SIMPLE);
540
541 //Draw contours and record areas
542 Mat drawing = Mat.zeros(test.size(), CvType.CV_8UC3);
543 int areaCounter = 0;
544 for (int i = 0; i < contours.size(); i++) {
545 double area = Imgproc.contourArea(contours.get(i));
546 if(area > THRESHOLD_AREA_SIZE ) {
547 areaCounter++;
548 Scalar color = new Scalar(0, 0, 255);
549 Imgproc.drawContours(drawing, contours, i, color, 1);
550 System.out.println("AREA: " + area);
551 }
552 }
553
554 //Classifier Calculation
555 if(areaCounter >= THRESHOLD_AREA_COUNT){
556 System.out.println("THIS IS SHEET MUSIC");
557 System.out.println(areaCounter);
558 }
559
560
561 //Show in a window
562 imageViewer("Contours", drawing);
563 }
564 //MASK UNDERSTANDING
565 if(CODE_VERSION == 6) {
566 String path ="/Scratch/cpb16/is-sheet-music-encore/hires-download-images/MU/NotSheetMusic/aeu.ark+=13960=t0dv28v9r-1.png";
567 Mat mask = new Mat();
568 Mat dst = new Mat();
569 //Get source image and binerize
570 Mat src = Imgcodecs.imread(path, Imgcodecs.IMREAD_GRAYSCALE);
571 Imgproc.adaptiveThreshold(original1, src,255, Imgproc.ADAPTIVE_THRESH_GAUSSIAN_C,Imgproc.THRESH_BINARY_INV, 15, THRESHOLD_C);
572 imageViewer("src", src);
573
574 //Find unwanted material, then invert it so mask removes not keeps.
575 Mat kernelErode = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(100,1));
576 Imgproc.erode(src,mask,kernelErode);
577 Mat kernelDilate = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(110,10));
578 Imgproc.dilate(mask, mask, kernelDilate);
579 Core.bitwise_not(mask,mask);
580 imageViewer("mask", mask);
581
582 //Copy source image to new Mat, with mask in use
583 src.copyTo(dst, mask);
584 imageViewer("dst", dst);
585
586
587
588
589 }
590 //Mask implementation
591 if(CODE_VERSION == 7) {
592
593 //Display Original
594 imageViewer("original", original1);
595
596 Mat src = original.clone();
597 Mat test = original.clone();
598 Mat mask = new Mat();
599 Mat dst = new Mat();
600
601 imageViewer("00 Inverse Binarized Original", src);
602
603 //denoize
604 Mat denoize = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(3,3));
605 Imgproc.morphologyEx(src,mask, Imgproc.MORPH_OPEN, denoize);
606 imageViewer("01 Denoize - mask", mask);
607
608 //close up gaps
609 Mat gapCloser = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(5,5));
610 Imgproc.morphologyEx(mask,mask,Imgproc.MORPH_CLOSE, gapCloser);
611 imageViewer("02 gap closer - mask", mask);
612
613 //Isolate large items
614 Mat isolateLarge = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(8, 8));
615 Imgproc.morphologyEx(mask,mask,Imgproc.MORPH_OPEN, isolateLarge);
616 imageViewer("03 Isolate Large - mask", mask);
617 Core.bitwise_not(mask,mask);
618
619 //Remove unwanted large items from image
620 src.copyTo(dst, mask);
621 imageViewer("04 Large Items Removed", dst);
622
623 //start staff line detection
624
625 Mat kernelErode = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(10,1));
626 Imgproc.erode(dst,test,kernelErode);
627 imageViewer("11 Erode plus pre", test);
628
629 Mat kernelDilate = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(20,3));
630 Imgproc.dilate(test,test,kernelDilate);
631 imageViewer("12 Dilate", test);
632
633 Mat kernelOpening = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(4,4));
634 Imgproc.morphologyEx(test, test, Imgproc.MORPH_CLOSE, kernelOpening);
635 imageViewer("13 Open", test);
636
637 Mat kernelErode02 = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(8,8));
638 Imgproc.erode(test,test,kernelErode02);
639 imageViewer("14 Erode (Final)", test);
640
641
642 //DETECT OUTLINE AND FIND AREA OF THESE LINES.
643 ArrayList<MatOfPoint> contours = new ArrayList<MatOfPoint>();
644 Mat hierarchy = new Mat();
645
646 //PARAMETERS: input image, output array of arrays, output array, contour retrieval mode, contour approximation method.
647 //(contours) output array of arrays: Detected contours. Each contour is stored as a vector of points
648 //(hierarchy) output array: Optional output vector, containing information about the image topology.
649 //https://docs.opencv.org/3.3.1/d3/dc0/group__imgproc__shape.html#ga17ed9f5d79ae97bd4c7cf18403e1689a
650
651 Imgproc.findContours(test, contours, hierarchy, Imgproc.RETR_EXTERNAL, Imgproc.CHAIN_APPROX_SIMPLE);
652
653 //Draw contours and record areas
654 Mat drawing = Mat.zeros(test.size(), CvType.CV_8UC3);
655 int areaCounter = 0;
656
657
658 Imgproc.drawContours(drawing, contours, -1, new Scalar(0, 255, 0), FILLED);
659// for (int i = 0; i < contours.size(); i++) {
660// Scalar color = new Scalar(0, i, i);
661// double area = Imgproc.contourArea(contours.get(i));
662// Imgproc.drawContours(drawing, contours, i, color, FILLED);
663// System.out.println("AREA: " + area);
664//
665// }
666 imageViewer("Contours found", drawing);
667
668 //Classifier Calculation
669 if(areaCounter >= THRESHOLD_AREA_COUNT){
670 System.out.println("THIS IS SHEET MUSIC");
671 System.out.println(areaCounter);
672 }
673
674
675 }
676 //Mask implementations (LARGE AND SMALL) - HIGH RES NUMBER MOD
677 if(CODE_VERSION == 8) {
678
679 //Display Original
680 imageViewer("original", original1);
681
682 Mat test = original.clone();
683
684
685 imageViewer("00 Inverse Binarized Original", test);
686
687
688 //************************************
689 //Large Object Removal
690 //************************************
691 Mat srcLOR = original.clone();
692 Mat maskLOR = new Mat();
693 Mat dstLOR = new Mat();
694
695 //denoize
696 Mat denoize = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(5,5));
697 Imgproc.morphologyEx(srcLOR,maskLOR, Imgproc.MORPH_OPEN, denoize);
698 imageViewer("01 Denoize - mask", maskLOR);
699
700 //close up gaps
701 Mat gapCloser = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(5,5));
702 Imgproc.morphologyEx(maskLOR,maskLOR,Imgproc.MORPH_CLOSE, gapCloser);
703 imageViewer("02 gap closer - mask", maskLOR);
704
705 //Isolate large items
706 Mat isolateLarge = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(8, 8));
707 Imgproc.morphologyEx(maskLOR,maskLOR,Imgproc.MORPH_OPEN, isolateLarge);
708 imageViewer("03 Isolate Large - mask", maskLOR);
709
710 //Remove large items from image
711 Core.bitwise_not(maskLOR,maskLOR);
712 srcLOR.copyTo(dstLOR, maskLOR);
713 imageViewer("04 Large Items Removed", dstLOR);
714
715 //****************************************
716 //Small object removal (SOR)
717 //****************************************
718
719 Mat srcSOR = dstLOR.clone();
720 Mat maskSOR = new Mat();
721 Mat dstSOR = new Mat();
722
723 Mat startSOR =Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(7,7));
724 Imgproc.morphologyEx(srcSOR,maskSOR, Imgproc.MORPH_OPEN, startSOR);
725 imageViewer("11 show small - mask", maskSOR);
726
727 Mat highlightSmall = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(7,7));
728 Imgproc.dilate(maskSOR, maskSOR, highlightSmall);
729 imageViewer("12 highlight small - mask", maskSOR);
730
731/* Mat isolateSmall =Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(10,10));
732 Imgproc.morphologyEx(maskSOR,maskSOR,Imgproc.MORPH_CLOSE, isolateSmall);
733 imageViewer("13 isolate small - mask", maskSOR);
734*/
735
736 //Remove small items from image
737 Core.bitwise_not(maskSOR, maskSOR);
738 srcSOR.copyTo(dstSOR, maskSOR);
739 imageViewer("14 Small Items Removed", dstSOR);
740
741
742 //****************************************
743 //start staff line detection
744 //****************************************
745
746 Mat kernelErode = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(15,2)); //10,2
747 Imgproc.erode(dstSOR,test,kernelErode);
748 imageViewer("21 Erode plus pre", test);
749
750 Mat kernelDilate = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(10,4)); //20,3
751 Imgproc.dilate(test,test,kernelDilate);
752 imageViewer("22 Dilate", test);
753
754 Mat kernelClose = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(10,4)); //4,4
755 Imgproc.morphologyEx(test, test, Imgproc.MORPH_CLOSE, kernelClose);
756 imageViewer("23 Close", test);
757
758
759 Mat kernelErode02 = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(10,4)); //10,1
760 Imgproc.erode(test,test,kernelErode02);
761 imageViewer("24 Erode (Final)", test);
762
763 //********************************************************************************
764 //DETECT OUTLINE AND FIND AREA OF THESE LINES.
765 //********************************************************************************
766 ArrayList<MatOfPoint> contours = new ArrayList<MatOfPoint>();
767 ArrayList<MatOfPoint> largeContours = new ArrayList<MatOfPoint>();
768 ArrayList<MatOfPoint> postContours = new ArrayList<MatOfPoint>();
769 Mat hierarchy = new Mat();
770
771 //PARAMETERS: input image, output array of arrays, output array, contour retrieval mode, contour approximation method.
772 //(contours) output array of arrays: Detected contours. Each contour is stored as a vector of points
773 //(hierarchy) output array: Optional output vector, containing information about the image topology.
774 //https://docs.opencv.org/3.3.1/d3/dc0/group__imgproc__shape.html#ga17ed9f5d79ae97bd4c7cf18403e1689a
775
776 Imgproc.findContours(test, contours, hierarchy, Imgproc.RETR_EXTERNAL, Imgproc.CHAIN_APPROX_SIMPLE);
777
778 System.out.println(contours.size());
779 //Draw contours and record areas
780 Mat allContoursFound = Mat.zeros(test.size(), CvType.CV_8UC3);
781 Mat largeContoursFound = allContoursFound.clone() ;
782 Mat postContoursFound = allContoursFound.clone();
783 int areaCounter = 0;
784
785 //Have created a preprocess to remove large objects.
786 //Need to now finalized Classifier, re try area detection.
787 //Paths to take - rectangle boxes around detected contours over threshold (area or perimeter)
788 //Just use area and periemter to determine if sheet music
789 //Discuss with david before weekend perhaps?
790
791 Imgproc.drawContours(allContoursFound, contours, -1, new Scalar(0, 255, 0), 1); //USES LINE_8
792 for (int i = 0; i < contours.size(); i++) {
793 double area = Imgproc.contourArea(contours.get(i));
794 if(area > 100) {
795 System.out.println("AREA: " + area);
796 Imgproc.drawContours(largeContoursFound, contours, i, new Scalar(255, 0, 0), FILLED);
797 //create list of large coutours found
798 largeContours.add(contours.get(i));
799 }
800 }
801 imageViewer("80 All Contours found", allContoursFound);
802 imageViewer("81 Large Contours Found", largeContoursFound);
803
804 //*****************************************************************
805 //Circles and centres on processed images
806 //*****************************************************************
807
808 //Init arrays
809 Mat circleOutput = allContoursFound.clone();
810 MatOfPoint2f[] contoursPoly = new MatOfPoint2f[largeContours.size()];
811 Point[] centers = new Point[largeContours.size()];
812 float[][] radius = new float[largeContours.size()][1];
813
814 //Fill arrays
815 for (int i = 0; i < largeContours.size(); i++) {
816 contoursPoly[i] = new MatOfPoint2f();
817 Imgproc.approxPolyDP(new MatOfPoint2f(largeContours.get(i).toArray()), contoursPoly[i], 1, true);
818 centers[i] = new Point();
819 Imgproc.minEnclosingCircle(contoursPoly[i], centers[i], radius[i]);
820
821 }
822 //Draw circle for each large contour
823 for (int i = 0; i < largeContours.size(); i++) {
824 Imgproc.circle(circleOutput, centers[i], (int) radius[i][0],new Scalar(255, 0, 0), 1);
825 }
826 imageViewer("82 Circles found", circleOutput);
827
828 //********************************************************************************
829 //Centroids - Everything must be to scale
830 //********************************************************************************
831
832 ArrayList<Moments> mu = new ArrayList<Moments>(largeContours.size());
833 Mat centreOutput = Mat.zeros(largeContoursFound.size(), CvType.CV_8UC3);
834 for (int i = 0; i < largeContours.size(); i++) {
835 mu.add(i, Imgproc.moments(largeContours.get(i), false));
836 Moments p = mu.get(i);
837 int x = (int) (p.get_m10() / p.get_m00());
838 int y = (int) (p.get_m01() / p.get_m00());
839 Imgproc.circle(centreOutput, new Point(x, y), 4, new Scalar(255, 255, 255), 30);
840 }
841 imageViewer("83 Centres found", centreOutput);
842
843
844 //***********************************************
845 //PostProcessing - Morphology Classifier
846 // Use dilation to "Connect the dots"
847 // Testing showed the centroids were clustered together
848 // Then use area or perimeter as a classifier filter
849 //REFINEREFINEREIFEN
850 //REFINEREFINEREIFEN
851 //REFINEREFINEREIFEN
852 //REFINEREFINEREIFEN
853 //REFINEREFINEREIFEN
854 //REFINEREFINEREIFEN
855 // FIX UP CLASSIFIER COMPARISON.
856 // MORPHOLOGIES FUNCTIONS RETURN NULL AS THEIR RETURN VARIABLES. WHY?
857 //REFINEREFINEREIFEN
858 //REFINEREFINEREIFEN
859 //REFINEREFINEREIFEN
860 //REFINEREFINEREIFEN
861 //REFINEREFINEREIFEN
862 //***********************************************
863
864 Mat postDilate = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(150,15));
865 Imgproc.dilate(centreOutput,centreOutput,postDilate);
866 imageViewer("91 PostDilated", centreOutput);
867
868 Mat postClose = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(10,4)); //4,4
869 Imgproc.morphologyEx(centreOutput, centreOutput, Imgproc.MORPH_CLOSE, postClose);
870 imageViewer("92 PostClose", centreOutput);
871
872 Mat postDenoize = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(100,100));
873 Imgproc.morphologyEx(centreOutput,centreOutput, Imgproc.MORPH_OPEN, postDenoize);
874 imageViewer("93 PostDenoize", centreOutput);
875
876 //Mat postOutline = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(50,50));
877 //Imgproc.morphologyEx(centreOutput, centreOutput, Imgproc.MORPH_GRADIENT, postOutline);
878
879
880
881 //Find area
882 Mat centreOutputGrey = new Mat();
883 Imgproc.cvtColor(centreOutput, centreOutputGrey, Imgproc.COLOR_RGB2GRAY);
884 Imgproc.findContours(centreOutputGrey, postContours, hierarchy, Imgproc.RETR_EXTERNAL, Imgproc.CHAIN_APPROX_SIMPLE);
885
886 for (int i = 0; i < postContours.size(); i++) {
887 double area = Imgproc.contourArea(postContours.get(i));
888 if(area > THRESHOLD_AREA_SIZE) {
889 System.out.println("POST AREA: " + area);
890 Imgproc.drawContours(postContoursFound, postContours, i, new Scalar(0, 255, 0), FILLED);
891 areaCounter++;
892 }
893 }
894
895
896
897 imageViewer("93 PostEND", postContoursFound);
898
899 //Classifier Calculation
900 if(areaCounter >= THRESHOLD_AREA_COUNT){
901 System.out.println("THIS IS SHEET MUSIC");
902 System.out.println(areaCounter);
903 }
904
905
906 }
907 //ClassifierComparison - Using code version 8
908 if(CODE_VERSION == 81) {
909
910 //Display Original
911 //imageViewer("original", original1);
912
913 Mat test = original.clone();
914
915
916 //imageViewer("00 Inverse Binarized Original", test);
917
918
919 //************************************
920 //Large Object Removal
921 //************************************
922 Mat srcLOR = original.clone();
923 Mat maskLOR = new Mat();
924 Mat dstLOR = new Mat();
925
926 //denoize
927 Mat denoize = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(5,5));
928 Imgproc.morphologyEx(srcLOR,maskLOR, Imgproc.MORPH_OPEN, denoize);
929 //imageViewer("01 Denoize - mask", maskLOR);
930
931 //close up gaps
932 Mat gapCloser = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(5,5));
933 Imgproc.morphologyEx(maskLOR,maskLOR,Imgproc.MORPH_CLOSE, gapCloser);
934 //imageViewer("02 gap closer - mask", maskLOR);
935
936 //Isolate large items
937 Mat isolateLarge = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(8, 8));
938 Imgproc.morphologyEx(maskLOR,maskLOR,Imgproc.MORPH_OPEN, isolateLarge);
939 //imageViewer("03 Isolate Large - mask", maskLOR);
940
941 //Remove large items from image
942 Core.bitwise_not(maskLOR,maskLOR);
943 srcLOR.copyTo(dstLOR, maskLOR);
944 //imageViewer("04 Large Items Removed", dstLOR);
945
946 //****************************************
947 //Small object removal (SOR)
948 //****************************************
949
950 Mat srcSOR = dstLOR.clone();
951 Mat maskSOR = new Mat();
952 Mat dstSOR = new Mat();
953
954 Mat startSOR =Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(7,7));
955 Imgproc.morphologyEx(srcSOR,maskSOR, Imgproc.MORPH_OPEN, startSOR);
956 //imageViewer("11 show small - mask", maskSOR);
957
958 Mat highlightSmall = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(7,7));
959 Imgproc.dilate(maskSOR, maskSOR, highlightSmall);
960 //imageViewer("12 highlight small - mask", maskSOR);
961
962/* Mat isolateSmall =Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(10,10));
963 Imgproc.morphologyEx(maskSOR,maskSOR,Imgproc.MORPH_CLOSE, isolateSmall);
964 imageViewer("13 isolate small - mask", maskSOR);
965*/
966
967 //Remove small items from image
968 Core.bitwise_not(maskSOR, maskSOR);
969 srcSOR.copyTo(dstSOR, maskSOR);
970 //imageViewer("14 Small Items Removed", dstSOR);
971
972
973 //****************************************
974 //start staff line detection
975 //****************************************
976
977 Mat kernelErode = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(15,2)); //10,2
978 Imgproc.erode(dstSOR,test,kernelErode);
979 //imageViewer("21 Erode plus pre", test);
980
981 Mat kernelDilate = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(10,4)); //20,3
982 Imgproc.dilate(test,test,kernelDilate);
983 //imageViewer("22 Dilate", test);
984
985 Mat kernelClose = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(10,4)); //4,4
986 Imgproc.morphologyEx(test, test, Imgproc.MORPH_CLOSE, kernelClose);
987 //imageViewer("23 Close", test);
988
989
990 Mat kernelErode02 = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(10,4)); //10,1
991 Imgproc.erode(test,test,kernelErode02);
992 //imageViewer("24 Erode (Final)", test);
993
994 //********************************************************************************
995 //DETECT OUTLINE AND FIND AREA OF THESE LINES.
996 //********************************************************************************
997 ArrayList<MatOfPoint> contours = new ArrayList<MatOfPoint>();
998 ArrayList<MatOfPoint> largeContours = new ArrayList<MatOfPoint>();
999 ArrayList<MatOfPoint> postContours = new ArrayList<MatOfPoint>();
1000 Mat hierarchy = new Mat();
1001
1002 //PARAMETERS: input image, output array of arrays, output array, contour retrieval mode, contour approximation method.
1003 //(contours) output array of arrays: Detected contours. Each contour is stored as a vector of points
1004 //(hierarchy) output array: Optional output vector, containing information about the image topology.
1005 //https://docs.opencv.org/3.3.1/d3/dc0/group__imgproc__shape.html#ga17ed9f5d79ae97bd4c7cf18403e1689a
1006
1007 Imgproc.findContours(test, contours, hierarchy, Imgproc.RETR_EXTERNAL, Imgproc.CHAIN_APPROX_SIMPLE);
1008
1009 System.out.println(contours.size());
1010 //Draw contours and record areas
1011 Mat allContoursFound = Mat.zeros(test.size(), CvType.CV_8UC3);
1012 Mat largeContoursFound = allContoursFound.clone() ;
1013 Mat postContoursFound = allContoursFound.clone();
1014 int areaCounter = 0;
1015
1016 //Have created a preprocess to remove large objects.
1017 //Need to now finalized Classifier, re try area detection.
1018 //Paths to take - rectangle boxes around detected contours over threshold (area or perimeter)
1019 //Just use area and periemter to determine if sheet music
1020 //Discuss with david before weekend perhaps?
1021
1022 Imgproc.drawContours(allContoursFound, contours, -1, new Scalar(0, 255, 0), 1); //USES LINE_8
1023 for (int i = 0; i < contours.size(); i++) {
1024 double area = Imgproc.contourArea(contours.get(i));
1025 if(area > 100) {
1026 //System.out.println("AREA: " + area);
1027 Imgproc.drawContours(largeContoursFound, contours, i, new Scalar(255, 0, 0), FILLED);
1028 //create list of large coutours found
1029 largeContours.add(contours.get(i));
1030 }
1031 }
1032 //imageViewer("80 All Contours found", allContoursFound);
1033 //imageViewer("81 Large Contours Found", largeContoursFound);
1034
1035 //*****************************************************************
1036 //Circles and centres on processed images
1037 //*****************************************************************
1038
1039 //Init arrays
1040 Mat circleOutput = allContoursFound.clone();
1041 MatOfPoint2f[] contoursPoly = new MatOfPoint2f[largeContours.size()];
1042 Point[] centers = new Point[largeContours.size()];
1043 float[][] radius = new float[largeContours.size()][1];
1044
1045 //Fill arrays
1046 for (int i = 0; i < largeContours.size(); i++) {
1047 contoursPoly[i] = new MatOfPoint2f();
1048 Imgproc.approxPolyDP(new MatOfPoint2f(largeContours.get(i).toArray()), contoursPoly[i], 1, true);
1049 centers[i] = new Point();
1050 Imgproc.minEnclosingCircle(contoursPoly[i], centers[i], radius[i]);
1051
1052 }
1053 //Draw circle for each large contour
1054 for (int i = 0; i < largeContours.size(); i++) {
1055 Imgproc.circle(circleOutput, centers[i], (int) radius[i][0],new Scalar(255, 0, 0), 1);
1056 }
1057 //imageViewer("82 Circles found", circleOutput);
1058
1059 //********************************************************************************
1060 //Centroids - Everything must be to scale
1061 //********************************************************************************
1062
1063 ArrayList<Moments> mu = new ArrayList<Moments>(largeContours.size());
1064 Mat centreOutput = Mat.zeros(largeContoursFound.size(), CvType.CV_8UC3);
1065 for (int i = 0; i < largeContours.size(); i++) {
1066 mu.add(i, Imgproc.moments(largeContours.get(i), false));
1067 Moments p = mu.get(i);
1068 int x = (int) (p.get_m10() / p.get_m00());
1069 int y = (int) (p.get_m01() / p.get_m00());
1070 Imgproc.circle(centreOutput, new Point(x, y), 4, new Scalar(255, 255, 255), 30);
1071 }
1072 //imageViewer("83 Centres found", centreOutput);
1073
1074
1075 //***********************************************
1076 //PostProcessing - Morphology Classifier
1077 // Use dilation to "Connect the dots"
1078 // Testing showed the centroids were clustered together
1079 // Then use area or perimeter as a classifier filter
1080 //REFINEREFINEREIFEN
1081 //REFINEREFINEREIFEN
1082 //REFINEREFINEREIFEN
1083 //REFINEREFINEREIFEN
1084 //REFINEREFINEREIFEN
1085 //REFINEREFINEREIFEN
1086 //***********************************************
1087
1088 Mat postDilate = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(150,15));
1089 Imgproc.dilate(centreOutput,centreOutput,postDilate);
1090 //imageViewer("91 PostDilated", centreOutput);
1091
1092 Mat postClose = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(10,4)); //4,4
1093 Imgproc.morphologyEx(centreOutput, centreOutput, Imgproc.MORPH_CLOSE, postClose);
1094 //imageViewer("92 PostClose", centreOutput);
1095
1096 Mat postDenoize = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(100,100));
1097 Imgproc.morphologyEx(centreOutput,centreOutput, Imgproc.MORPH_OPEN, postDenoize);
1098 //imageViewer("93 PostDenoize", centreOutput);
1099
1100 //Mat postOutline = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new Size(50,50));
1101 //Imgproc.morphologyEx(centreOutput, centreOutput, Imgproc.MORPH_GRADIENT, postOutline);
1102
1103
1104
1105 //Find area
1106 Mat centreOutputGrey = new Mat();
1107 Imgproc.cvtColor(centreOutput, centreOutputGrey, Imgproc.COLOR_RGB2GRAY);
1108 Imgproc.findContours(centreOutputGrey, postContours, hierarchy, Imgproc.RETR_EXTERNAL, Imgproc.CHAIN_APPROX_SIMPLE);
1109
1110 for (int i = 0; i < postContours.size(); i++) {
1111 double area = Imgproc.contourArea(postContours.get(i));
1112 if(area > 10000) {
1113 //System.out.println("POST AREA: " + area);
1114 Imgproc.drawContours(postContoursFound, postContours, i, new Scalar(0, 255, 0), FILLED);
1115 areaCounter++;
1116 }
1117 }
1118 //imageViewer("93 PostEND", postContoursFound);
1119
1120 //Classifier Calculation
1121 if(areaCounter >= THRESHOLD_AREA_COUNT){
1122 //System.out.println("THIS IS SHEET MUSIC");
1123 //System.out.println(areaCounter);
1124 }
1125
1126
1127 }
1128
1129 //USE stuc element, to rule out large wide and long pieces of black and white.
1130
1131
1132 //****************MORPHOLOGY****************************************************************************************
1133
1134 //BufferedImage toBeClassifiedImg = toBufferedImage(edgesDetectedRGB);
1135
1136 //Display Results
1137 //HighGui.imshow("Source", original);
1138 //HighGui.imshow("Just Edges", justEdges); //TESTING
1139
1140
1141 //imshow("LINESFOUND", edgesDetectedRGB);
1142 //HighGui.resizeWindow("LINESFOUND", 1000,1000);
1143
1144 //HighGui.imshow("CLUSTERS FOUND", clustersFoundRGB);
1145 //HighGui.imshow("Detected Lines (in red) - negative", edgesDetectedRGBProb);
1146
1147 //COUNT OF LINES CLASSIFICATION
1148 //System.out.println("LINE CLUSTER RESULT: " + ClassifierLineClusterOLD(toBeClassifiedImg).get(0) + '\t' + "LinesFound: " + ClassifierLineClusterOLD(toBeClassifiedImg).get(1) + '\t' + "ClustersFound: " + ClassifierLineClusterOLD(toBeClassifiedImg).get(2));
1149 //System.out.println("NEW CLUSTER RESULTS: " + ClassifierLineClusterPt(pointArrayList,clustersFoundRGB).get(0) + '\t' + "LinesFound: " + horizontalLineCount + '\t' + "ClustersFound: " + ClassifierLineClusterPt(pointArrayList,clustersFoundRGB).get(1));
1150 //System.out.println(ClassifierLineClusterPt(pointArrayList, clustersFoundRGB));
1151
1152 //System.out.println("TEST: " + LineCountOrCluster(horizontalLineCount, pointArrayList, clustersFoundRGB));
1153
1154 // Wait and Exit
1155 //HighGui.waitKey();
1156 System.exit(0);
1157 }
1158 catch(Exception e){
1159 System.err.println(e);
1160 }
1161 }
1162}
Note: See TracBrowser for help on using the repository browser.