use of boofcv.struct.PointIndex_I32 in project narchy by automenta.
the class ShapeSensor method isConvex.
public static boolean isConvex(List<PointIndex_I32> poly) {
int n = poly.size();
if (n < 4)
return true;
boolean sign = false;
for (int i = 0; i < n; i++) {
PointIndex_I32 a = poly.get((i + 2) % n);
PointIndex_I32 b = poly.get((i + 1) % n);
double dx1 = a.x - b.x;
double dy1 = a.y - b.y;
PointIndex_I32 c = poly.get(i);
double dx2 = c.x - b.x;
double dy2 = c.y - b.y;
double zcrossproduct = dx1 * dy2 - dy1 * dx2;
if (i == 0)
sign = zcrossproduct > 0;
else if (sign != (zcrossproduct > 0))
return false;
}
return true;
}
use of boofcv.struct.PointIndex_I32 in project narchy by automenta.
the class ShapeSensor method inputQuadBlob.
private void inputQuadBlob(int k, List<PointIndex_I32> polygon, float w, float h) {
Polygon2D_I32 p = new Polygon2D_I32(polygon.size());
for (PointIndex_I32 v : polygon) p.vertexes.add(v);
Rectangle2D_I32 quad = new Rectangle2D_I32();
UtilPolygons2D_I32.bounding(p, quad);
float cx = ((quad.x0 + quad.x1) / 2f) / w;
float cy = ((quad.y0 + quad.y1) / 2f) / h;
float cw = quad.getWidth() / w;
float ch = quad.getHeight() / h;
Term pid = $.p(id, $.the(k));
float conf = nar.confDefault(BELIEF);
long now = nar.time();
believe(now, $.inh(pid, $.the("x")), $.t(cx, conf));
believe(now, $.inh(pid, $.the("y")), $.t(cy, conf));
believe(now, $.inh(pid, $.the("w")), $.t(cw, conf));
believe(now, $.inh(pid, $.the("h")), $.t(ch, conf));
}
use of boofcv.struct.PointIndex_I32 in project narchy by automenta.
the class ShapeSensor method run.
@Override
public void run() {
long last = now;
now = nar.time();
if (last == ETERNAL)
last = now;
input.update();
if (img == null || img.width != input.width() || img.height != input.height()) {
// img = new GrayF32(input.width(), input.height());
img = new GrayU8(input.width(), input.height());
}
int w = img.width;
int h = img.height;
for (int x = 0; x < w; x++) {
for (int y = 0; y < h; y++) {
img.set(x, y, Math.round(256f * input.brightness(x, y, R, G, B)));
}
}
if (debug) {
if (polyDebug == null)
polyDebug = new BufferedImage(img.width, img.height, BufferedImage.TYPE_INT_RGB);
}
// the mean pixel value is often a reasonable threshold when creating a binary image
int mean = (int) ImageStatistics.mean(img);
// create a binary image by thresholding
ThresholdImageOps.threshold(img, img, mean, true);
// reduce noise with some filtering
GrayU8 filtered = img;
// for (int i = 0; i < 2; i++) {
filtered = BinaryImageOps.dilate8(filtered, 1, null);
filtered = BinaryImageOps.erode8(filtered, 1, null);
// // Fit a polygon to each shape and draw the results
if (debug) {
if (g2 == null) {
g2 = polyDebug.createGraphics();
}
g2.setColor(Color.BLACK);
g2.clearRect(0, 0, polyDebug.getWidth(), polyDebug.getHeight());
} else {
g2 = null;
}
List<Contour> contours = BinaryImageOps.contour(filtered, // ConnectRule.EIGHT,
ConnectRule.FOUR, null);
Grid g = new Grid(id, 12, 8, w, h) {
@Override
public Term line(int ax, int ay, int bx, int by) {
Term l = super.line(ax, ay, bx, by);
if (g2 != null) {
int aax = Math.round(ax * sx);
int aay = Math.round(ay * sy);
int bbx = Math.round(bx * sx);
int bby = Math.round(by * sy);
g2.setColor(Color.GRAY);
g2.setStroke(new BasicStroke(1));
g2.drawLine(Math.round(aax / sx), Math.round(aay / sy), Math.round(bbx / sx), Math.round(bby / sy));
}
return l;
}
};
int k = 0;
for (Contour c : contours) {
// Fit the polygon to the found external contour. Note loop = true
List<PointIndex_I32> outer = ShapeFittingOps.fitPolygon(c.external, true, 100, minimumSideFraction);
if (debug) {
g2.setColor(Color.getHSBColor(k / 10f, 0.8f, 0.8f));
g2.setStroke(new BasicStroke(2));
drawPolygon(outer, true, g2);
// System.out.println(c + ": " + polygon);
}
g.addPoly(k++, outer, true);
// // handle internal contours
// for (List<Point2D_I32> internal : c.internal) {
// List<PointIndex_I32> inner = ShapeFittingOps.fitPolygon(internal, true, splitFraction, minimumSideFraction, 100);
// g2.setColor(Color.getHSBColor(c.id / 10f, 0.8f, 0.4f));
// g2.setStroke(new BasicStroke(2));
// drawPolygon(inner, true, g2);
// g.addPoly(pk, inner, false);
// }
}
g.input(in, last, nar);
if (debug) {
gui.setImageRepaint(polyDebug);
}
}
use of boofcv.struct.PointIndex_I32 in project BoofCV by lessthanoptimal.
the class ShapeFittingOps method indexToPointIndex.
/**
* Converts the list of indexes in a sequence into a list of {@link PointIndex_I32}.
*
* @param sequence Sequence of points.
* @param indexes List of indexes in the sequence.
* @param output Output list of {@link PointIndex_I32}.
*/
public static void indexToPointIndex(List<Point2D_I32> sequence, DogArray_I32 indexes, DogArray<PointIndex_I32> output) {
output.reset();
for (int i = 0; i < indexes.size; i++) {
int index = indexes.data[i];
Point2D_I32 p = sequence.get(index);
PointIndex_I32 o = output.grow();
o.x = p.x;
o.y = p.y;
o.index = index;
}
}
use of boofcv.struct.PointIndex_I32 in project BoofCV by lessthanoptimal.
the class ExampleFitPolygon method fitBinaryImage.
/**
* Fits polygons to found contours around binary blobs.
*/
public static void fitBinaryImage(GrayF32 input) {
GrayU8 binary = new GrayU8(input.width, input.height);
BufferedImage polygon = new BufferedImage(input.width, input.height, BufferedImage.TYPE_INT_RGB);
// the mean pixel value is often a reasonable threshold when creating a binary image
double mean = ImageStatistics.mean(input);
// create a binary image by thresholding
ThresholdImageOps.threshold(input, binary, (float) mean, true);
// reduce noise with some filtering
GrayU8 filtered = BinaryImageOps.erode8(binary, 1, null);
filtered = BinaryImageOps.dilate8(filtered, 1, null);
// Find internal and external contour around each shape
List<Contour> contours = BinaryImageOps.contour(filtered, ConnectRule.EIGHT, null);
// Fit a polygon to each shape and draw the results
Graphics2D g2 = polygon.createGraphics();
g2.setStroke(new BasicStroke(2));
for (Contour c : contours) {
// Fit the polygon to the found external contour. Note loop = true
List<PointIndex_I32> vertexes = ShapeFittingOps.fitPolygon(c.external, true, minSide, cornerPenalty);
g2.setColor(Color.RED);
VisualizeShapes.drawPolygon(vertexes, true, g2);
// handle internal contours now
g2.setColor(Color.BLUE);
for (List<Point2D_I32> internal : c.internal) {
vertexes = ShapeFittingOps.fitPolygon(internal, true, minSide, cornerPenalty);
VisualizeShapes.drawPolygon(vertexes, true, g2);
}
}
gui.addImage(polygon, "Binary Blob Contours");
}
Aggregations