Cpper
C/C++高级工程师 Android高级软件工程师 IT集成工程师 音频工程师 熟悉c,c++,java,c#,py,js,asp等多种语言 程序猿

初步做完粒子系统想着如何从脚本中载入数据,配送方法这样不是很好
脚本我打算首先支持lua和天使脚本等引擎成熟了再支持python

首先来看使用lua语言改写上篇的粒子系统代码.
(不过鄙人的lua,python都很菜的,其原因就是一直没有练习的机会)
对于Lua,其扩展有luabind,tolua++,luaplus,前2着都与boost有关
所以就使用luaplus,简单些
开始了先上lua脚本代码(我把lua当成了c++,开始书写很不习惯,居然不知道lua中的逻辑符号是not and or 而非 !&& || 呵呵)

  1 
  2 -- 这是盖莫引擎中使用lua脚本的测试粒子 
  3 
  4 -- 定义粒子池粒子个数
  5 max_particles = 2400
  6 
  7 -- 定义粒子初始位置
  8 particle_pos_x = 0.0
  9 particle_pos_y = 0.0
 10 particle_pos_z = 3.0
 11 
 12 -- 定义重力加速度
 13 gravity = 9.8
 14 
 15 -- 定义粒子大小
 16 particle_size = 0.8
 17 
 18 -- 定义粒子寿命
 19 particle_life = 8.2
 20 
 21 -- 定义批处理粒子个数
 22 batch_particles = 80
 23 
 24 -- 定义粒子和地面之间的摩擦力
 25 friction = 0.75
 26 
 27 -- 定义粒子系统发射半径
 28 fountain_radius = 1.6
 29 
 30 -- 定义粒子范围半径
 31 particle_r = (fountain_radius + particle_size/2)*(fountain_radius + particle_size/2)
 32 
 33 -- 初始化随机种子
 34 function InitRand()
 35    math.randomseed(os.time());
 36 end
 37    
 38 -- 初始化粒子颜色red,green,blue
 39 function InitColorRed(t)
 40     return 0.7 + 0.3 * math.sin(0.34*+ 0.1);
 41 end
 42 function InitColorGreen(t)
 43     return 0.6 + 0.4 * math.sin(0.63*+ 1.1);
 44 end
 45 function InitColorBlue(t)
 46     return 0.6 + 0.4 * math.sin(0.91*+ 2.1);
 47 end
 48 
 49 -- 定义粒子速度
 50 particle_vel = 8.0
 51 
 52 -- 获取时间对应的速度值
 53 function GetVelByTime(t)
 54     return particle_vel*(0.8 + 0.1*(math.sin(0.5*t)+math.sin(0.31*t)));
 55 end
 56 
 57 -- 获取粒子初始速度
 58 function InitZVel()
 59     return 0.7 + (0.3/4096.0* (math.random(1,4095));
 60 end
 61     
 62 -- 获取xy平面随机转角
 63 function GetRandRotXY()
 64     return (2.0*3.14159265/4096.0* math.random(1,4095)
 65 end    
 66 
 67 -- 获取粒子随机速度x分量
 68 function InitXVel(t)
 69    xy_angle = GetRandRotXY();
 70    vt = GetVelByTime(t);
 71    return 0.45 * math.cos(xy_angle)*vt;
 72 end
 73 
 74 -- 获取粒子随机速度y分量
 75 function InitYVel(t)
 76    xy_angle = GetRandRotXY();
 77    vt = GetVelByTime(t);
 78    return 0.45 * math.sin(xy_angle)*vt;
 79 end
 80 
 81 -- 定义更新粒子后的全局变量
 82 new_life = 0;
 83 new_xpos = 0;
 84 new_ypos = 0;
 85 new_zpos = 0;
 86 new_xvel = 1;
 87 new_yvel = 1;
 88 new_zvel = 1;
 89  
 90 -- 更新粒子状态
 91 function UpdateParticles(life,xpos,ypos,zpos,xvel,yvel,zvel,dt)
 92     -- 修正粒子生命 
 93     new_life = life - dt * (1.0 / particle_life);
 94     -- 修正粒子速度 
 95     new_zvel = zvel - gravity  *dt;
 96     new_xpos = xpos + xvel*dt;
 97     new_ypos = ypos + yvel*dt;
 98     new_zpos = zpos + new_zvel*dt;  
 99     if new_zvel < 0.0 then
100         if new_xpos*new_xpos + new_ypos*new_ypos < particle_r and new_zpos < particle_pos_z + particle_size/2 then
101             new_zvel = -friction * new_zvel;
102             new_zpos  = particle_pos_z + particle_size/2 + friction * (particle_pos_z + particle_size/2 - new_zpos);
103         -- 当粒子碰撞到地面应该跳起来 
104         elseif new_zpos < particle_size/2 then
105            new_zvel = -friction * new_zvel;
106            new_zpos  = particle_size/2 + friction * (particle_size/2 - new_zpos);
107         end
108     end         
109 end

cppblog居然没有lua的代码高亮...

然后其关联的c++代码如下:
  1 
  2 #include <GEngine/Main.hpp>
  3 #include <luaplus/luaplus.h>
  4 
  5 #define WIN_WIDTH  640
  6 #define WIN_HEIGHT 480
  7 
  8 //! 粒子纹理 
  9 static const unsigned char particle_texture[] = 
 10 {
 11     0x000x000x000x000x000x000x000x00,
 12     0x000x000x110x220x220x110x000x00,
 13     0x000x110x330x880x770x330x110x00,
 14     0x000x220x880xff0xee0x770x220x00,
 15     0x000x220x770xee0xff0x880x220x00,
 16     0x000x110x330x770x880x330x110x00,
 17     0x000x000x110x330x220x110x000x00,
 18     0x000x000x000x000x000x000x000x00
 19 };
 20  
 21 //! 粒子纹理大小  
 22 #define P_TEX_WIDTH  8    
 23 #define P_TEX_HEIGHT 8
 24  
 25 ////////////////////////////////////////////////////////////
 26 /// 给出一个初始化粒子的方法 
 27 ////////////////////////////////////////////////////////////
 28 void G_CALL InitParticle(core::Particle* p,float t);
 29 
 30 ////////////////////////////////////////////////////////////
 31 /// 更新粒子函数 
 32 ////////////////////////////////////////////////////////////
 33 void G_CALL UpdateParticle(core::Particle* p,float time);
 34 
 35 ////////////////////////////////////////////////////////////
 36 /// 场景旋转和偏移 
 37 //////////////////////////////////////////////////////////// 
 38 float TransForm(double t);
 39  
 40 ////////////////////////////////////////////////////////////
 41 /// 构造纹理 
 42 ////////////////////////////////////////////////////////////  
 43 void BuildTexture(GLuint& texture_id);
 44 
 45 ////////////////////////////////////////////////////////////
 46 /// 渲染场景 
 47 //////////////////////////////////////////////////////////// 
 48 void RenderScene(); 
 49 
 50 core::Device* device = NULL; 
 51 libmath::TriTable* table = NULL;  
 52 
 53 LuaPlus::LuaStateOwner *state = NULL; 
 54   
 55 ////////////////////////////////////////////////////////////
 56 /// 初始化luaplus  
 57 ////////////////////////////////////////////////////////////     
 58 void InitLua(const char* lua)
 59 {    
 60     state = new  LuaPlus::LuaStateOwner;
 61     // 载入Lua脚本
 62     (*state)->DoFile(lua);  
 63     LuaPlus::LuaFunction<void> initrand(*state,"InitRand");
 64     initrand();  
 65 }  
 66 
 67 void DeinitLua()
 68 {
 69     delete state; 
 70 
 71 
 72 ////////////////////////////////////////////////////////////
 73 /// 从脚本载入粒子描述数据 
 74 //////////////////////////////////////////////////////////// 
 75 void LoadData(core::ParticleSystemDesc &desc); 
 76  
 77 int main(int argc, char **argv)
 78 {
 79     InitLua("particle.lua");
 80     int        i;
 81     double     t0, t;
 82     
 83     core::VideoMode mode;
 84     mode.width = WIN_WIDTH;
 85     mode.height = WIN_HEIGHT; 
 86     
 87     device = core::InitDevice("盖莫引擎粒子系统",false,mode); 
 88     table = device->GetTriTable();
 89  
 90     core::ParticleSystemDesc desc;
 91     
 92     GLuint texture_id;
 93     BuildTexture(texture_id);
 94     desc.texture_id = texture_id;    
 95     desc.init_fn = &InitParticle;
 96     desc.update_fn = &UpdateParticle;
 97     LoadData(desc);
 98     core::ParticleSystem* ps = device->GetParticleSystem(desc); 
 99  
100     t0 = device->GetTime();
101     BEGIN_LOOP(device)
102         t = device->GetTime() - t0;
103         RenderScene();
104         float dt = TransForm(t);
105         ps->Render(); 
106     END_LOOP(device)
107     
108     device->Close();
109     device->Drop();
110     
111     DeinitLua();
112     return 0;
113 }
114  
115 void BuildTexture(GLuint& texture_id)
116 {
117     glGenTextures( 1&texture_id );
118     glBindTexture( GL_TEXTURE_2D, texture_id);
119     glPixelStorei( GL_UNPACK_ALIGNMENT, 1 );
120     glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP );
121     glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP );
122     glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR );
123     glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR );
124     glTexImage2D(GL_TEXTURE_2D, 0, GL_LUMINANCE, P_TEX_WIDTH, P_TEX_HEIGHT,
125                  0, GL_LUMINANCE, GL_UNSIGNED_BYTE, particle_texture);  
126 }
127 
128 ////////////////////////////////////////////////////////////
129 /// 场景旋转和偏移 
130 //////////////////////////////////////////////////////////// 
131 float TransForm(double t)
132 {
133     double xpos, ypos, zpos, angle_x, angle_y, angle_z;
134     static double t_old = 0.0;
135     float  dt = (float)(t-t_old);
136     t_old = t;
137  
138     angle_x = 90.0 - 10.0;
139     angle_y = 10.0 * sin( 0.3 * t );
140     angle_z = 10.0 * t;
141     glRotated( -angle_x, 1.00.00.0 );
142     glRotated( -angle_y, 0.01.00.0 );
143     glRotated( -angle_z, 0.00.01.0 );
144  
145     xpos =  15.0 * sin( (M_PI/180.0* angle_z ) +
146              2.0 * sin( (M_PI/180.0* 3.1 * t );
147     ypos = -15.0 * cos( (M_PI/180.0* angle_z ) +
148              2.0 * cos( (M_PI/180.0* 2.9 * t );
149     zpos = 4.0 + 2.0 * cos( (M_PI/180.0* 4.9 * t );
150     glTranslated( -xpos, -ypos, -zpos );
151     return dt; 
152 }
153 
154 void RenderScene()
155 {
156     glViewport( 00, WIN_WIDTH,WIN_HEIGHT);
157     glClearColor( 0.1f0.1f0.1f1.0f );
158     glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT );
159     glMatrixMode( GL_PROJECTION );
160     glLoadIdentity();
161     gluPerspective(65.0640.0/480.01.060.0 );
162     glMatrixMode( GL_MODELVIEW );
163     glLoadIdentity();
164 }
165 
166 ////////////////////////////////////////////////////////////
167 /// 给出一个初始化粒子的方法(t为粒子系统启动时间(单位:秒)) 
168 ////////////////////////////////////////////////////////////
169 void G_CALL InitParticle(core::Particle* p,float t)
170 {
171     //! 初始化粒子位置位置
172     float xpos = (*state)->GetGlobal("particle_pos_x").GetFloat(); 
173     float ypos = (*state)->GetGlobal("particle_pos_y").GetFloat(); 
174     float zpos = (*state)->GetGlobal("particle_pos_z").GetFloat();
175     p->position = Vector3f(xpos,ypos,zpos); 
176     
177     //! 初始化粒子颜色 
178     LuaPlus::LuaFunction<float> red(*state,"InitColorRed");
179     LuaPlus::LuaFunction<float> green(*state,"InitColorGreen");
180     LuaPlus::LuaFunction<float> blue(*state,"InitColorBlue");
181     p->color.red = red(t);
182     p->color.green = green(t);
183     p->color.blue = blue(t);
184     
185     //! 初始化粒子初始速度 
186     LuaPlus::LuaFunction<float> xvel(*state,"InitXVel");
187     LuaPlus::LuaFunction<float> yvel(*state,"InitYVel"); 
188     LuaPlus::LuaFunction<float> zvel(*state,"InitZVel");    
189     p->velocity = Vector3f(xvel(t),yvel(t),zvel(t));
190 }
191 
192 ////////////////////////////////////////////////////////////
193 /// 更新粒子函数 
194 ////////////////////////////////////////////////////////////
195 void G_CALL UpdateParticle(core::Particle* p,float time)
196 {
197     LuaPlus::LuaFunction<void> update_fn(*state,"UpdateParticles");  
198     float life = p->life;
199     float xpos = p->position.x;
200     float ypos = p->position.y;
201     float zpos = p->position.z;
202     float xvel = p->velocity.x;
203     float yvel = p->velocity.y;
204     float zvel = p->velocity.z;
205     update_fn(life,xpos,ypos,zpos,xvel,yvel,zvel,time); 
206     
207     //! 获取粒子的更新后数据 
208     p->life = (*state)->GetGlobal("new_life").GetFloat();  
209     p->position.x = (*state)->GetGlobal("new_xpos").GetFloat(); 
210     p->position.y = (*state)->GetGlobal("new_ypos").GetFloat(); 
211     p->position.z = (*state)->GetGlobal("new_zpos").GetFloat(); 
212     p->velocity.x = xvel; 
213     p->velocity.y = yvel;  
214     p->velocity.z = (*state)->GetGlobal("new_zvel").GetFloat();  
215 
216 
217 ////////////////////////////////////////////////////////////
218 /// 从脚本载入粒子描述数据 
219 //////////////////////////////////////////////////////////// 
220 void LoadData(core::ParticleSystemDesc &desc)
221 {
222     desc.batch_particles = (*state)->GetGlobal("batch_particles").GetInteger();
223     desc.particle_size = (*state)->GetGlobal("particle_size").GetFloat(); 
224     desc.life_span = (*state)->GetGlobal("particle_life").GetFloat(); 
225     int max_particles = (*state)->GetGlobal("max_particles").GetInteger(); 
226     desc.particle_number = max_particles;     
227 }
228 
对应的贴图如下:

不过刚开始做的时候写lua的时候有点问题其结果变成了下图,看来要熟悉Lua只有多多练习啊

那么下一步要做的就是把lua集成进引擎中了
posted on 2010-02-24 19:43 ccsdu2009 阅读(2033) 评论(1)  编辑 收藏 引用 所属分类: Game引擎
Comments

只有注册用户登录后才能发表评论。
【推荐】超50万行VC++源码: 大型组态工控、电力仿真CAD与GIS源码库
网站导航: 博客园   IT新闻   BlogJava   知识库   博问   管理