GDI textout and DirectDraw problem
I wrote an application using directdraw for output and i decided to use
textout to print the framerate.
The problem is when i write to the screen the ouput is not cleared. Example:
When i first write ''20'' to the screen en after this ''10'' the first location
(2 and 1) get mixed up like it''s not cleared up or something.. I really
don''t know where this problem comes from.. I included the source (cpp + h)..
// Video.h: interface for the CVideo class.
//////////////////////////////////////////////////////////////////////
#ifndef _CVIDEO_H
#define _CVIDEO_H
#include
class CVideo
{
public:
void Flip();
void DrawTextGDI(char *pcText, ...);
void Draw(LPDIRECTDRAWSURFACE lpddsSource, RECT rSrc, RECT rDest);
bool Init(HWND hWindow, int iWidth = 640, int iHeight = 480, int
iColorDepth = 16, int iBufferCount = 1, bool bClipper = true);
void Shutdown();
static CVideo *GetInstance() {static CVideo vidInstance; return
&vidInstance }
private:
CVideo();
bool AttachClipper(LPDIRECTDRAWSURFACE surface, int x, int y, int width,
int height);
LPDIRECTDRAW m_lpdd; // DirectDraw Object
DDSURFACEDESC m_ddsd; // DirectDraw Surface Description Structure
LPDIRECTDRAWSURFACE m_lpddsprimary; // DirectDraw Primary Surface
LPDIRECTDRAWSURFACE m_lpddsback; // DirectDraw Back Surface
LPDIRECTDRAWCLIPPER m_lpddclipper; // DirectDraw Clipper
};
#endif
// Video.cpp: implementation of the CVideo class.
//
//////////////////////////////////////////////////////////////////////
#include "Video.h"
#include "LogFile.h"
//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////
CVideo::CVideo()
{
m_lpdd = NULL; // DirectDraw Object
m_lpddsprimary = NULL; // DirectDraw Primary Surface
m_lpddsback = NULL; // DirectDraw Back Surface
m_lpddclipper = NULL; // DirectDraw Clipper
CLogFile *plLogFile;
// Acces the singleton
plLogFile = CLogFile::GetInstance();
//
plLogFile->Printf("CVideo\t\tCreated\n");
}
bool CVideo::Init(HWND hWindow, int iWidth, int iHeight, int iColorDepth,
int iBufferCount, bool bClipper)
{
//Create Instance Of A DirectDraw Object
if (FAILED(DirectDrawCreate(NULL, &m_lpdd, NULL)))
{
CLogFile *plLogFile;
// Acces the singleton
plLogFile = CLogFile::GetInstance();
//
plLogFile->Printf("CVideo::Init CRITICAL ERROR DirectDrawCreate\n");
return false;
}
//Set Cooperative Level To Fullscreen And Exclusive
if(FAILED(m_lpdd->SetCooperativeLevel(hWindow, DDSCL_FULLSCREEN |
DDSCL_EXCLUSIVE)))
{
CLogFile *plLogFile;
// Acces the singleton
plLogFile = CLogFile::GetInstance();
//
plLogFile->Printf("CVideo::Init CRITICAL ERROR SetCooperativeLevel\n");
return false;
}
//Set Display Mode
if (FAILED(m_lpdd->SetDisplayMode(iWidth, iHeight, iColorDepth)))
{
CLogFile *plLogFile;
// Acces the singleton
plLogFile = CLogFile::GetInstance();
//
plLogFile->Printf("CVideo::Init CRITICAL ERROR SetDisplayMode\n");
return false;
}
//Surface Description Structure
memset(&m_ddsd,0,sizeof(m_ddsd));
m_ddsd.dwSize = sizeof(m_ddsd);
m_ddsd.dwFlags = DDSD_CAPS | DDSD_BACKBUFFERCOUNT;
m_ddsd.ddsCaps.dwCaps = DDSCAPS_PRIMARYSURFACE | DDSCAPS_FLIP |
DDSCAPS_COMPLEX;
m_ddsd.dwBackBufferCount = 1; //1 = double buffering, 2 = triplebuffering
//Create The Primary Surface
if(FAILED(m_lpdd->CreateSurface(&m_ddsd, &m_lpddsprimary, NULL)))
{
CLogFile *plLogFile;
// Acces the singleton
plLogFile = CLogFile::GetInstance();
//
plLogFile->Printf("CVideo::Init CRITICAL ERROR CreateSurface\n");
return false;
}
m_ddsd.ddsCaps.dwCaps = DDSCAPS_BACKBUFFER;
//Create The Back Surface
if (FAILED(m_lpddsprimary->GetAttachedSurface(&m_ddsd.ddsCaps,
&m_lpddsback)))
{
CLogFile *plLogFile;
// Acces the singleton
plLogFile = CLogFile::GetInstance();
//
plLogFile->Printf("CVideo::Init CRITICAL ERROR GetAttachedSurface\n");
return false;
}
if (bClipper)
{
//Attach Clipper To Surface With Size: iWidth x iHeight
if(!AttachClipper(m_lpddsback, 0, 0, iWidth, iHeight))
{
CLogFile *plLogFile;
// Acces the singleton
plLogFile = CLogFile::GetInstance();
//
plLogFile->Printf("CVideo::Init CRITICAL ERROR AttachClipper\n");
return false;
}
}
CLogFile *plLogFile;
// Acces the singleton
plLogFile = CLogFile::GetInstance();
//
plLogFile->Printf("CVideo\t\tInit\t\t(%d x %d x %d) BackBuffers=%d
Clipping=%d \n", iWidth, iHeight, iColorDepth, iBufferCount, bClipper);
return true;
}
void CVideo::Shutdown()
{
if(m_lpddsback)
{
m_lpddsback->Release();
m_lpddsback = NULL;
}
if(m_lpddsprimary)
{
m_lpddsprimary->Release();
m_lpddsprimary = NULL;
}
if(m_lpdd)
{
m_lpdd->Release();
m_lpdd = NULL;
}
CLogFile *plLogFile;
// Acces the singleton
plLogFile = CLogFile::GetInstance();
//
plLogFile->Printf("CVideo\t\tShutdown\n");
}
bool CVideo::AttachClipper(LPDIRECTDRAWSURFACE surface, int x, int y, int
width, int height)
{
//Region Data Struct Needed To Fill In The Clipper Info
LPRGNDATA rd;
RECT rRect = {x, y, width, height};
//Create DirectDraw Clipper
if(FAILED(m_lpdd->CreateClipper(0, &m_lpddclipper, NULL)))
{
CLogFile *plLogFile;
// Acces the singleton
plLogFile = CLogFile::GetInstance();
//
plLogFile->Printf("CVideo::Init CRITICAL ERROR AttachClipper\n");
return false;
}
//Allocate Memory For The Region Data
rd = (LPRGNDATA)malloc(sizeof(RGNDATAHEADER)+sizeof(RECT));
//Copy The Rect Data Into The RGNDATA Buffer
memcpy(rd->Buffer, &rRect, sizeof(RECT));
rd->rdh.dwSize = sizeof(RGNDATAHEADER);
rd->rdh.iType = RDH_RECTANGLES;
rd->rdh.nCount = 1;
rd->rdh.nRgnSize = sizeof(RECT);
rd->rdh.rcBound.left = x;
rd->rdh.rcBound.right = x+width;
rd->rdh.rcBound.top = y;
rd->rdh.rcBound.bottom = y+height;
//Set Clip List With LPGRNDATA Info
if(FAILED(m_lpddclipper->SetClipList(rd, 0)))
{
return false;
}
//Attach Clipper To The Surface
if(FAILED(surface->SetClipper(m_lpddclipper)))
{
return false;
}
free(rd);
return true;
}
void CVideo::Draw(LPDIRECTDRAWSURFACE lpddsSource, RECT rSrc, RECT rDest)
{
m_lpddsback->Blt(&rDest, lpddsSource, &rSrc, DDBLT_WAIT, NULL);
}
void CVideo::Flip()
{
m_lpddsprimary->Flip(NULL, DDFLIP_WAIT);
}
void CVideo::DrawTextGDI(char *pcText, ...)
{
HDC xdc;
char acBuffer[1024];
va_list vaArgList; //Variable Argument List
// print out the string using the variable number of arguments on stack
va_start (vaArgList, pcText);
vsprintf (acBuffer, pcText, vaArgList);
va_end (vaArgList);
if (FAILED(m_lpddsback->GetDC(&xdc))) //Get Device Context From
DirectDraw Surface
return;
SetTextColor(xdc,RGB(255, 255, 255)); //Set Front White And Background
Transparent
SetBkMode(xdc, TRANSPARENT);
TextOut(xdc,10,10,acBuffer,strlen(acBuffer));
m_lpddsback->ReleaseDC(xdc); //Release The Device Context
}
Judging by the past, it seems certain that something we cannot imagine today will dominate the landscape in 2021. That''''s why the future of the PC is even more exciting than the past.
Yes I did. I use this (source included) method:
void CVideo::Clear()
{
DDBLTFX ddbltfx;
memset(&ddbltfx, 0, sizeof(ddbltfx));
ddbltfx.dwSize = sizeof(ddbltfx);
ddbltfx.dwFillColor = RGB(0,0,0);
m_lpddsback->Blt(NULL, NULL, NULL, DDBLT_COLORFILL, &ddbltfx);
}
I found out the problem, I should have used DDBLT_WAIT too, but I really don't understand why! Anyway problem solved.. everybody is happy
Thanks in advance
Edited by - DEimers on November 5, 2001 3:13:23 AM
Edited by - DEimers on November 5, 2001 3:38:13 AM
void CVideo::Clear()
{
DDBLTFX ddbltfx;
memset(&ddbltfx, 0, sizeof(ddbltfx));
ddbltfx.dwSize = sizeof(ddbltfx);
ddbltfx.dwFillColor = RGB(0,0,0);
m_lpddsback->Blt(NULL, NULL, NULL, DDBLT_COLORFILL, &ddbltfx);
}
I found out the problem, I should have used DDBLT_WAIT too, but I really don't understand why! Anyway problem solved.. everybody is happy
Thanks in advance
Edited by - DEimers on November 5, 2001 3:13:23 AM
Edited by - DEimers on November 5, 2001 3:38:13 AM
This topic is closed to new replies.
Advertisement
Popular Topics
Advertisement