1

I have a problem with off-screen rendering with OpenGL. I searched for a lot about FBO and PBO but nothing was helpful for me. I guess the matter was from memDC which was made by CreateCompatibleDC.

Here is a part of my code

void COpenGLWnd::ShowinWnd(int ID)
{
    m_hDC = ::GetDC(m_hWnd);
    memDC = CreateCompatibleDC(m_hDC);
    SetDCPixelFormat(memDC);

    m_hRC = wglCreateContext(memDC);
    VERIFY(wglMakeCurrent(memDC, m_hRC));
    m_isitStart = 0;

    GLuint pbo;
    glGenBuffersARB(1,&pbo);
    glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, pbo);
    glBufferDataARB(GL_PIXEL_PACK_BUFFER_ARB, (m_WndWidth * 3 + 3) / 4 * 4 * m_WndHeight, NULL, GL_STREAM_READ);

    glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, pbo);

    switch(ID)
    {
    case T_FADEIN:
         GLFadeinRender();
        break;
    case T_PARANORAMAL:
         GLParanormalRender();
        break;
    case T_3DCUBE:
         GL3DcubeRender();
        break;
    default:
        break;
    }

    glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, pbo);
    glReadBuffer(GL_BACK);
    glReadPixels(0,0,m_WndWidth,m_WndHeight,GL_BGR_EXT,GL_UNSIGNED_BYTE, 0);
    BYTE* data = (BYTE*) glMapBufferARB(GL_PIXEL_PACK_BUFFER_ARB, GL_READ_ONLY_ARB);
    if(data)
    {
        SaveBitmapToDirectFile(data);    //this makes bitmap file with pixel BYTE array, "data".
        glUnmapBufferARB(GL_PIXEL_PACK_BUFFER_ARB);
    }

    glBindFramebuffer(GL_PIXEL_PACK_BUFFER_ARB,0);

    SwapBuffers(memDC);

    glDeleteBuffers(1,&pbo);

    wglMakeCurrent(memDC, NULL);
    wglDeleteContext(m_hRC);
    DeleteDC(memDC);
    ::ReleaseDC(m_hWnd, m_hDC);
}

If I run this programm without memDC and CreateContext on m_hDC, nothing was matter. Well rendered on window, well written bitmap file. But I want to render in off-screen and only saving bitmap files. How can I handle this?

phraust
  • 123
  • 1
  • 9
  • thanks for you answer!, but how can I use SelectObject then? Could you recommend it me again please? – phraust Feb 10 '14 at 08:51
  • I inserted new code on initializing step like __m_hMemBmp = ::CreateCompatibleBitmap(m_hDC, m_WndWidth, m_WndHeight); ::SelectObject(memDC, m_hMemBmp);__ but still nothing changed – phraust Feb 10 '14 at 09:15
  • I use Borland and under it I never get bitmap rendering running. So if your problems persist you can draw to Texture without any additional DC/RC needed (only the target window is needed)... but the size of texture is limited on some cards/drivers a lot more than the screen resolution so may be you have to use more textures for coverage. – Spektre Feb 10 '14 at 10:31

1 Answers1

1

MemDCs will automatically drop you back to the old, OpenGL-1.1 software rasterizer. This rasterizer is very limited, does not support any kind of modern features, like FBOs, PBuffers and so on.

If you want a GPU accelerated OpenGL context you need to create this on a regular window (or a PBuffer DC, but to get a PBuffer DC you need a window first). You need the window just for getting the context, you don't have to render there and the window can stay hidden all the time (omit the ShowWindow call of the creation process). With a valid pixelformat set for the window create the OpenGL context on its HDC.

Since you already have a window, just go with that then.

With the OpenGL context from a regular window you can then use FBOs for off-screen rendering.

datenwolf
  • 159,371
  • 13
  • 185
  • 298