|
|
发表于 2004-11-20 23:01:00
|
显示全部楼层
Re: OpenGL只给我们提供了大炮而没有给我们提供苍蝇拍?
以下是一个2D示例,OpenGL下的2D功能一点不比3D的差.只是人们用2D用得少.以下是 一个示例.
#include <math.h>
HGLRC hRC;
HDC hDC;
//回调函数
LRESULT CALLBACK WndProc(HWND,UINT,WPARAM ,LPARAM);
//设置视见区大小
void SceneResizeViewport(GLsizei w,GLsizei h)
{
if(h==0)
h=1;
//设置视见区
glViewport(0,0,w,h);
//重置投影矩阵
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
//设置修剪范围
glOrtho(0,w,h,0,0,1);
//重置模形矩阵
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
}
//把绘制信息全放到一个函数里进行
//#define GL_PI 3.1415f
void Draw()
{
glPushMatrix();
glBegin(GL_TRIANGLES);
glVertex2f(25.0f,0.0f);
glVertex2f(0.0f ,25.0f);
glVertex2f(50.0f,25.0f);
glEnd();
glPopMatrix();
}
//在这里进行渲染
void SceneShow()
{
//清除缓冲区及深度缓冲区
glClear(GL_COLOR_BUFFER_BIT );
//重置所有的矩阵
glLoadIdentity();
//以下绘制开始
Draw();
//交换缓冲区,显示
SwapBuffers(hDC);
}
//初始化OpenGL
void InitOpenGL(HWND hWnd)
{
PIXELFORMATDESCRIPTOR pfd;
int iFormat;
//从窗口句柄取得设备句柄
hDC=GetDC(hWnd);
//以下设置像素格式
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 = 16;
pfd.cDepthBits = 16;
pfd.iLayerType = PFD_MAIN_PLANE;
//设置像素格式
iFormat=ChoosePixelFormat(hDC,&pfd);
SetPixelFormat(hDC,iFormat,&pfd);
//创建渲染场景
hRC=wglCreateContext(hDC);
//设置为当前渲染场景
wglMakeCurrent(hDC,hRC);
glShadeModel(GL_SMOOTH); //允许平滑着色
glClearColor(0.0f,0.0f,0.0f,1.0f); //设置清屏颜色
//下面的代码没有确切的意思.是为了程序在运行初始能够显示而设立的
RECT rect;
int sw,sh;
GetClientRect(hWnd,&rect);
sw=rect.right-rect.left;
sh=rect.bottom-rect.top;
if(sw > 0 && sh >0 )
{
SceneResizeViewport(sw,sh);
}
}
//释放OpenGL和窗体对象
void ReleaseOpenGL(HWND hWnd)
{
wglMakeCurrent(NULL,NULL);
wglDeleteContext(hRC);
ReleaseDC(hWnd,hDC);
}
//更改分辩率
bool ChangeResolution(int w,int h,int bitdepth,int fre)
{
DEVMODE devMode;
int modeSwitch;
int closeMode=0;
//枚举
EnumDisplaySettings(NULL,closeMode,&devMode);
//设置为当前所请求的
devMode.dmBitsPerPel=bitdepth;
devMode.dmPelsHeight=h;
devMode.dmPelsWidth =w;
devMode.dmDisplayFrequency=fre;
devMode.dmFields=DM_BITSPERPEL | DM_PELSWIDTH |DM_PELSHEIGHT|DM_DISPLAYFREQUENCY;
//更改
modeSwitch=ChangeDisplaySettings(&devMode,CDS_FULLSCREEN);
if(modeSwitch==DISP_CHANGE_SUCCESSFUL)
{
return true;
}
else
{
return false;
}
}
LRESULT CALLBACK WndProc(HWND hWnd,UINT message,WPARAM wParam,LPARAM lParam)
{
RECT rect;
int sw,sh;
switch(message)
{
case WM_SIZE:
GetClientRect(hWnd,&rect);
sw=rect.right-rect.left;
sh=rect.bottom-rect.top;
if(sw > 0 && sh >0 )
{
SceneResizeViewport(sw,sh);
}
return 0;
case WM_CLOSE:
PostQuitMessage(0);
return 0;
case WM_KEYDOWN:
switch(wParam)
{
case VK_ESCAPE:
PostMessage(hWnd,WM_CLOSE,0,0);
break;
}
return 0;
}
return DefWindowProc(hWnd,message,wParam,lParam);
}
//创建一个窗口供OpenGL使用.
//窗口标题,程序实例句柄,窗口宽,高,颜色位,是否全屏
HWND CreateOpenGL(char*title,HINSTANCE hInst,int sw,int sh,int bit,bool fullscreen)
{
HWND hWnd;
WNDCLASS wc;
wc.style = CS_OWNDC;
wc.lpfnWndProc = WndProc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = hInst;
wc.hIcon = LoadIcon(NULL,IDI_APPLICATION);
wc.hCursor = LoadCursor(NULL,IDC_ARROW);
wc.hbrBackground = (HBRUSH)GetStockObject(BLACK_BRUSH);
wc.lpszMenuName = NULL;
wc.lpszClassName = "OpenGL框架程序";
//注册窗口类
RegisterClass(&wc);
//全屏模式开
if(fullscreen)
{
//创建窗口
hWnd=CreateWindow("OpenGL框架程序",title,WS_POPUP | WS_CLIPSIBLINGS | WS_VISIBLE,
0,0,sw,sh,NULL,NULL,hInst,NULL);
}
else
{
//让窗口保持在屏幕的正中间,计算左起,和上起 坐标
int t,l;
l=(GetSystemMetrics(SM_CXSCREEN)-sw)/2;
t=(GetSystemMetrics(SM_CYSCREEN)-sh)/2;
hWnd=CreateWindow("OpenGL框架程序",title,WS_VISIBLE|WS_THICKFRAME|WS_SYSMENU|WS_MINIMIZEBOX,
l,t,sw,sh,NULL,NULL,hInst,NULL);
}
//显示窗口
ShowWindow(hWnd,SW_SHOW);
//更新
UpdateWindow(hWnd);
if(fullscreen)
{
//更改分辩率
ChangeResolution(sw,sh,bit,75);
//隐藏鼠标
ShowCursor(false);
}
//返回窗口句柄
return hWnd;
}
//入口函数
int WINAPI WinMain(HINSTANCE hInst,HINSTANCE,LPSTR,int)
{
MSG msg;
HWND hWnd;
bool fullscreen=false;
//创建窗口
hWnd=CreateOpenGL("OpenGL 2D",hInst,800,600,16,fullscreen);
//初始化OpenGL设置
InitOpenGL(hWnd);
//进入循环
while(1)
{
if(PeekMessage(&msg,NULL,0,0,PM_REMOVE))
{
if(msg.message==WM_QUIT)
{
break;
}
else
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
else
{
SceneShow();
}
}
ReleaseOpenGL(hWnd);
DestroyWindow(hWnd);
return 0;
}
|
|