⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 dx_2d.c

📁 一个用于智能手机的多媒体库适合S60 WinCE的跨平台开发库
💻 C
📖 第 1 页 / 共 2 页
字号:
	if ((dst_w==src_w) && (dst_h==src_h)) {		flags = DDBLTFAST_WAIT;		if (key) flags |= DDBLTFAST_SRCCOLORKEY;		if (dst_wnd) { left = r_dst.left; top = r_dst.top; } else left = top = 0; 		hr = IDirectDrawSurface_BltFast(dd->pBack, left, top, src->pSurface, src_wnd ? &r_src : NULL, flags);	} else {		flags = DDBLT_WAIT;		if (key) flags |= DDBLT_KEYSRC;		hr = IDirectDrawSurface_Blt(dd->pBack, dst_wnd ? &r_dst : NULL, src->pSurface, src_wnd ? &r_src : NULL, flags, NULL);	}	return FAILED(hr) ? GF_IO_ERR : GF_OK;}static Bool pixelformat_yuv(u32 pixel_format){	switch (pixel_format) {	case GF_PIXEL_YUY2:	case GF_PIXEL_YVYU:	case GF_PIXEL_UYVY:	case GF_PIXEL_VYUY:	case GF_PIXEL_Y422:	case GF_PIXEL_UYNV:	case GF_PIXEL_YUNV:	case GF_PIXEL_V422:	case GF_PIXEL_YV12:	case GF_PIXEL_IYUV:	case GF_PIXEL_I420:		return 1;	default:		return 0;	}}static u32 get_win_4CC(u32 pixel_format){	switch (pixel_format) {	case GF_PIXEL_YUY2:		return mmioFOURCC('Y', 'U', 'Y', '2');	case GF_PIXEL_YVYU:		return mmioFOURCC('Y', 'V', 'Y', 'U');	case GF_PIXEL_UYVY:		return mmioFOURCC('U', 'Y', 'V', 'Y');	case GF_PIXEL_VYUY:		return mmioFOURCC('V', 'Y', 'U', 'Y');	case GF_PIXEL_Y422:		return mmioFOURCC('Y', '4', '2', '2');	case GF_PIXEL_UYNV:		return mmioFOURCC('U', 'Y', 'N', 'V');	case GF_PIXEL_YUNV:		return mmioFOURCC('Y', 'U', 'N', 'V');	case GF_PIXEL_V422:		return mmioFOURCC('V', '4', '2', '2');	case GF_PIXEL_YV12:		return mmioFOURCC('Y', 'V', '1', '2');	case GF_PIXEL_IYUV:		return mmioFOURCC('I', 'Y', 'U', 'V');	case GF_PIXEL_I420:		return mmioFOURCC('I', '4', '2', '0');	default:		return 0;	}}static DDSurface *DD_GetSurface(GF_VideoOutput *dr, u32 width, u32 height, u32 pixel_format){#ifdef USE_DX_3	DDSURFACEDESC ddsd;#else	DDSURFACEDESC2 ddsd;#endif	HRESULT hr;	DDCONTEXT;	/*yuv format*/	if (pixelformat_yuv(pixel_format)) {		if (dr->yuv_pixel_format) {			/*don't recreate a surface if not needed*/			if (dd->yuv_pool.pSurface && (dd->yuv_pool.width >= width) && (dd->yuv_pool.height >= height) ) return &dd->yuv_pool;			width = MAX(dd->yuv_pool.width, width);			height = MAX(dd->yuv_pool.height, height);			SAFE_DD_RELEASE(dd->yuv_pool.pSurface);			memset(&dd->yuv_pool, 0, sizeof(DDSurface));			memset (&ddsd, 0, sizeof(ddsd));			ddsd.dwSize = sizeof(ddsd);			ddsd.ddpfPixelFormat.dwSize = sizeof(ddsd.ddpfPixelFormat);			ddsd.dwFlags = DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH | DDSD_PIXELFORMAT;			ddsd.ddsCaps.dwCaps = DDSCAPS_OVERLAY | DDSCAPS_VIDEOMEMORY;			ddsd.ddpfPixelFormat.dwFlags = DDPF_FOURCC;			ddsd.dwWidth = width;			ddsd.dwHeight = height;			ddsd.ddpfPixelFormat.dwFourCC = get_win_4CC(dr->yuv_pixel_format);#ifdef USE_DX_3			if( FAILED( hr = IDirectDraw_CreateSurface(dd->pDD, &ddsd, &dd->yuv_pool.pSurface, NULL ) ) )				return NULL;#else			if( FAILED( hr = IDirectDraw7_CreateSurface(dd->pDD, &ddsd, &dd->yuv_pool.pSurface, NULL ) ) )				return NULL;#endif			dd->yuv_pool.format = dr->yuv_pixel_format;			dd->yuv_pool.width = width;			dd->yuv_pool.height = height;			return &dd->yuv_pool;		}	}	/*don't recreate a surface if not needed*/	if ((dd->rgb_pool.width >= width) && (dd->rgb_pool.height >= height) ) return &dd->rgb_pool;	width = MAX(dd->rgb_pool.width, width);	height = MAX(dd->rgb_pool.height, height);	SAFE_DD_RELEASE(dd->rgb_pool.pSurface);	memset(&dd->rgb_pool, 0, sizeof(DDSurface));	memset (&ddsd, 0, sizeof(ddsd));	ddsd.dwSize = sizeof(ddsd);	ddsd.dwFlags = DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH;	ddsd.ddsCaps.dwCaps = DDSCAPS_OFFSCREENPLAIN;	ddsd.dwWidth = width;	ddsd.dwHeight = height;#ifdef USE_DX_3	if( FAILED( hr = IDirectDraw_CreateSurface(dd->pDD, &ddsd, &dd->rgb_pool.pSurface, NULL ) ) )		return NULL;#else	if( FAILED( hr = IDirectDraw7_CreateSurface(dd->pDD, &ddsd, &dd->rgb_pool.pSurface, NULL ) ) )		return NULL;#endif	dd->rgb_pool.width = width;	dd->rgb_pool.height = height;	dd->rgb_pool.format = dd->pixelFormat;	return &dd->rgb_pool;}static GF_Err DD_Blit(GF_VideoOutput *dr, GF_VideoSurface *video_src, GF_Window *src_wnd, GF_Window *dst_wnd, u32 *key){	GF_VideoSurface temp_surf;	GF_Err e;	GF_Window src_wnd_2;	u32 w, h;	DDSurface *pool;	DDCONTEXT;	if (src_wnd) {		w = src_wnd->w;		h = src_wnd->h;	} else {		w = video_src->width;		h = video_src->height;	}	/*get RGB or YUV pool surface*/	pool = DD_GetSurface(dr, w, h, key ? dd->pixelFormat : video_src->pixel_format);	if (!pool) return GF_IO_ERR;	temp_surf.pixel_format = pool->format;	e = DD_LockSurface(dd, &temp_surf, pool->pSurface);	if (e) return e;	/*copy pixels to pool*/	dx_copy_pixels(&temp_surf, video_src, src_wnd);	e = DD_UnlockSurface(dd, pool->pSurface);	if (e) return e;	src_wnd_2.x = src_wnd_2.y = 0;	if (src_wnd) {		src_wnd_2.w = src_wnd->w;		src_wnd_2.h = src_wnd->h;	} else {		src_wnd_2.w = video_src->width;		src_wnd_2.h = video_src->height;	}	/*and blit surface*/	return DD_BlitSurface(dd, pool, &src_wnd_2, dst_wnd, key);}static GFINLINE u32 is_yuv_supported(u32 win_4cc){	if (win_4cc==get_win_4CC(GF_PIXEL_YV12)) return GF_PIXEL_YV12;	else if (win_4cc==get_win_4CC(GF_PIXEL_I420)) return GF_PIXEL_I420;	else if (win_4cc==get_win_4CC(GF_PIXEL_IYUV)) return GF_PIXEL_IYUV;	else if (win_4cc==get_win_4CC(GF_PIXEL_UYVY)) return GF_PIXEL_UYVY;	else if (win_4cc==get_win_4CC(GF_PIXEL_Y422)) return GF_PIXEL_Y422;	else if (win_4cc==get_win_4CC(GF_PIXEL_UYNV)) return GF_PIXEL_UYNV;	else if (win_4cc==get_win_4CC(GF_PIXEL_YUY2)) return GF_PIXEL_YUY2;	else if (win_4cc==get_win_4CC(GF_PIXEL_YUNV)) return GF_PIXEL_YUNV;	else if (win_4cc==get_win_4CC(GF_PIXEL_V422)) return GF_PIXEL_V422;	else if (win_4cc==get_win_4CC(GF_PIXEL_YVYU)) return GF_PIXEL_YVYU;	else return 0;}static GFINLINE Bool is_yuv_planar(u32 format){	switch  (format) {	case GF_PIXEL_YV12:	case GF_PIXEL_I420:	case GF_PIXEL_IYUV:		return 1;	default:		return 0;	}}#define YUV_NUM_TEST	20/*gets fastest YUV format for YUV to RGB blit from YUV overlay (support is quite random on most cards)*/void DD_InitYUV(GF_VideoOutput *dr){	u32 w, h, j, i, num_yuv;	DWORD numCodes;	DWORD formats[30];	DWORD *codes;	u32 now, min_packed = 0xFFFFFFFF, min_planar = 0xFFFFFFFF;	u32 best_packed = 0, best_planar = 0;	Bool checkPacked = TRUE;		DDCONTEXT;	w = 320;	h = 240;	dd->yuv_init = 1;#ifdef USE_DX_3	IDirectDraw_GetFourCCCodes(dd->pDD, &numCodes, NULL);	if (!numCodes) return;	codes = (DWORD *)malloc(numCodes*sizeof(DWORD));	IDirectDraw_GetFourCCCodes(dd->pDD, &numCodes, codes);#else	IDirectDraw7_GetFourCCCodes(dd->pDD, &numCodes, NULL);	if (!numCodes) return;	codes = (DWORD *)malloc(numCodes*sizeof(DWORD));	IDirectDraw7_GetFourCCCodes(dd->pDD, &numCodes, codes);#endif		num_yuv = 0;	for (i=0; i<numCodes; i++) {		formats[num_yuv] = is_yuv_supported(codes[i]);		if (formats[num_yuv]) num_yuv++;	}	free(codes);	/*too bad*/	if (!num_yuv) {		dr->hw_caps &= ~GF_VIDEO_HW_HAS_YUV;		dr->yuv_pixel_format = 0;		return;	}	for (i=0; i<num_yuv; i++) {		/*check planar first*/		if (!checkPacked && !is_yuv_planar(formats[i])) goto go_on;		/*then check packed */		if (checkPacked && is_yuv_planar(formats[i])) goto go_on;		if (dd->yuv_pool.pSurface) {			SAFE_DD_RELEASE(dd->yuv_pool.pSurface);			memset(&dd->yuv_pool, 0, sizeof(DDSurface));		}		dr->yuv_pixel_format = formats[i];		if (DD_GetSurface(dr, w, h, dr->yuv_pixel_format) == NULL)			goto rem_fmt;		now = gf_sys_clock();		/*perform blank blit*/		for (j=0; j<YUV_NUM_TEST; j++) {			if (DD_BlitSurface(dd, &dd->yuv_pool, NULL, NULL, NULL) != GF_OK)				goto rem_fmt;		}		now = gf_sys_clock() - now;		if (!checkPacked) {			if (now<min_planar) {				min_planar = now;				best_planar = dr->yuv_pixel_format;			}		} else {			if (now<min_packed) {				min_packed = now;				best_packed = dr->yuv_pixel_format;			}		}go_on:		if (checkPacked && (i+1==num_yuv)) {			i = -1;			checkPacked = FALSE;		}		continue;rem_fmt:		for (j=i; j<num_yuv-1; j++) {			formats[j] = formats[j+1];		}		i--;		num_yuv--;	}	if (dd->yuv_pool.pSurface) {		SAFE_DD_RELEASE(dd->yuv_pool.pSurface);		memset(&dd->yuv_pool, 0, sizeof(DDSurface));	}	/*too bad*/	if (!num_yuv) {		dr->hw_caps &= ~GF_VIDEO_HW_HAS_YUV;		dr->yuv_pixel_format = 0;		return;	}	if (best_planar && (min_planar < min_packed )) {		dr->yuv_pixel_format = best_planar;	} else {		dr->yuv_pixel_format = best_packed;	} 	dr->hw_caps |= GF_VIDEO_HW_HAS_YUV;}GF_Err DD_SetBackBufferSize(GF_VideoOutput *dr, u32 width, u32 height){	DDCONTEXT;	if (dd->is_3D_out) return GF_BAD_PARAM;	if (!dd->ddraw_init) return InitDirectDraw(dr, width, height);	return CreateBackBuffer(dr, width, height);}void DD_SetupDDraw(GF_VideoOutput *driv){	driv->hw_caps |= GF_VIDEO_HW_HAS_COLOR_KEY;	driv->Blit = DD_Blit;	driv->LockBackBuffer = DD_LockBackBuffer;	driv->LockOSContext = LockOSContext;}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -