/** * Try to recognize a clef in the compound of the provided glyphs. * * @param glyphs the parts of a clef candidate * @param staff the containing staff * @return true if successful */ private boolean checkClef(Collection<Glyph> glyphs, StaffInfo staff) { if (glyphs.isEmpty()) { return false; } // Check if we already have a clef among the intersected glyphs Set<Glyph> clefs = Glyphs.lookupGlyphs(glyphs, clefGlyphPredicate); Glyph orgClef = null; if (!clefs.isEmpty()) { if (Glyphs.containsManual(clefs)) { return false; // Respect user decision } else { // Remember grade of the best existing clef for (Glyph glyph : clefs) { if ((orgClef == null) || (glyph.getGrade() > orgClef.getGrade())) { orgClef = glyph; } } } } // Remove potential aliens Glyphs.purgeManuals(glyphs); Glyph compound = system.buildTransientCompound(glyphs); // Check if a clef appears in the top evaluations Evaluation vote = GlyphNetwork.getInstance().vote(compound, system, Grades.clefMinGrade, clefShapePredicate); if ((vote != null) && ((orgClef == null) || (vote.grade > orgClef.getGrade()))) { // We now have a clef! // Look around for an even better result... logger.debug("{} built from {}", vote.shape, Glyphs.toString(glyphs)); // Look for larger stuff Rectangle outer = compound.getBounds(); outer.grow(xMargin, yMargin); // Remember the box, for visual debug staff.addAttachment("co", outer); List<Glyph> outerGlyphs = system.lookupIntersectedGlyphs(outer); outerGlyphs.removeAll(glyphs); Collections.sort(outerGlyphs, Glyph.byReverseWeight); final double minWeight = constants.minWeight.getValue(); for (Glyph g : outerGlyphs) { // Consider only glyphs with a minimum weight if (g.getNormalizedWeight() < minWeight) { break; } logger.debug("Considering {}", g); Glyph newCompound = system.buildTransientCompound(Arrays.asList(compound, g)); final Evaluation newVote = GlyphNetwork.getInstance() .vote(newCompound, system, Grades.clefMinGrade, clefShapePredicate); if ((newVote != null) && (newVote.grade > vote.grade)) { logger.debug("{} better built with {}", vote, g.idString()); compound = newCompound; vote = newVote; } } // Register the last definition of the clef compound = system.addGlyph(compound); compound.setShape(vote.shape, Evaluation.ALGORITHM); logger.debug("{} rebuilt as {}", vote.shape, compound.idString()); return true; } else { return false; } }