示例#1
0
int directdraw_uninit(void)
{
	if(!video_window) return 0;

	if(!lpDDS) return 0;

	KillTimer(video_window, 131);

    if(lpDDS_secondary) IDirectDrawSurface2_Release(lpDDS_secondary);
	if(lpDDS)           IDirectDrawSurface2_Release(lpDDS);
	if(surface_osd)     IDirectDrawSurface2_Release(surface_osd);
	if(lpDD)            IDirectDraw2_RestoreDisplayMode(lpDD);
	if(lpDD)            IDirectDraw2_SetCooperativeLevel(lpDD, video_window, DDSCL_NORMAL);
	if(lpDD)            IDirectDraw2_Release(lpDD);
	if(video_window)    DestroyWindow(video_window);
	if(library)         FreeLibrary(library);
	
	library         = 0;
	lpDD            = 0;
	lpDDS           = 0;
	lpDDS_secondary = 0;
	surface_osd     = 0;

	video_window    = 0;
	return 1;
}
示例#2
0
/* wnd_set_video_mode:
 *  Called by window thread to set a gfx mode; this is needed because DirectDraw can only
 *  change the mode in the thread that handles the window.
 */
static int wnd_set_video_mode(void)
{
   HRESULT hr;
   HWND allegro_wnd = win_get_window();

   /* set the cooperative level to allow fullscreen access */
   hr = IDirectDraw2_SetCooperativeLevel(directdraw, allegro_wnd, DDSCL_EXCLUSIVE | DDSCL_FULLSCREEN);
   if (FAILED(hr)) {
      _TRACE(PREFIX_E "SetCooperativeLevel() failed (%x)\n", hr);
      return -1;
   }

   /* switch to fullscreen mode */
   hr = IDirectDraw2_SetDisplayMode(directdraw, _wnd_width, _wnd_height, _wnd_depth,
                                                _wnd_refresh_rate, _wnd_flags);
   if (FAILED(hr)) {
      _TRACE(PREFIX_E "SetDisplayMode(%u, %u, %u, %u, %u) failed (%x)\n", _wnd_width, _wnd_height, _wnd_depth,
                                                                 _wnd_refresh_rate, _wnd_flags, hr);
      return -1;
   }

   return 0;
}
示例#3
0
文件: ddinit.c 项目: antrik/libggi
static void
DDDestroySurface(directx_priv *priv)
{
	int i;
	if (priv->lpddp != NULL) {
		IDirectDrawPalette_Release(priv->lpddp);
		priv->lpddp = NULL;
	}
	for (i = 0; i < GGI_DISPLAY_DIRECTX_FRAMES; ++i) {
		if (priv->lpbdds[i] != NULL) {
			IDirectDrawSurface_Release(priv->lpbdds[i]);
			priv->lpbdds[i] = NULL;
		}
	}
	if (priv->lppdds != NULL) {
		IDirectDrawSurface_Release(priv->lppdds);
		priv->lppdds = NULL;
	}
	if (priv->fullscreen) {
		IDirectDraw2_RestoreDisplayMode(priv->lpddext);
		IDirectDraw2_SetCooperativeLevel(priv->lpddext, priv->hWnd,
						DDSCL_NORMAL);
	}
}
示例#4
0
文件: winshaddd.c 项目: L3oV1nc3/VMGL
static Bool
winAllocateFBShadowDD (ScreenPtr pScreen)
{
  winScreenPriv(pScreen);
  winScreenInfo		*pScreenInfo = pScreenPriv->pScreenInfo;  
  HRESULT		ddrval = DD_OK;
  DDSURFACEDESC		ddsd;
  DDSURFACEDESC		*pddsdShadow = NULL;

#if CYGDEBUG
  winDebug ("winAllocateFBShadowDD\n");
#endif

  /* Create a clipper */
  ddrval = (*g_fpDirectDrawCreateClipper) (0,
					   &pScreenPriv->pddcPrimary,
					   NULL);
  if (FAILED (ddrval))
    {
      ErrorF ("winAllocateFBShadowDD - Could not create clipper: %08x\n",
	      (unsigned int) ddrval);
      return FALSE;
    }

#if CYGDEBUG
  winDebug ("winAllocateFBShadowDD - Created a clipper\n");
#endif

  /* Get a device context for the screen  */
  pScreenPriv->hdcScreen = GetDC (pScreenPriv->hwndScreen);

  /* Attach the clipper to our display window */
  ddrval = IDirectDrawClipper_SetHWnd (pScreenPriv->pddcPrimary,
				       0,
				       pScreenPriv->hwndScreen);
  if (FAILED (ddrval))
    {
      ErrorF ("winAllocateFBShadowDD - Clipper not attached to "
	      "window: %08x\n",
	      (unsigned int) ddrval);
      return FALSE;
    }

#if CYGDEBUG
  winDebug ("winAllocateFBShadowDD - Attached clipper to window\n");
#endif

  /* Create a DirectDraw object, store the address at lpdd */
  ddrval = (*g_fpDirectDrawCreate) (NULL, &pScreenPriv->pdd, NULL);
  if (FAILED (ddrval))
    {
      ErrorF ("winAllocateFBShadowDD - Could not start DirectDraw: %08x\n",
	      (unsigned int) ddrval);
      return FALSE;
    }

#if CYGDEBUG
  winDebug ("winAllocateFBShadowDD () - Created and initialized DD\n");
#endif

  /* Get a DirectDraw2 interface pointer */
  ddrval = IDirectDraw_QueryInterface (pScreenPriv->pdd,
				       &IID_IDirectDraw2,
				       (LPVOID*) &pScreenPriv->pdd2);
  if (FAILED (ddrval))
    {
      ErrorF ("winAllocateFBShadowDD - Failed DD2 query: %08x\n",
	      (unsigned int) ddrval);
      return FALSE;
    }

  /* Are we full screen? */
  if (pScreenInfo->fFullScreen)
    {
      DDSURFACEDESC	ddsdCurrent;
      DWORD		dwRefreshRateCurrent = 0;
      HDC		hdc = NULL;

      /* Set the cooperative level to full screen */
      ddrval = IDirectDraw2_SetCooperativeLevel (pScreenPriv->pdd2,
						 pScreenPriv->hwndScreen,
						 DDSCL_EXCLUSIVE
						 | DDSCL_FULLSCREEN);
      if (FAILED (ddrval))
	{
	  ErrorF ("winAllocateFBShadowDD - Could not set "
		  "cooperative level: %08x\n",
		  (unsigned int) ddrval);
	  return FALSE;
	}

      /*
       * We only need to get the current refresh rate for comparison
       * if a refresh rate has been passed on the command line.
       */
      if (pScreenInfo->dwRefreshRate != 0)
	{
	  ZeroMemory (&ddsdCurrent, sizeof (ddsdCurrent));
	  ddsdCurrent.dwSize = sizeof (ddsdCurrent);
	  
	  /* Get information about current display settings */
	  ddrval = IDirectDraw2_GetDisplayMode (pScreenPriv->pdd2,
						&ddsdCurrent);
	  if (FAILED (ddrval))
	    {
	      ErrorF ("winAllocateFBShadowDD - Could not get current "
		      "refresh rate: %08x.  Continuing.\n",
		      (unsigned int) ddrval);
	      dwRefreshRateCurrent = 0;
	    }
	  else
	    {
	      /* Grab the current refresh rate */
	      dwRefreshRateCurrent = ddsdCurrent.u2.dwRefreshRate;
	    }
	}

      /* Clean up the refresh rate */
      if (dwRefreshRateCurrent == pScreenInfo->dwRefreshRate)
	{
	  /*
	   * Refresh rate is non-specified or equal to current.
	   */
	  pScreenInfo->dwRefreshRate = 0;
	}

      /* Grab a device context for the screen */
      hdc = GetDC (NULL);
      if (hdc == NULL)
	{
	  ErrorF ("winAllocateFBShadowDD - GetDC () failed\n");
	  return FALSE;
	}

      /* Only change the video mode when different than current mode */
      if (!pScreenInfo->fMultipleMonitors
	  && (pScreenInfo->dwWidth != GetSystemMetrics (SM_CXSCREEN)
	      || pScreenInfo->dwHeight != GetSystemMetrics (SM_CYSCREEN)
	      || pScreenInfo->dwBPP != GetDeviceCaps (hdc, BITSPIXEL)
	      || pScreenInfo->dwRefreshRate != 0))
	{
	  ErrorF ("winAllocateFBShadowDD - Changing video mode\n");

	  /* Change the video mode to the mode requested, and use the driver default refresh rate on failure */
	  ddrval = IDirectDraw2_SetDisplayMode (pScreenPriv->pdd2,
						pScreenInfo->dwWidth,
						pScreenInfo->dwHeight,
						pScreenInfo->dwBPP,
						pScreenInfo->dwRefreshRate,
						0);
	  if (FAILED (ddrval))
	    {
	      ErrorF ("winAllocateFBShadowDD - Could not set "\
		      "full screen display mode: %08x\n",
		      (unsigned int) ddrval);
	      ErrorF ("winAllocateFBShadowDD - Using default driver refresh rate\n");
	      ddrval = IDirectDraw2_SetDisplayMode (pScreenPriv->pdd2,
						    pScreenInfo->dwWidth,
						    pScreenInfo->dwHeight,
						    pScreenInfo->dwBPP,
						    0,
						    0);
	      if (FAILED(ddrval))
		{
			ErrorF ("winAllocateFBShadowDD - Could not set default refresh rate "
				"full screen display mode: %08x\n",
				(unsigned int) ddrval);
			return FALSE;
		}
	    }
	}
      else
	{
	  ErrorF ("winAllocateFBShadowDD - Not changing video mode\n");
	}

      /* Release our DC */
      ReleaseDC (NULL, hdc);
      hdc = NULL;
    }
  else
    {
      /* Set the cooperative level for windowed mode */
      ddrval = IDirectDraw2_SetCooperativeLevel (pScreenPriv->pdd2,
						 pScreenPriv->hwndScreen,
						 DDSCL_NORMAL);
      if (FAILED (ddrval))
	{
	  ErrorF ("winAllocateFBShadowDD - Could not set "\
		  "cooperative level: %08x\n",
		  (unsigned int) ddrval);
	  return FALSE;
	}
    }

  /* Create the primary surface */
  if (!winCreatePrimarySurfaceShadowDD (pScreen))
    {
      ErrorF ("winAllocateFBShadowDD - winCreatePrimarySurfaceShadowDD "
	      "failed\n");
      return FALSE;
    }

  /* Describe the shadow surface to be created */
  /* NOTE: Do not use a DDSCAPS_VIDEOMEMORY surface,
   * as drawing, locking, and unlocking take forever
   * with video memory surfaces.  In addition,
   * video memory is a somewhat scarce resource,
   * so you shouldn't be allocating video memory when
   * you have the option of using system memory instead.
   */
  ZeroMemory (&ddsd, sizeof (ddsd));
  ddsd.dwSize = sizeof (ddsd);
  ddsd.dwFlags = DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH;
  ddsd.ddsCaps.dwCaps = DDSCAPS_OFFSCREENPLAIN | DDSCAPS_SYSTEMMEMORY;
  ddsd.dwHeight = pScreenInfo->dwHeight;
  ddsd.dwWidth = pScreenInfo->dwWidth;

  /* Create the shadow surface */
  ddrval = IDirectDraw2_CreateSurface (pScreenPriv->pdd2,
				       &ddsd,
				       &pScreenPriv->pddsShadow,
				       NULL);
  if (FAILED (ddrval))
    {
      ErrorF ("winAllocateFBShadowDD - Could not create shadow "\
	      "surface: %08x\n", (unsigned int) ddrval);
      return FALSE;
    }
  
#if CYGDEBUG
  winDebug ("winAllocateFBShadowDD - Created shadow\n");
#endif

  /* Allocate a DD surface description for our screen privates */
  pddsdShadow = pScreenPriv->pddsdShadow = malloc (sizeof (DDSURFACEDESC));
  if (pddsdShadow == NULL)
    {
      ErrorF ("winAllocateFBShadowDD - Could not allocate surface "\
	      "description memory\n");
      return FALSE;
    }
  ZeroMemory (pddsdShadow, sizeof (*pddsdShadow));
  pddsdShadow->dwSize = sizeof (*pddsdShadow);

#if CYGDEBUG
  winDebug ("winAllocateFBShadowDD - Locking shadow\n");
#endif

  /* Lock the shadow surface */
  ddrval = IDirectDrawSurface2_Lock (pScreenPriv->pddsShadow,
				     NULL,
				     pddsdShadow,
				     DDLOCK_WAIT,
				     NULL);
  if (FAILED (ddrval) || pddsdShadow->lpSurface == NULL)
    {
      ErrorF ("winAllocateFBShadowDD - Could not lock shadow "\
	      "surface: %08x\n", (unsigned int) ddrval);
      return FALSE;
    }

#if CYGDEBUG
  winDebug ("winAllocateFBShadowDD - Locked shadow\n");
#endif

  /* We don't know how to deal with anything other than RGB */
  if (!(pddsdShadow->ddpfPixelFormat.dwFlags & DDPF_RGB))
    {
      ErrorF ("winAllocateFBShadowDD - Color format other than RGB\n");
      return FALSE;
    }

  /* Grab the pitch from the surface desc */
  pScreenInfo->dwStride = (pddsdShadow->u1.lPitch * 8)
    / pScreenInfo->dwBPP;

  /* Save the pointer to our surface memory */
  pScreenInfo->pfb = pddsdShadow->lpSurface;
  
  /* Grab the color depth and masks from the surface description */
  pScreenPriv->dwRedMask = pddsdShadow->ddpfPixelFormat.u2.dwRBitMask;
  pScreenPriv->dwGreenMask = pddsdShadow->ddpfPixelFormat.u3.dwGBitMask;
  pScreenPriv->dwBlueMask = pddsdShadow->ddpfPixelFormat.u4.dwBBitMask;

#if CYGDEBUG
  winDebug ("winAllocateFBShadowDD - Returning\n");
#endif

  return TRUE;
}
示例#5
0
static int DirectXOpenDDraw(vout_display_t *vd)
{
    vout_display_sys_t *sys = vd->sys;
    HRESULT hr;

    /* */
    HRESULT (WINAPI *OurDirectDrawCreate)(GUID *,LPDIRECTDRAW *,IUnknown *);
    OurDirectDrawCreate =
        (void *)GetProcAddress(sys->hddraw_dll, _T("DirectDrawCreate"));
    if (!OurDirectDrawCreate) {
        msg_Err(vd, "DirectXInitDDraw failed GetProcAddress");
        return VLC_EGENERIC;
    }

    /* */
    HRESULT (WINAPI *OurDirectDrawEnumerateEx)(LPDDENUMCALLBACKEXA, LPVOID, DWORD);
    OurDirectDrawEnumerateEx =
        (void *)GetProcAddress(sys->hddraw_dll, _T("DirectDrawEnumerateExA"));

    if (OurDirectDrawEnumerateEx) {
        char *device = var_GetString(vd, "directx-device");
        if (device) {
            msg_Dbg(vd, "directx-device: %s", device);
            free(device);
        }

        sys->hmonitor = MonitorFromWindow(sys->hwnd, MONITOR_DEFAULTTONEAREST);

        /* Enumerate displays */
        OurDirectDrawEnumerateEx(DirectXOpenDDrawCallback,
                                 vd, DDENUM_ATTACHEDSECONDARYDEVICES);
    }

    /* Initialize DirectDraw now */
    LPDIRECTDRAW ddobject;
    hr = OurDirectDrawCreate(sys->display_driver, &ddobject, NULL);
    if (hr != DD_OK) {
        msg_Err(vd, "DirectXInitDDraw cannot initialize DDraw");
        return VLC_EGENERIC;
    }

    /* Get the IDirectDraw2 interface */
    hr = IDirectDraw_QueryInterface(ddobject, &IID_IDirectDraw2,
                                    &sys->ddobject);
    /* Release the unused interface */
    IDirectDraw_Release(ddobject);

    if (hr != DD_OK) {
        msg_Err(vd, "cannot get IDirectDraw2 interface");
        sys->ddobject = NULL;
        return VLC_EGENERIC;
    }

    /* Set DirectDraw Cooperative level, ie what control we want over Windows
     * display */
    hr = IDirectDraw2_SetCooperativeLevel(sys->ddobject, NULL, DDSCL_NORMAL);
    if (hr != DD_OK) {
        msg_Err(vd, "cannot set direct draw cooperative level");
        return VLC_EGENERIC;
    }

    /* Get the size of the current display device */
    if (sys->hmonitor) {
        MONITORINFO monitor_info;
        monitor_info.cbSize = sizeof(MONITORINFO);
        GetMonitorInfoA(vd->sys->hmonitor, &monitor_info);
        sys->rect_display = monitor_info.rcMonitor;
    } else {
        sys->rect_display.left   = 0;
        sys->rect_display.top    = 0;
        sys->rect_display.right  = GetSystemMetrics(SM_CXSCREEN);
        sys->rect_display.bottom = GetSystemMetrics(SM_CYSCREEN);
    }

    msg_Dbg(vd, "screen dimensions (%lix%li,%lix%li)",
            sys->rect_display.left,
            sys->rect_display.top,
            sys->rect_display.right,
            sys->rect_display.bottom);

    /* Probe the capabilities of the hardware */
    DirectXGetDDrawCaps(vd);

    return VLC_SUCCESS;
}
示例#6
0
//
// - returns true if DirectDraw was initialized properly
//
int  InitDirectDrawe (HWND appWin, int width, int height, int bpp, int fullScr)
{
	DDSURFACEDESC ddsd; // DirectDraw surface description for allocating
	DDSCAPS       ddscaps;
	HRESULT       ddrval;

	DWORD         dwStyle;
	RECT          rect;

	// enumerate directdraw devices
	//if (FAILED(DirectDrawEnumerate (myEnumDDDevicesCallback, NULL)))
	//      I_Error("Error with DirectDrawEnumerate");

	if (!DDr2)
		CreateDirectDrawInstance();

	// remember what screen mode we are in
	bAppFullScreen = fullScr;
	ScreenHeight = height;
	ScreenWidth = width;

	if (bAppFullScreen)
	{
		// Change window attributes
		dwStyle = WS_POPUP | WS_VISIBLE;
		SetWindowLong (appWin, GWL_STYLE, dwStyle);
		SetWindowPos(appWin, HWND_TOPMOST, 0, 0, 0, 0, SWP_NOACTIVATE |
			SWP_NOMOVE | SWP_NOSIZE | SWP_NOZORDER);

		// Get exclusive mode
		ddrval = IDirectDraw2_SetCooperativeLevel(DDr2, appWin, DDSCL_EXCLUSIVE |
		                                          DDSCL_FULLSCREEN |
		                                          DDSCL_ALLOWREBOOT);
		if (ddrval != DD_OK)
			I_Error("SetCooperativeLevel FAILED: %s\n", DXErrorToString(ddrval));

		// Switch from windows desktop to fullscreen

#ifdef NT4COMPAT
		ddrval = IDirectDraw2_SetDisplayMode(DDr2, width, height, bpp, 0, 0);
#else
		ddrval = IDirectDraw2_SetDisplayMode(DDr2, width, height, bpp, 0, DDSDM_STANDARDVGAMODE);
#endif
		if (ddrval != DD_OK)
			I_Error("SetDisplayMode FAILED: %s\n", DXErrorToString(ddrval));

		// This is not really needed, except in certain cases. One case
		// is while using MFC. When the desktop is initally at 16bpp, a mode
		// switch to 8bpp somehow causes the MFC window to not fully initialize
		// and a CreateSurface will fail with DDERR_NOEXCLUSIVEMODE. This will
		// ensure that the window is initialized properly after a mode switch.

		ShowWindow(appWin, SW_SHOW);

		// Create the primary surface with 1 back buffer. Always zero the
		// DDSURFACEDESC structure and set the dwSize member!

		ZeroMemory(&ddsd, sizeof (ddsd));
		ddsd.dwSize = sizeof (ddsd);
		ddsd.dwFlags = DDSD_CAPS | DDSD_BACKBUFFERCOUNT;
		ddsd.ddsCaps.dwCaps = DDSCAPS_PRIMARYSURFACE | DDSCAPS_FLIP | DDSCAPS_COMPLEX;

		// for fullscreen we use page flipping, for windowed mode, we blit the hidden surface to
		// the visible surface, in both cases we have a visible (or 'real') surface, and a hidden
		// (or 'virtual', or 'backbuffer') surface.
		ddsd.dwBackBufferCount = 2;

		ddrval = IDirectDraw2_CreateSurface(DDr2,&ddsd, &ScreenReal, NULL);
		if (ddrval != DD_OK)
			I_Error("CreateSurface Primary Screen FAILED");

		// Get a pointer to the back buffer

		ddscaps.dwCaps = DDSCAPS_BACKBUFFER;
		ddrval = IDirectDrawSurface_GetAttachedSurface(ScreenReal,&ddscaps, &ScreenVirtual);
		if (ddrval != DD_OK)
			I_Error("GetAttachedSurface FAILED");
	}
	else
	{
		rect.top = 0;
		rect.left = 0;
		rect.bottom = height;
		rect.right = width;

		// Change window attributes

		dwStyle = GetWindowStyle(appWin);
		dwStyle &= ~WS_POPUP;
		dwStyle |= WS_OVERLAPPED | WS_SYSMENU | WS_CAPTION;

		SetWindowLong(appWin, GWL_STYLE, dwStyle);

		// Resize the window so that the client area is the requested width/height

		AdjustWindowRectEx(&rect, GetWindowStyle(appWin), GetMenu(appWin) != NULL,
		                   GetWindowExStyle(appWin));

		// Just in case the window was moved off the visible area of the
		// screen.

		SetWindowPos(appWin, NULL, 0, 0, rect.right-rect.left,
		             rect.bottom-rect.top, SWP_NOMOVE | SWP_NOZORDER |
		             SWP_NOACTIVATE);

		SetWindowPos(appWin, HWND_NOTOPMOST, 0, 0, 0, 0,
		             SWP_NOSIZE | SWP_NOMOVE | SWP_NOACTIVATE);

		// Exclusive mode is normal since it's in windowed mode and needs
		// to cooperate with GDI

		ddrval = IDirectDraw2_SetCooperativeLevel(DDr2,appWin, DDSCL_NORMAL);
		if (ddrval != DD_OK)
			I_Error("SetCooperativeLevel FAILED");

		// Always zero the DDSURFACEDESC structure and set the dwSize member!

		ZeroMemory(&ddsd, sizeof (ddsd));
		ddsd.dwSize = sizeof (ddsd);
		ddsd.dwFlags = DDSD_CAPS;
		ddsd.ddsCaps.dwCaps = DDSCAPS_PRIMARYSURFACE;

		// Create the primary surface

		ddrval = IDirectDraw2_CreateSurface(DDr2,&ddsd, &ScreenReal, NULL);
		if (ddrval != DD_OK)
			I_Error("CreateSurface Primary Screen FAILED");

		// Create a back buffer for offscreen rendering, this will be used to
		// blt to the primary

		ScreenVirtual = CreateNewSurface(width, height, DDSCAPS_OFFSCREENPLAIN |
		                                 DDSCAPS_SYSTEMMEMORY);
		if (ScreenVirtual == NULL)
			I_Error("CreateSurface Secondary Screen FAILED");

		/// \todo get the desktop bit depth, and build a lookup table
		/// for quick conversions of 8bit color indexes 0-255 to desktop colors
		/// eg: 256 entries of equivalent of palette colors 0-255 in 15,16,24,32 bit format
		/// when blit virtual to real, convert pixels through lookup table..

		// Use a clipper object for clipping when in windowed mode
		// (make sure our drawing doesn't affect other windows)

		ddrval = IDirectDraw2_CreateClipper (DDr2, 0, &windclip, 0);
		if (ddrval != DD_OK)
			I_Error("CreateClipper FAILED");

		// Associate the clipper with the window.
		ddrval = IDirectDrawClipper_SetHWnd (windclip,0, appWin);
		if (ddrval != DD_OK)
			I_Error("Clipper -> SetHWnd  FAILED");

		// Attach the clipper to the surface.
		ddrval = IDirectDrawSurface_SetClipper (ScreenReal,windclip);
		if (ddrval != DD_OK)
			I_Error("PrimaryScreen -> SetClipperClipper  FAILED");
	}

	return TRUE;
}
示例#7
0
Bool
winAllocateFBPrimaryDD (ScreenPtr pScreen)
{
  winScreenPriv(pScreen);
  winScreenInfo		*pScreenInfo = pScreenPriv->pScreenInfo;  
  HRESULT		ddrval = DD_OK;
  DDSURFACEDESC		ddsd;
  DDSURFACEDESC		*pddsdPrimary = NULL;
  DDSURFACEDESC		*pddsdOffscreen = NULL;
  RECT			rcClient;

  ErrorF ("winAllocateFBPrimaryDD\n");

  /* Get client area location in screen coords */
  GetClientRect (pScreenPriv->hwndScreen, &rcClient);
  MapWindowPoints (pScreenPriv->hwndScreen,
		   HWND_DESKTOP,
		   (LPPOINT)&rcClient, 2);

  /* Create a DirectDraw object, store the address at lpdd */
  ddrval = (*g_fpDirectDrawCreate) (NULL, &pScreenPriv->pdd, NULL);
  if (ddrval != DD_OK)
    FatalError ("winAllocateFBPrimaryDD - Could not start DirectDraw\n");
  
  /* Get a DirectDraw2 interface pointer */
  ddrval = IDirectDraw_QueryInterface (pScreenPriv->pdd,
				       &IID_IDirectDraw2,
				       (LPVOID*) &pScreenPriv->pdd2);
  if (FAILED (ddrval))
    {
      ErrorF ("winAllocateFBShadowDD - Failed DD2 query: %08x\n",
	      ddrval);
      return FALSE;
    }


  ErrorF ("winAllocateFBPrimaryDD - Created and initialized DD\n");

  /* Are we windowed or fullscreen? */
  if (pScreenInfo->fFullScreen)
    {
      /* Full screen mode */
      ddrval = IDirectDraw2_SetCooperativeLevel (pScreenPriv->pdd2,
						 pScreenPriv->hwndScreen,
						 DDSCL_FULLSCREEN
						 | DDSCL_EXCLUSIVE);
      if (FAILED (ddrval))
	FatalError ("winAllocateFBPrimaryDD - Could not set "
		    "cooperative level\n");

      /* Change the video mode to the mode requested */
      ddrval = IDirectDraw2_SetDisplayMode (pScreenPriv->pdd2,
					    pScreenInfo->dwWidth,
					    pScreenInfo->dwHeight,
					    pScreenInfo->dwBPP,
					    pScreenInfo->dwRefreshRate,
					    0);
       if (FAILED (ddrval))
	FatalError ("winAllocateFBPrimaryDD - Could not set "
		    "full screen display mode\n");
    }
  else
    {
      /* Windowed mode */
      ddrval = IDirectDraw2_SetCooperativeLevel (pScreenPriv->pdd2,
						 pScreenPriv->hwndScreen,
						 DDSCL_NORMAL);
      if (FAILED (ddrval))
	FatalError ("winAllocateFBPrimaryDD - Could not set "
		    "cooperative level\n");
    }

  /* Describe the primary surface */
  ZeroMemory (&ddsd, sizeof (ddsd));
  ddsd.dwSize = sizeof (ddsd);
  ddsd.dwFlags = DDSD_CAPS;
  ddsd.ddsCaps.dwCaps = DDSCAPS_PRIMARYSURFACE;
  
  /* Create the primary surface */
  ddrval = IDirectDraw2_CreateSurface (pScreenPriv->pdd2,
				       &ddsd,
				       &pScreenPriv->pddsPrimary,
				       NULL);
  if (FAILED (ddrval))
       FatalError ("winAllocateFBPrimaryDD - Could not create primary "
		  "surface %08x\n", ddrval);

  ErrorF ("winAllocateFBPrimaryDD - Created primary\n");

  /* Allocate a DD surface description for our screen privates */
  pddsdPrimary = pScreenPriv->pddsdPrimary
    = malloc (sizeof (DDSURFACEDESC));
  if (pddsdPrimary == NULL)
    FatalError ("winAllocateFBPrimaryDD - Could not allocate surface "
		"description memory\n");
  ZeroMemory (pddsdPrimary, sizeof (*pddsdPrimary));
  pddsdPrimary->dwSize = sizeof (*pddsdPrimary);

  /* Describe the offscreen surface to be created */
  /*
   * NOTE: Do not use a DDSCAPS_VIDEOMEMORY surface,
   * as drawing, locking, and unlocking take forever
   * with video memory surfaces.  In addition,
   * video memory is a somewhat scarce resource,
   * so you shouldn't be allocating video memory when
   * you have the option of using system memory instead.
   */
  ZeroMemory (&ddsd, sizeof (ddsd));
  ddsd.dwSize = sizeof (ddsd);
  ddsd.dwFlags = DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH;
  ddsd.ddsCaps.dwCaps = DDSCAPS_OFFSCREENPLAIN | DDSCAPS_SYSTEMMEMORY;
  ddsd.dwHeight = pScreenInfo->dwHeight;
  ddsd.dwWidth = pScreenInfo->dwWidth;

  /* Create the shadow surface */
  ddrval = IDirectDraw2_CreateSurface (pScreenPriv->pdd2,
				       &ddsd,
				       &pScreenPriv->pddsOffscreen,
				       NULL);
  if (ddrval != DD_OK)
    FatalError ("winAllocateFBPrimaryDD - Could not create shadow "
		"surface\n");
  
  ErrorF ("winAllocateFBPrimaryDD - Created offscreen\n");

  /* Allocate a DD surface description for our screen privates */
  pddsdOffscreen = pScreenPriv->pddsdOffscreen
    = malloc (sizeof (DDSURFACEDESC));
  if (pddsdOffscreen == NULL)
    FatalError ("winAllocateFBPrimaryDD - Could not allocate surface "
		"description memory\n");
  ZeroMemory (pddsdOffscreen, sizeof (*pddsdOffscreen));
  pddsdOffscreen->dwSize = sizeof (*pddsdOffscreen);

  ErrorF ("winAllocateFBPrimaryDD - Locking primary\n");

  /* Lock the primary surface */
  ddrval = IDirectDrawSurface2_Lock (pScreenPriv->pddsPrimary,
				    pScreenInfo->fFullScreen ? NULL:&rcClient,
				    pddsdPrimary,
				    DDLOCK_WAIT,
				    NULL);
  if (ddrval != DD_OK || pddsdPrimary->lpSurface == NULL)
    FatalError ("winAllocateFBPrimaryDD - Could not lock "
		"primary surface\n");

  ErrorF ("winAllocateFBPrimaryDD - Locked primary\n");

  /* We don't know how to deal with anything other than RGB */
  if (!(pddsdPrimary->ddpfPixelFormat.dwFlags & DDPF_RGB))
    FatalError ("winAllocateFBPrimaryDD - Color format other than RGB\n");

  /* Grab the pitch from the surface desc */
  pScreenInfo->dwStride = (pddsdPrimary->u1.lPitch * 8)
    / pScreenInfo->dwBPP;

  /* Save the pointer to our surface memory */
  pScreenInfo->pfb = pddsdPrimary->lpSurface;
  
  /* Grab the color depth and masks from the surface description */
  pScreenPriv->dwRedMask = pddsdPrimary->ddpfPixelFormat.u2.dwRBitMask;
  pScreenPriv->dwGreenMask = pddsdPrimary->ddpfPixelFormat.u3.dwGBitMask;
  pScreenPriv->dwBlueMask = pddsdPrimary->ddpfPixelFormat.u4.dwBBitMask;

  ErrorF ("winAllocateFBPrimaryDD - Returning\n");

  return TRUE;
}
示例#8
0
int directdraw_init(HWND hwndp)
{
    int                 width = 320, height = 200;
    RECT                rect;
    DDPIXELFORMAT       format;
    DDSURFACEDESC       descriptor;
    DIRECTDRAWCREATE    DirectDrawCreate;

	if(lpDDS) return 0;
	if(!hwndp) return 0;
	if(video_window) return 0; /* you gotta uninitialize it first */

    library = (HMODULE) LoadLibrary(uni("ddraw.dll"));
    if(!library) return 0;

    DirectDrawCreate = (DIRECTDRAWCREATE) GetProcAddress(library, "DirectDrawCreate");
    if(!DirectDrawCreate) return 0;

    if(FAILED(DirectDrawCreate(0,&lpDD,0))) return 0;

    wc.style         = CS_VREDRAW | CS_HREDRAW | CS_DBLCLKS;
    wc.lpfnWndProc   = WndProc;
    wc.cbClsExtra    = 0;
    wc.cbWndExtra    = 0;
    wc.hInstance     = 0;
    wc.hIcon         = 0;
    wc.hCursor       = LoadCursor(0, IDC_ARROW);
    wc.hbrBackground = 0;
    wc.lpszMenuName  = 0;
    wc.lpszClassName = window_class_name;

    RegisterClass(&wc);

    video_window = CreateWindow(window_class_name, uni("Video"), WS_CHILD, 0, 0, width, height, hwndp, 0, 0, 0);

    ShowWindow(video_window, SW_NORMAL);

    if(FAILED(IDirectDraw2_SetCooperativeLevel(lpDD, video_window, DDSCL_NORMAL))) return 0;


    descriptor.dwSize         = sizeof(descriptor);
    descriptor.dwFlags        = DDSD_CAPS;
    descriptor.ddsCaps.dwCaps = DDSCAPS_PRIMARYSURFACE | DDSCAPS_VIDEOMEMORY;

    if(FAILED(IDirectDraw2_CreateSurface(lpDD, &descriptor, &lpDDS, 0))) return 0;

    descriptor.dwFlags        = DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH;
	descriptor.ddsCaps.dwCaps = DDSCAPS_OFFSCREENPLAIN;
    descriptor.dwWidth        = d_width ;
    descriptor.dwHeight       = d_height;

    if(FAILED(IDirectDraw2_CreateSurface(lpDD, &descriptor, &lpDDS_secondary, 0))) return 0;
    
    if(FAILED(IDirectDraw2_CreateClipper(lpDD, 0, &lpDDC, 0))) return 0;

    if(FAILED(IDirectDrawClipper_SetHWnd(lpDDC, 0, video_window))) return 0;

    if(FAILED(IDirectDrawSurface2_SetClipper(lpDDS, lpDDC))) return 0;
    
    lpDDS_back    = lpDDS_secondary;
    format.dwSize = sizeof(format);

    if(FAILED(IDirectDrawSurface2_GetPixelFormat(lpDDS, &format))) return 0;

    if(!(format.dwFlags & DDPF_RGB)) return 0;


	IDirectDraw2_EnumDisplayModes(lpDD, DDEDM_STANDARDVGAMODES, 0, 0, EnumDisplayModesCallback);


	osd_initialize();
	osd_created = 0;

    return 1;
}
示例#9
0
文件: ddinit.c 项目: antrik/libggi
static int
DDCreateSurface(directx_priv *priv, ggi_mode *mode)
{
	HRESULT hr;
	LPDIRECTDRAWCLIPPER pClipper;
	DDSURFACEDESC pddsd, bddsd;
	int i;

	if (!priv->fullscreen)
		IDirectDraw2_SetCooperativeLevel(priv->lpddext, priv->hWnd,
						DDSCL_NORMAL);
	else {
		/* Only the thread that has excluse access (Cooperative level)
		 * may restore the surfaces when they are lost. Therefore
		 * let the helper thread get exclusive access so that it can
		 * later do restores.
		 */
		directx_fullscreen dxfull;
		dxfull.priv = priv;
		dxfull.mode = mode;
		dxfull.event = CreateEvent(NULL, FALSE, FALSE, NULL);
		PostThreadMessage(priv->nThreadID,
			WM_DDFULLSCREEN, 0, (long)&dxfull);
		WaitForSingleObject(dxfull.event, INFINITE);
		CloseHandle(dxfull.event);
	}

	/* create the primary surface */
	memset(&pddsd, 0, sizeof(pddsd));
	pddsd.dwSize = sizeof(pddsd);
	pddsd.dwFlags = DDSD_CAPS;
	pddsd.ddsCaps.dwCaps = DDSCAPS_PRIMARYSURFACE;
	if (priv->fullscreen)
		pddsd.ddsCaps.dwCaps |= DDSCAPS_VIDEOMEMORY;
	hr = IDirectDraw2_CreateSurface(priv->lpddext, &pddsd,
				       &priv->lppdds, NULL);
	if (hr != 0) {
		fprintf(stderr,
			"Init Primary Surface Failed RC = %lx. Exiting\n",
			hr);
		exit(-1);
	}
	IDirectDraw2_CreateClipper(priv->lpddext, 0, &pClipper, NULL);
	IDirectDrawClipper_SetHWnd(pClipper, 0, priv->hWnd);
	IDirectDrawSurface_SetClipper(priv->lppdds, pClipper);
	IDirectDrawClipper_Release(pClipper);
	pddsd.dwSize = sizeof(pddsd);
	IDirectDrawSurface_GetSurfaceDesc(priv->lppdds, &pddsd);

	DPRINT_MISC("DDraw pixel format:\n");
	DPRINT_MISC("  Size %u\n", pddsd.ddpfPixelFormat.dwSize);
	DPRINT_MISC("  Flags %08x\n", pddsd.ddpfPixelFormat.dwFlags);
	DPRINT_MISC("  FourCC %08x\n", pddsd.ddpfPixelFormat.dwFourCC);
	DPRINT_MISC("  Count %u\n", pddsd.ddpfPixelFormat.dwRGBBitCount);
	DPRINT_MISC("  R-Mask(etc) %08x\n", pddsd.ddpfPixelFormat.dwRBitMask);
	DPRINT_MISC("  G-Mask(etc) %08x\n", pddsd.ddpfPixelFormat.dwGBitMask);
	DPRINT_MISC("  B-Mask(etc) %08x\n", pddsd.ddpfPixelFormat.dwBBitMask);
	DPRINT_MISC("  Z-Mask(etc) %08x\n",
		pddsd.ddpfPixelFormat.dwRGBZBitMask);

	/* create the back storages */
	for (i = 0; i < mode->frames; ++i) {
		memset(&bddsd, 0, sizeof(bddsd));
		bddsd.dwSize = sizeof(bddsd);
		bddsd.dwFlags =
		    DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH | DDSD_PIXELFORMAT;
		bddsd.ddsCaps.dwCaps =
		    DDSCAPS_OFFSCREENPLAIN | DDSCAPS_SYSTEMMEMORY;
		bddsd.dwWidth = mode->virt.x;
		bddsd.dwHeight = mode->virt.y;

		/* set up the pixel format */
		ZeroMemory(&bddsd.ddpfPixelFormat, sizeof(DDPIXELFORMAT));
		bddsd.ddpfPixelFormat.dwSize = sizeof(DDPIXELFORMAT);
		bddsd.ddpfPixelFormat.dwFlags =
		    pddsd.ddpfPixelFormat.dwFlags;
		bddsd.ddpfPixelFormat.dwFourCC =
		    pddsd.ddpfPixelFormat.dwFourCC;
		bddsd.ddpfPixelFormat.dwRGBBitCount =
		    pddsd.ddpfPixelFormat.dwRGBBitCount;
		bddsd.ddpfPixelFormat.dwRBitMask =
		    pddsd.ddpfPixelFormat.dwRBitMask;
		bddsd.ddpfPixelFormat.dwGBitMask =
		    pddsd.ddpfPixelFormat.dwGBitMask;
		bddsd.ddpfPixelFormat.dwBBitMask =
		    pddsd.ddpfPixelFormat.dwBBitMask;
		bddsd.ddpfPixelFormat.dwRGBAlphaBitMask =
		    pddsd.ddpfPixelFormat.dwRGBAlphaBitMask;

		hr = IDirectDraw2_CreateSurface(priv->lpddext,
					       &bddsd, &priv->lpbdds[i],
					       NULL);
		if (hr) {
			fprintf(stderr,
				"Init Backup Failed RC = %lx. Exiting\n", hr);
			exit(-1);
		}
		IDirectDrawSurface2_Lock(priv->lpbdds[i], NULL, &bddsd,
					 DDLOCK_SURFACEMEMORYPTR, NULL);
		priv->lpSurfaceAdd[i] = (char *) bddsd.lpSurface;
		IDirectDrawSurface2_Unlock(priv->lpbdds[i],
					   bddsd.lpSurface);
	}

	/* set private mode parameters */
	priv->maxX = mode->virt.x;
	priv->maxY = mode->virt.y;
	priv->ColorDepth = pddsd.ddpfPixelFormat.dwRGBBitCount;
	priv->pitch = bddsd.lPitch;

	if (pddsd.ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED8) {
		static PALETTEENTRY pal[256];
		/* todo fill in pal */
		hr = IDirectDraw_CreatePalette(priv->lpddext,
			DDPCAPS_8BIT|DDPCAPS_ALLOW256,
			pal, &priv->lpddp, NULL);
		if (hr) {
			fprintf(stderr,
				"Init Palette failed RC = %lx. Exiting\n",
				hr);
			exit(-1);
		}
		hr = IDirectDrawSurface_SetPalette(priv->lppdds, priv->lpddp);
		if (hr) {
			fprintf(stderr,
				 "Install Palette failed RC = %lx. Exiting\n",
				hr);
			exit(-1);
		}
	}

	return 1;
}
示例#10
0
文件: ddinit.c 项目: antrik/libggi
static unsigned __stdcall
DDEventLoop(void *lpParm)
{
	MSG msg;
	struct ggi_visual *vis = (struct ggi_visual *) lpParm;
	directx_priv *priv = GGIDIRECTX_PRIV(vis);

	priv->nThreadID = GetCurrentThreadId();

	/* create the window */
	if (!DDCreateWindow(vis)) {
		SetEvent(priv->hInit);
		return 0;
	}

	SetEvent(priv->hInit);

	while (GetMessage(&msg, NULL, 0, 0)) {
		if (msg.hwnd == NULL && msg.message == WM_DDEND) {
			/* Use PostThreadMessage to get here */
			DPRINT("Ending session, "
				  "destroying window.\n");
			DestroyWindow(priv->hWnd);
			break;
		}
		if (msg.hwnd == NULL && msg.message == WM_DDFULLSCREEN) {
			directx_fullscreen *dxfull =
				(directx_fullscreen *)msg.lParam;
			if (!dxfull) {
				fprintf(stderr, "Aieee! "
					"No lParam for WM_DDFULLSCREEN\n");
				exit(1);
			}
			DPRINT_MODE("Set coop level\n");
			dxfull->hr = IDirectDraw2_SetCooperativeLevel(
				dxfull->priv->lpddext, dxfull->priv->hWnd,
				DDSCL_EXCLUSIVE | DDSCL_FULLSCREEN);
			if (FAILED(dxfull->hr))
				DPRINT_MODE("SetCooperativeLevel failed %x\n",
					dxfull->hr);
			DPRINT_MODE("Set fullscreen mode "
				"(%i,%i) size %d\n",
				dxfull->mode->visible.x,
				dxfull->mode->visible.y,
				GT_SIZE(dxfull->mode->graphtype));
			dxfull->hr = IDirectDraw2_SetDisplayMode(
				dxfull->priv->lpddext,
				dxfull->mode->visible.x,
				dxfull->mode->visible.y,
				GT_SIZE(dxfull->mode->graphtype), 0, 0);
			if (FAILED(dxfull->hr))
				DPRINT_MODE("SetDisplayMode failed %x\n",
					dxfull->hr);
			SetEvent(dxfull->event);
			continue;
		}
		if (msg.hwnd == NULL && msg.message == WM_DDHOTKEY) {
			if (msg.wParam) {
				DPRINT("Grab hotkeys\n");
				RegisterHotKey(priv->hWnd, 0x0000,
					MOD_ALT, VK_TAB);
				RegisterHotKey(priv->hWnd, 0x0001,
					MOD_ALT | MOD_SHIFT, VK_TAB);
				RegisterHotKey(priv->hWnd, 0x0002,
					MOD_ALT, VK_F4);
			}
			else {
				DPRINT("Ungrab hotkeys\n");
				UnregisterHotKey(priv->hWnd, 0x0000);
				UnregisterHotKey(priv->hWnd, 0x0001);
				UnregisterHotKey(priv->hWnd, 0x0002);
			}
			continue;
		}

		TranslateMessage(&msg);
		DispatchMessage(&msg);
	}
	DPRINT("Helper thread terminating\n");

#ifndef __CYGWIN__
	_endthreadex(msg.wParam);
#endif
	return msg.wParam;
}
示例#11
0
文件: ui_win32.c 项目: Azizou/XaoS
static int ResizeDD(int fullscreen)
{
    HRESULT ddrval;
    DDSURFACEDESC ddsd;
    /*DDCAPS2 ddscaps; */
    LPDIRECTDRAWCLIPPER pClipper;
    int dxwidth;
    int dxheight;
    int dxbpp;

    // free DirectX objects
    if (lpSurfaces[0])
	IDirectDrawSurface_Release(lpSurfaces[0]);
    lpSurfaces[0] = NULL;
    if (dxPalette)
	IDirectDrawPalette_Release(dxPalette);
    dxPalette = NULL;
    /* Set cooperative level */
    ddrval = IDirectDraw2_SetCooperativeLevel(lpDD2, hWnd,
					      fullscreen
					      ? (DDSCL_FULLSCREEN |
						 DDSCL_EXCLUSIVE |
						 DDSCL_ALLOWREBOOT)
					      : DDSCL_NORMAL);
    if (ddrval != DD_OK) {
	DeInitDD();
	x_error("Failed to set cooperative level");
	return 0;
    }

    if (fullscreen) {
	if (sscanf(dxsize, "%ix%ix%i", &dxwidth, &dxheight, &dxbpp) != 3) {
	    dxwidth = DXWIDTH;
	    dxheight = DXHEIGHT;
	    dxbpp = DXBPP;
	}
	displayX = dxwidth;
	displayY = dxheight;
	bitDepth = dxbpp;
	if (bitDepth < 10)
	    bitDepth = 8;
	if (bitDepth >= 10 && bitDepth < 20)
	    bitDepth = 16;
	if (bitDepth >= 20 && bitDepth < 28)
	    bitDepth = 24;
	if (bitDepth >= 32 && bitDepth < 32)
	    bitDepth = 32;

	/* set resolution and bit depth */
	ddrval =
	    IDirectDraw2_SetDisplayMode(lpDD2, displayX, displayY,
					bitDepth, 0, 0);
	if (ddrval != DD_OK) {
	    /* The display mode cannot be changed. 
	       The mode is either not supported or 
	       another application has exclusive mode.

	       Try 320x200x256 and 640x480x256 modes before giving up */
	    displayX = 320;
	    displayY = 200;
	    bitDepth = 8;
	    ddrval =
		IDirectDraw2_SetDisplayMode(lpDD2, displayX, displayY,
					    bitDepth, 0, 0);
	    if (ddrval != DD_OK) {
		displayY = 240;
		if (ddrval != DD_OK) {
		    displayX = 640;
		    displayY = 480;
		    ddrval =
			IDirectDraw2_SetDisplayMode(lpDD2, displayX,
						    displayY, bitDepth, 0,
						    0);
		    if (ddrval != DD_OK) {
			/* Bad luck... give up. */
			DeInitDD();
			return 0;
		    }
		}
	    }
	}
	SetRect(&rcViewport, 0, 0, displayX, displayY);
	rcScreen = rcViewport;
    } else {
	/* Get the dimensions of the viewport and screen bounds */
	GetClientRect(hWnd, &rcViewport);
	GetClientRect(hWnd, &rcScreen);
	ClientToScreen(hWnd, (POINT *) & rcScreen.left);
	ClientToScreen(hWnd, (POINT *) & rcScreen.right);
	/*bitDepth = GetDeviceCaps (hDC, BITSPIXEL); */

	/* Create clipper object for window */
	ddrval = IDirectDraw_CreateClipper(lpDD, 0, &pClipper, NULL);
	if (ddrval != DD_OK) {
	    DeInitDD();
	    x_error("Failed to create clipper object");
	    return 0;
	}
	/* Asociate it */
	IDirectDrawClipper_SetHWnd(pClipper, 0, hWnd);
    }
    /* Create the primary surface with one back buffer */
    CalculateBITMAPINFO();	// calculate BITMAPINFO structure

    memset(&ddsd, 0, sizeof(ddsd));
    ddsd.dwSize = sizeof(ddsd);
    ddsd.dwFlags = DDSD_CAPS;
    ddsd.ddsCaps.dwCaps = DDSCAPS_PRIMARYSURFACE;

    ddrval = IDirectDraw_CreateSurface(lpDD, &ddsd, &lpSurfaces[0], NULL);
    if (ddrval != DD_OK) {
	DeInitDD();
	x_error("Failed to create flipping surface");
	return 0;
    }

    if (!fullscreen) {
	IDirectDrawSurface_SetClipper(lpSurfaces[0], pClipper);
	IDirectDrawClipper_Release(pClipper);
	if (IDirectDrawSurface_GetSurfaceDesc(lpSurfaces[0], &ddsd) !=
	    DD_OK) {
	    DeInitDD();
	    x_error("Failed to get pixel format");
	    return 0;
	}
	bitDepth = ddsd.ddpfPixelFormat.u1.dwRGBBitCount;
    }

    if (bitDepth == 8) {
	/* create palette */
	ddrval =
	    IDirectDraw_CreatePalette(lpDD, DDPCAPS_8BIT,
				      (LPPALETTEENTRY) bmp->bmiColors,
				      &dxPalette, NULL);
	if (ddrval != DD_OK) {
	    DeInitDD();
	    x_error("Failed to create palette");
	    return 0;
	}

	/* set palette */
	IDirectDrawSurface_SetPalette(lpSurfaces[0], dxPalette);
    }
    if (fullscreen)
	SetCursor(NULL);
    needredraw = 1;
    return 1;

}