000
13.09.2004, 11:22 Uhr
~alx1
Gast
|
Hallo c++ freunde
ich habe hier ein mittelschweres prob... (ihr wisst schon was). also: ich möchte ein bmp-bild in ein 3 dimensionales array einlesen. die ersten beiden dimensionen sind für die positionen der pixel und die dritte dimension für die 3 farbwerte der pixel, der 24Bit bilder. ich habe mal euer forum durchsucht und habe da was ähnliches gefunden (http://www.fun-soft.de/showtopic.php?threadid=6738). leider hatte "er" immer gleich große bilder. meine wenigkeit hingegen hat immer unterschiedlich große bilder. ich habe da auch schon ein kleines script geschrieben. leider funktioniert es nur für bilder, die maximal 255 pixel in höhe oder breite groß sind. ich denke ich sollte es mal zeigen:
C++: |
#include <iostream> #include <fstream>
#include <cmath> #include <stdlib.h> #include <stdio.h> #include <time.h> #include <iomanip>
using namespace std;
ifstream inputFile("mein.bmp", ios::binary | ios::in);//oeffnet den lesestream ofstream file("outgoing.bmp", ios::out|ios::binary); int ***imagearray;//array der pixel: hoehe breite des pixels + 1ster,2ter,3ter farbwert desses int hoehe,breite;
void sleep() { int t; for (t=0;t<100000000;++t) {}; }
void printer() { int i,j; for (i=0;i<hoehe;++i) //Ausgabe des Inhaltes des Arrays { for(j=0;j<breite;++j) { cout<<imagearray[i][j][0]<<" , "<<imagearray[i][j][1]<<" , "<<imagearray[i][j][2]<<endl; } cout<<endl; sleep(); } };
void einlesen()//das bild wird von links unten nach rechts oben ausgelesen { unsigned char currByte;//hat den index dst int dst=1,i,j,pixel=1,h;//dst ist dateistelle float tripel[3];//enthaelt die 3 farbwerte eines pixels while (dst<55)//auselen des headers { currByte = inputFile.get();//ein element der datei wird in currByte geschrieben cout<<int(currByte)<<endl; if (dst==19) breite=int(currByte); else if (dst==23) hoehe=int(currByte); ++dst; file.write( (char*) &currByte,1);//Uebertragen des Headers in die Datei }
cout<<breite<<" - "<<hoehe<<endl; imagearray=new int**[hoehe]; for(j=0;j<hoehe;++j)//Allokieren des Array Image, das die bildpixelinformationen speichert { imagearray[j]=new int*[breite]; for(i=0;i<breite;++i) imagearray[j][i]=new int[3]; } h=0; cout<<"Noch einzulesene Zeilen: "<<endl; float *zeile; //allokieren des array, zeile= new float[breite]; //der eine zeile des bildes speichert. const unsigned long linesize =3*breite, fillbytes = (4-linesize%4)%4;
while (dst<=breite*hoehe*3+55)//abfragen der farbwerte aller bilpunkte { currByte = inputFile.get();//siehe oben if ((((dst-55)%(3*breite))==0)&&(dst>55)) //wenn zeile zu ende { for(i=0;i<breite;++i)/////// ausgabe der graustufen fuer alle pixel in einer zeile, imagearray[h][i][0]=imagearray[h][i][1]=imagearray[h][i][2]=zeile[i];//Uebertragen der Grauwerte in das Array cout<<hoehe-h<<", "; for(i=0;i<fillbytes;++i) //herausstreichen der zusatzinformationen am ende der zeile currByte = inputFile.get();
++h; } tripel[(dst-55)%3]=int(currByte);//einlesen der farbinformation eines pixels, format: B G R if ((((dst-55)+1)%3)==0) //jeden dritten eingabewert (nach b-r-g) //(dst-55) ergibt die pixelnummer, da der header(55) abgezogen wurde { zeile[(pixel-1)%breite]=((tripel[0]+tripel[1]+tripel[2])/3);//berechnung der graustufe, als mittelwert der farben(falls ein farbiges bild eingegeben wird), da eine graustufe bei R,G,B die selben werte hat ++pixel; } ++dst; } cout<<endl<<"Fertig mit einlesen"<<endl; };
void ausgeben() { int i,i2; unsigned char currByte; const unsigned long linesize =3*breite, // 24 bit per pixel fillbytes = (4-linesize%4)%4, // at line end to quad boundary imagesize = (linesize+fillbytes)*hoehe;
/*struct BMPheader { // file info char ID[2]; unsigned long filesize, reserved, offset;
// BMP info unsigned long infosize, width, height; unsigned short planes, bitsperpixel; unsigned long compression, imagesize, xPixelPerMeter, yPixelPerMeter,colorsUsed, colorsImportant; } header = { // file info { 'B', 'M' }, sizeof(header) + imagesize, // 24 bits per pixel 0, sizeof(header), // 0x36
// BMP info 40, breite, hoehe, 1, 24, 0, imagesize, 1000, 1000, 0, 0 }; file.write( (char*)&header, sizeof(header));*/ cout<<"Noch auszugebene Zeilen: "<<endl; for (i=0;i<hoehe;++i) { for(i2=0;i2<breite;++i2) { currByte=imagearray[i][i2][0]; file.write((char*) &currByte,1);
currByte=imagearray[i][i2][1]; file.write((char*) &currByte,1);
currByte=imagearray[i][i2][2]; file.write((char*) &currByte,1); }
if(fillbytes) { int zero = 0; file.write( (char*) &zero, fillbytes); }
cout<<hoehe-i<<", "; } cout<<endl<<"Fertig mit ausgeben"<<endl<<endl; };
void main () { einlesen(); ausgeben();
}
|
ich wäre sehr glücklich, wenn jemand das problem beheben könnte, sodass ich beliebig große bilder in mein array speichern kann. ich habe schon in erfahrung bringen können, dass es an der maximalen speicherkapazität von 1byte des "unsigned char currByte;" liegt, zumal ja die größe des bmps in 4 bit gespeichert wird. nur weiss ich nicht, wie ich hier herangehen soll.
danke schonmal im voraus.... |