|
JLI Spieleprogrammierung
|
Vorheriges Thema anzeigen :: Nächstes Thema anzeigen |
Autor |
Nachricht |
TheMillenium Dark JLI'ler
Anmeldedatum: 21.07.2002 Beiträge: 1427 Wohnort: World Medaillen: Keine
|
Verfasst am: 24.07.2003, 13:50 Titel: Eigene BMP2Surface Routine |
|
|
Hi!
Ich wollte nicht mehr diese langsame billige Laderoutine per GDI zum Laden von BMP in meine Surfaces, deshalb hab ich meine eigene Routine geschrieben, aber leider stürzt das Programm gleich ab und meine Error(char *message) Fehlerkontrolle, die bei jedem AUfruf die Datei erneut öffnet - etwas reinschreibt - und dann die Datei sofort wieder schließt, zeigt statt einer Fehlöermeldung, nur leere Zeilen an. Und bei diesem Verfahren hat er bis jetzt immer die Fehler angezeigt, da die Datei ja immer sofort nach jedem Schreibvorgang wieder geschlossen wird...
Hier ist der Code:
Code: |
LPDIRECTDRAWSURFACE7 CreateSurfaceFromBitmap_own(LPCTSTR ImageFile)
{
LPBYTE lpbyImage; // Speichert die BMP Bilddaten
HANDLE hDatei; // Handle auf die BMP Datei
BITMAPFILEHEADER BMPFileHeader; // BMP Datei Header
BITMAPINFOHEADER BMPFileInfo; // BMP Datei Info Header
RGBQUAD *pPalette; // Farbpalette
DWORD dwReadRAM; // Zwischenspeicher
WORD* lpDestinyRAM; // Zielspeicher (DDraw Surface)
WORD* lpSourceRAM; // Quellspeicher (BMP Bild)
// SURFACE
LPDIRECTDRAWSURFACE7 lpDDSurface; // Zielsurface
DDSURFACEDESC2 SurfDesc; // Beschreibung der Zielsurface
int DDS_Width; // Breite der Zielsurface
int DDS_Height; // Höhe der ZielSurface
// BMP Datei öffnen
hDatei = CreateFile(ImageFile,GENERIC_READ,FILE_SHARE_READ,(LPSECURITY_ATTRIBUTES) NULL,
OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, (HANDLE) NULL);
if(hDatei == INVALID_HANDLE_VALUE)
{
Error("CreateSurfaceFromBitmap_own: Kann auf Datei nicht zugreifen");
return false;
}
// BMP Header einlesen
if(!ReadFile(hDatei, &BMPFileHeader,sizeof(BMPFileHeader),&dwReadRAM,NULL))
{
Error("CreateSurfaceFromBitmap_own: Fehler beim EInlesen des BMP FileHeader");
CloseHandle(hDatei);
return false;
}
// BMP Info Header einlesen
if(!ReadFile(hDatei, &BMPFileInfo,sizeof(BMPFileInfo),&dwReadRAM,NULL))
{
Error("CreateSurfaceFromBitmap_own: Fehler beim EInlesen des BMP Info Header");
CloseHandle(hDatei);
return false;
}
// Größe & Breite des Zielsurface festlegen
DDS_Width = BMPFileInfo.biWidth;
DDS_Height = BMPFileInfo.biHeight;
// Überprüfen, wie groß die Palette ist
if(BMPFileInfo.biClrImportant == 0)
{
switch(BMPFileInfo.biBitCount)
{
case 8: pPalette = new RGBQUAD[256];
case 15: pPalette = new RGBQUAD[32768];
case 16: pPalette = new RGBQUAD[65536];
case 24: pPalette = new RGBQUAD[16777216];
case 32: pPalette = new RGBQUAD[16777216];
default: return false;
}
} else pPalette = new RGBQUAD[BMPFileInfo.biClrImportant];
// Palette einlesen
if(!ReadFile(hDatei, pPalette, sizeof(pPalette), &dwReadRAM, NULL))
{
Error("CreateSurfaceFromBitmap_own: Fehler beim Einlesen der Palette");
CloseHandle(hDatei);
return false;
}
// Speicher für die Bilddaten bereitstellen
if(!(lpbyImage=(LPBYTE)malloc(DDS_Width*DDS_Height)))
{
Error("CreateSurfaceFromBitmap_own: Fehler beim Bereitstellen des Speichers für die Bilddaten");
return false;
}
// Eigentliche Bilddaten einlesen
if(!ReadFile(hDatei, lpbyImage, DDS_Width*DDS_Height, &dwReadRAM, NULL))
{
Error("CreateSurfaceFromBitmap_own: Fehler beim Einlesen der Bilddaten");
CloseHandle(hDatei);
return false;
}
// Schliesse die Datei
CloseHandle(hDatei);
// Oberflächenbeschreibung initialisieren
ZeroMemory(&SurfDesc, sizeof(SurfDesc));
SurfDesc.dwSize = sizeof(SurfDesc);
// Caps, Höhe und Breite sollen berücksichtigt werden
SurfDesc.dwFlags = DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH;
SurfDesc.ddsCaps.dwCaps = DDSCAPS_OFFSCREENPLAIN;
SurfDesc.dwWidth = DDS_Width;
SurfDesc.dwHeight = DDS_Height;
// Oberfläche anlegen
if(FAILED(lpDD7->CreateSurface(&SurfDesc,&lpDDSurface,NULL)))
{
Error("CreateSurfaceFromBitmap_own: Fehler beim Anlegen der Surface");
return 0;
}
lpDDSurface->Lock(NULL,&SurfDesc,DDLOCK_WAIT,NULL);
lpDestinyRAM = (WORD*)SurfDesc.lpSurface;
int Pitch = SurfDesc.lPitch/2; // bei 16-Bit!!!
lpSourceRAM = (WORD*) (&lpbyImage[(DDS_Height-1)*DDS_Width]);
// Kopieren aller Bilddaten von lpbyImage in die Zielsurface
for(int i=0;i<DDS_Height;i++)
{
memcpy(lpDestinyRAM, lpSourceRAM, DDS_Width);
lpDestinyRAM += Pitch;
lpSourceRAM -= DDS_Width;
}
lpDDSurface->Unlock(NULL);
// Speicher freigeben
if(lpbyImage)
free(lpbyImage);
return lpDDSurface;
}
|
_________________ The source of all power is in its destiny... |
|
Nach oben |
|
|
X-FILE Super JLI'ler
Anmeldedatum: 12.07.2003 Beiträge: 349
Medaillen: Keine
|
Verfasst am: 24.07.2003, 16:08 Titel: Hmmm |
|
|
Hallo,
also wenn ichs ned besser wuesste und hier Herr Rouselle das sagen hat, wuerd ich sagen, die Routine riecht und schmeckt fast 100% nach Zerbies Buch Numero Uno
Aber zu dem Problem. Warum benutzt du DirectX7 Aufrufe?? Hat das nen Grund? Solltest du naemlich nen neueren SDK nutzen, funktioniert diese Version nicht mehr so reibungslos. Siehe Aenderungen von DX7 auf 8 und speziell DirectDraw, was es in 8 ja nicht mehr gibt. D.h. ddraw.lib muss nun auf d3d8.lib gelinkt werden usw. Aber dann haette der Kompiler ja schon nen Fehler gemacht. Auch ist es LPDIRECT3DSURFACE8 und weiter... naja egal.
Was heißt, das Programm stuerzt sofort ab?? Kein Fehler, kein Speicherfehler usw? Nur schwarz und dann nix mehr? Debugge doch mal die Funktion und kucke wo er haengt. Ich jedenfalls verstehe nach wie vor nicht, warum DX7?
P.S. den ersten Handle auf das Errorprotokoll schließt du uebrigens nicht, oder sehe ich das falsch??
Auch ist die Sache so, dass du ja nur Fehler ausgibst. Dreh das doch mal um, und schreib positive Ereignisse in die Datei.
Ich persoenlich denke, dass der Fehler beim CreateSurface liegt. Dort schließt du uebrigens die Datei auch nicht (wenn vorher alles gefunzt haette, waere die Datei somit leer). |
|
Nach oben |
|
|
Christian Rousselle Site Admin
Alter: 48 Anmeldedatum: 19.07.2002 Beiträge: 1630
Medaillen: Keine
|
Verfasst am: 24.07.2003, 17:39 Titel: |
|
|
Zitat: |
Ich wollte nicht mehr diese langsame billige Laderoutine...
|
Warum? Lädst du die Bitmaps zur Laufzeit? Ansonsten ist es völlig egal.
Christian |
|
Nach oben |
|
|
TheMillenium Dark JLI'ler
Anmeldedatum: 21.07.2002 Beiträge: 1427 Wohnort: World Medaillen: Keine
|
Verfasst am: 24.07.2003, 21:38 Titel: |
|
|
Zur Laufzeit, muss ich wohl oder Übel Bilder laden, denn ich habe Animation von 320*240, aber mit ca. 120 Bilder und das kostet doch sauviel Space?
Ja ist an Zerbst angelehnt aber schon etwas deutlich verändert...
Warum ich DX8 benutze?
Naja die DX9 finde ich scheiße!!!
Da muss man alles 3D Zeug erstellen und solches Zeug machen, was nicht im geringsten nur mit 2D zu tun hat...
Deshalb bleib ich bei DX8 laut Christians erstem Buch, obwohl ich auch die zweite Ausgabe von ihm habe...aber wie schon gesagt. _________________ The source of all power is in its destiny... |
|
Nach oben |
|
|
X-FILE Super JLI'ler
Anmeldedatum: 12.07.2003 Beiträge: 349
Medaillen: Keine
|
Verfasst am: 24.07.2003, 21:44 Titel: Hmmm... |
|
|
Abend,
hmm also meine Programmiererfahrung mit DX8 beziehen sich auf genau 3 Abende, danach gleich 9, aber das was du da Oben gepostet hast, ist kein DX8, sondern DX7. Und da sind doch gravierende Unterschiede?!
Oder liege ich da falsch? Wie gesagt die CreateSurface-Methode gibt es im DX8 nicht mehr. |
|
Nach oben |
|
|
Hazel JLI MVP
Alter: 39 Anmeldedatum: 19.07.2002 Beiträge: 1761
Medaillen: Keine
|
Verfasst am: 24.07.2003, 21:51 Titel: |
|
|
Ja das ist DX7. Ab 8 gab es schon DirectGraphics.
TheMillenium: Vielleicht hilft dir das ja? http://www.gamedev.net/reference/articles/article1966.asp Ich habs mir noch nicht so genau durchgelesen.
Aber wenn sich dein Programm einfach so, ohne Fehlermeldung verabschieded ist es meist falscher Umgang mit Zeigern... ist bei mir jedenfalls immer so. _________________ *click* Dabuu!?
Twitter: http://twitter.com/Ollie_R
|
|
Nach oben |
|
|
TheMillenium Dark JLI'ler
Anmeldedatum: 21.07.2002 Beiträge: 1427 Wohnort: World Medaillen: Keine
|
Verfasst am: 24.07.2003, 22:04 Titel: |
|
|
also Debuggen geht im Fullscreen-Mode leider nicht.
Ich habe aber gemerkt, dass alles gut läuft sobald ich dann wirklich die Surface blitten will... _________________ The source of all power is in its destiny... |
|
Nach oben |
|
|
X-FILE Super JLI'ler
Anmeldedatum: 12.07.2003 Beiträge: 349
Medaillen: Keine
|
Verfasst am: 24.07.2003, 22:36 Titel: Hmmm |
|
|
Abend,
stimmt im Fullscreen is Debuggen Mistig. Setze doch wie ich gesagt habe deine Dateiereignisse auf positive Werte (also wenn etwas erfolg hatte). Dann solltest du bis zu CreateSurface auf jeden Fall kommen. Danach versteh ich es auch nicht richtig.
Wenn du korrekt auf DX7 gelinket hast, sollte es gehen. Wenn nicht und du benutzt die d3d8.h, dann musst du die CreateSurface durch lpD3DDevice->CreateImageSurface ersetzen.
Naja probiers aus |
|
Nach oben |
|
|
TheMillenium Dark JLI'ler
Anmeldedatum: 21.07.2002 Beiträge: 1427 Wohnort: World Medaillen: Keine
|
Verfasst am: 26.07.2003, 18:02 Titel: |
|
|
Code: |
Error("vor switch");
// Überprüfen, wie groß die Palette ist
if(BMPFileInfo.biClrImportant == 0)
{
Error("nach if");
switch(BMPFileInfo.biBitCount)
{
Error("vor case");
case 8: pPalette = new RGBQUAD[256];
Error("1");
break;
case 15: pPalette = new RGBQUAD[32768];
Error("2");
break;
case 16: pPalette = new RGBQUAD[65536];
Error("3");
break;
case 24: pPalette = new RGBQUAD[16777216];
Error("4");
break;
case 32: pPalette = new RGBQUAD[16777216];
Error("5");
break;
default: return false;
}
} else pPalette = new RGBQUAD[BMPFileInfo.biClrImportant];
Error("nach switch");
|
da steht dann bei einer datei mit 256 Farben:
Code: |
vor switch
nach if
1
nach switch
|
das bild wird da zwar etwas falsch angezeigt, das liegt ja aber daran, dass mein Spiel mit 16-Bit läuft...
bei mehr als 256 Farben kommt das:
Kann es sein, dass ich die falsche Anzahl von Farben für die anderen Farbtiefen nehme oder kann man irgendwie auf BMPFileInfo.biBitCount nicht zugreifen??? _________________ The source of all power is in its destiny... |
|
Nach oben |
|
|
|
|
Du kannst keine Beiträge in dieses Forum schreiben. Du kannst auf Beiträge in diesem Forum nicht antworten. Du kannst deine Beiträge in diesem Forum nicht bearbeiten. Du kannst deine Beiträge in diesem Forum nicht löschen. Du kannst an Umfragen in diesem Forum nicht mitmachen.
|
Powered by phpBB © 2001, 2005 phpBB Group Deutsche Übersetzung von phpBB.de
|