0
  • 聊天消息
  • 系统消息
  • 评论与回复
登录后你可以
  • 下载海量资料
  • 学习在线课程
  • 观看技术视频
  • 写文章/发帖/加入社区
会员中心
创作中心

完善资料让更多小伙伴认识你,还能领取20积分哦,立即完善>

3天内不再提示

如何利用Open GL在MFC中实现喷泉模拟应用程序的开发设计

电子设计 来源:微型机与应用 作者:梅章明,张秀山 2020-10-13 10:34 次阅读

由于自然环境中大部分景物(如云彩、火焰、烟雾、瀑布、雪花等特效)具有不规则性、复杂性与随机性,且随着时间变化形状会随之变化,对其进行逼真的实时模拟十分困难,需要大量的计算量和数据量。在虚拟环境中,自然景物的视觉效果直接影响到观察者对周围环境的感知,所以开发一个既能满足逼真度要求,又能实时显示的粒子系统是非常必要的。自从OpenGL公布以来,有关图形学方面的书籍、论文等资料就层出不穷,如何利用Open GL开发出具有一定水平的计算机图形程序就成为众多学者的追求目标。在Visual C++中,既可利用Win32编程,也可利用MFC编程,两者各有特点,本文就如何利用Open GL在MFC中开发出一个简单的喷泉模拟程序作一个简单探讨。

1 OpenGL绘图环境初始化

OpenGL是一个跨平台的三维图形库,可在Windows、Unix和Mac等平台上运行。而Visual C++完善的基本类库MFC和应用向导AppWizard使得开发一个复杂的应用程序变得轻松自如。如果将两者结合,便可开发出较高水平的Windows下三维图形应用程序。

在3D游戏的渲染过程中,传统的建模方法一般只适用于外形比较规则的形体,对于那些像雨、雪、瀑布、喷泉以及火焰等没有固定形状,甚至要随着外部环境或者其他因素的改变而改变的物质建模,传统的方法就显得无能为力了[2]。1983年REEVES W T提出了一种新的建模方法,称为模糊物体建模,该方法就是粒子系统,它的出现正好解决了上述问题。

OpenGL函数库和操作系统无关,它有自己的独特设计,与Windows的图像设备接口GDI模型以及多数MFC应用程序的建立方法不太一致。在Windows系统中,这样的一组函数称为wiggle函数,每个wiggle函数的前缀是“wgl”。

在Win32下,首先必须重新设置画图窗口的像素格式,使其符合OpenGL对像素格式的需要。为此,声明一个PIXELFORMATDESCRIPTOR结构的变量,并适当设置其结构成员的值,使其支持OpenGL及其颜色模式。再以此变量为参数调用ChoosePixelFormat(),分配一个像素格式号,然后调用SetPixelFormat()将其设置为当前像素格式。

完成了像素格式的重新设置后,需要为OpenGL建立绘制描述表(Render Context)。绘制描述表的作用类似于Windows中的设备描述表(Device Context)。只有建立了绘制描述表RC后,OpenGL才能调用绘图原语在窗口中做出图形。Win32API提供了几个操作绘制描述表的函数,包括建立、复制、使用、删除和查询等,它们都以wgl为词头。RC是以线程为单位的,每一个线程必须使用一个RC作为当前RC才能执行OpenGL绘图原语。

wglCreateContext()是建立绘制描述表的函数,它以一个指向GDI设备描述表的句柄为参数,返回一个与此设备描述表相关联的绘制描述表句柄。在以此2句柄为参数调用函数wglMakeCurrent(),使RC成为线程当前使用的RC,完成Windows下OpenGL绘图环境的初始化过程[4]。

2 建立OpenGL单文档应用程序框架

使用Visual C++的AppWizard和Class Wizard可以很容易地生成一个使用MFC的OpenGL单文档应用程序框架,名称为MyFountain。

2.1 PreCreateWindow方法

BOOL CMySDOpenGLView:: PreCreateWindow(CREATESTRUCT& cs)

{

cs.style|=WS_CLIPCHILDREN|WS_CLIPSIBLINGS;

return CView::PreCreateWindow(cs);

}

使视窗口具有WS_CLIPCHILDREN和WS_CLIPSIBLINGS风格,确保成功地设置像素格式。

2.2 添加消息响应函数

利用MFC ClassWizard为CMySDOpenGLView类添加消息WM_CREATE、WM_DESTROY、WM_SIZE和WM_TIMER的响应函数。

首先在OnCreate方法中初始化OpenGL,并设置定时器

然后在OnTimer响应函数中添加定时器响应函数和场景更新命令,使得程序按照定时器设置的时间步长进行中断,并调用OnDraw对场景进行更新、渲染。

第三步,添加OnSize函数对用户进行窗口调整的消息进行响应,并即时调整窗口的大小[5]。

最后,当关闭窗口时,将值NULL(或0)赋值给wglMakeCurrent()的参数hRC后,调用wglDeleteContext()删除绘制描述表,并删除调色板和定时器。

3 基于粒子系统的喷泉模拟

构造可视化系统的建模技术大致可以分为两类:几何建模和行为建模。几何建模处理物体的几何和形状的表示,研究图形数据结构等基本问题;行为建模处理物体运动和行为的描述。

一个粒子系统由大量称为粒子的简单体素构成。每个粒子有一组属性,如位置、速度、颜色和生命期。一个粒子究竟有什么样的属性,主要取决于具体的应用。粒子的初值由随机过程产生。粒子往往由位于空间的某个地方的粒子源产生。

粒子系统也利用了随机过程,并常将物体的几何和行为组合在一个有机模型中。

一个粒子系统是不断进化的。在生命期的每一刻,都要完成以下4步工作:

(1)粒子源产生新粒子。产生任意数目的新粒子,它们的初始属性由随机过程控制。每个粒子都有一个生命期,如果某些粒子不应删除,则可以赋予它无限长的生命期。

(2)更新现有粒子属性。例如,若粒子有位置和速度属性,在模拟重力场中的运动时,可以如下更新粒子的位置和速度属性:

v=v+gts=s+vt

在该步中,粒子的生命期递减一个时间步。

(3)删除“死”粒子。检查粒子的生命期,若为0则将粒子从系统中删除。

(4)绘制粒子。显示粒子系统中所有现存的粒子。

在一般情况下,粒子的几何特征十分简单,可以采用一个像素或小的多边形来代表[6]。

3.1 粒子数据结构的定义

粒子数据结构的定义如下:

struct particle

{

float t; //粒子的生命期

float vel; //粒子运动的速度

float dir; //粒子运动的方向

float x,y,z; //粒子的位置坐标

float xd,zd; //粒子的X和Z方向增加值

char type; //粒子类型(运动或淡化)

float a; //淡化alpha值

struct particle*next,*prev;

};

3.2 绘制喷泉

3.2.1 先构造一个场景

由于重点是喷泉,因此简单构造一个模拟的地面能突出喷泉就可以了。实现代码如下:

glClear(GL_COLOR_BUFFER_BIT);

glLoadIdentity();

glBindTexture(GL_TEXTURE_2D,texture[1]);

a+=0.2;

gluLookAt(cam.x,cam.y,cam.z,0,0,0,upv.x,upv.y, upv.z);

3.2.2 喷泉的渲染处理

喷泉的渲染处理过程主要是利用了OpenGL的特征函数[7]和方法,主要进行了两方面的处理:(1)将喷泉模型渲染成纹理文件[8];(2)采用透明纹理渲染技术[9]。

3.2.3 喷泉的实现

在构造了简单的地面场景后,取以原点为中心的圆周上的均匀点序列作为喷泉的喷射点,按照上述提到的绘制方法[10]即完成了喷泉的动态模拟。喷泉系统模拟的主要关键代码在于向内存中添加渲染粒子,即函数AddParticles(),之后粒子将按照预定的轨道运行,其主要实现代码如下:

//添加新的粒子

void CMyFountainView::AddParticles()

{

struct particle*tempp;

int i, j;

for (j=0;j《18;j++)

for (i=0;i《2;i++)

{

tempp=(struct particle*)malloc(sizeof(struct particle));

if (fn[j])fn[j]-》prev=tempp;

tempp-》next=fn[j];

fn[j]=tempp;

tempp-》t=-9.9; //粒子的生命期

tempp-》v=(float)(rand()%200000)/100000+1;

// 粒子速度

tempp-》d=(float)(rand()%400)/100-2;

//粒子方向

tempp-》x=20*cos((j*3.14159)/180); //开始位置的坐标

tempp-》y=0;

tempp-》z=20*sin((j*3.14159)/180);

tempp-》xd=cos((tempp-》d*3.14159)/180)*tempp-》v/4;

tempp-》zd=sin((tempp-》d*3.14159)/180)*tempp-》v;

tempp-》type=0; //粒子状态为运动

tempp-》a=1; //粒子淡化

}

}

喷泉的效果显示如图1所示。

通过改变程序中alpha(圆的内接正多边形圆心角)的值,可以改变喷泉粒子流的股数。喷泉的粒子流粗细可通过改变矢量的乘积来实现,通过改变“vectl.x*=5;vectl.y*=5;vectl.z*=5;”等式右边的数值可以控制,图1就是改为“5;3;2;”的结果。

通过上述的试验比较可知,喷泉粒子流的股数和每股粒子流的粒子数目都会影响到喷泉模拟效果的真实感[11]。

越来越多的人注意到使用Visual C++和OpenGL开发三维图形动画软件的有利之处,但是有关OpenGL的资料大多都是介绍基本的编程指南或者一些基础的原理或方法,却很少有大型的与应用有关的编程案例,而且有也大多都是基于Win32的类来实现一些简单的图形功能,介绍MFC与OpenGL连接的资料却少之又少,本文主要是在MFC下实现了一个简单的喷泉模拟程序,主要的创新点是分析了MFC下消息响应的内部机制,所以希望本次的探索能对以后利用MFC开发出更高效的程序有所帮助。

责任编辑:gt

声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉
  • 计算机
    +关注

    关注

    19

    文章

    7494

    浏览量

    87950
  • C++
    C++
    +关注

    关注

    22

    文章

    2108

    浏览量

    73649
  • 应用程序
    +关注

    关注

    37

    文章

    3268

    浏览量

    57704
收藏 人收藏

    评论

    相关推荐

    MFC 程序

    处理;消息处理函数,根据消息的类型与各控件的属性,点缀整个窗口;MFC程序设计,为了设计
    发表于 10-11 22:13

    利用Open GLMFC开发出一个简单的喷泉模拟程序探讨

    Open GL开发出具有一定水平的计算机图形程序就成为众多学者的追求目标。Visual C++
    发表于 07-17 07:21

    怎样用vs2008去开发一种MFC应用程序

    怎样用vs2008去开发一种MFC应用程序MFC应用程序有何功能?
    发表于 09-30 06:12

    利用lpc2104开发应用程序时哪几个需要在.c文件实现

    利用 lpc2104 开发应用程序时, Os_call_ARM.s,Os_call.c 两个文件,那几个函数需要在汇编
    发表于 02-24 15:18

    TMS320C6713DSP音乐喷泉控制系统的应用

    TMS320C6713DSP音乐喷泉控制系统的应用 音乐喷泉是现代科技与艺术的综合,利用喷泉
    发表于 10-04 09:43 1510次阅读

    利用OPC实现VC应用程序与PLC的数据交换

    利用OPC实现VC应用程序与PLC的数据交换   VC(Visual  C++)是功能强大的一种Windows应用程序可视化软件开发
    发表于 04-17 18:04 4872次阅读
    <b class='flag-5'>利用</b>OPC<b class='flag-5'>实现</b>VC<b class='flag-5'>应用程序</b>与PLC的数据交换

    利用FTP实现应用程序的远程更新

    FTP (File Transfer Protocol),是用于Internet上的控制文件的双向传输的协议。同时,它也是一个应用程序。本方案主要介绍如何利用网络(以太网、GPRS上网),通过FTP协议来实现
    发表于 06-09 16:08 46次下载

    MFC原理与方法

    )微软基础类就是这样一个由Microsoft公司设计的类库。采用MFC方式编程提高了Windows应用程序开发效率,但由于MFC应用程序
    发表于 04-19 14:52 8次下载

    C语言MFC制作剪刀石头布游戏资料合集应用程序免费下载

    本文档的主要内容详细介绍的是C语言MFC制作剪刀石头布游戏资料合集应用程序免费下载。
    发表于 07-23 08:00 20次下载

    海为PLC音乐喷泉实现喷泉的声、光、水完美控制设计

    音乐喷泉集光、色、音于一身,即根据音乐的特殊要素来控制喷泉水泵的运行和转速变化,结合灯光的变化而形成喷泉,选用海为PLC对喷泉控制系统进行控制,通过
    发表于 08-15 08:46 3409次阅读

    利用USBXpress开发包简化应用程序实现USB通信设计

    的准备工作,USBXpress开发包完全可以实现USB通信的所有功能。本文介绍USB通信开发的全过程,以及开发过程中需要注意的事项。(主要
    的头像 发表于 01-14 08:02 2623次阅读
    <b class='flag-5'>利用</b>USBXpress<b class='flag-5'>开发</b>包简化<b class='flag-5'>应用程序</b><b class='flag-5'>实现</b>USB通信设计

    vc++应用程序和使用vc++设计的MFC计时器和计算机程序免费下载

    本文档的主要内容详细介绍的是vc++应用程序和使用vc++设计的MFC计时器和计算机程序免费下载。
    发表于 12-24 08:00 15次下载
    vc++<b class='flag-5'>应用程序</b>和使用vc++设计的<b class='flag-5'>MFC</b>计时器和计算机<b class='flag-5'>程序</b>免费下载

    Django应用程序开发设计Django模板的方法

    本文中,我将介绍Django应用程序开发设计Django模板的方法。目的是保持Django应用程序
    的头像 发表于 07-29 15:44 1879次阅读

    mfc多线程编程实例

    (图形用户界面)应用程序开发。在这篇文章,我们将重点介绍MFC的多线程编程。 多线程编程
    的头像 发表于 12-01 14:29 1507次阅读

    花样喷泉控制的PLC梯形图实现

    喷泉广泛用于广场、车站、公园等各种公共和休闲娱乐场所。喷泉控制采用PLC,就可以通过改变PLC程序,来改变喷泉的造型及各种不同颜色灯光的
    的头像 发表于 03-15 14:10 2167次阅读
    花样<b class='flag-5'>喷泉</b>控制<b class='flag-5'>中</b>的PLC梯形图<b class='flag-5'>实现</b>