|
发表于 2004-4-30 10:41:00
|
显示全部楼层
Re:求助 ,图片显示的问题
我把我自己写的一个完整的图象显示程序给你吧。我没用bltfast,而是自己写的copy函数。(效果比blt好多了)自己建个工程加进去,再把你要显示的两张图放在同一目录下(一张叫“yuna.bmp",一张叫"rikku.bmp")。(alpha是半透明函数)
#include<windows.h>
#include<ddraw.h>
HWND hwnd;
LPDIRECTDRAW7 IpDD;
LPDIRECTDRAWSURFACE7 IpDDSPrimary;
LPDIRECTDRAWSURFACE7 IpDDSBuffer;
LPDIRECTDRAWSURFACE7 IpDDSBack[2];
DDSURFACEDESC2 ddsd,ddsd_src,ddsd_dest;
HBITMAP bitmap;
HDC hdc1,hdc;
int i;
LRESULT CALLBACK WinProc(HWND hwnd,UINT message,WPARAM wParam,LPARAM lParam);
bool LoadPicture(char *PictureName,int i);
bool initwindow(char *windowname,HINSTANCE hinstance,int windowmodw);
bool initddraw();
void Copy(LPDIRECTDRAWSURFACE7 lPrimary,LPDIRECTDRAWSURFACE7 lPbuffer);
void CALLBACK Go(HWND hwnd,UINT uMsg,UINT iDevent,DWORD dwTime);
void Alpha();
int PASCAL WinMain(HINSTANCE hinstance,HINSTANCE hPrevhinstance,LPSTR lpCmdLine,int windowmode){
if(!initwindow("ExpForCopy",hinstance,windowmode)||!initddraw()){
MessageBox(hwnd,"MyFish","There must be something wrong!",MB_OK);
return false;
}
if(!LoadPicture("rikku.bmp",0))return false;
if(!LoadPicture("yuna.bmp",1))return false;
SetTimer(hwnd,0,500,Go);
MSG msg;
for(;;){
if(PeekMessage(&msg,NULL,0,0,PM_REMOVE)){
if(msg.message==WM_QUIT){
MessageBox(hwnd,"Let's us get out of this window","gogogo",MB_OK);
break;
}
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
return msg.lParam;
}
bool initwindow(char *windowname,HINSTANCE hinstance,int windowmode){
WNDCLASSEX win;
win.cbSize=sizeof(WNDCLASSEX);
win.style=CS_HREDRAW|CS_VREDRAW;
win.lpfnWndProc=(WNDPROC)WinProc;
win.cbClsExtra=0;
win.cbWndExtra=0;
win.hInstance=hinstance;
win.hIcon=NULL;
win.hCursor=NULL;
win.hbrBackground=CreateSolidBrush(RGB(255,255,255));
win.lpszMenuName=NULL;
win.lpszClassName=windowname;
win.hIconSm=NULL;
RegisterClassEx(&win);
hwnd=CreateWindow(windowname,windowname,WS_POPUP|WS_MAXIMIZE,CW_USEDEFAULT,0,GetSystemMetrics(SM_CXSCREEN),GetSystemMetrics(SM_CYSCREEN),NULL,NULL,hinstance,NULL);
if(!hwnd)return false;
ShowWindow(hwnd,windowmode);
UpdateWindow(hwnd);
return true;
}
LRESULT CALLBACK WinProc(HWND hwnd,UINT message,WPARAM wParam,LPARAM lParam){
switch(message){
case WM_KEYDOWN:
switch(wParam){
case VK_ESCAPE:
KillTimer(hwnd,0);
PostMessage(hwnd,WM_CLOSE,0,0);
break;
}
return 0;
case WM_DESTROY:
PostQuitMessage(0);
return 0;
}
return DefWindowProc(hwnd,message,wParam,lParam);
}
bool initddraw(){
if(DirectDrawCreateEx(NULL,(void**)&IpDD,IID_IDirectDraw7,NULL)!=DD_OK)return false;
if(IpDD->SetCooperativeLevel(hwnd,DDSCL_EXCLUSIVE|DDSCL_FULLSCREEN|DDSCL_NOWINDOWCHANGES|DDSCL_ALLOWREBOOT)!=DD_OK)return false;
if(IpDD->SetDisplayMode(1024,768,32,0,DDSDM_STANDARDVGAMODE)!=DD_OK)return false;
memset(&ddsd,0,sizeof(DDSURFACEDESC2));
ddsd.dwSize=sizeof(ddsd);
ddsd.dwFlags=DDSD_CAPS;
ddsd.ddsCaps.dwCaps=DDSCAPS_PRIMARYSURFACE;
if(IpDD->CreateSurface(&ddsd,&IpDDSPrimary,NULL)!=DD_OK)return false;
ddsd.dwFlags=DDSD_CAPS|DDSD_WIDTH|DDSD_HEIGHT;
ddsd.ddsCaps.dwCaps=DDSCAPS_OFFSCREENPLAIN|DDSCAPS_SYSTEMMEMORY;
ddsd.dwHeight=768;
ddsd.dwWidth=1024;
if(IpDD->CreateSurface(&ddsd,&IpDDSBuffer,NULL)!=DD_OK)return false;
for(int i=0;i<2;i++)if(IpDD->CreateSurface(&ddsd,&IpDDSBack,NULL)!=DD_OK)return false;
hdc=::CreateCompatibleDC(NULL);
return true;
}
bool LoadPicture(char *PictureName,int i){
bitmap=(HBITMAP): oadImage(NULL,PictureName,IMAGE_BITMAP,1024,768,LR_LOADFROMFILE);
::SelectObject(hdc,bitmap);
if(IpDDSBack->GetSurfaceDesc(&ddsd)!=DD_OK)return false;
if(IpDDSBack->GetDC(&hdc1)!=DD_OK)return false;
::BitBlt(hdc1,0,0,ddsd.dwWidth,ddsd.dwHeight,hdc,0,0,SRCCOPY);
IpDDSBack->ReleaseDC(hdc1);
return true;
}
void Copy(LPDIRECTDRAWSURFACE7 lPrimary,LPDIRECTDRAWSURFACE7 lPbuffer){
ZeroMemory(&ddsd_src,sizeof(ddsd_src));
ddsd_src.dwSize=sizeof(ddsd_src);
ZeroMemory(&ddsd_dest,sizeof(ddsd_dest));
ddsd_dest.dwSize=sizeof(ddsd_dest);
lPrimary->Lock(NULL,&ddsd_src,DDLOCK_WAIT,NULL);
lPbuffer->Lock(NULL,&ddsd_dest,DDLOCK_WAIT,NULL);
BYTE *lPsrc=(BYTE*)ddsd_src.lpSurface;
BYTE *lPdest=(BYTE*)ddsd_dest.lpSurface;
for(int y=0;y<768;y++){
memcpy(lPsrc,lPdest,4096);
lPsrc+=ddsd_src.lPitch;
lPdest+=ddsd_dest.lPitch;
}
lPrimary->Unlock(NULL);
lPbuffer->Unlock(NULL);
}
void CALLBACK Go(HWND hwnd,UINT uMsg,UINT iDevent,DWORD dwTime){
/*Copy(IpDDSBuffer,IpDDSBack[PictureNumber]);
if(PictureNumber==0)PictureNumber++;
else PictureNumber--;
Copy(IpDDSPrimary,IpDDSBuffer);*/
Alpha();
Copy(IpDDSPrimary,IpDDSBuffer);
i++;
}
void Alpha(){
Copy(IpDDSBuffer,IpDDSBack[0]);
ZeroMemory(&ddsd_src,sizeof(ddsd_src));
ddsd_src.dwSize=sizeof(ddsd_src);
ZeroMemory(&ddsd_dest,sizeof(ddsd_dest));
ddsd_dest.dwSize=sizeof(ddsd_dest);
IpDDSBuffer->Lock(NULL,&ddsd_src,DDLOCK_WAIT,NULL);
IpDDSBack[1]->Lock(NULL,&ddsd_dest,DDLOCK_WAIT,NULL);
_int64 mask=0x7f7f7f7f7f7f7f7f;
_asm{
mov eax,ddsd_src.lpSurface
mov ebx,ddsd_dest.lpSurface
mov edi,768
FirstLoop:
push eax
push ebx
mov esi,512
SecondLoop:
movq mm0,[eax]
movq mm1,[ebx]
psrlw mm0, 1
pand mm0, mask
paddusb mm0,mm1
movq [eax],mm0
add eax,8
add ebx,8
dec esi
jnz SecondLoop
pop ebx
pop eax
add eax,ddsd_src.lPitch
add ebx,ddsd_dest.lPitch
dec edi
jnz FirstLoop
emms
}
IpDDSBuffer->Unlock(NULL);
IpDDSBack[1]->Unlock(NULL);
}
|
|