void skeletonVisualization::updateSkeleton() { if (imagepath.size() != 0) { image = QImage(imagepath); byte* img = new byte[image.height() * image.width()]; for (int i = 0; i < image.height(); i++) for(int j = 0; j < image.width(); j++) if (skeletonView) img[i * image.width() + j] = toGrayscale(image.pixel(j, image.height() - 1 - i)); else img[i * image.width() + j] = 255 - toGrayscale(image.pixel(j, image.height() - 1 - i)); SkeletonMaker::SourceImage srcimg; srcimg.height = image.height(); srcimg.width = image.width(); srcimg.pixels = img; skeleton = skeletonMaker.createSkeleton(&srcimg, ui.spinBoxPruning->value(), ui.spinBoxArea->value()); ui.labelTime->setText( QString("Elapsed time:\n%1 ms - DLL\n%2 ms - C++"). arg(skeleton.totalTime).arg(skeleton.cppTime)); ready = true; updateImage(); } }
//------------------------------------------------------------------- // main int main(int argc, char* argv[]) { try { float* pBuffer[2]; Cbmp bmp[2]; if (argc != 5) throw "引数に以下を指定してください.\n" \ " <入力ファイル1> <入力ファイル2> <出力ファイル> <重み付け[0.0-1.0]>"; float weight = atof(argv[4]); if (weight<0.0f || weight>1.0f) throw "重み付けが[0.0-1.0]の範囲外."; bmp[0].loadFromFile(argv[1]); // load bitmap bmp[1].loadFromFile(argv[2]); // load bitmap if (bmp[0].getBitsPerPixcel() != 32) throw "32 ビット画像ファイルでない."; if ((bmp[0].getWidth() % 8) != 0) throw "横幅が8ピクセル単位でない."; if (bmp[0].getWidth() != bmp[1].getWidth() || bmp[0].getHeight() != bmp[1].getHeight() || bmp[0].getBitsPerPixcel() != bmp[1].getBitsPerPixcel()) throw "二つの画像のサイズや属性が異なる."; // print image size fprintf(stdout, "ビットマップサイズ= %d x %d, %d/pixel\n", bmp[0].getWidth(), bmp[0].getHeight(), bmp[0].getBitsPerPixcel()); pBuffer[0] = toGrayscale(&bmp[0]); // toGrayscale pBuffer[1] = toGrayscale(&bmp[1]); // toGrayscale effect(pBuffer, &bmp[0], weight); cnvFormat(pBuffer[0], &bmp[0]); // chang format SP_MM_FREE(pBuffer[0]); SP_MM_FREE(pBuffer[1]); bmp[0].saveToFile(argv[3]); // save bitmap } catch (char *str) { fprintf(stderr, "error: %s\n", str); } return 0; }
const QImage& ImageTransformer:: Quantify(unsigned int times) { int height = _DataHandled.height(); int width = _DataHandled.width(); int depth = _DataHandled.depth(); /*量化*/ if(depth == 32) { toGrayscale(_DataHandled); int pixGain = 256/times; int pixVal; QColor pixTmp; for(int i=0;i<width;++i) { for(int j = 0;j<height;++j) { pixVal = QColor(_DataHandled.pixel(i,j)).red() / pixGain * pixGain; pixTmp.setRgb(pixVal,pixVal,pixVal); _DataHandled.setPixel(i,j,pixTmp.rgb()); } } } return _DataHandled; }
const QString ImageTransformer:: toTXT(int linelen) { int lineLength = linelen; QString result; if(_DataHandled.width()!=0) { result.clear(); QString mask("@&%$#*:. "); int step = 256/mask.size(); QImage ImageBuf = _DataHandled.scaled(lineLength, lineLength*_DataHandled.height()/_DataHandled.width()); int width = ImageBuf.width(); int height = ImageBuf.height(); int depth = ImageBuf.depth(); if(depth == 32) { toGrayscale(ImageBuf); for(int j=0;j+1<height;j+=2) { for(int i=0;i<width;++i) { result.append(mask[(QColor(ImageBuf.pixel(i,j)).red() + QColor(ImageBuf.pixel(i,j+1)).red())/2/step]); } result.append("\r\n"); } } } return result; }
ofPixels_<unsigned char> ImageUtils::dither(const ofPixels_<unsigned char>& pixels, float threshold, float quantWeight) { // Special thanks to @julapy / ofxDither ofPixels_<unsigned char> pixelsIn = pixels; // ensure the image is grayscale if (OF_IMAGE_GRAYSCALE != pixelsIn.getImageType()) { pixelsIn = toGrayscale(pixels); } // make a copy ofPixels_<unsigned char> pixelsOut = pixelsIn; // set up the quantization error int width = pixelsOut.getWidth(); int height = pixelsOut.getHeight(); std::size_t numPixels = width * height; // 1 byte / pixel float qErrors[numPixels]; std::fill(qErrors, qErrors + numPixels, 0.0); //unsigned char* inPix = pixelsIn.getPixels(); unsigned char* outPix = pixelsOut.getPixels(); float limit = ofColor_<unsigned char>::limit(); for (int y = 0; y < height; y++) { for (int x = 0; x < width; x++) { int p = pixelsIn.getPixelIndex(x, y); int oldPx = outPix[p] + qErrors[p]; // add error int newPx = (oldPx < (threshold * limit)) ? 0 : limit; // threshold outPix[p] = newPx; int qError = oldPx - newPx; accumulateDitherError(x+1,y ,pixelsOut,qError,qErrors,quantWeight); // check east accumulateDitherError(x+2,y ,pixelsOut,qError,qErrors,quantWeight); // check east east accumulateDitherError(x-1,y+1,pixelsOut,qError,qErrors,quantWeight); // check southwest accumulateDitherError(x ,y+1,pixelsOut,qError,qErrors,quantWeight); // check south accumulateDitherError(x+1,y+1,pixelsOut,qError,qErrors,quantWeight); // check southeast accumulateDitherError(x ,y+2,pixelsOut,qError,qErrors,quantWeight); // check south south } } return pixelsOut; }
void myPCA::recoginize(double dis, double threshold, Mat& disMatrix) { float min = disMatrix.at<float>(0,0); int minCol = 0; int flagKnow = 1; int flagUnknow = 1; int i; for(i = 0; i < disMatrix.cols; ++i) { float x = disMatrix.at<float>(0,i); if(x < threshold) { flagUnknow = 0; if(min > x) { min = x; minCol = i; } } else { flagKnow = 0; } if(flagKnow + flagUnknow == 0) { cout << "No I don't know this guy!" << endl; break; } } if(flagKnow) { cout << "Yes I know this guy!" <<endl; cout << "It's the "<<trainImageID.at<short>(0,minCol) << "th person in the database."; Mat imgFace = sampleMatrixOri.col(minCol).clone(); Mat toShow; imgFace.reshape(1,ROWDB).copyTo(toShow); toShow = toGrayscale(toShow); imshow("recognize",toShow); waitKey(0); } if(flagUnknow) { cout << "Sorry I think it's not a human face" <<endl; } }
void myPCA::show10EigenFaces() { Mat all; for (int i =0; i < min(10, eigenVectors.cols); i++) { Mat imgFace = eigenVectors.col(i).clone(); if(i == 0) all = imgFace.clone(); else all = all + imgFace; } all.reshape(1, ROW).copyTo(all); all = toGrayscale(all); resize(all,all,Size(COL*4,ROW*4),0,0,1); imshow("Top 10",all); waitKey(0); }
const std::array<QImage,8>& ImageTransformer:: ByteQuantify() { int width = _DataHandled.width(); int height = _DataHandled.height(); int depth = _DataHandled.depth(); if(depth == 32) { toGrayscale(_DataHandled); /*载入灰度图*/ for(int i=0;i<8;++i) { _ByteQuantified[i] = _DataHandled; } /*分级量化灰度图数组*/ unsigned char mask; mask = 1;//Ox 0000 0001 for(int k=0;k<8;++k) { for(int i =0;i<width;++i) { for(int j=0;j<height;++j) { QColor pixTmp = _ByteQuantified[k].pixel(i,j); int rgb = (pixTmp.red() & mask)==0?0:255; pixTmp.setRgb(rgb,rgb,rgb); _ByteQuantified[k].setPixel(i,j,pixTmp.rgb()); } } mask<<=1; } } else { for(int i=0;i<8;++i) { _ByteQuantified[i] = _DataHandled; } } return _ByteQuantified; }
/* *Contains algorithm to turn an image into ASCII art! *Parameters: *filename: the file to write our art to. *pixAmount: the amount of pixels per character (in a square) *img: a pointer to our image in memory. * *return 0 if no errors were encountered, 1 otherwise. */ int ascii(Image* img, char* filename, int pixAmount) { // if we don't have a file in memory, say so. if(img->data == NULL) { fprintf(stderr, "Error, no file currently in memory\n"); return 1; } //first we need to pixelate pixelate(img, pixAmount); //then turn it into grayscale toGrayscale(img); //our file to write to FILE* fout= fopen(filename, "w"); // our indicator of brightness int brightness = 0; //the character we want to use to write char c = ' '; //for each "square" of our image for(int j=0; j<(img->rowNum/pixAmount); j++) { for(int i=0; i<(img->colNum/pixAmount); i++) { //our brightness value is equal to the actual brightness over 8, because we're //using 31 different characters to create our image. brightness =(int)((img->data[pixAmount*((j*img->colNum)+i)].r)/(2.34375)); //mapping brightness to character c = toASCII(brightness); //printing the character twice so we can have a square image. fprintf(fout,"%c%c",c,c); } //print a line break. fprintf(fout,"\n"); } //close our file! fclose(fout); return 0; }
void ImageTransforms::toGrayscale(QImage& in, QImage& out) { if (in.isNull()) return; int w = in.width(), h = in.height(); if (in.format()!=QImage::Format_ARGB32 && in.format()!=QImage::Format_RGB32 && in.format() != QImage::Format_RGB888 ) { std::cout << "ImageTransforms::toGrayscale : Error - accepted input format is ARGB32 o RGB888." << std::endl; return; } if(out.format() == QImage::Format_Indexed8) { QImage gout = toGrayscale(in); memcpy(out.bits(), gout.bits(), h*out.bytesPerLine()); out.setColorTable(gout.colorTable()); } else if( out.format() == QImage::Format_ARGB32 || out.format() == QImage::Format_RGB32 || out.format() == QImage::Format_RGB888 ) { //Color output image int i, j, k, g, cind1, cind2, bplin = in.bytesPerLine(), bplout = out.bytesPerLine(), step1 = (in.format() == QImage::Format_RGB888) ? 3 : 4, step2 = (out.format() == QImage::Format_RGB888) ? 3 : 4, wstep = w*step1; uchar *pin = in.bits(), *pout = out.bits(); for(i=0; i<h; i++) for(j=0,k=0; j<wstep; j+=step1,k+=step2) { cind1 = i*bplin + j; cind2 = i*bplout + k; g = qGray(pin[cind1+2],pin[cind1+1],pin[cind1]); pout[cind2+2] = pout[cind2+1] = pout[cind2] = g; } } }
float fuzzyCompare (const FuzzyCompareParams& params, const ConstPixelBufferAccess& ref, const ConstPixelBufferAccess& cmp, const PixelBufferAccess& errorMask) { DE_ASSERT(ref.getWidth() == cmp.getWidth() && ref.getHeight() == cmp.getHeight()); DE_ASSERT(errorMask.getWidth() == ref.getWidth() && errorMask.getHeight() == ref.getHeight()); if (!isFormatSupported(ref.getFormat()) || !isFormatSupported(cmp.getFormat())) throw InternalError("Unsupported format in fuzzy comparison", DE_NULL, __FILE__, __LINE__); int width = ref.getWidth(); int height = ref.getHeight(); de::Random rnd (667); // Filtered TextureLevel refFiltered(TextureFormat(TextureFormat::RGBA, TextureFormat::UNORM_INT8), width, height); TextureLevel cmpFiltered(TextureFormat(TextureFormat::RGBA, TextureFormat::UNORM_INT8), width, height); // Kernel = {0.15, 0.7, 0.15} vector<float> kernel(3); kernel[0] = kernel[2] = 0.1f; kernel[1]= 0.8f; int shift = (int)(kernel.size() - 1) / 2; switch (ref.getFormat().order) { case TextureFormat::RGBA: separableConvolve<4, 4>(refFiltered, ref, shift, shift, kernel, kernel); break; case TextureFormat::RGB: separableConvolve<4, 3>(refFiltered, ref, shift, shift, kernel, kernel); break; default: DE_ASSERT(DE_FALSE); } switch (cmp.getFormat().order) { case TextureFormat::RGBA: separableConvolve<4, 4>(cmpFiltered, cmp, shift, shift, kernel, kernel); break; case TextureFormat::RGB: separableConvolve<4, 3>(cmpFiltered, cmp, shift, shift, kernel, kernel); break; default: DE_ASSERT(DE_FALSE); } int numSamples = 0; float errSum = 0.0f; // Clear error mask to green. clear(errorMask, Vec4(0.0f, 1.0f, 0.0f, 1.0f)); ConstPixelBufferAccess refAccess = refFiltered.getAccess(); ConstPixelBufferAccess cmpAccess = cmpFiltered.getAccess(); for (int y = 1; y < height-1; y++) { for (int x = 1; x < width-1; x += params.maxSampleSkip > 0 ? (int)rnd.getInt(0, params.maxSampleSkip) : 1) { float err = deFloatMin(compareToNeighbor<4>(params, rnd, readUnorm8<4>(refAccess, x, y), cmpAccess, x, y), compareToNeighbor<4>(params, rnd, readUnorm8<4>(cmpAccess, x, y), refAccess, x, y)); err = deFloatPow(err, params.errExp); errSum += err; numSamples += 1; // Build error image. float red = err * 500.0f; float luma = toGrayscale(cmp.getPixel(x, y)); float rF = 0.7f + 0.3f*luma; errorMask.setPixel(Vec4(red*rF, (1.0f-red)*rF, 0.0f, 1.0f), x, y); } } // Scale error sum based on number of samples taken errSum *= (float)((width-2) * (height-2)) / (float)numSamples; return errSum; }
int main(int argc, char **argv){ if(argc != 9){ printf("wrong # args\n"); printf("inputfile outDir(./lol/) invert (0 or 1) k*1000 windowRadius gaussPyramidThresh(>= survive) finalMixThresh(>= survive) writeDebugImages(0 or 1)\n"); } int width, height, channels; unsigned char *data; char *dir = argv[2]; int inv = atoi(argv[3]); float k = float(atoi(argv[4]))/1000.f; int window = atoi(argv[5]); int gaussPyramidThresh = atoi(argv[6]); int finalMixThresh = atoi(argv[7]); bool debugImages = atoi(argv[8]); bool res = loadImage(argv[1], &width, &height, &channels, &data); if(!res){ printf("error reading image\n"); return 1; } printf("start\n"); // to grayscale unsigned char *dataGray = new unsigned char[width*height]; toGrayscale(width,height,data,dataGray); // build SAT unsigned int *sat = new unsigned int[width*height]; float * satSquared = new float[width*height]; SAT(dataGray,sat,width,height); SATSquared(dataGray,satSquared,width,height); // do thresh thresh(dataGray, sat, satSquared, width, height, k, window); if(inv){invert(dataGray,width,height);} char filename[200]; sprintf(filename,"%sresRaw.bmp",dir); if(debugImages){saveImage(filename, width, height, 1, dataGray);} unsigned char ** pyramid=NULL; makePyramid(dataGray, &pyramid, pyramidLevels, gaussPyramidThresh, width,height); for(int L=0; L<pyramidLevels; L++){ char filename[200]; sprintf(filename,"%sres_raw_%d.bmp",dir,L); if(debugImages){saveImage(filename,width/pow(2,L),height/pow(2,L),1,pyramid[L]);} } // label int vecSizeY=32; int vecSizeX=128; unsigned char *dist=new unsigned char[width*height]; unsigned short *labels = new unsigned short[width*height]; unsigned short area[maxLabels]; unsigned char *reason = new unsigned char[width*height]; unsigned char *tile = new unsigned char[width*height]; for(int l = pyramidLevels-1; l>=0; l--){ int lw = width/pow(2,l); int lh = height/pow(2,l); // write out debug data char filename[200]; sprintf(filename,"%sres_%dp2.bmp",dir,l); if(debugImages){saveImage(filename, lw,lh, 1, pyramid[l]);} } for(int L = pyramidLevels-1; L>=0; L--){ int lw = width/pow(2,L); int lh = height/pow(2,L); // clear out labels so that we can do progressive cleanup passes for(int i=0; i<lw*lh; i++){reason[i]=0;labels[i]=0;} unsigned short firstId = 1; int tileId = 0; int minArea = 6; if(L<2){minArea = 30;} int nTilesX = ceil((float)lw/(float)vecSizeX); int nTilesY = ceil((float)lh/(float)vecSizeY); int lastFixup = 0; for(int by=0; by<nTilesY; by++){ int endY = (by+1)*vecSizeY; if(endY>lh){endY=lh;} bool fixupRanThisRow = false; for(int bx=0; bx<nTilesX; bx++){ int endX = (bx+1)*vecSizeX; if(endX>lw){endX=lw;} label(pyramid[L],labels,reason,area,lw,lh,minArea,vecSizeX*bx,endX,vecSizeY*by,endY,maxLabels); unsigned short lastId=0; if(!condenseLabels(labels,area,firstId,&lastId,lw,lh,vecSizeX*bx,endX,vecSizeY*by,endY,maxLabels)){ printf("Error: ran out of labels!\n"); goto writeout; // an exception occured } firstId=lastId+1; //printf("ML %d\n",(int)firstId); // for debugging for(int x=vecSizeX*bx; x<endX; x++){ for(int y=vecSizeY*by; y<endY; y++){ tile[x+y*lw]=tileId; } } tileId++; if(firstId > (maxLabels*4)/5 && !fixupRanThisRow){ labelProp(labels,area,lw,lh,0,lw,0,endY,maxLabels); filter(pyramid,L,reason,labels,minArea,lw,lh,width,0,lw,lastFixup,endY,maxLabels); computeArea(labels,area,lw,lh,0,lw,0,endY,maxLabels); condenseLabels(labels,area,1,&firstId,lw,lh,0,lw,0,endY,maxLabels); firstId++; printf("fixup TL %d\n",firstId); lastFixup = (by+1)*vecSizeY; fixupRanThisRow=true; } } } // fix labels across region boundries labelProp(labels,area,lw,lh,0,lw,0,lh,maxLabels); computeArea(labels,area,lw,lh,0,lw,0,lh,maxLabels); condenseLabels(labels,area,1,&firstId,lw,lh,0,lw,0,lh,maxLabels); //printf("TL %d\n",firstId); distanceTransform(pyramid[L],dist,0,lw,lh); filter(pyramid,L,reason,labels,minArea,lw,lh,width,0,lw,0,lh,maxLabels); // now what's left "must" be text, so delete it from other pyrmid levels and save it writeout: // write out debug data char filename[200]; if(debugImages){ sprintf(filename,"%sL_%d.bmp",dir,L); saveImage(filename, lw,lh, labels); sprintf(filename,"%sD_%d.bmp",dir,L); saveImage(filename, lw,lh, 1, dist); sprintf(filename,"%sres_%d.bmp",dir,L); saveImage(filename, lw,lh, 1, pyramid[L]); sprintf(filename,"%sR_%d.bmp",dir,L); saveImage(filename, lw,lh, 1, reason); sprintf(filename,"%sT_%d.bmp",dir,L); saveImage(filename, lw,lh, 1, tile); } if(L==pyramidLevels-1){ for(int l = 2; l>=0; l--){ int lw = width/pow(2,l); int lh = height/pow(2,l); // write out debug data char filename[200]; sprintf(filename,"%sres_%dp.bmp",dir,l); if(debugImages){saveImage(filename, lw,lh, 1, pyramid[l]);} } } } for(int y=0; y<height; y++){ for(int x=0; x<width; x++){ int count=0; for(int l=0; l<pyramidLevels; l++){ int lx = x/pow(2,l); int ly = y/pow(2,l); int lw = width/pow(2,l); if(pyramid[l][lx+ly*lw]){count++;} } if(count<finalMixThresh){ dataGray[x+y*width]=0; } } } sprintf(filename,"%sres.bmp",dir); saveImage(filename, width, height, 1, dataGray); return 0; }