 |
JLI Spieleprogrammierung
|
Vorheriges Thema anzeigen :: Nächstes Thema anzeigen |
Autor |
Nachricht |
Flow Junior JLI'ler
Alter: 42 Anmeldedatum: 13.09.2005 Beiträge: 57
Medaillen: Keine
|
Verfasst am: 30.09.2005, 12:46 Titel: Hilfe! Meine Bitmap-Font Funktion drückt auf die CPU Bremse! |
|
|
Hallo Leute,
ich hab ein Problem. Habe mir gerade eine Bitmap-Font Funktion geschrieben. Die funktioniert soweit auch. Ich habe jetzt nur zwei Buchstaben zu Testzwecken (A und B) implementiert und ein paar ausgegeben. Das Problem ist aber, dass das meine ganze Anwendung innerhalb von 2 sekunden vollkommen ausbremst. Ich kann mir das nicht erklären. Ich habe im Vordergrund zu Testzwecken eine kleine 2d Sprite die man mit den Pfeiltasten nach links und rechts bewegen kann. Sobald ich die Fontfunktion einbinde bewegt sie sich kaum noch und mein PC wird gähnend langsam. Ich kann mir darauf keinen Reim machen.
Hier der Code für die BitmapFon-Funktion:
(Sie übernimmt als Argument einen char-array, den ich ihr übergebe)
CPP: | // ***************************************************************************************
// Modul: Font.cpp
// Zweck: Funktionen für BitmapFont
// ***************************************************************************************
#include <iostream.h>
#include <windows.h>
#include "Spaceball.h"
#include "DDrawClass.h"
// ***************************************************************************************
// Globale Variablen und Zeiger
// ***************************************************************************************
// Zeiger auf die Primäre Oberfläche
LPDIRECTDRAWSURFACE7 lpDDFontSurface = NULL;
// ***************************************************************************************
// Funktionen
// ***************************************************************************************
// Funktion für das umwandeln des Textes in der Bitmapfont
void BitmapText(char text[])
{
// BitmapFont auf die Oberfläche laden
lpDDFontSurface=DrawBitmap("media\\font.bmp",0,0);
// Länge des Strings herausfinden
int anzahlZeichen = strlen(text);
// Die Konstanten für die zeilenhöhe und spaltenbreite pro Zeichen in der Fonttextur
const int spalte = 32;
const int zeile = 32;
// länge der Surface mit den zu zeichnenden Zeichen (abhängig von der Anzahl an Zeichen)
int textLaenge = 0;
// RECT Struktur für die Zeichen
RECT zeichen;
zeichen.top = 0;
zeichen.left = 0;
zeichen.bottom = 0;
zeichen.right = 0;
// Vorbereitung der DestinationRects (Koordinaten, wo der Buchstabe gezeichnet werden soll)
RECT ZeichenDest;
ZeichenDest.top = 100;
ZeichenDest.left = 100;
ZeichenDest.bottom = 132;
ZeichenDest.right = 132;
// Die Schleife durchläuft den array solange, bis das Nullbyte (\0) auftritt
// dann wird abgebrochen und der Text ausgegeben
for(int i = 0; text[i] != '\0'; i++)
{
switch(text[i])
{
case 'A':
zeichen.top = 4*zeile;
zeichen.left = 1*spalte;
zeichen.bottom = zeichen.top+zeile;
zeichen.right = zeichen.left+spalte;
break;
case 'B':
zeichen.top = 4*zeile;
zeichen.left = 2*spalte;
zeichen.bottom = zeichen.top+zeile;
zeichen.right = zeichen.left+spalte;
break;
default:
Error("Hier darf er nicht hinkommen.");
break;
}
// Zeichen-Rect an Array mit den Buchstaben übergeben
//pFinalText[i] = zeichen;
// ausgabe der Zeichen am Bildschirm
// Zeichnen des Buchstabens
Render(lpDDFontSurface, ZeichenDest, zeichen,1);
// Cursor um eine Spalte weiterbewegen
ZeichenDest.left += spalte;
ZeichenDest.right += spalte;
}
}
|
Hier ist noch die Spielschleife mit Nachrichtenvermittlung, wo ich die Funktion aufrufe:
CPP: | // Text für die Testausgabe
char text[] = "AABBBAB";
// Struktur, in der Informationen zur Nachricht gespeichert werden
MSG msg;
while(TRUE)
{
if(PeekMessage(&msg,NULL,0,0,PM_REMOVE))
{
if(msg.message == WM_QUIT)
{
break;
}
TranslateMessage(&msg);
DispatchMessage(&msg);
}
// wenn keine Nachricht vorliegt,
else
{
// abfangen der Tastatureingabe und neuberechnen der Position
if(sprung=KeyboardInput() < 0 && (DestRect.left-sprung) > 0)
{
DestRect.left -= (sprung);
DestRect.right -= (sprung);
sprung = 0; // Sprung wieder auf Null setzen
}
if(sprung=KeyboardInput() > 0 && (DestRect.right+sprung) < SCR_WIDTH-175)
{
DestRect.left += (sprung);
DestRect.right += (sprung);
sprung = 0; // Sprung wieder auf Null setzen
}
// Blitten der Grafik auf die Oberfläche
// Syntax: Render(Oberfläche, ZielRect, QuellRect, Colorkey-Code)
Render(lpDDTitelbild, FullScreen, FullScreen,0);
Render(lpDDGamebar, BarDest, BarSrc, 0);
Render(lpDDSpaceball, DestRect, SrcRect,1);
// ******************************************** //
// ********** Hier der kritische Aufruf ************* //
BitmapText(text);
Flip();
}
|
Hier noch meine DirectDraw Funktionen für Render und DrawBitmap:
CPP: | LPDIRECTDRAWSURFACE7 DrawBitmap(LPCTSTR File, int dWidth, int dHeight)
{
// Device Context für das Bild und die DirectDraw-Oberfläche anlegen
HDC hBmDC,hSurfDC;
// Handle der zu ladenden Bitmap
HBITMAP hBM;
// Oberflächenbeschreibung
DDSURFACEDESC2 SurfDesc;
// Zeiger auf die Oberfläche
LPDIRECTDRAWSURFACE7 lpDDSurface;
// Bild laden
hBM = (HBITMAP)LoadImage(NULL,File,IMAGE_BITMAP,dWidth,dHeight,LR_LOADFROMFILE);
// testen ob ein Fehler während des Ladens aufgetreten ist
if(NULL == hBM)
{
return 0;
}
// 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 = SCR_WIDTH;
SurfDesc.dwHeight = SCR_HEIGHT;
// Oberfläche anlegen
if(FAILED(lpDD7->CreateSurface(&SurfDesc,&lpDDSurface,NULL)))
{
return 0;
}
ZeroMemory(&SurfDesc,sizeof(SurfDesc));
SurfDesc.dwSize = sizeof(SurfDesc);
lpDDSurface->GetSurfaceDesc(&SurfDesc);
// wo befindet sich die erzeugt Oberfläche ?
if(SurfDesc.ddsCaps.dwCaps & DDSCAPS_VIDEOMEMORY)
{
if(SurfDesc.ddsCaps.dwCaps & DDSCAPS_LOCALVIDMEM)
{
OutputDebugString("Oberfläche befindet sich im LOCALVIDMEM (Grafikspeicher)\n");
}
else
{
OutputDebugString("Oberfläche befindet sich im NONLOCALVIDMEM (AGP-Speicher)\n");
}
}
else
{
OutputDebugString("Oberfläche befindet sich im SYSTEMSPEICHER\n");
}
// Device Context der Oberfläche holen
lpDDSurface->GetDC(&hSurfDC);
// Compatiblen Device Context für das Bild anlegen
hBmDC = CreateCompatibleDC(hSurfDC);
// Bild in den Device Context holen
SelectObject(hBmDC,hBM);
// Bild in die Oberfläche kopieren
BitBlt(hSurfDC,0,0,SCR_WIDTH,SCR_HEIGHT,hBmDC,0,0,SRCCOPY);
// Device Context freigeben
lpDDSurface->ReleaseDC(hSurfDC);
// Device Context und Bild löschen
DeleteDC(hBmDC);
DeleteObject(hBM);
// Zeiger auf die Oberfläche zurückgeben
return lpDDSurface;
}
// Blitten der Grafik auf die Oberfläche
// 3. Parameter: 0 = normal; 1 = Source Colorkey
void Render(LPDIRECTDRAWSURFACE7 lpDDSurface, RECT DestRect, RECT SrcRect, int ColorKey)
{
// Die DDBLTFX-Struktur füllen
DDBLTFX DDBltFx;
ZeroMemory(&DDBltFx,sizeof(DDBLTFX));
DDBltFx.dwSize=sizeof(DDBLTFX);
// Wenn Colorkey auf 1 gesetzt ist, wird mit einem Source Colorkey gearbeitet
if(ColorKey==1)
{
//DDBltFx.dwFillColor = 1;
DDBltFx.ddckSrcColorkey.dwColorSpaceHighValue=0;
DDBltFx.ddckSrcColorkey.dwColorSpaceLowValue=0;
// Puffer löschen
lpBackBuffer->Blt(NULL,NULL,NULL,DDBLT_WAIT,&DDBltFx);
// die Oberfläche, die das geladene Bild enthält
// auf die primäre Oberfläche Blitten
if(FAILED(lpBackBuffer->Blt(&DestRect,lpDDSurface,&SrcRect,DDBLT_WAIT | DDBLT_KEYSRCOVERRIDE,&DDBltFx)))
{
Error("Blt ist fehlgeschlagen");
}
}
// Wenn Colorkey auf 0 gesetzt ist, wird ohne Colorkey gearbeitet
if(ColorKey==0)
{
// Puffer löschen
lpBackBuffer->Blt(NULL,NULL,NULL,DDBLT_WAIT,&DDBltFx);
// die Oberfläche, die das geladene Bild enthält
// auf die primäre Oberfläche Blitten
if(FAILED(lpBackBuffer->Blt(&DestRect,lpDDSurface,&SrcRect,DDBLT_WAIT ,&DDBltFx)))
{
Error("Blt ist fehlgeschlagen");
}
}
}
BOOL Flip(void)
{
lpDDSPrimary->Flip(NULL, DDFLIP_NOVSYNC);
return TRUE;
}
|
Ich hoffe, dass Ihr mir irgendwie helfen könnt, denn erklären kann ich mir das partout nicht.
Gruß Flo |
|
Nach oben |
|
 |
OLiver Super JLI'ler

Alter: 33 Anmeldedatum: 29.06.2003 Beiträge: 306 Wohnort: Jena Medaillen: Keine
|
Verfasst am: 30.09.2005, 13:06 Titel: |
|
|
DrawBitmap läd das Bild jedesmal neu.
Ach, ich seh grad, dass es die Ladefunktion ist, evtl. logischere Namen verwenden...  _________________ http://www.sieder25.org/ (Siedler 2 - Remake) |
|
Nach oben |
|
 |
Flow Junior JLI'ler
Alter: 42 Anmeldedatum: 13.09.2005 Beiträge: 57
Medaillen: Keine
|
Verfasst am: 30.09.2005, 13:36 Titel: |
|
|
Ich könnte Dich küssen Oliver!!!
Das hatte ich total übersehen. Jetzt läuft das 1a. Daran hatte ich überhaupt nicht gedacht. D.h. er hat die Bitmap unzählige male auf die Oberfläche geladen.
Danke !  |
|
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
|