diff options
Diffstat (limited to 'noatun-plugins/tippercanoe/polygon.h')
-rw-r--r-- | noatun-plugins/tippercanoe/polygon.h | 98 |
1 files changed, 98 insertions, 0 deletions
diff --git a/noatun-plugins/tippercanoe/polygon.h b/noatun-plugins/tippercanoe/polygon.h new file mode 100644 index 0000000..f711c03 --- /dev/null +++ b/noatun-plugins/tippercanoe/polygon.h @@ -0,0 +1,98 @@ +#include <string.h> + +template<class Pixel> +struct Bitmap { + int width, height, extra; + Pixel *data; + + Bitmap(int e=0) : extra(e), data(0) { }; + ~Bitmap() { delete[] data; }; + + void size(int w,int h) { + delete[] data; + width = w; + height = h; + data = new Pixel[w*h+extra]; + clear(); + } + + void clear() { + memset(data,0,sizeof(Pixel)*(width*height+extra)); + } +}; + +template<class Pixel, class Combiner, int superSampleShift> +struct PolygonEngine : public Bitmap<Pixel> { + PolygonEngine() : Bitmap<Pixel>(1) { } + +#define super (1<<superSampleShift) + void apply(Pixel *dest) { + Pixel sum=0; + int count = this->width*this->height; + Pixel *src = this->data; + while(count--) { + sum += *(src++); + if (sum) + *dest = Combiner::combine(sum,*dest); + dest++; + } + } + + void add(Pixel color,int x,int y) { + if (y < 0) return; + if (y >= this->height) return; + if (x < 0) x = 0; + if (x > this->width) x = this->width; + this->data[x+y*this->width] += color; + } + + /* Color is char[layers] */ + + // zwoosh, yknow, it goes... zwoosh an all these bars and lines and + // crap intersect. + Pixel colorTable[2][super+1]; + void pen(Pixel color) { + for(int i=0;i<super+1;i++) { + colorTable[0][i] = color*i; + colorTable[1][i] = -(color*i); + } + } + + void line(int x1,int y1,int x2,int y2) { + Pixel *colors; + if (y2 < y1) { + int temp; + temp = x2; x2 = x1; x1 = temp; + temp = y2; y2 = y1; y1 = temp; + colors = colorTable[1]; + } else { + if (y1 == y2) return; + + colors= colorTable[0]; + } + + int slope = (x1-x2 << 16)/(y1-y2); + int x = x1<<16, y = y1; + while(y < y2) { + add(colors[super-((x>>16)&(super-1))], + x>>(16+superSampleShift),y>>superSampleShift); + add(colors[(x>>16)&(super-1)], + 1+(x>>(16+superSampleShift)),y>>superSampleShift); + x += slope; + y++; + } + } + + void icon(double icon[][4],Pixel color,double x,double y, + double scaleX, double scaleY) { + pen(color); + x *= super; + y *= super; + scaleX *= super; + scaleY *= super; + for(int i=0;icon[i][1] != icon[i][3];i++) + line(int(icon[i][0]*scaleX+x),int(icon[i][1]*scaleY+y), + int(icon[i][2]*scaleX+x),int(icon[i][3]*scaleY+y)); + } +#undef super +}; |