use of com.joliciel.jochre.graphics.Shape in project jochre by urieli.
the class JochreDocument method getXml.
/**
* Returns an xml representation of this document as it currently stands, to
* be used for correcting the text associated with this document.
*/
public void getXml(OutputStream outputStream) {
try {
XMLOutputFactory xmlOutputFactory = XMLOutputFactory.newFactory();
XMLStreamWriter writer = xmlOutputFactory.createXMLStreamWriter(outputStream);
writer.writeStartDocument("UTF-8", "1.0");
writer.writeStartElement("doc");
writer.writeAttribute("name", this.getName());
writer.writeAttribute("fileName", this.getFileName());
writer.writeAttribute("locale", this.getLocale().getLanguage());
for (JochrePage page : this.getPages()) {
writer.writeStartElement("page");
writer.writeAttribute("index", "" + page.getIndex());
for (JochreImage image : page.getImages()) {
writer.writeStartElement("image");
writer.writeAttribute("name", image.getName());
writer.writeAttribute("index", "" + image.getIndex());
for (Paragraph paragraph : image.getParagraphs()) {
writer.writeStartElement("paragraph");
writer.writeAttribute("index", "" + paragraph.getIndex());
StringBuffer sb = new StringBuffer();
for (RowOfShapes row : paragraph.getRows()) {
for (GroupOfShapes group : row.getGroups()) {
for (Shape shape : group.getShapes()) {
if (shape.getLetter() != null)
sb.append(shape.getLetter());
}
sb.append(" ");
}
sb.append("\r\n");
}
writer.writeCData(sb.toString());
// paragraph
writer.writeEndElement();
}
// image
writer.writeEndElement();
}
// page
writer.writeEndElement();
}
// doc
writer.writeEndElement();
writer.writeEndDocument();
writer.flush();
} catch (XMLStreamException e) {
throw new JochreException(e);
}
}
use of com.joliciel.jochre.graphics.Shape in project jochre by urieli.
the class HeightFeature method checkInternal.
@Override
public FeatureResult<Double> checkInternal(ShapeWrapper shapeWrapper, RuntimeEnvironment env) {
Shape shape = shapeWrapper.getShape();
double ratio = (double) shape.getHeight() / (double) (shape.getBaseLine() - shape.getMeanLine());
FeatureResult<Double> outcome = this.generateResult(ratio);
return outcome;
}
use of com.joliciel.jochre.graphics.Shape in project jochre by urieli.
the class LowerLefthandOpeningFeature method checkInternal.
@Override
public FeatureResult<Boolean> checkInternal(ShapeWrapper shapeWrapper, RuntimeEnvironment env) {
Shape shape = shapeWrapper.getShape();
int lowerPoint = (int) ((double) shape.getHeight() * (7.0 / 8.0));
int upperPoint = shape.getHeight() / 2;
int openingThreshold = shape.getWidth() / 2;
int wallThreshold = shape.getWidth() / 4;
if (LOG.isTraceEnabled()) {
LOG.trace("lowerPoint: " + lowerPoint);
LOG.trace("upperPoint: " + upperPoint);
LOG.trace("openingThreshold: " + openingThreshold);
LOG.trace("wallThreshold: " + wallThreshold);
}
boolean foundWall = false;
boolean foundOpening = false;
boolean foundAnotherWall = false;
for (int y = upperPoint; y <= lowerPoint; y++) {
for (int x = 0; x <= openingThreshold; x++) {
if (!foundWall && x > wallThreshold) {
break;
} else if (!foundWall && shape.isPixelBlack(x, y, shape.getJochreImage().getBlackThreshold())) {
foundWall = true;
if (LOG.isTraceEnabled())
LOG.trace("foundWall y=" + y + ", x=" + x);
break;
} else if (foundWall && !foundOpening && shape.isPixelBlack(x, y, shape.getJochreImage().getBlackThreshold())) {
break;
} else if (foundWall && !foundOpening && x == openingThreshold) {
foundOpening = true;
if (LOG.isTraceEnabled())
LOG.trace("foundOpening y=" + y + ", x=" + x);
break;
} else if (foundOpening && !foundAnotherWall && x >= wallThreshold) {
break;
} else if (foundOpening && !foundAnotherWall && shape.isPixelBlack(x, y, shape.getJochreImage().getBlackThreshold())) {
foundAnotherWall = true;
if (LOG.isTraceEnabled())
LOG.trace("foundAnotherWall y=" + y + ", x=" + x);
break;
}
}
if (foundAnotherWall)
break;
}
FeatureResult<Boolean> outcome = this.generateResult(foundAnotherWall);
return outcome;
}
use of com.joliciel.jochre.graphics.Shape in project jochre by urieli.
the class LowerRightCornerFullFeature method checkInternal.
@Override
public FeatureResult<Boolean> checkInternal(ShapeWrapper shapeWrapper, RuntimeEnvironment env) {
Shape shape = shapeWrapper.getShape();
int xSectors = 5;
int centreSectors = 7;
int marginSectors = 1;
double[][] grid = shape.getBrightnessBySection(xSectors, centreSectors, marginSectors, SectionBrightnessMeasurementMethod.RELATIVE_TO_MAX_SECTION);
boolean cornerFull = false;
int cornerY = grid[0].length - (2 * marginSectors);
cornerFull = (grid[grid.length - 1][cornerY] >= 0.5);
FeatureResult<Boolean> outcome = this.generateResult(cornerFull);
return outcome;
}
use of com.joliciel.jochre.graphics.Shape in project jochre by urieli.
the class LowerRighthandGapFeature method checkInternal.
@Override
public FeatureResult<Boolean> checkInternal(ShapeWrapper shapeWrapper, RuntimeEnvironment env) {
Shape shape = shapeWrapper.getShape();
int xSectors = 7;
int centreSectors = 21;
int marginSectors = 1;
double[][] initialGrid = shape.getBrightnessBySection(xSectors, centreSectors, marginSectors, SectionBrightnessMeasurementMethod.RELATIVE_TO_MAX_SECTION);
double[][] grid = initialGrid.clone();
// get rid of holes
for (int i = 1; i < grid.length - 1; i++) {
for (int j = 1; j < grid[0].length - 1; j++) {
if (grid[i][j] == 0) {
if (grid[i - 1][j] >= 0.5 && grid[i + 1][j] >= 0.5 && grid[i][j - 1] >= 0.5 && grid[i][j + 1] >= 0.5)
grid[i][j] = 1;
}
}
}
boolean foundGap = false;
boolean goodGap = true;
int gapLeft = grid[0].length;
int gapRight = 0;
for (int j = (centreSectors / 2) + 1; j < grid[0].length; j++) {
if (LOG.isTraceEnabled())
LOG.trace("Row " + j);
if (foundGap) {
// check that there's a bit of white beneath it
goodGap = false;
for (int i = gapLeft; i <= gapRight; i++) {
double brightness = grid[i][j];
if (brightness < 0.5) {
goodGap = true;
gapRight = i;
gapLeft = i;
break;
}
}
if (!goodGap) {
foundGap = false;
goodGap = true;
}
// check the gap's limits
for (int i = gapRight - 1; i >= 0; i--) {
double brightness = grid[i][j];
if (brightness < 0.5)
gapLeft = i;
else
break;
}
for (int i = gapLeft + 1; i < grid.length; i++) {
double brightness = grid[i][j];
if (brightness < 0.5)
gapRight = i;
else
break;
}
if (LOG.isTraceEnabled())
LOG.trace("foundGap, gapLeft=" + gapLeft + ", gapRight=" + gapRight);
}
if (!foundGap) {
boolean reachedBlack = false;
boolean reachedWhite = false;
for (int i = 0; i < grid.length; i++) {
double brightness = grid[i][j];
if (foundGap)
reachedBlack = true;
if (!reachedBlack && brightness >= 0.5) {
if (LOG.isTraceEnabled())
LOG.trace("reachedBlack");
reachedBlack = true;
} else if (reachedBlack && brightness >= 0.5) {
if (grid[i][j - 1] == 1.0) {
if (!reachedWhite) {
if (LOG.isTraceEnabled())
LOG.trace("reachedWhite");
reachedWhite = true;
gapLeft = i;
}
} else {
reachedBlack = false;
reachedWhite = false;
}
} else if (reachedWhite && brightness >= 0.5) {
foundGap = true;
gapRight = i - 1;
if (LOG.isTraceEnabled())
LOG.trace("foundGap, gapLeft=" + gapLeft + ", gapRight=" + gapRight);
break;
}
}
}
}
FeatureResult<Boolean> outcome = this.generateResult(foundGap && goodGap);
return outcome;
}
Aggregations