win7下 使用ddraw显示YUV数据,系统配色方案总会改为win7 basic

dixuexiongyingss 2014-08-20 06:19:03
下面是具体代码:
LPDIRECTDRAW            lpDD;                // DirectDraw 对象指针 
LPDIRECTDRAWSURFACE lpDDSPrimary; // DirectDraw 主表面指针
LPDIRECTDRAWSURFACE lpDDSOffScr; // DirectDraw 离屏表面指针
DDSURFACEDESC ddsd; // DirectDraw 表面描述
RECT rctDest; // 目标区域
RECT rctSour; // 源区域
HRESULT ddRval; // DirectDraw 函数返回值

// 创建DirectCraw对象
if (DirectDrawCreate(NULL, &lpDD, NULL) != DD_OK)
return FALSE;
// 设置协作层
if (lpDD->SetCooperativeLevel(hWnd,
DDSCL_NORMAL | DDSCL_NOWINDOWCHANGES) != DD_OK)
return FALSE;
// 创建主表面
ZeroMemory(&ddsd, sizeof(ddsd));
ddsd.dwSize = sizeof(ddsd);
ddsd.dwFlags = DDSD_CAPS;
ddsd.ddsCaps.dwCaps = DDSCAPS_PRIMARYSURFACE;
if (lpDD->CreateSurface(&ddsd, &lpDDSPrimary, NULL) != DD_OK)
return FALSE;

//DDSURFACEDESC surface;
//surface.dwSize = sizeof(surface);

//lpDDSPrimary->GetSurfaceDesc(&surface);
// 创建离屏表面对象
ZeroMemory(&ddsd, sizeof(ddsd));
ddsd.dwSize = sizeof(ddsd);
ddsd.ddsCaps.dwCaps = DDSCAPS_OFFSCREENPLAIN | DDSCAPS_VIDEOMEMORY; //DDSCAPS_OVERLAY

DDSCAPS_OFFSCREENPLAIN;
ddsd.dwFlags = DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH | DDSD_PIXELFORMAT;
ddsd.dwWidth = DRAW_WIDHT;
ddsd.dwHeight = DRAW_HEIGHT;
ddsd.ddpfPixelFormat.dwSize = sizeof(DDPIXELFORMAT);
ddsd.ddpfPixelFormat.dwFlags = DDPF_FOURCC | DDPF_YUV ;
ddsd.ddpfPixelFormat.dwFourCC = MAKEFOURCC('Y','V','1','2');
ddsd.ddpfPixelFormat.dwYUVBitCount = 8;
if (lpDD->CreateSurface(&ddsd, &lpDDSOffScr, NULL) != DD_OK)
return FALSE;

// 加载yv12图像文件
FILE * f = fopen("test.yv12","rb");
LPBYTE lpYV12 = new BYTE[FILE_WIDTH * FILE_HEIGHT * 3 / 2];
UINT iLen = fread(lpYV12, 1, FILE_WIDTH * FILE_HEIGHT * 3 / 2, f);
fclose(f);
LPBYTE lpY = lpYV12;
LPBYTE lpU = lpYV12 + FILE_WIDTH * FILE_HEIGHT;
LPBYTE lpV = lpYV12 + FILE_WIDTH * FILE_HEIGHT * 5 / 4;
ddRval = lpDDSOffScr->Lock(NULL,&ddsd,DDLOCK_WAIT | DDLOCK_WRITEONLY,NULL);
while(ddRval == DDERR_WASSTILLDRAWING);
if(ddRval != DD_OK)
return FALSE;
LPBYTE lpSurf = (LPBYTE)ddsd.lpSurface;
LPBYTE lpY1 = lpSurf;
/*LPBYTE lpV1 = lpSurf + ddsd.lPitch * FILE_HEIGHT;
LPBYTE lpU1 = lpV1 + ddsd.lPitch * FILE_HEIGHT / 4;
*/
LPBYTE lpU1 = lpSurf + ddsd.lPitch * FILE_HEIGHT;
LPBYTE lpV1 = lpU1 + ddsd.lPitch * FILE_HEIGHT / 4;
int nOffset = DRAW_TOP*FILE_WIDTH+DRAW_LEFT;
// 填充离屏表面
if(lpSurf)
{
int i = 0;
// fill Y data
lpY += nOffset;
for(i=0; i<ddsd.dwHeight; i++)
{
memcpy(lpSurf, lpY, ddsd.dwWidth);
lpY += FILE_WIDTH;
lpSurf += ddsd.lPitch;
}

// fill V data
lpV += DRAW_TOP * FILE_WIDTH / 4 + DRAW_LEFT / 2;
for(i=0; i<ddsd.dwHeight/2; i++)
{
memcpy(lpSurf, lpV, ddsd.dwWidth / 2);
lpV += FILE_WIDTH / 2;
lpSurf += ddsd.lPitch / 2;
}

// fill U data
lpU += DRAW_TOP * FILE_WIDTH / 4 + DRAW_LEFT / 2;
for(i=0; i<ddsd.dwHeight/2; i++)
{
memcpy(lpSurf, lpU, ddsd.dwWidth / 2);
lpU += FILE_WIDTH / 2;
lpSurf += ddsd.lPitch / 2;
}
}
lpDDSOffScr->Unlock(NULL);
delete lpYV12;

// Blt到主表面上
rctSour.left = 0;
rctSour.top = 0;
rctSour.right = ddsd.dwWidth;
rctSour.bottom = ddsd.dwHeight;
GetClientRect(hWnd,&rctDest);
ClientToScreen(hWnd, (LPPOINT)&rctDest.left);
ClientToScreen(hWnd, (LPPOINT)&rctDest.right);

ddRval = lpDDSPrimary->Blt(&rctDest, lpDDSOffScr, &rctSour, DDBLT_ASYNC | DDBLT_WAIT, NULL);
while(ddRval == DDERR_WASSTILLDRAWING);
if(ddRval != DD_OK)
return FALSE;
// 释放DirectDraw对象
if(lpDD != NULL)
{
if(lpDDSPrimary != NULL)
{
lpDDSPrimary->Release();
lpDDSPrimary = NULL;
}
if(lpDDSOffScr != NULL)
{
lpDDSOffScr->Release();
lpDDSOffScr = NULL;
}
lpDD->Release();
lpDD = NULL;
}
return TRUE;
...全文
884 7 打赏 收藏 转发到动态 举报
写回复
用AI写文章
7 条回复
切换为时间正序
请发表友善的回复…
发表回复
xsfandzll 2015-03-12
  • 打赏
  • 举报
回复
我也遇到同样的问题,求分享!!!!
Beyond_cn 2014-12-22
  • 打赏
  • 举报
回复
楼主愿意分享吗
deary0188 2014-11-28
  • 打赏
  • 举报
回复
楼主怎么解决的? 现在也碰到这个问题了,在线求助啊
dixuexiongyingss 2014-08-22
  • 打赏
  • 举报
回复
搞好了
三条猫 2014-08-22
  • 打赏
  • 举报
回复
楼主自己解决了?
dixuexiongyingss 2014-08-22
  • 打赏
  • 举报
回复
来人 结贴给分
dixuexiongyingss 2014-08-21
  • 打赏
  • 举报
回复
大神快来吧

3,248

社区成员

发帖
与我相关
我的任务
社区描述
ATL,Active Template Library活动(动态)模板库,是一种微软程序库,支持利用C++语言编写ASP代码以及其它ActiveX程序。
社区管理员
  • ATL/ActiveX/COM社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧