Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
PokéPieChart, now with 200% more comments
import java.util.Map;
import java.util.Comparator;
import java.util.Collections;
int index = 0;
// sprite sheet
PImage pokemon;
// current pokemon sprite
PImage current;
// current pie chart
PGraphics pie;
// color -> color count
HashMap<Integer,Integer> colorMap;
// colors sorted by color count
ArrayList<Integer> colorByCount;
// total (significant) colors in sprite
int totalColors = 0;
void setup(){
size(250, 250);
frameRate(30);
pokemon = loadImage("allpokemon.png");
pokemon.loadPixels();
current = createImage(80, 80, ARGB);
pie = createGraphics(200, 200);
updateCurrent();
analyzePixels();
drawChartToBuffer();
}
void draw(){
background(0xFF);
image(pie, width/2-pie.width/2, height/2-pie.height/2);
}
// navigation
void keyPressed(){
switch(keyCode){
case 37:
index = index > 0 ? index - 1 : 492;
break;
case 39:
index = index < 492 ? index + 1 : 0;
break;
}
updateCurrent();
analyzePixels();
drawChartToBuffer();
}
// displays color, used for debugging
void mousePressed() {
color c = get(mouseX, mouseY);
println("#" + hex(c, 6) + " (" +hue(c)+ ")");
}
// draws the pie chart to the "pie" buffer
void drawChartToBuffer() {
pie.clear();
pie.beginDraw();
pie.noStroke();
drawChart(pie, min(pie.width - 8, pie.height - 8));
// this draws the pokemon in the middle
pie.image(
current,
pie.width / 2 - current.width / 2,
pie.height / 2 - current.height / 2
);
pie.endDraw();
}
// this draws the raw pie chart using the currently collected data
// g is the destination PGraphics buffer
// diameter is... well, the chart's diameter
void drawChart(PGraphics g, float diameter) {
float currentAngle = 0;
g.fill(0x10);
g.arc(g.width/2, g.height/2, diameter + 2, diameter + 2, radians(0), radians(360));
for(int i = 0; i < colorByCount.size(); i ++) {
color c = colorByCount.get(i);
float a = 360 * (float(colorMap.get(c))/float(totalColors));
g.fill(c);
g.arc(g.width/2, g.height/2, diameter, diameter, radians(currentAngle), radians(currentAngle + a + 1));
currentAngle += a;
}
}
// iterates over every pixel, adding it to/incrementing its entry in the mapColor hashmap
// after, it copies the keys of that hashmap into colorByCount and sorts them by the color count
void analyzePixels(){
// reset the currently collected data
totalColors = 0;
colorMap = new HashMap<Integer,Integer>();
current.loadPixels();
// load colorMap
for(int i = 0; i < 80; i ++) {
for(int j = 0; j < 80; j ++) {
color c = current.pixels[j * 80 + i];
// ignore BS colors
if(alpha(c) == 0) continue;
if((c & 0xFFFFFF) == 0x000000) continue;
if((c & 0xFFFFFF) == 0x101010) continue;
if((c & 0xFFFFFF) == 0x181818) continue;
// no key in colorMap, create one
if(!colorMap.containsKey(c))
colorMap.put(c, 0);
// count current pixel in colorMap
colorMap.put(c, colorMap.get(c) + 1);
totalColors ++;
}
}
// load colorByCount with the colors stored in colorMap's keys
colorByCount = new ArrayList<Integer>(colorMap.keySet());
// sort it by colorMap's values using Java's Collections thingy
Collections.sort(colorByCount, new Comparator<Integer>() {
public int compare(Integer a, Integer b) {
return colorMap.get(b) - colorMap.get(a);
}
});
}
// copies the sprite associated with the current index into the "current" PImage for analysis
// doing things the hard way because i forgot this was Processing when i was writing it
void updateCurrent(){
int k = 80 * (index % 25), l = 80 * floor(index / 25);
current.loadPixels();
for(int i = 0; i < 80; i ++)
for(int j = 0; j < 80; j ++)
current.pixels[j * 80 + i] = pokemon.pixels[(l + j) * pokemon.width + (k + i)];
current.updatePixels();
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.