I'm trying to implement flood fill algorithm using to fill the closed shape with specific color.
I think my code is worked out, but i don't know why are"StackOverflowError" rising up !!
i looked for the solution more and more but without finding the perfect answer.
public void paintComponent(Graphics g){
indecies.clear();
float x1 = 20;
float y1 = 20;
float x2 = 350;
float y2 = 20;
/* put the points of first line in ArraList */
for(int i = (int) x1; i < x2 ; i++){
index = (int) (i + y1 * img.getWidth());
list.add(index);
}
/***************************************************/
x1 = 350;
y1 = 20;
x2 = 100;
y2 = 100;
/* put the points of second line in ArraList */
for(int i = (int) y1; i <= y2 ; i++){
index = (int) (x1 * img.getWidth());
list.add(index);
}
/***************************************************/
x1 = 100;
y1 = 100;
x2 = 20;
y2 = 100;
/* put the points of the third line in ArraList */
for(int i = (int) x2; i < x1 ; i++){
index = (int) (i + y1 * img.getWidth());
list.add(index);
}
/*****************************************************/
x1 = 20;
y1 = 100;
x2 = 20;
y2 = 20;
/* put the points of the forth line in ArraList */
for(int i = (int) y2; i < y1 ; i++){
index = (int) (x1 * img.getWidth());
list.add(index);
}
/**************************************************/
/* Get each pixel from ArrayList of indecies then print into data raster of image */
for (Integer integer : indecies) {
pixels[integer] = Color.yellow.getRGB();
}
/* Flood fill recursive algorithm */
/* border color is yellow */
/* green is the new colow must be filled inside the shape */
fill(50, 50, Color.yellow.getRGB(), Color.green.getRGB());
g.drawImage(img, 0, 0, this);
}
Here is the fill method !!
public void fill(int x, int y, int borderColor, int newColor){
if(x >= 0 && x < width && y >= 0 && y < height){
int index = x + y * width;
if(pixels[index] != borderColor && pixels[index] != newColor){
pixels[index] = newColor;
fill(x, y - 1, borderColor, newColor);
fill(x, y + 1, borderColor, newColor);
fill(x + 1, y, borderColor, newColor);
fill(x - 1, y, borderColor, newColor);
}
}
}
Exception Details ..
java.lang.StackOverflowErrorjava.lang.StackOverflowErrorjava.lang.StackOverflowErrorjava.lang.StackOverflowErrorjava.lang.StackOverflowErrorjava.lang.StackOverflowError
at java.nio.Buffer.limit(Buffer.java:274)
at java.nio.Buffer.<init>(Buffer.java:201)
at java.nio.CharBuffer.<init>(CharBuffer.java:281)
at java.nio.HeapCharBuffer.<init>(HeapCharBuffer.java:70)
at java.nio.CharBuffer.wrap(CharBuffer.java:373)
at sun.nio.cs.StreamEncoder.implWrite(StreamEncoder.java:265)
at sun.nio.cs.StreamEncoder.write(StreamEncoder.java:125)
at java.io.OutputStreamWriter.write(OutputStreamWriter.java:207)
at java.io.BufferedWriter.flushBuffer(BufferedWriter.java:129)
at java.io.PrintStream.write(PrintStream.java:526)
at java.io.PrintStream.print(PrintStream.java:669)
at java.io.PrintStream.println(PrintStream.java:823)
at java.lang.Throwable$WrappedPrintStream.println(Throwable.java:748)
at java.lang.Throwable.printStackTrace(Throwable.java:655)
at java.lang.Throwable.printStackTrace(Throwable.java:643)
at java.lang.Throwable.printStackTrace(Throwable.java:634)
at FillColorAlgorithm.fill(FillColorAlgorithm.java:170)
at FillColorAlgorithm.fill(FillColorAlgorithm.java:162)
......... etc
public void floodFill(int x, int y, int borderColor, int fillColor, int imgWidth, int imgHeight){
Queue<java.awt.Point> nodesList = new LinkedList<>();
if(borderColor == fillColor) return;
if(x >= 0 && x < imgWidth && y >= 0 && y < imgHeight){
int index = x + y * imgWidth;
if(pixels[index] == fillColor) return;
nodesList.add(new java.awt.Point(x, y));
}
while(!nodesList.isEmpty()) {
java.awt.Point currentNode = nodesList.element();
int index = currentNode.x + currentNode.y * imgWidth;
if(pixels[index] != fillColor){
java.awt.Point westNode = currentNode;
java.awt.Point eastNode = currentNode;
westNode = MoveWest(westNode, borderColor);
eastNode = MoveEast(eastNode, borderColor);
for (int j = westNode.x + 1; j < eastNode.x; j++) {
index = j + currentNode.y * imgWidth;
pixels[index] = fillColor;
java.awt.Point northNode = new java.awt.Point(j, currentNode.y - 1);
java.awt.Point southNode = new java.awt.Point(j, currentNode.y + 1);
index = northNode.x + northNode.y * imgWidth;
if(northNode.y >= 0 && pixels[index] != fillColor && pixels[index] != borderColor) nodesList.add(northNode);
index = southNode.x + southNode.y * imgWidth;
if(southNode.y < imgHeight && pixels[index] != fillColor && pixels[index] != borderColor) nodesList.add(southNode);
}
}
nodesList.remove();
}
}
java.awt.Point MoveWest(java.awt.Point w, int borderColor){
int index;
do{
--w.x;
index = w.x + w.y * width;
}
while(w.x >= 0 && pixels[index] != borderColor);
return new java.awt.Point(w.x, w.y);
}
java.awt.Point MoveEast(java.awt.Point e, int borderColor){
int index;
do{
++e.x;
index = e.x + e.y * width;
}
while( e.x < width && pixels[index] != borderColor);
return new java.awt.Point(e.x, e.y);
}
Related
Displaying different images with different views. For example, sharpen is one. I cannot get it to show Sharpen. I cannot find out how to complete sharpen. I used the professor's code as example.
There are others:
blur 3 x 3
blur 5 x 5
edge detection
grayscale
RGB > GRB
Zoom in
Zoom out
I tried adding 1 to the for loops instead of zero.
Here is code:
PImage source;
PImage destination;
int w = 80;
float[][] matrix_3_3_average = {
{1.0/9.0, 1.0/9.0, 1.0/9.0 },
{1.0/9.0, 1.0/9.0, 1.0/9.0 },
{1.0/9.0, 1.0/9.0, 1.0/9.0 }
};
float[][] matrix_3_3_sharpen =
{ { -1, -1, -1 },
{ -1, 9, -1 },
{ -1, -1, -1 } };
void setup() {
size(200, 200);
source = loadImage("sunflower.jpg");
destination = createImage(source.width, source.height, RGB);
}
void draw() {
destination.loadPixels(); // Tell Processing that we want to read the pixels of the output window
source.loadPixels();
int xStart = constrain(mouseX - w/2, 0, width);
int xEnd = constrain(mouseX + w/2, 0, width);
int yStart = constrain(mouseY - w/2, 0, height);
int yEnd = constrain(mouseY + w/2, 0, height);
if (keyPressed) {
if (key == '0') {
image(source, 0, 0);
for (int x = 1; x < source.width; x++) {
for (int y = 1; y < source.height; y++) {
int loc = x + y * source.width;
if ((x > xStart) && (x < xEnd) && (y > yStart) && (y < yEnd))
destination.pixels[loc] = convolution(x, y, matrix_3_3_average, 3, source);
else
// set the color of the corresponding pixel to the output window to the color of the pixel to the input image
destination.pixels[loc] = source.pixels[loc];
}
}
} else if (key == '1') {
for (int x = 1; x < source.width; x++) {
for (int y = 1; y < source.height; y++) {
int loc = x * y * source.width;
if ((x > xStart) && (x <xEnd) && (y > yStart) && (y < yEnd))
destination.pixels[loc] = convolution(x, y, matrix_3_3_sharpen, 3, source);
else
destination.pixels[loc] = source.pixels[loc];
}
}
}
}
}
color convolution(int x, int y, float[][] matrix, int matrixSize, PImage img) {
int offset = (matrixSize - 1)/2;
float r = 0;
float g = 0;
float b = 0;
for (int i = 0; i < matrixSize; i++) {
for (int j = 0; j < matrixSize; j++) {
int xLoc = x + i - offset;
int yLoc = y + j - offset;
int loc = xLoc * yLoc * img.width;
loc = constrain(loc, 0, img.pixels.length-1);
r = r + matrix[i][j] * red(img.pixels[loc]);
g = g + matrix[i][j] * green(img.pixels[loc]);
b = b + matrix[i][j] * blue(img.pixels[loc]);
}
}
return color(r, g, b);
}
There is an issue when the index of the pixel in the image plan is calculated in the function convolution. The index of an pixel is x + y * width rather than x * width:
int loc = xLoc * yLoc * img.width;</s>
int loc = xLoc + yLoc * img.width;
Copy the source image to the destination at startup and continuously draw the destination image:
void setup() {
size(200, 200);
source = loadImage("C:/temp/flower.jpg"); //source = loadImage("sunflower.jpg");
destination = createImage(source.width, source.height, RGB);
destination.copy(source, 0, 0, source.width, source.height, 0, 0, source.width, source.height);
}
void draw() {
// [...]
image(destination, 0, 0);
}
Use the keyPressed() event to identify if a key was pressed, which starts am image filter:
boolean average = key == '0';
boolean sharpen = key == '1';
void keyPressed() {
average = key == '0';
sharpen = key == '1';
}
When an image filter is performed, the copy the copy the source image to the destination image. Update the pixel in the filtered region. Finally copy the changed destination image to the source image, to be prepared for the next filter operation:
destination.copy(source, 0, 0, source.width, source.height, 0, 0, source.width, source.height);
for (int x = 0; x < source.width; x++) {
for (int y = 0; y < source.height; y++) {
int loc = x + y * source.width;
if (x > xStart && x < xEnd && y > yStart && y < yEnd) {
if ( average )
destination.pixels[loc] = convolution(x, y, matrix_3_3_average, 3, source);
else
destination.pixels[loc] = convolution(x, y, matrix_3_3_sharpen, 3, source);
}
}
}
source.copy(destination, 0, 0, source.width, source.height, 0, 0, source.width, source.height);
See the example, where I applied th suggestions to the code of your question:
PImage source;
PImage destination;
int w = 80;
float[][] matrix_3_3_average = {
{1.0/9.0, 1.0/9.0, 1.0/9.0 },
{1.0/9.0, 1.0/9.0, 1.0/9.0 },
{1.0/9.0, 1.0/9.0, 1.0/9.0 }
};
float[][] matrix_3_3_sharpen =
{ { -1, -1, -1 },
{ -1, 9, -1 },
{ -1, -1, -1 } };
void setup() {
size(200, 200);
source = loadImage("C:/temp/flower.jpg"); //source = loadImage("sunflower.jpg");
destination = createImage(source.width, source.height, RGB);
destination.copy(source, 0, 0, source.width, source.height, 0, 0, source.width, source.height);
}
boolean average = key == '0';
boolean sharpen = key == '1';
void keyPressed() {
average = key == '0';
sharpen = key == '1';
}
void draw() {
int xStart = constrain(mouseX - w/2, 0, width);
int xEnd = constrain(mouseX + w/2, 0, width);
int yStart = constrain(mouseY - w/2, 0, height);
int yEnd = constrain(mouseY + w/2, 0, height);
println(xStart, xEnd, yStart, yEnd);
if (average || sharpen) {
destination.copy(source, 0, 0, source.width, source.height, 0, 0, source.width, source.height);
for (int x = 0; x < source.width; x++) {
for (int y = 0; y < source.height; y++) {
int loc = x + y * source.width;
if (x > xStart && x < xEnd && y > yStart && y < yEnd) {
if ( average )
destination.pixels[loc] = convolution(x, y, matrix_3_3_average, 3, source);
else
destination.pixels[loc] = convolution(x, y, matrix_3_3_sharpen, 3, source);
}
}
}
source.copy(destination, 0, 0, source.width, source.height, 0, 0, source.width, source.height);
average = sharpen = false;
}
image(destination, 0, 0);
}
color convolution(int x, int y, float[][] matrix, int matrixSize, PImage img) {
int offset = (matrixSize - 1)/2;
float r = 0;
float g = 0;
float b = 0;
for (int i = 0; i < matrixSize; i++) {
for (int j = 0; j < matrixSize; j++) {
int xLoc = x + i - offset;
int yLoc = y + j - offset;
int loc = xLoc + yLoc * img.width;
loc = constrain(loc, 0, img.pixels.length-1);
r = r + matrix[i][j] * red(img.pixels[loc]);
g = g + matrix[i][j] * green(img.pixels[loc]);
b = b + matrix[i][j] * blue(img.pixels[loc]);
}
}
return color(r, g, b);
}
The image rotates with code below, but wrong, some black dots appears on original image. I believe it's something with rotation code. Any solution? Thanks. The image dimensions is 32x32 pixels loaded on center of screen (320x240).
public class RendPanel extends JPanel {
private static final long serialVersionUID = 1L;
int widthe = 320;
int heighte = 240;
double angle = Math.toRadians(220);
double sin = Math.sin(angle);
double cos = Math.cos(angle);
double x0 = 0.5 * (widthe - 1); // point to rotate about
double y0 = 0.5 * (heighte - 1); // center of image
public static BufferedImage fbuffer;
public RendPanel(int width, int height) {
fbuffer = new BufferedImage(320, 240, BufferedImage.TYPE_INT_RGB);
BufferedImage in = null;
try { in = ImageIO.read(new File("square.png")); } //32x32 square .png
catch (IOException e) { e.printStackTrace(); }
for (int i = 0; i < in.getWidth(); i++) {
for (int j = 0; j < in.getHeight(); j++) {
fbuffer.setRGB(i + (320 / 2) - 16, j + (240 / 2) - 16, in.getRGB(i, j));
}
}
BufferedImage neww = new BufferedImage(320, 240, BufferedImage.TYPE_INT_RGB);
for (int x = 0; x < widthe; x++) {
for (int y = 0; y < heighte; y++) {
if(x >= x0 - 32 && x <= x0 + 32 && y >= y0 - 32 && y <= y0 + 32){
double a = x - x0;
double b = y - y0;
int xx = (int) (+a * cos - b * sin + x0);
int yy = (int) (+a * sin + b * cos + y0);
// plot pixel (x, y) the same color as (xx, yy) if it's in bounds
if (xx >= 0 && xx < width && yy >= 0 && yy < height) {
neww.setRGB(xx, yy, fbuffer.getRGB(x, y));
}
}
}
}
fbuffer = neww;
repaint();
setPreferredSize(new Dimension(width, height));
}
protected void paintComponent(Graphics g) {
super.paintComponent(g);
g.drawImage(fbuffer, 0, 0, null);
}
}
A beginner's mistake (sorry).
Taking every source pixel in turn, transforming the coordinates to the destination and copying the pixel value is not the right way.because the regular input grid will not map to a regular grid, and there will be voids (and overlaps).
The correct way is to scan the destination image (so that every destination pixel is reached) and counter-transform the coordinates to fetch the pixel value from the source.
As a refinement, you can use the four neighboring pixel from where you land in the source and perform bilinear interpolation, to reduce aliasing.
Man, it's strange, because in this code it works properly!
Heres a working code:
public class RendPanel extends JPanel {
private static final long serialVersionUID = 1L;
int widthe = 320;
int heighte = 240;
int ang = 0;
double x0 = 0.5 * (widthe - 1); // point to rotate about
double y0 = 0.5 * (heighte - 1); // center of image
public static BufferedImage fbuffer;
public RendPanel(int width, int height) {
fbuffer = new BufferedImage(320, 240, BufferedImage.TYPE_INT_RGB);
BufferedImage in = null;
try { in = ImageIO.read(new File("square.png")); } //32x32 square .png
catch (IOException e) { e.printStackTrace(); }
for (int i = 0; i < in.getWidth(); i++) {
for (int j = 0; j < in.getHeight(); j++) {
fbuffer.setRGB(i + (320 / 2) - 16, j + (240 / 2) - 16, in.getRGB(i, j));
}
}
setPreferredSize(new Dimension(width, height));
}
BufferedImage neww;
public void r(){
neww = new BufferedImage(320, 240, BufferedImage.TYPE_INT_RGB);
double angle = Math.toRadians(ang);
double sin = Math.sin(angle);
double cos = Math.cos(angle);
for (int x = 0; x < widthe; x++) {
for (int y = 0; y < heighte; y++) {
if(x >= x0 - 32 && x <= x0 + 32 && y >= y0 - 32 && y <= y0 + 32){
double a = x - x0;
double b = y - y0;
int xx = (int) (+a * cos - b * sin + x0);
int yy = (int) (+a * sin + b * cos + y0);
// plot pixel (x, y) the same color as (xx, yy) if it's in bounds
if (xx >= 0 && xx < widthe && yy >= 0 && yy < heighte) {
neww.setRGB(x, y, fbuffer.getRGB(xx, yy));
}
}
}
}
ang++;
repaint();
}
protected void paintComponent(Graphics g) {
super.paintComponent(g);
g.drawImage(neww, 0, 0, null);
}
}
Thanks for:
https://introcs.cs.princeton.edu/java/31datatype/Rotation.java.html
EDIT:
You have to invert the vars on bf2.setRGB(x, y, fbuffer.getRGB(xx, yy)); to the rotated coordinate.
I have defined a shape using an array of vertices:
float[] points = new float[]{50,60,50,70,60,70, 60,60,50,60};
And I am drawing this here:
shapeRenderer.polygon(floatNew);
This just gives an outline of the shape.
How do I fill it with colour?
Thanks
Currently, ShapeRenderer supports polygon drawing (by line) but not filling.
This code is clipping the polygon on triangles, and then drawing each triangle separately.
Edit ShapeRenderer.java like this:
EarClippingTriangulator ear = new EarClippingTriangulator();
public void polygon(float[] vertices, int offset, int count)
{
if (shapeType != ShapeType.Filled && shapeType != ShapeType.Line)
throw new GdxRuntimeException("Must call begin(ShapeType.Filled) or begin(ShapeType.Line)");
if (count < 6)
throw new IllegalArgumentException("Polygons must contain at least 3 points.");
if (count % 2 != 0)
throw new IllegalArgumentException("Polygons must have an even number of vertices.");
check(shapeType, null, count);
final float firstX = vertices[0];
final float firstY = vertices[1];
if (shapeType == ShapeType.Line)
{
for (int i = offset, n = offset + count; i < n; i += 2)
{
final float x1 = vertices[i];
final float y1 = vertices[i + 1];
final float x2;
final float y2;
if (i + 2 >= count)
{
x2 = firstX;
y2 = firstY;
} else
{
x2 = vertices[i + 2];
y2 = vertices[i + 3];
}
renderer.color(color);
renderer.vertex(x1, y1, 0);
renderer.color(color);
renderer.vertex(x2, y2, 0);
}
} else
{
ShortArray arrRes = ear.computeTriangles(vertices);
for (int i = 0; i < arrRes.size - 2; i = i + 3)
{
float x1 = vertices[arrRes.get(i) * 2];
float y1 = vertices[(arrRes.get(i) * 2) + 1];
float x2 = vertices[(arrRes.get(i + 1)) * 2];
float y2 = vertices[(arrRes.get(i + 1) * 2) + 1];
float x3 = vertices[arrRes.get(i + 2) * 2];
float y3 = vertices[(arrRes.get(i + 2) * 2) + 1];
this.triangle(x1, y1, x2, y2, x3, y3);
}
}
}
You cant draw a filled Polygon with the shaperender yet. take a look at this from the bugtracker
You can also read that in the API.
public void polygon(float[] vertices)
Draws a polygon in the x/y plane. The vertices must contain at least 3
points (6 floats x,y). The ShapeRenderer.ShapeType passed to begin has
to be ShapeRenderer.ShapeType.Line.
API ShapeRender
Sure if its with ShapeType.Line you just get the outlines.
You need to draw it yourself with Triangles in that case. It should be possible to fill at least Triangles.
Maybe take a look at this from Stackoverflow: drawing-filled-polygon-with-libgdx
Edit your ShapeRenderer.java class replacing polygon() method with the following code:
public void polygon(float[] vertices, int offset, int count) {
if (currType != ShapeType.Filled && currType != ShapeType.Line)
throw new GdxRuntimeException(
"Must call begin(ShapeType.Filled) or begin(ShapeType.Line)");
if (count < 6)
throw new IllegalArgumentException(
"Polygons must contain at least 3 points.");
if (count % 2 != 0)
throw new IllegalArgumentException(
"Polygons must have an even number of vertices.");
checkDirty();
checkFlush(count);
final float firstX = vertices[0];
final float firstY = vertices[1];
if (currType == ShapeType.Line) {
for (int i = offset, n = offset + count; i < n; i += 2) {
final float x1 = vertices[i];
final float y1 = vertices[i + 1];
final float x2;
final float y2;
if (i + 2 >= count) {
x2 = firstX;
y2 = firstY;
} else {
x2 = vertices[i + 2];
y2 = vertices[i + 3];
}
renderer.color(color);
renderer.vertex(x1, y1, 0);
renderer.color(color);
renderer.vertex(x2, y2, 0);
}
} else {
for (int i = offset, n = offset + count; i < n; i += 4) {
final float x1 = vertices[i];
final float y1 = vertices[i + 1];
if (i + 2 >= count) {
break;
}
final float x2 = vertices[i + 2];
final float y2 = vertices[i + 3];
final float x3;
final float y3;
if (i + 4 >= count) {
x3 = firstX;
y3 = firstY;
} else {
x3 = vertices[i + 4];
y3 = vertices[i + 5];
}
renderer.color(color);
renderer.vertex(x1, y1, 0);
renderer.color(color);
renderer.vertex(x2, y2, 0);
renderer.color(color);
renderer.vertex(x3, y3, 0);
}
}
}
Usage:
gdx_shape_renderer.begin(ShapeType.Filled);
gdx_shape_renderer.setColor(fill_r, fill_g, fill_b, fill_a);
gdx_shape_renderer.polygon(vertices);
gdx_shape_renderer.end();
gdx_shape_renderer.begin(ShapeType.Line);
gdx_shape_renderer.setColor(border_r, border_g, border_b, border_a);
gdx_shape_renderer.polygon(vertices);
gdx_shape_renderer.end();
I am trying to make a processing program, but if I use P2D, P3D, or OPENGL mode I get an error:
com.sun.jdi.VMDisconnectedException
at com.sun.tools.jdi.TargetVM.waitForReply(TargetVM.java:285)
at com.sun.tools.jdi.VirtualMachineImpl.waitForTargetReply(VirtualMachineImpl.java:1015)
at com.sun.tools.jdi.PacketStream.waitForReply(PacketStream.java:51)
at com.sun.tools.jdi.JDWP$ObjectReference$InvokeMethod.waitForReply(JDWP.java:4589)
at com.sun.tools.jdi.ObjectReferenceImpl.invokeMethod(ObjectReferenceImpl.java:374)
at processing.mode.java.runner.Runner.findException(Runner.java:701)
at processing.mode.java.runner.Runner.reportException(Runner.java:652)
at processing.mode.java.runner.Runner.exception(Runner.java:595)
at processing.mode.java.runner.EventThread.exceptionEvent(EventThread.java:367)
at processing.mode.java.runner.EventThread.handleEvent(EventThread.java:255)
at processing.mode.java.runner.EventThread.run(EventThread.java:89)
the error message itself varies between P2D and P3D, but they both get a no framebuffer objects available error. I am using processing 2.0b7, please help and let me know if you need more info.
Note: I don't know if this is a separate issue or not, but I am also getting GLSL shader errors to.
Now, here is my code:
Cell[][] Cells = new Cell[50][50];
byte Direction = 1;
byte Times = 1;
int oldwidth = 500;
int oldheight = 500;
void setup() {
size(oldwidth, oldheight, OPENGL);
background(255);
colorMode(HSB,250);
for (int x = 0; x < 50; x++) {
for (int y = 0; y < 50; y++) {
Cells[x][y] = new Cell(x * 5, y * 5, 255, x * (width / 50), y * (height / 50), width / 50, height / 50);
}
}
}
void draw() {
for (int x = 0; x < 50; x++) {
for (int y = 0; y < 50; y++) {
if (width == oldwidth) Cells[x][y].Width = width / 50;
if (height == oldheight) Cells[x][y].Height = height / 50;
if (Direction == 1){
Cells[x][y].Hue += 5;
if (Cells[x][y].Hue > 250) Cells[x][y].Hue -= 250;
}
if (Direction == 2){
Cells[x][y].Saturation -= 5;
if (Cells[x][y].Saturation < 0) Cells[x][y].Saturation += 500;
}
if (Direction == 3){
Cells[x][y].Hue -= 5;
if (Cells[x][y].Hue < 0) Cells[x][y].Hue += 250;
}
if (Direction == 4){
Cells[x][y].Saturation += 5;
if (Cells[x][y].Saturation > 500) Cells[x][y].Saturation -= 500;
}
Cells[x][y].Draw();
}
}
if (Times == 50){
Times = 1;
if (Direction == 4) Direction = 1; else Direction += 1;
} else Times += 1;
delay(10);
}
class Cell {
int X;
int Y;
int Width;
int Height;
float Hue;
float Saturation;
float Brightness;
Cell(color parC, int parX, int parY, int parWidth, int parHeight) {
Hue = hue(parC);
Saturation = saturation(parC);
Brightness = brightness(parC);
X = parX;
Y = parY;
Width = parWidth;
Height = parHeight;
}
Cell(float parHue, float parSaturation, float parBrightness, int parX, int parY, int parWidth, int parHeight) {
Hue = parHue;
Saturation = parSaturation;
Brightness = parBrightness;
X = parX;
Y = parY;
Width = parWidth;
Height = parHeight;
}
void Draw() {
if (Saturation > 250) if (Saturation > 500) stroke(color(Hue,0,Brightness)); else stroke(color(Hue,Saturation - (Saturation - 250) * 2,Brightness)); else stroke(color(Hue,Saturation,Brightness));
if (Saturation > 250) if (Saturation > 500) fill(color(Hue,0,Brightness)); else fill(color(Hue,Saturation - (Saturation - 250) * 2,Brightness)); else fill(color(Hue,Saturation,Brightness));
rect(X, Y, Width, Height);
}
}
I just realized that it is just that my graphics card does not support OPENGL 2.0
I am trying to make a bounding box over the blue-colored pixels (from Kinect v1 camera, using Processing). Y-axis of bounding box works perfectly but x-axis is very off.
void display() {
PImage img = kinect.getDepthImage();
float maxValue = 0;
float minValue = kinect.width*kinect.height ;
float maxValueX = 0;
float maxValueY = 0;
float minValueX = kinect.width;
float minValueY = kinect.height;
// Being overly cautious here
if (depth == null || img == null) return;
display.loadPixels();
for (int x = 0; x < kinect.width; x++) { //goes through all the window
for (int y = 0; y < kinect.height; y++) {
int offset = x + y * kinect.width;
// Raw depth
int rawDepth = depth[offset];
int pix = x + y * display.width; //why is it y*width
if (rawDepth < threshold) {
// A blue color instead
display.pixels[pix] = color(0, 0, 255); //set correct pixels to blue
if(pix > maxValue){
maxValue = pix;
maxValueX = x;
maxValueY = y;
}
if(pix < minValue){
minValue = pix;
minValueX = x;
minValueY = y;
}
} else {
display.pixels[pix] = img.pixels[offset];
}
}
}
display.updatePixels();
image(display, 0, 0);
rect(minValueX, minValueY, maxValueX-minValueX, maxValueY-minValueY);
}
You have to calculate the minimum and maximum values for each index or coordinate separately. Use the min respectively max function for this:
maxValue = max(maxValue, pix);
minValue = min(minValue, pix);
maxValueX = max(maxValueX, x);
minValueX = min(minValueX, x);
maxValueY = max(maxValueY, y);
minValueY = min(minValueY, y);
or with an ifstatement:
if (pix > maxValue) { maxValue = pix; }
if (pix < minValue) { minValue = pix; }
if (x > maxValueX) { maxValueX = x; }
if (x < minValueX) { minValueX = x; }
if (y > maxValueY) { maxValueY = y; }
if (y < minValueY) { minValueY = y; }