2016-02-27 56 views
1

我想繪製一個位圖到屏幕上;調用從文件加載位圖的代碼有效,但看起來實際的繪圖部分導致一些程序崩潰。Direct2D加載和繪製位圖

我遵循MSDN的教程,但我所做的唯一更改不是使用ID2D1RenderTarget,而是使用ID2D1DCRenderTarget。

下面是工作負載的方法:

HRESULT LoadBitmapFromFile(
    ID2D1DCRenderTarget *pRenderTarget, 
    IWICImagingFactory *pIWICFactory, 
    PCWSTR uri, 
    UINT destinationWidth, 
    UINT destinationHeight, 
    ID2D1Bitmap **ppBitmap 
    ) 
{ 
    IWICBitmapDecoder *pDecoder = NULL; 
    IWICBitmapFrameDecode *pSource = NULL; 
    IWICStream *pStream = NULL; 
    IWICFormatConverter *pConverter = NULL; 
    IWICBitmapScaler *pScaler = NULL; 
    HRESULT hr = pIWICFactory->CreateDecoderFromFilename(
     uri, 
     NULL, 
     GENERIC_READ, 
     WICDecodeMetadataCacheOnLoad, 
     &pDecoder 
     ); 



    if (SUCCEEDED(hr)) 
    { 
     // Create the initial frame. 
     hr = pDecoder->GetFrame(0, &pSource); 
    } 
    if (SUCCEEDED(hr)) 
    { 

     // Convert the image format to 32bppPBGRA 
     // (DXGI_FORMAT_B8G8R8A8_UNORM + D2D1_ALPHA_MODE_PREMULTIPLIED). 
     hr = pIWICFactory->CreateFormatConverter(&pConverter); 

    } 


    if (SUCCEEDED(hr)) 
    { 
     // If a new width or height was specified, create an 
     // IWICBitmapScaler and use it to resize the image. 
     if (destinationWidth != 0 || destinationHeight != 0) 
     { 
      UINT originalWidth, originalHeight; 
      hr = pSource->GetSize(&originalWidth, &originalHeight); 
      if (SUCCEEDED(hr)) 
      { 
       if (destinationWidth == 0) 
       { 
        FLOAT scalar = static_cast<FLOAT>(destinationHeight)/static_cast<FLOAT>(originalHeight); 
        destinationWidth = static_cast<UINT>(scalar * static_cast<FLOAT>(originalWidth)); 
       } 
       else if (destinationHeight == 0) 
       { 
        FLOAT scalar = static_cast<FLOAT>(destinationWidth)/static_cast<FLOAT>(originalWidth); 
        destinationHeight = static_cast<UINT>(scalar * static_cast<FLOAT>(originalHeight)); 
       } 

       hr = pIWICFactory->CreateBitmapScaler(&pScaler); 
       if (SUCCEEDED(hr)) 
       { 
        hr = pScaler->Initialize(
         pSource, 
         destinationWidth, 
         destinationHeight, 
         WICBitmapInterpolationModeCubic 
         ); 
       } 
       if (SUCCEEDED(hr)) 
       { 
        hr = pConverter->Initialize(
         pScaler, 
         GUID_WICPixelFormat32bppPBGRA, 
         WICBitmapDitherTypeNone, 
         NULL, 
         0.f, 
         WICBitmapPaletteTypeMedianCut 
         ); 
       } 
      } 
     } 
     else // Don't scale the image. 
     { 
      hr = pConverter->Initialize(
       pSource, 
       GUID_WICPixelFormat32bppPBGRA, 
       WICBitmapDitherTypeNone, 
       NULL, 
       0.f, 
       WICBitmapPaletteTypeMedianCut 
       ); 
     } 
    } 
    if (SUCCEEDED(hr)) 
    { 

     // Create a Direct2D bitmap from the WIC bitmap. 
     hr = pRenderTarget->CreateBitmapFromWicBitmap(
      pConverter, 
      NULL, 
      ppBitmap 
      ); 
    } 

    if (pDecoder) pDecoder->Release(); 
    if (pSource) pSource->Release(); 
    if (pStream) pStream->Release(); 
    if (pScaler) pScaler->Release(); 

    return hr; 
} 

而在BeginDraw()和EndDraw()之間的渲染目標,我有以下代碼繪製位圖。這是當我嘗試運行時崩潰程序的部分:

d2dg->pRT->BeginDraw(); 

// Create a WIC Factory 
HRESULT hr = CoCreateInstance(
CLSID_WICImagingFactory, 
NULL, 
CLSCTX_INPROC_SERVER, 
IID_IWICImagingFactory, 
(LPVOID*)&wicFactory); 

hr = LoadBitmapFromFile(d2dg->pRT, wicFactory, L"image1.png", 400, 400, &pBitmap); 

D2D1_SIZE_F size = pBitmap->GetSize(); 
D2D1_POINT_2F upperLeftCorner = D2D1::Point2F(100.f, 10.f); 
// Draw a bitmap. 
d2dg->pRT->DrawBitmap(
    pBitmap, 
    D2D1::RectF(
    upperLeftCorner.x, 
    upperLeftCorner.y, 
    upperLeftCorner.x + size.width, 
    upperLeftCorner.y + size.height) 
    ); 

d2dg->pRT->EndDraw(); 

回答

0

發現問題:我想繪製的位圖仍然是NULL。

可以通過從LoadBitmapFromFile中刪除ID2D1Bitmap **ppBitmap參數來修復此問題,並且只需使用指向&pBitmap的指針就可以瞭解該方法中對位圖的任何引用。

這樣,pBitmap被操縱,不會保持NULL。