#include #include #include #pragma comment(lib,"cv.lib") #pragma comment(lib,"cxcore.lib") #pragma comment(lib,"highgui.lib") #define MAG 1.5 void Bilinear(unsigned char *out, unsigned char *in, int inHeight, int inWidth, int inChannel, double mag); int main(){ IplImage *in, *out; in = cvLoadImage("./image640.bmp", 1); out = cvCreateImage(cvSize((int)(in->width*MAG), (int)(in->height*MAG)), 8, in->nChannels); Bilinear((unsigned char*)out->imageData, (unsigned char*)in->imageData, in->height, in->width, in->nChannels, MAG); cvNamedWindow("in", 1); cvShowImage("in", in); cvNamedWindow("out", 1); cvShowImage("out", out); cvWaitKey(-1); cvDestroyWindow("in"); cvDestroyWindow("out"); cvReleaseImage(&in); cvReleaseImage(&out); return 0; } /* in : 横は4バイト */ void Bilinear(unsigned char *out, unsigned char *in, int inHeight, int inWidth, int inChannel, double mag){ int height; int width; int outStep; int inStep; int i, j; double inX, inY; height = (int)((double)inHeight * mag); width = (int)((double)inWidth * mag); // OpenCVで使用する画像データの横幅は4バイト区切りのため調整 inStep = inWidth * inChannel; if( (inStep % 4) != 0){ inStep = inStep + (4 - inStep %4); } outStep = width * inChannel; if( (outStep % 4) != 0){ outStep = outStep + (4 - outStep %4); } // ループ中にif文を書くと遅いためループ前にビット数の条件分岐 switch(inChannel){ case 1: // 8bit画像 for(i = 0; i < height; ++i){ inY = (double)i / mag; // 入力画像の高さを超えないようにする if((int)inY >= inHeight){ --inY; } for(j = 0; j < width; ++j){ // 入力画像の幅を超えないようにする inX = (double)j / mag; if((int)inX >= inWidth){ --inX; } out[i * outStep + j] = (unsigned char)(((int)inX + 1 - inX) * ((int)inY + 1 - inY) * (double)in[(int)inY * inStep + (int)inX] + (inX - (int)inX) * ((int)inY + 1 - inY) * (double)in[(int)inY * inStep + (int)inX + 1] + ((int)inX + 1 - inX) * (inY - (int)inY) * (double)in[((int)inY + 1) * inStep + (int)inX] + (inX - (int)inX) * (inY - (int)inY) * (double)in[((int)inY + 1) * inStep + (int)inX + 1]); } } break; case 3: // 24bit画像 for(i = 0; i < height; ++i){ inY = (double)i / mag; // 入力画像の高さを超えないようにする if((int)inY >= inHeight){ --inY; } for(j = 0; j < width; ++j){ // 入力画像の幅を超えないようにする inX = (double)j / mag; if((int)inX >= inWidth){ --inX; } out[i * outStep + j * 3] = (unsigned char)(((int)inX + 1 - inX) * ((int)inY + 1 - inY) * (double)in[(int)inY * inStep + (int)inX * 3] + (inX - (int)inX) * ((int)inY + 1 - inY) * (double)in[(int)inY * inStep + ((int)inX + 1) * 3] + ((int)inX + 1 - inX) * (inY - (int)inY) * (double)in[((int)inY + 1) * inStep + (int)inX * 3] + (inX - (int)inX) * (inY - (int)inY) * (double)in[((int)inY + 1) * inStep + ((int)inX + 1) * 3]); out[i * outStep + j * 3 + 1] = (unsigned char)(((int)inX + 1 - inX) * ((int)inY + 1 - inY) * (double)in[(int)inY * inStep + (int)inX * 3 + 1] + (inX - (int)inX) * ((int)inY + 1 - inY) * (double)in[(int)inY * inStep + ((int)inX + 1) * 3 + 1] + ((int)inX + 1 - inX) * (inY - (int)inY) * (double)in[((int)inY + 1) * inStep + (int)inX * 3 + 1] + (inX - (int)inX) * (inY - (int)inY) * (double)in[((int)inY + 1) * inStep + ((int)inX + 1) * 3 + 1]); out[i * outStep + j * 3 + 2] = (unsigned char)(((int)inX + 1 - inX) * ((int)inY + 1 - inY) * (double)in[(int)inY * inStep + (int)inX * 3 + 2] + (inX - (int)inX) * ((int)inY + 1 - inY) * (double)in[(int)inY * inStep + ((int)inX + 1) * 3 + 2] + ((int)inX + 1 - inX) * (inY - (int)inY) * (double)in[((int)inY + 1) * inStep + (int)inX * 3 + 2] + (inX - (int)inX) * (inY - (int)inY) * (double)in[((int)inY + 1) * inStep + ((int)inX + 1) * 3 + 2]); } } break; case 4: // 32bit画像 break; default: break; } }