Пример #1
0
/**
 * This function locks a surface and get the surface descriptor.
 */
static int DirectXLockSurface(LPDIRECTDRAWSURFACE2 front_surface,
                              LPDIRECTDRAWSURFACE2 surface,
                              DDSURFACEDESC *ddsd)
{
    HRESULT hr;

    DDSURFACEDESC ddsd_dummy;
    if (!ddsd)
        ddsd = &ddsd_dummy;

    ZeroMemory(ddsd, sizeof(*ddsd));
    ddsd->dwSize = sizeof(*ddsd);
    hr = IDirectDrawSurface2_Lock(surface, NULL, ddsd, DDLOCK_NOSYSLOCK | DDLOCK_WAIT, NULL);
    if (hr != DD_OK) {
        if (hr == DDERR_INVALIDPARAMS) {
            /* DirectX 3 doesn't support the DDLOCK_NOSYSLOCK flag, resulting
             * in an invalid params error */
            hr = IDirectDrawSurface2_Lock(surface, NULL, ddsd, DDLOCK_WAIT, NULL);
        }
        if (hr == DDERR_SURFACELOST) {
            /* Your surface can be lost so be sure
             * to check this and restore it if needed */

            /* When using overlays with back-buffers, we need to restore
             * the front buffer so the back-buffers get restored as well. */
            if (front_surface != surface)
                IDirectDrawSurface2_Restore(front_surface);
            else
                IDirectDrawSurface2_Restore(surface);

            hr = IDirectDrawSurface2_Lock(surface, NULL, ddsd, DDLOCK_WAIT, NULL);
        }
        if (hr != DD_OK)
            return VLC_EGENERIC;
    }
    return VLC_SUCCESS;
}
Пример #2
0
static Bool
winActivateAppShadowDD (ScreenPtr pScreen)
{
  winScreenPriv(pScreen);

  /*
   * Do we have a surface?
   * Are we active?
   * Are we fullscreen?
   */
  if (pScreenPriv != NULL
      && pScreenPriv->pddsPrimary != NULL
      && pScreenPriv->fActive)
    {
      /* Primary surface was lost, restore it */
      IDirectDrawSurface2_Restore (pScreenPriv->pddsPrimary);
    }

  return TRUE;
}
Пример #3
0
/* restore_all_ddraw_surfaces:
 *  Restores all the surfaces. Returns 0 on success or -1 on failure,
 *  in which case restoring is stopped at the first failure.
 */
int restore_all_ddraw_surfaces(void)
{
   DDRAW_SURFACE *item = ddraw_surface_list;
   HRESULT hr;

   _enter_gfx_critical();

   while (item) {
      hr = IDirectDrawSurface2_Restore(item->id);
      if (FAILED(hr)) {
         _exit_gfx_critical();
         return -1;
      }

      item = item->next;
   }

   _exit_gfx_critical();

   _TRACE(PREFIX_I "all DirectDraw surfaces restored\n");

   return 0;
}
Пример #4
0
static Bool
winBltExposedRegionsShadowDD (ScreenPtr pScreen)
{
  winScreenPriv(pScreen);
  winScreenInfo		*pScreenInfo = pScreenPriv->pScreenInfo;
  RECT			rcSrc, rcDest;
  POINT			ptOrigin;
  HDC			hdcUpdate = NULL;
  PAINTSTRUCT		ps;
  HRESULT		ddrval = DD_OK;
  Bool			fReturn = TRUE;
  Bool			fLocked = TRUE;
  int			i;

  /* BeginPaint gives us an hdc that clips to the invalidated region */
  hdcUpdate = BeginPaint (pScreenPriv->hwndScreen, &ps);
  if (hdcUpdate == NULL)
    {
      ErrorF ("winBltExposedRegionsShadowDD - BeginPaint () returned "
	      "a NULL device context handle.  Aborting blit attempt.\n");
      return FALSE;
    }
  
  /* Unlock the shadow surface, so we can blit */
  ddrval = IDirectDrawSurface2_Unlock (pScreenPriv->pddsShadow, NULL);
  if (FAILED (ddrval))
    {
      fReturn = FALSE;
      goto winBltExposedRegionsShadowDD_Exit;
    }
  else
    {
      /* Flag that we have unlocked the shadow surface */
      fLocked = FALSE;
    }

  /* Get the origin of the window in the screen coords */
  ptOrigin.x = pScreenInfo->dwXOffset;
  ptOrigin.y = pScreenInfo->dwYOffset;

  MapWindowPoints (pScreenPriv->hwndScreen,
		   HWND_DESKTOP,
		   (LPPOINT)&ptOrigin, 1);
  rcDest.left = ptOrigin.x;
  rcDest.right = ptOrigin.x + pScreenInfo->dwWidth;
  rcDest.top = ptOrigin.y;
  rcDest.bottom = ptOrigin.y + pScreenInfo->dwHeight;

  /* Source can be enter shadow surface, as Blt should clip */
  rcSrc.left = 0;
  rcSrc.top = 0;
  rcSrc.right = pScreenInfo->dwWidth;
  rcSrc.bottom = pScreenInfo->dwHeight;

  /* Try to regain the primary surface and blit again if we've lost it */
  for (i = 0; i <= WIN_REGAIN_SURFACE_RETRIES; ++i)
    {
      /* Our Blt should be clipped to the invalidated region */
      ddrval = IDirectDrawSurface2_Blt (pScreenPriv->pddsPrimary,
					&rcDest,
					pScreenPriv->pddsShadow,
					&rcSrc,
					DDBLT_WAIT,
					NULL);
      if (ddrval == DDERR_SURFACELOST)
	{
	  /* Surface was lost */
	  ErrorF ("winBltExposedRegionsShadowDD - IDirectDrawSurface2_Blt "
		  "reported that the primary surface was lost, "
		  "trying to restore, retry: %d\n", i + 1);

	  /* Try to restore the surface, once */
	  ddrval = IDirectDrawSurface2_Restore (pScreenPriv->pddsPrimary);
	  ErrorF ("winBltExposedRegionsShadowDD - "
		  "IDirectDrawSurface2_Restore returned: ");
	  if (ddrval == DD_OK)
	    ErrorF ("DD_OK\n");
	  else if (ddrval == DDERR_WRONGMODE)
	    ErrorF ("DDERR_WRONGMODE\n");
	  else if (ddrval == DDERR_INCOMPATIBLEPRIMARY)
	    ErrorF ("DDERR_INCOMPATIBLEPRIMARY\n");
	  else if (ddrval == DDERR_UNSUPPORTED)
	    ErrorF ("DDERR_UNSUPPORTED\n");
	  else if (ddrval == DDERR_INVALIDPARAMS)
	    ErrorF ("DDERR_INVALIDPARAMS\n");
	  else if (ddrval == DDERR_INVALIDOBJECT)
	    ErrorF ("DDERR_INVALIDOBJECT\n");
	  else
	    ErrorF ("unknown error: %08x\n", (unsigned int) ddrval);

	  /* Loop around to try the blit one more time */
	  continue;
	}
      else if (FAILED (ddrval))
	{
	  fReturn = FALSE;
	  ErrorF ("winBltExposedRegionsShadowDD - IDirectDrawSurface2_Blt "
		  "failed, but surface not lost: %08x %d\n",
		  (unsigned int) ddrval, (int) ddrval);
	  goto winBltExposedRegionsShadowDD_Exit;
	}
      else
	{
	  /* Success, stop looping */
	  break;
	}
    }

  /* Relock the shadow surface */
  ddrval = IDirectDrawSurface2_Lock (pScreenPriv->pddsShadow,
				     NULL,
				     pScreenPriv->pddsdShadow,
				     DDLOCK_WAIT,
				     NULL);
  if (FAILED (ddrval))
    {
      fReturn = FALSE;
      ErrorF ("winBltExposedRegionsShadowDD - IDirectDrawSurface2_Lock "
	      "failed\n");
      goto winBltExposedRegionsShadowDD_Exit;
    }
  else
    {
      /* Indicate that we have relocked the shadow surface */
      fLocked = TRUE;
    }

  /* Has our memory pointer changed? */
  if (pScreenInfo->pfb != pScreenPriv->pddsdShadow->lpSurface)
    winUpdateFBPointer (pScreen,
			pScreenPriv->pddsdShadow->lpSurface);

 winBltExposedRegionsShadowDD_Exit:
  /* EndPaint frees the DC */
  if (hdcUpdate != NULL)
    EndPaint (pScreenPriv->hwndScreen, &ps);

  /*
   * Relock the surface if it is not locked.  We don't care if locking fails,
   * as it will cause the server to shutdown within a few more operations.
   */
  if (!fLocked)
    {
      IDirectDrawSurface2_Lock (pScreenPriv->pddsShadow,
				NULL,
				pScreenPriv->pddsdShadow,
				DDLOCK_WAIT,
				NULL);

      /* Has our memory pointer changed? */
      if (pScreenInfo->pfb != pScreenPriv->pddsdShadow->lpSurface)
	winUpdateFBPointer (pScreen,
			    pScreenPriv->pddsdShadow->lpSurface);
      
      fLocked = TRUE;
    }
  return fReturn;
}
Пример #5
0
Bool
winHotKeyAltTabPrimaryDD (ScreenPtr pScreen)
{
  winScreenPriv(pScreen);
  winScreenInfo		*pScreenInfo = pScreenPriv->pScreenInfo;
  RECT			rcClient, rcSrc;
  HRESULT		ddrval = DD_OK;

  ErrorF ("\nwinHotKeyAltTabPrimaryDD\n\n");

  /* Alt+Tab was pressed, we will lose focus very soon */
  pScreenPriv->fActive = FALSE;
  
  /* Check for error conditions */
  if (pScreenPriv->pddsPrimary == NULL
      || pScreenPriv->pddsOffscreen == NULL)
    return FALSE;

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

  /* Did we loose the primary surface? */
  ddrval = IDirectDrawSurface2_IsLost (pScreenPriv->pddsPrimary);
  if (ddrval == DD_OK)
    {
      ddrval = IDirectDrawSurface2_Unlock (pScreenPriv->pddsPrimary,
					   NULL);
      if (FAILED (ddrval))
	FatalError ("winHotKeyAltTabPrimaryDD - Failed unlocking primary "
		    "surface\n");
    }

  /* Setup a source rectangle */
  rcSrc.left = 0;
  rcSrc.top = 0;
  rcSrc.right = pScreenInfo->dwWidth;
  rcSrc.bottom = pScreenInfo->dwHeight;

      /* Blit the primary surface to the offscreen surface */
  ddrval = IDirectDrawSurface2_Blt (pScreenPriv->pddsOffscreen,
				    NULL, /* should be rcDest */
				    pScreenPriv->pddsPrimary,
				    NULL,
				    DDBLT_WAIT,
				    NULL);
  if (ddrval == DDERR_SURFACELOST)
    {
      IDirectDrawSurface2_Restore (pScreenPriv->pddsOffscreen);  
      IDirectDrawSurface2_Restore (pScreenPriv->pddsPrimary);
		  		  
      /* Blit the primary surface to the offscreen surface */
      ddrval = IDirectDrawSurface2_Blt (pScreenPriv->pddsOffscreen,
					NULL,
					pScreenPriv->pddsPrimary,
					NULL,
					DDBLT_WAIT,
					NULL);
      if (FAILED (ddrval))
	FatalError ("winHotKeyAltTabPrimaryDD - Failed blitting primary "
		    "surface to offscreen surface: %08x\n",
		    ddrval);
    }
  else
    {
      FatalError ("winHotKeyAltTabPrimaryDD - Unknown error from "
		  "Blt: %08dx\n", ddrval);
    }

  /* Lock the offscreen surface */
  ddrval = IDirectDrawSurface2_Lock (pScreenPriv->pddsOffscreen,
				     NULL,
				     pScreenPriv->pddsdOffscreen,
				     DDLOCK_WAIT,
				     NULL);
  if (ddrval != DD_OK
      || pScreenPriv->pddsdPrimary->lpSurface == NULL)
    FatalError ("winHotKeyAltTabPrimaryDD - Could not lock "
		"offscreen surface\n");

  /* Notify FB of the new memory pointer */
  winUpdateFBPointer (pScreen,
		      pScreenPriv->pddsdOffscreen->lpSurface);

  /* Unregister our hotkey */
  UnregisterHotKey (pScreenPriv->hwndScreen, 1);

  return TRUE;
}
Пример #6
0
Bool
winActivateAppPrimaryDD (ScreenPtr pScreen)
{
  winScreenPriv(pScreen);
  winScreenInfo		*pScreenInfo = pScreenPriv->pScreenInfo;
  RECT			rcSrc, rcClient;
  HRESULT		ddrval = DD_OK;

  /* Check for errors */
  if (pScreenPriv == NULL
      || pScreenPriv->pddsPrimary == NULL
      || pScreenPriv->pddsOffscreen == NULL)
    return FALSE;

  /* Check for do-nothing */
  if (!pScreenPriv->fActive)
    return TRUE;
  
  /* We are activating */
  ddrval = IDirectDrawSurface2_IsLost (pScreenPriv->pddsOffscreen);
  if (ddrval == DD_OK)
    {
      IDirectDrawSurface2_Unlock (pScreenPriv->pddsOffscreen,
				  NULL);
      /*
       * We don't check for an error from Unlock, because it
       * doesn't matter if the Unlock failed.
       */
    }

  /* Restore both surfaces, just cause I like it that way */
  IDirectDrawSurface2_Restore (pScreenPriv->pddsOffscreen);
  IDirectDrawSurface2_Restore (pScreenPriv->pddsPrimary);
			      
  /* Get client area in screen coords */
  GetClientRect (pScreenPriv->hwndScreen, &rcClient);
  MapWindowPoints (pScreenPriv->hwndScreen,
		   HWND_DESKTOP,
		   (LPPOINT)&rcClient, 2);

  /* Setup a source rectangle */
  rcSrc.left = 0;
  rcSrc.top = 0;
  rcSrc.right = pScreenInfo->dwWidth;
  rcSrc.bottom = pScreenInfo->dwHeight;

  ddrval = IDirectDrawSurface2_Blt (pScreenPriv->pddsPrimary,
				    &rcClient,
				    pScreenPriv->pddsOffscreen,
				    &rcSrc,
				    DDBLT_WAIT,
				    NULL);
  if (ddrval != DD_OK)
    FatalError ("winActivateAppPrimaryDD () - Failed blitting offscreen "
		"surface to primary surface %08x\n", ddrval);
  
  /* Lock the primary surface */
  ddrval = IDirectDrawSurface2_Lock (pScreenPriv->pddsPrimary,
				     &rcClient,
				     pScreenPriv->pddsdPrimary,
				     DDLOCK_WAIT,
				     NULL);
  if (ddrval != DD_OK
      || pScreenPriv->pddsdPrimary->lpSurface == NULL)
    FatalError ("winActivateAppPrimaryDD () - Could not lock "
		"primary surface\n");

  /* Notify FB of the new memory pointer */
  winUpdateFBPointer (pScreen,
		      pScreenPriv->pddsdPrimary->lpSurface);

  /*
   * Register the Alt-Tab combo as a hotkey so we can copy
   * the primary framebuffer before the display mode changes
   */
  RegisterHotKey (pScreenPriv->hwndScreen, 1, MOD_ALT, 9);

  return TRUE;
}
Пример #7
0
int directdraw_draw(void *pic, int w, int h)
{
	DDSURFACEDESC  descriptor;
	RECT           rct;
	HWND           hwndp;

#define fourcc(a,b,c,d) (( ((uint32_t)a) | ( ((uint32_t)b) << 8 ) | ( ((uint32_t)c) << 16 ) | ( ((uint32_t)d) << 24 ) ))

	int bh = h, bw = w;
	//w = default_sw;
	//h = default_sh;

	vdata.getdata(get_window_video, 0, &hwndp, 0);

	if(!hwndp) return 0;
	if(video_window_parent != hwndp)
	{
		video_uninit();
		video_init(hwndp);
		video_window_parent = hwndp;
	}

	if(w != d_width || h != d_height)
	{

		if(size_in_list(w, h))size_is_ok = 1;
		else size_is_ok = 0;

		if(w && h)
		{
			d_width  = w;
			d_height = h;

			if(lpDDS_secondary)
				IDirectDrawSurface2_Release(lpDDS_secondary);

			memset(&descriptor, 0, sizeof(descriptor));
			
			descriptor.dwSize         = sizeof(descriptor);
			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;
	    	
			lpDDS_back    = lpDDS_secondary;
		}
	}

	if(use_osd_surface)
	{
		GetClientRect(video_window, &rct);

		if(rct.right != window_w || rct.bottom != window_h || osd_created == 0)
		{
			window_w = rct.right;
			window_h = rct.bottom;

			if(surface_osd)
				IDirectDrawSurface2_Release(surface_osd);

			memset( &descriptor, 0, sizeof(descriptor));

			descriptor.dwSize         = sizeof(descriptor);
			descriptor.dwFlags        = DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH;
			descriptor.ddsCaps.dwCaps = DDSCAPS_OFFSCREENPLAIN;
			descriptor.dwWidth        = window_w;
			descriptor.dwHeight       = window_h;

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

			osd_created = 1;
		}
	}

    IDirectDrawSurface2_Restore(lpDDS);
    if(pic)
		IDirectDrawSurface2_Restore(lpDDS_secondary);

	memset(&descriptor, 0, sizeof(descriptor));
    descriptor.dwSize = sizeof(descriptor);

	if(pic)
	{
		HRESULT res;
		

		if(size_is_ok)
		{
			res = IDirectDrawSurface2_Lock(lpDDS_back, 0, &descriptor, DDLOCK_WAIT | DDLOCK_WRITEONLY, 0);
			if(FAILED(res)) return 0;

			memcpy(descriptor.lpSurface, pic, w * h * 4);

			IDirectDrawSurface2_Unlock(lpDDS_back, descriptor.lpSurface);

		}else{

			HBITMAP bmp;
			HDC     hdc, cdc;
						
			bmp = CreateBitmap(w, h, 1, 32, pic);

			if(!FAILED(IDirectDrawSurface2_GetDC(lpDDS_back, &hdc)))
			{
				cdc = CreateCompatibleDC(0);
				
				SelectObject(cdc, bmp);
				BitBlt(hdc, 0, 0, w, h, cdc, 0, 0, SRCCOPY);
				IDirectDrawSurface2_ReleaseDC(lpDDS_back, hdc);

				DeleteDC(cdc);
			}

			DeleteObject(bmp);
		}

		IDirectDrawSurface2_Flip(lpDDS, 0, DDFLIP_WAIT);
	}



	return 1;
}
Пример #8
0
void DDRestoreSurface( LPDIRECTDRAWSURFACE2 pSurface )
{
	Assert( pSurface != NULL );

	ATTEMPT( IDirectDrawSurface2_Restore( pSurface ) );
}