Herzlich Willkommen, lieber Gast!
  Sie befinden sich hier:

  Forum » C / C++ (WinAPI, Konsole) » Bitmaps einlesen

Forum | Hilfe | Team | Links | Impressum | > Suche < | Mitglieder | Registrieren | Einloggen
  Quicklinks: MSDN-Online || STL || clib Reference Grundlagen || Literatur || E-Books || Zubehör || > F.A.Q. < || Downloads   

Autor Thread - Seiten: > 1 <
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....
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
001
13.09.2004, 12:49 Uhr
~CDW
Gast


hm, es gibt sicherlich libs dafür, ich hab aber ungefähr die gleiche aufgabenstellung gelöst, in dem ich die BMP datei "Roh" eingelesen hab... denn:
www.wotsit.org/search.asp?s=graphics
www.edm2.com/0107/os2bmp.html

ist BMP beschrieben:

Zitat:

000Eh Bitmap Header Size 1 dword Length of the Bitmap Info Header used to describe the bitmap colors, compression, … The following sizes are possible:

28h - Windows 3.1x, 95, NT, …
0Ch - OS/2 1.x
F0h - OS/2 2.x
0012h Width 1 dword Horizontal width of bitmap in pixels.
0016h Height 1 dword Vertical height of bitmap in pixels.
001Ah Planes 1 word Number of planes in this bitmap.
001Ch Bits Per Pixel 1 word Bits per pixel used to store palette entry information. This also identifies in an indirect way the number of possible colors. Possible values are:
1 - Monochrome bitmap
4 - 16 color bitmap
8 - 256 color bitmap
16 - 16bit (high color) bitmap
24 - 24bit (true color) bitmap
32 - 32bit (true color) bitmap



usw. wenn du also weißt wie dein bmp aufgebaut ist, dann kannst du die auch "manuell" laden...
ich könnte dir zwar beispielcode geben, leider ists kein c++ sondern masm und damit dürftest du nicht so viel anfangen können
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
002
13.09.2004, 13:18 Uhr
~alx1
Gast


diese beiden seite habe ich auch schon studiert. hat mir leider nicht so viel gebracht. wie das bitmap aufgebaut ist, weiss ich ja (eigendlich), nur ich schaffe es nicht aus den bytes 19-22 und den bytes 23-26 die hoehe und breiteinformationen auszulesen.
wäre toll wenn jemand die korrekte zeile an der stelle

C++:
currByte = inputFile.get();//ein element der datei wird in currByte geschrieben
        cout<<int(currByte)<<endl;
        if (dst==19)
            breite=int(currByte);


sagen könnte.
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
Seiten: > 1 <     [ C / C++ (WinAPI, Konsole) ]  


ThWBoard 2.73 FloSoft-Edition
© by Paul Baecher & Felix Gonschorek (www.thwboard.de)

Anpassungen des Forums
© by Flo-Soft (www.flo-soft.de)

Sie sind Besucher: