Jump to content
  • Advertisement
Sign in to follow this  
was2_0

OpenGL Why I can't display anything use glViewport in this program?

This topic is 4425 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

I have tested it for a long time, but nothing be different...
#include <windows.h>
#include <gl/gl.h>
#include <gl/glu.h>

unsigned long image[16] = {
	0xFF0000FF, 0xFF0000FF, 0xFF0000FF, 0xFF0000FF,
	0xFF0000FF, 0xFF0000FF, 0xFF0000FF, 0xFF0000FF,
	0xFF0000FF, 0xFF0000FF, 0xFF0000FF, 0xFF0000FF,
	0xFF0000FF, 0xFF0000FF, 0xFF0000FF, 0xFF0000FF,
};
unsigned int texobj[1];

LRESULT CALLBACK WndProc (HWND hWnd, UINT message,
WPARAM wParam, LPARAM lParam);
void EnableOpenGL (HWND hWnd, HDC *hDC, HGLRC *hRC);
void DisableOpenGL (HWND hWnd, HDC hDC, HGLRC hRC);

int WINAPI WinMain (HINSTANCE hInstance,
                    HINSTANCE hPrevInstance,
                    LPSTR lpCmdLine,
                    int iCmdShow)
{
    WNDCLASS wc;
    HWND hWnd;
    HDC hDC;
    HGLRC hRC;        
    MSG msg;
    BOOL bQuit = FALSE;

    /* register window class */
    wc.style = CS_OWNDC;
    wc.lpfnWndProc = WndProc;
    wc.cbClsExtra = 0;
    wc.cbWndExtra = 0;
    wc.hInstance = hInstance;
    wc.hIcon = LoadIcon (NULL, IDI_APPLICATION);
    wc.hCursor = LoadCursor (NULL, IDC_ARROW);
    wc.hbrBackground = (HBRUSH) GetStockObject (BLACK_BRUSH);
    wc.lpszMenuName = NULL;
    wc.lpszClassName = "GLSample";
    RegisterClass (&wc);

    /* create main window */
    hWnd = CreateWindow (
      "GLSample", "OpenGL Sample", 
      WS_CAPTION | WS_POPUPWINDOW | WS_VISIBLE,
      50, 50, 256, 256,
      NULL, NULL, hInstance, NULL);

    /* enable OpenGL for the window */
    EnableOpenGL (hWnd, &hDC, &hRC);
	glEnable(GL_BLEND);
	glEnable(GL_TEXTURE_2D);
	glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
	glGenTextures(1, texobj);
	glBindTexture(GL_TEXTURE_2D, texobj[0]);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
	glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 4, 4, 0, GL_RGBA, GL_UNSIGNED_BYTE, image);
glViewport(0, 0, 256, 256);
glMatrixMode(GL_PROJECTION);
glOrtho(-0.5, 256-0.5, 256-0.5, -0.5, -1, 1);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
    /* program main loop */
    while (!bQuit)
    {
        /* check for messages */
        if (PeekMessage (&msg, NULL, 0, 0, PM_REMOVE))
        {
            /* handle or dispatch messages */
            if (msg.message == WM_QUIT)
            {
                bQuit = TRUE;
            }
            else
            {
                TranslateMessage (&msg);
                DispatchMessage (&msg);
            }
        }
        else
        {
            /* OpenGL animation code goes here */

            glClearColor (0.0f, 0.0f, 0.0f, 0.0f);
            glClear (GL_COLOR_BUFFER_BIT);

            glBegin (GL_QUADS);
            glTexCoord2f(0.0, 0.0);glColor4f(1.0f, 1.0f, 1.0f, 1.0f);glVertex2f(0.0f, 0.0f);
            glTexCoord2f(1.0, 0.0);glColor4f(1.0f, 1.0f, 1.0f, 1.0f);glVertex2f(10.5f, 0.0f);
            glTexCoord2f(1.0, 1.0);glColor4f(1.0f, 1.0f, 1.0f, 1.0f);glVertex2f(10.5f, 10.5f);
			glTexCoord2f(0.0, 1.0);glColor4f(1.0f, 1.0f, 1.0f, 1.0f);glVertex2f(0.0f, 10.5f);
            glEnd ();

            SwapBuffers (hDC);

            Sleep (1);
        }
    }

    /* shutdown OpenGL */
    DisableOpenGL (hWnd, hDC, hRC);

    /* destroy the window explicitly */
    DestroyWindow (hWnd);

    return msg.wParam;
}

LRESULT CALLBACK WndProc (HWND hWnd, UINT message,
                          WPARAM wParam, LPARAM lParam)
{

    switch (message)
    {
    case WM_CREATE:
        return 0;
    case WM_CLOSE:
        PostQuitMessage (0);
        return 0;

    case WM_DESTROY:
        return 0;

    case WM_KEYDOWN:
        switch (wParam)
        {
        case VK_ESCAPE:
            PostQuitMessage(0);
            return 0;
        }
        return 0;

    default:
        return DefWindowProc (hWnd, message, wParam, lParam);
    }
}

void EnableOpenGL (HWND hWnd, HDC *hDC, HGLRC *hRC)
{
    PIXELFORMATDESCRIPTOR pfd;
    int iFormat;

    /* get the device context (DC) */
    *hDC = GetDC (hWnd);

    /* set the pixel format for the DC */
    ZeroMemory (&pfd, sizeof (pfd));
    pfd.nSize = sizeof (pfd);
    pfd.nVersion = 1;
    pfd.dwFlags = PFD_DRAW_TO_WINDOW | 
      PFD_SUPPORT_OPENGL | PFD_DOUBLEBUFFER;
    pfd.iPixelType = PFD_TYPE_RGBA;
    pfd.cColorBits = 24;
    pfd.cDepthBits = 16;
    pfd.iLayerType = PFD_MAIN_PLANE;
    iFormat = ChoosePixelFormat (*hDC, &pfd);
    SetPixelFormat (*hDC, iFormat, &pfd);

    /* create and enable the render context (RC) */
    *hRC = wglCreateContext( *hDC );
    wglMakeCurrent( *hDC, *hRC );

}

void DisableOpenGL (HWND hWnd, HDC hDC, HGLRC hRC)
{
    wglMakeCurrent (NULL, NULL);
    wglDeleteContext (hRC);
    ReleaseDC (hWnd, hDC);
}

It run expectly if I remove the line:
glViewport(0, 0, 256, 256);
I tried testing the program to use glViewport correctly, but failed...

Share this post


Link to post
Share on other sites
Advertisement
I have tested it for you. I don't know a lot of OGL though...
I change your code:

glOrtho(-0.5, 256-0.5, 256-0.5, -0.5, -1, 1);

to:

glOrtho(-0.5, 256-0.5, -0.5, 256-0.5, -1, 1);

then it display the red rect at lower left of window.(I can't make it at upper left though...)

hope that helpful...

Share this post


Link to post
Share on other sites
Just so you know the 0.5 offset isn't necessary for pixel-perfect graphics in OpenGL.

Share this post


Link to post
Share on other sites
Quote:
Original post by Boder
Just so you know the 0.5 offset isn't necessary for pixel-perfect graphics in OpenGL.

Necessary if you're drawing lines and points, not necessary if you're drawing triangles. The rules which specifies which pixels are drawn are different for point/lines and triangles. One needs the offset, one doesn't. Or rather, it's needed/not needed only if you want to hit a pixel center with integer coordinates.
Quote:
Original post by was2_0
I tried testing the program to use glViewport correctly, but failed...

Becuase the size of the window is not really what you think it is. The size you specify in CreateWindow includes borders and menu bars, so the effective area of you use for OpenGL is smaller than 256x256. Therefore, with a 256x256 viewport, the square you draw is effectively behind the title bar.

Quick solution; let Windows tell you the size of the client area instead of assume it's size.

Add two global variables.

int viewportwidth;
int viewportheight;

Add a WM_SIZE to the message callback. This message holds the actual size of the client area.

case WM_SIZE:
viewportwidth = LOWORD(lParam);
viewportheight = HIWORD(lParam);
return 0;

And make some adjustments to the code just befor the message and rendering loop.

glViewport(0, 0, viewportwidth, viewportheight);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glOrtho(0, viewportwidth, viewportheight, 0, -1, 1);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();

If you want to specify a size of the client area instead of the window itself, check out AdjustWindowRect.

Share this post


Link to post
Share on other sites
Quote:
Original post by Brother Bob
Quote:
Original post by Boder
Just so you know the 0.5 offset isn't necessary for pixel-perfect graphics in OpenGL.

Necessary if you're drawing lines and points, not necessary if you're drawing triangles. The rules which specifies which pixels are drawn are different for point/lines and triangles. One needs the offset, one doesn't. Or rather, it's needed/not needed only if you want to hit a pixel center with integer coordinates.
Quote:
Original post by was2_0
I tried testing the program to use glViewport correctly, but failed...

Becuase the size of the window is not really what you think it is. The size you specify in CreateWindow includes borders and menu bars, so the effective area of you use for OpenGL is smaller than 256x256. Therefore, with a 256x256 viewport, the square you draw is effectively behind the title bar.

Quick solution; let Windows tell you the size of the client area instead of assume it's size.

Add two global variables.

int viewportwidth;
int viewportheight;

Add a WM_SIZE to the message callback. This message holds the actual size of the client area.

case WM_SIZE:
viewportwidth = LOWORD(lParam);
viewportheight = HIWORD(lParam);
return 0;

And make some adjustments to the code just befor the message and rendering loop.

glViewport(0, 0, viewportwidth, viewportheight);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glOrtho(0, viewportwidth, viewportheight, 0, -1, 1);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();

If you want to specify a size of the client area instead of the window itself, check out AdjustWindowRect.

THANKS!!!

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!