2

CDC から CBitmap に画像を転送するにはどうすればよいですか? 全体的な問題: CBitmap A に大きな画像があります。これには多数の CDC を使用できないため、この画像の一部をいくつかの CBitmap に転送して、ベクトルに格納する必要があります:)準備された CDC をサイクルに変換し (CBitmap A の必要な部分を取得)、それを CBitmap x に転送する必要があります。どうすればいいですか?

これが私のコードです:

m_bitmaps.clear();
m_bitmaps.reserve(4);

CDC SourceDC, destDC;
SourceDC.CreateCompatibleDC(pMainDC);
destDC.CreateCompatibleDC(pMainDC);

CBitmap bmpWhole; // bmp 200*200
bmpWhole.LoadBitmap(IDB_TEST_BITMAP);
SourceDC.SelectObject(&bmpWhole);

//pMainDC->BitBlt(0,0,200,200,&SourceDC,0,0,SRCCOPY);

// OK - ソース画像を取得しました

for (int x=100; x>=0; x-=100)
    for (int y=100; y>=0; y-=100)
    {
        CBitmap *destBitmap = new CBitmap();
        destBitmap->CreateCompatibleBitmap(&destDC, 100, 100);

        CBitmap *oldBitmap = destDC.SelectObject(destBitmap);

        destDC.BitBlt(0,0,100,100,&SourceDC,x,y,SRCCOPY);

        pMainDC->BitBlt(x*1.1,y*1.1,100,100,&destDC,0,0,SRCCOPY);

// ここに黒い四角があります! - 前のコードに問題がある

        m_bitmaps.push_back(destBitmap);

        destDC.SelectObject(oldBitmap);
    }

bmpWhole.DeleteObject();
destDC.DeleteDC();
SourceDC.DeleteDC();

// そしてそれ以降の CBitmaps は黒い四角形です


解決策を見つけました!

CBitmap の解析とベクターの初期化

m_bitmaps.clear();
m_bitmaps.reserve(4);

CDC SourceDC, destDC;
SourceDC.CreateCompatibleDC(pMainDC);

CBitmap bmpWhole;
bmpWhole.LoadBitmap(IDB_TEST_BITMAP);
SourceDC.SelectObject(&bmpWhole);

for (int x=100; x>=0; x-=100)
    for (int y=100; y>=0; y-=100)
    {
        CImage *destImage = new CImage();
        destImage->Create(100, 100, 24);

        destDC.Attach(destImage->GetDC());
        destDC.BitBlt(0,0,100,100,&SourceDC,x,y,SRCCOPY);
        destDC.Detach();
        destImage->ReleaseDC();

        m_bitmaps.push_back(destImage);
    }

bmpWhole.DeleteObject();
destDC.DeleteDC();
SourceDC.DeleteDC();

描く:

WORD nShift=0;
for (auto iter = m_bitmaps.begin(); iter != m_bitmaps.end(); ++iter, nShift+=110)
{
    CBitmap* pBitmap = CBitmap::FromHandle((*iter)->operator HBITMAP());

    CDC memDC;
    memDC.CreateCompatibleDC(pMainDC);
    memDC.SelectObject(pBitmap);
    pMainDC->BitBlt(nShift, 0, 100, 100, &memDC, 0, 0, SRCCOPY);
}
4

1 に答える 1

1

別のデバイス コンテキストを作成し、ターゲット ビットマップを 1 つずつ作成して選択しBitBlt、ソース ビットマップの一部をそれらにコピーするために使用します。以下は、これを行う方法の例です。

// Create a DC compatible with the display
// this is used to copy FROM the source bitmap
sourceDC.CreateDC(NULL); 
sourceDC.SelectObject(&sourceBitmap);

// Create another device context for the destination bitmap
destDC.CreateCompatibleDC(&sourceDC);
for(int i = 0; i < numBitmaps; i++)
{
    // Determine the x, y, sourceX, sourceY, with and height here
    // ...

    // create a new bitmap
    CBitmap *destBitmap = new CBitmap();
    destBitmap->CreateCompatibleBitmap(&destDC, width, height);
    // Select the bitmap into the destination device context
    CBitmap *oldBitmap = destDC.SelectObject(destBitmap);

    // copy the bitmap
    destDC.BitBlt(x, y, width, height, &sourceDC, sourceX, sourceY, SRCCOPY);

    // add it to the vector    
    bitmapVector.push_back(destBitmap);

    // Clean up
    destDC.SelectObject(oldBitmap);
}

簡単にするためにエラーチェックを省略しました。C++11 または Boost を使用している場合unique_ptrは、ビットマップ オブジェクトの有効期間を管理するために使用することをお勧めします。deleteそれ以外の場合は、デストラクタなどの適切な場所でそれを行う必要があります。

于 2013-07-02T02:37:36.433 に答える