Skip to content

Instantly share code, notes, and snippets.

@frederickk
Created June 15, 2012 14:10
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save frederickk/2936680 to your computer and use it in GitHub Desktop.
Save frederickk/2936680 to your computer and use it in GitHub Desktop.
A collection of processing classes for the rendering of circle-packed pie chart illustrations
// ------------------------------------------------------------------------
// libraries
// ------------------------------------------------------------------------
import javax.media.opengl.GL;
import com.sun.opengl.util.BufferUtil;
public class glColorPieChart extends Circle {
// ------------------------------------------------------------------------
// properties
// ------------------------------------------------------------------------
// chart
protected float sz;
protected ArrayList piecesColors = new ArrayList();
protected int total = 0;
// hole
protected float holeRadius;
// colors
protected int piecesNum;
protected PImage img;
// ------------------------------------------------------------------------
// constructor
// ------------------------------------------------------------------------
public glColorPieChart() {
setCoord( new PVector() );
setSize(1);
piecesColors.add( color(255) );
}
public glColorPieChart(PVector _pos, float _sz, PImage _img) {
setCoord(_pos);
setSize(_sz);
setImage(_img);
piecesColors.add( color(255) );
}
// ------------------------------------------------------------------------
// methods
// ------------------------------------------------------------------------
public void init() {
float lastAng = 0.0;
for (int i=0; i<piecesColors.size(); i++) {
float ang = i*(360/piecesNum);
float[] rgba = getColor( (Integer) piecesColors.get(i) );
float bright = rgba[3]*255;
float val = radians( map(bright, 0, total, 0, 360) );
glArc(
pos.x, pos.y,
sz/2,
lastAng,
lastAng + val,
rgba//col
);
// int j = i+1;
// if(j < 0) j = piecesColors.size()-1;
// else if(j >= piecesColors.size()) j = 0;
//
// glArc(
// pos.x, pos.y,
// sz/2,
// lastAng,
// lastAng + val,
// rgba,
// getColor( (Integer) piecesColors.get(j) )
// );
lastAng += val;
}
}
// ------------------------------------------------------------------------
public void draw() {
draw(true);
}
public void draw(boolean bGatherColors) {
if (bGatherColors) gather();
init();
}
// ------------------------------------------------------------------------
protected void glArc(float cx, float cy, float r, float startRadAngle, float endRadAngle, float[] _rgba) {
PGraphicsOpenGL pgl = (PGraphicsOpenGL) g;
GL gl = pgl.beginGL();
gl.glBegin(GL.GL_TRIANGLE_STRIP);
int segments = 20;
float inc = abs(endRadAngle-startRadAngle)/segments;
float adj = radians(inc);
for (float i=startRadAngle-adj; i<endRadAngle+adj; i+=inc) {
// colors
gl.glColor4f(
_rgba[0],
_rgba[1],
_rgba[2],
_rgba[3]
);
// outer
float xo = cx + sin(i) * r;
float yo = cy + cos(i) * r;
gl.glVertex2f(xo, yo);
// inter
float xi = cx + sin(i) * (holeRadius/2);
float yi = cy + cos(i) * (holeRadius/2);
gl.glVertex2f(xi, yi);
}
gl.glEnd();
pgl.endGL();
}
// protected void glArc(float cx, float cy, float r, float startRadAngle, float endRadAngle, float[] _rgba1, float[] _rgba2) {
// PGraphicsOpenGL pgl = (PGraphicsOpenGL) g;
// GL gl = pgl.beginGL();
//
// gl.glBegin(GL.GL_TRIANGLE_STRIP);
//
// int segments = 20;
// float inc = (endRadAngle-startRadAngle)/segments;
// float amt = segments/100;
// for (float i=startRadAngle-inc; i<endRadAngle+inc; i+=inc) {
// // colors
// gl.glColor4f(
// lerp( _rgba1[0], _rgba2[0], amt),
// lerp( _rgba1[1], _rgba2[1], amt),
// lerp( _rgba1[2], _rgba2[2], amt),
// lerp( _rgba1[3], _rgba2[3], amt )
// );
// amt+=0.05;
//
// // outer
// float xo = cx + sin(i) * r;
// float yo = cy + cos(i) * r;
// gl.glVertex2f(xo, yo);
//
// // inter
// float xi = cx + sin(i) * (holeRadius/2);
// float yi = cy + cos(i) * (holeRadius/2);
// gl.glVertex2f(xi, yi);
// }
//
// gl.glEnd();
//
// pgl.endGL();
// }
// ------------------------------------------------------------------------
protected ArrayList gather() {
piecesColors.clear();
for (int i=0; i<piecesNum; i++) {
float angle = i*(360/piecesNum);
int ax = int(pos.x + cos(radians(angle)) * sz);
int ay = int(pos.y + sin(radians(angle)) * sz);
try {
if ((ax >= img.width) || (ay >= img.height) || (ax < 0) || (ay < 0)) {
continue;
}
else {
color col = img.pixels[ay * img.width + ax];
piecesColors.add( col );
}
}
catch (Exception e) {
}
}
total = colorArraySum();
return piecesColors;
}
// ------------------------------------------------------------------------
protected int colorArraySum() {
total = 0;
try {
for (int i=0; i<piecesColors.size(); i++) total += brightness( (Integer) piecesColors.get(i) );
}
catch(Exception e) {
}
return total;
}
// ------------------------------------------------------------------------
// sets
// ------------------------------------------------------------------------
public void setSize(float _sz) {
sz = _sz;
if (holeRadius > sz) holeRadius = int( sz*0.90 );
setRadius(sz/2);
}
// ------------------------------------------------------------------------
public void setHoleRadius(float _radius) {
holeRadius = _radius;
if (holeRadius > sz) holeRadius = int( sz*0.90 );
}
// ------------------------------------------------------------------------
public void setNumPieces(int _piecesNum) {
piecesNum = _piecesNum;
gather();
}
public void setImage(PImage _img) {
img = _img;
gather();
}
// ------------------------------------------------------------------------
// gets
// ------------------------------------------------------------------------
public float getSize() {
return sz;
}
// ------------------------------------------------------------------------
public float getHoleRadius() {
return holeRadius;
}
// ------------------------------------------------------------------------
public int getNumPieces() {
return piecesNum;
}
public PImage getImage() {
return img;
}
// ------------------------------------------------------------------------
public float[] getColor(int _col) {
int r = (_col >> 16) & 0xFF;
int g = (_col >> 8) & 0xFF;
int b = _col & 0xFF;
int a = (_col >> 24) & 0xFF;
float[] rgba = {
norm(r, 0, 255), norm(g, 0, 255), norm(b, 0, 255), norm(a, 0, 255)
};
return rgba;
}
}
public class RecolorImage extends Thread {
// ------------------------------------------------------------------------
// properties
// ------------------------------------------------------------------------
private PImage src;
private PImage newImg;
private int[] palette;
private int lo;
private int hi;
private int thresh;
private boolean bRunning;
private int waitMS = 10;
// ------------------------------------------------------------------------
// constructor
// ------------------------------------------------------------------------
public RecolorImage(PImage _src) {
src = _src;
setThresh(255);
//println("src.width: " + src.width + "\t" + "src.width " + src.height);
newImg = createImage(src.width, src.height, ARGB);
}
// ------------------------------------------------------------------------
// methods
// ------------------------------------------------------------------------
public void start() {
//println("start()");
bRunning = true;
super.start();
}
//-----------------------------------------------------------------------------
public void run() {
do {
update();
try {
//sleep( (long)waitMS );
} catch (Exception e) {
//println("error\t" + e);
}
} while(bRunning);
}
//-----------------------------------------------------------------------------
public void quit() {
//println("quit()");
bRunning = false;
interrupt();
}
// ------------------------------------------------------------------------
private void update() {
//println("update()");
if(src != null) {
newImg.loadPixels();
for (int i=0; i<newImg.pixels.length; i++) {
int pix = src.pixels[i];
int col = matchBrightness(pix);
newImg.pixels[i] = col;
}
newImg.updatePixels();
}
}
// ------------------------------------------------------------------------
private int matchBrightness(int _col) {
int val = -1;
if(palette.length > 0) {
for(int i=lo; i<hi; i++) {
int r = thresh;
do {
try {
if( brightness(_col) >= (brightness(palette[i]) - r) &&
brightness(_col) <= (brightness(palette[i]) + r) ) {
val = palette[i];
if(val != -1) break;
} else {
r += thresh;
}
} catch(Exception e) {
}
} while(val == -1);
}
}
return val;
}
//-----------------------------------------------------------------------------
// sets
//-----------------------------------------------------------------------------
public void set(int[] _palette, int _thresh) {
setPalette(_palette);
setThresh(thresh);
}
public void set(int[] _palette, int _lo, int _hi, int _thresh) {
setPalette(_palette, _lo,_hi);
setThresh(thresh);
}
//-----------------------------------------------------------------------------
public void setPalette(int[] _palette) {
palette = _palette;
lo = 0;
hi = palette.length;
}
public void setPalette(int[] _palette, int _lo, int _hi) {
palette = _palette;
lo = _lo;
hi = _hi;
}
//-----------------------------------------------------------------------------
public void setThresh(int _thresh) {
thresh = _thresh;
}
//-----------------------------------------------------------------------------
// gets
// ------------------------------------------------------------------------
public PImage get() {
if(newImg != null) {
return newImg;
}
else {
return null;
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment