summaryrefslogtreecommitdiff
path: root/rotord/src/cvimage.h
diff options
context:
space:
mode:
authorComment <tim@gray.(none)>2013-07-26 22:46:17 +0100
committerComment <tim@gray.(none)>2013-07-26 22:46:17 +0100
commitf4170d6bfb763ad0af4002277a37dcd1692534d5 (patch)
treedb32d9753de780063e3afeb64764e13e5c4f5087 /rotord/src/cvimage.h
parent3d7eea02aa7a155b84c8c74ecbfd55a1941a9297 (diff)
tidy files
Diffstat (limited to 'rotord/src/cvimage.h')
-rw-r--r--rotord/src/cvimage.h191
1 files changed, 191 insertions, 0 deletions
diff --git a/rotord/src/cvimage.h b/rotord/src/cvimage.h
new file mode 100644
index 0000000..2f9ed3b
--- /dev/null
+++ b/rotord/src/cvimage.h
@@ -0,0 +1,191 @@
+#ifndef ROTOR_CVIMAGE
+#define ROTOR_CVIMAGE
+
+#include <math.h>
+#include <cv.h>
+
+//converting to use a cv image...
+//cv::Mat supports most of what we want here
+//need to think
+//http://answers.opencv.org/question/8202/using-external-image-data-in-a-cvmat/
+
+//all access to the image is presently through a pointer to the data
+//cv::Mat supports this
+
+//how will copying work?
+//Rotor::Image will contain a cv::Mat object which may own its data or inherit it
+//cv::Mat should take care of reference counting
+
+//can cv::Mat
+
+namespace Rotor {
+ class pixeltables{
+ //handy pixel arithmetic lookup tables as nested arrays
+ //so - pixels.add[0x78][0x66]; will give the precalculated result of adding with saturation
+ // pixels.mono_weights[0][0x100]; will give the red component to convert to mono
+ public:
+ pixeltables(){
+ add=new uint8_t*[256];
+ multiply=new uint8_t*[256];
+ for (int i=0;i<256;i++){
+ add[i]=new uint8_t[256];
+ multiply[i]=new uint8_t[256];
+ for (int j=0;j<256;j++){
+ add[i][j]=(uint8_t)std::min(i+j,0xFF);
+ multiply[i][j]=(uint8_t)((((float)i)/255.0f)*(((float)j)/255.0f)*255.0f);
+ }
+ }
+ mono_weights=new uint8_t*[3];
+ float weights[3]={0.2989, 0.5870, 0.1140};
+ for (int i=0;i<3;i++) {
+ mono_weights[i]=new uint8_t[256];
+ for (int j=0;j<256;j++){
+ mono_weights[i][j]=(uint8_t)(((float)j)*weights[i]);
+ }
+ }
+ }
+ virtual ~pixeltables(){
+ for (int i=0;i<256;i++){
+ delete[] add[i];
+ delete[] multiply[i];
+ }
+ delete[] add;
+ delete[] multiply;
+ for (int i=0;i<3;i++) {
+ delete[] mono_weights[i];
+ }
+ delete[] mono_weights;
+ }
+ uint8_t **add;
+ uint8_t **multiply;
+ uint8_t **mono_weights;
+ };
+ static pixeltables pixels;
+ class Image{
+ public:
+ Image(){
+ zero();
+ };
+ Image(int _w,int _h){
+ zero();
+ setup(_w,_h);
+ };
+ ~Image() {
+ free();
+ };
+ void free(){
+ if (RGBdata&&ownsRGBdata) delete[] RGBdata;
+ if (Adata&&ownsAdata) delete[] Adata;
+ if (Zdata&&ownsZdata) delete[] Zdata;
+ zero();
+ }
+ void zero(){
+ RGBdata=nullptr;
+ Adata=nullptr;
+ Zdata=nullptr;
+ w=0;
+ h=0;
+ ownsRGBdata=ownsAdata=ownsZdata=false;
+ }
+ int getStride(){
+ return w*3;
+ }
+ bool setup(int _w,int _h){ //set up with internal data
+ rgb.create(_h,_w,CV_8UC3);
+ RGBdata=rgb.data; //can move to use the bare pointer eventually
+ ownsRGBdata=false; //will not be necessary
+ w=_w;
+ h=_h;
+ return true;
+ /*
+ if (w!=_w||h!=_h||!ownsRGBdata||!ownsAdata||!ownsZdata){
+ free();
+ w=_w;
+ h=_h;
+ RGBdata=new uint8_t[w*h*3];
+ Adata=new uint8_t[w*h];
+ Zdata=new uint16_t[w*h];
+ ownsRGBdata=ownsAdata=ownsZdata=true;
+ return true;
+ }
+ else return false;
+ */
+ }
+ bool setup_fromRGB(int _w,int _h,uint8_t *pRGBdata,int linepadding=0){
+ //here the data belongs to libavcodec or other
+ //could move to using cv::Mat there also and just passing cv:Mat over
+
+ //linepadding causes crash, but it doesn't seem to be necessary
+ // Mat::Mat(int rows, int cols, int type, void* data, size_t step=AUTO_STEP)
+ rgb=cv::Mat(_h,_w,CV_8UC3,pRGBdata,(_w*3)+linepadding);
+ //std::cerr<<"created cv::Mat with step= "<<rgb.step<<",should be "<<((_w*3)+linepadding)<<std::endl;
+
+ RGBdata=rgb.data; //can move to use the bare pointer eventually
+ ownsRGBdata=false; //will not be necessary
+ w=_w;
+ h=_h;
+ return true;
+ /*
+ if (w!=_w||h!=_h||ownsRGBdata||!ownsAdata||!ownsZdata){
+ free();
+ w=_w;
+ h=_h;
+ RGBdata=pRGBdata;
+ Adata=new uint8_t[w*h];
+ Zdata=new uint16_t[w*h];
+ ownsRGBdata=false;
+ ownsAdata=ownsZdata=true;
+ return true;
+ }
+ return false;
+ */
+ }
+ bool setup_fromMat(cv::Mat& othermat){
+ //here the mat belongs to another Image object
+ rgb=cv::Mat(othermat);
+ RGBdata=rgb.data; //can move to use the bare pointer eventually
+ ownsRGBdata=false; //will not be necessary
+ w=rgb.rows;
+ h=rgb.cols;
+ return true;
+ }
+ Image* clone(){
+ Image *t=new Image();
+ t->rgb=rgb.clone();
+ t->w=w;
+ t->h=h;
+ t->RGBdata=t->rgb.data; //can move to use the bare pointer eventually
+ t->ownsRGBdata=false; //will not be necessary
+ /*
+ for (int i=0;i<w*h*3;i++) {
+ t->RGBdata[i]=RGBdata[i];
+ }
+ */
+ return t;
+ }
+ //believe these still work, don't know if these optimisations are better than opencvs..
+ Image & operator+=(const Image &other);
+ Image & operator*=(const Image &other);
+ Image & operator^=(const Image &other);
+ Image & alpha_blend(const Image &other);
+ Image & alpha_blend_cv(const Image &other);
+ Image & alpha_merge(const Image &other);
+ Image & add_wrap(const Image &other);
+ Image & divide_wrap(const Image &other);
+ Image & operator*=(const float &amount);
+ Image * operator*(const float &amount);
+ Image * operator+(const float &amount);
+ Image * operator-(const float &amount);
+ Image * operator/(const float &amount);
+ uint8_t *RGBdata;
+ uint8_t *Adata;
+ uint16_t *Zdata;
+ int h,w;
+ bool ownsRGBdata,ownsAdata,ownsZdata; //better done through auto_ptr?
+
+ cv::Mat rgb;
+ cv::Mat alpha;
+ };
+}
+
+#endif \ No newline at end of file