📄 tutorial_32.htm
字号:
到 40.0f.我们加距离 最小 10.0f 除以 2. 举个例子,设x变量为 15 ,距离是 -30.0f:</p>
<p>object[num].x=float(rand()%int(-30.0f-10.0f))+((-30.0f-10.0f)/2.0f);
</p>
<p>object[num].x=float(rand()%int(-40.0f)+(-40.0f)/2.0f); </p>
<p>object[num].x=float(15 {assuming 15 was returned))+(-20.0f); </p>
<p>object[num].x=15.0f-20.0f; </p>
<p>object[num].x=-5.0f; </p>
<p>下面设y. 我们想水桶从天上下来. 我人不想穿过云. 所以我们设 y 为 4.5f. 刚在去的下面一点. <br>
</p>
</td><td background="Tutorial_32_files/r.png"><img src="Tutorial_32_files/r.png"></td></tr></tbody></table><table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td><img src="Tutorial_32_files/bl.png" height="28" width="28"></td><td width="100%"><img src="Tutorial_32_files/bc.png" height="28" width="100%"></td><td><img src="Tutorial_32_files/br.png" height="28" width="28"></td></tr></tbody></table>
<font color="#aaffaa" size="3">
<pre>
if (object[num].texid==1) <font color="#ffffaa">// 水桶(Bucket)</font>
{
object[num].dir=3; <font color="#ffffaa">// 下落</font>
object[num].x=float(rand()%int(object[num].distance-10.0f))+((object[num].distance-10.0f)/2.0f);
object[num].y=4.5f; <font color="#ffffaa">// 随机 X, 开始在屏模上方</font>
}
</pre>
</font>
<table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td><img src="Tutorial_32_files/tl.png" height="28" width="28"></td><td width="100%"><img src="Tutorial_32_files/tc.png" height="28" width="100%"></td><td><img src="Tutorial_32_files/tr.png" height="28" width="28"></td></tr></tbody></table><table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td background="Tutorial_32_files/l.png"><img src="Tutorial_32_files/l.png"></td>
<td valign="top" width="100%">我们想靶子从地面突出到天上. 我们检查物体为 (texid 是 2). 若是, 设方向(dir)
是 2 (上). 用精确的数 x 位置.
<p>我们不想target 开始在地上. 设 y 初值为-3.0f (在地下). 然后减一个值从0.0f 到 5 乘当前 level. 靶子不是立即出现.
在高级别是有延时, 通过delay, 靶子将出现在一个在另一个以后, 给你很少时间打到他们. </p>
<p></p></td><td background="Tutorial_32_files/r.png"><img src="Tutorial_32_files/r.png"></td></tr></tbody></table><table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td><img src="Tutorial_32_files/bl.png" height="28" width="28"></td><td width="100%"><img src="Tutorial_32_files/bc.png" height="28" width="100%"></td><td><img src="Tutorial_32_files/br.png" height="28" width="28"></td></tr></tbody></table>
<font color="#aaffaa" size="3">
<pre> if (object[num].texid==2) <font color="#ffffaa">// 靶子</font>
{
object[num].dir=2; <font color="#ffffaa">// 开始向上飞</font>
object[num].x=float(rand()%int(object[num].distance-10.0f))+((object[num].distance-10.0f)/2.0f);
object[num].y=-3.0f-float(rand()%(5*level)); <font color="#ffffaa">// 随机 X, 开始在下面的大地 + 随机变量</font>
}
</pre>
</font>
<table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td><img src="Tutorial_32_files/tl.png" height="28" width="28"></td><td width="100%"><img src="Tutorial_32_files/tc.png" height="28" width="100%"></td><td><img src="Tutorial_32_files/tr.png" height="28" width="28"></td></tr></tbody></table><table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td background="Tutorial_32_files/l.png"><img src="Tutorial_32_files/l.png"></td>
<td valign="top" width="100%">所有其它的物体从右到左旅行, 因而不必给任何变量付值来改变物体. 它们应该刚好工作在所给的随机变量.
<p>现在来点有趣的材料! "为了alpha 混合技术正常的工作, 透明的原物必须不断地排定在从后向前画". 当画alpha
混合物体是, 在远处的物体是先画的,这是非常重要的, 下面画紧临的上面的物体. </p>
<p>理由是简单的... Z 缓冲区防止 OpenGL 从已画好的混合东西再画象素. 这就是为什么会发生物体画在透明混合之后而不再显示出来. 为什么你最后看到的是一个四边形与物体重叠...
很不好看! </p>
<p>我们已知道每个物体的深度. 因而在初始化一个物体之后, 我们能通过把物体排序,而用qsort 函数(快速排序sort),来解决这个问题 .
通过物体排序, 我们能确信第一个画的是最远的物体. 这意味着当我们画物体时, 起始于第一个物体, 物体通过用距离将被先画. 紧挨着那个物体(晚一会儿画)
将看到先前的物体在他们的后面, 再将适度的混合! </p>
<p>这文中的这行线注释是我在 MSDN 里发现这些代码,在网上花时间查找之后找到的解答 . 他们工作的很好,允许各种的排序结构. qsort
传送 4 个参数. 第一个参数指向物体数组 (被排序的数组d). 第二个参数是我们想排序数组的个数... 当然,我们想所有的排序的物体普遍的被显示(各个level).
第三个参数规定物体结构的大不, 第四个参数指向我们的 Compare() 函数. </p>
<p>大概有更好的排序结构的方法, 但是 qsort() 工作起来... 快速方便,简单易用! </p>
<p>这个是重要的知识点, 若你们想用 glAlphaFunc() 和 glEnable(GL_ALPHA_TEST), 排序是没必要的. 然而,
用Alpha 功能你被限制在完全透明或完全白底混合, 没有中间值. 用 Blendfunc()排序用一些更多的工作,但他顾及半透明物体. <br>
</p>
</td><td background="Tutorial_32_files/r.png"><img src="Tutorial_32_files/r.png"></td></tr></tbody></table><table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td><img src="Tutorial_32_files/bl.png" height="28" width="28"></td><td width="100%"><img src="Tutorial_32_files/bc.png" height="28" width="100%"></td><td><img src="Tutorial_32_files/br.png" height="28" width="28"></td></tr></tbody></table>
<font color="#aaffaa" size="3">
<pre><font color="#ffffaa">// 排序物体从距离:我们物体数组的开始地址 *** MSDN 代码修改为这个 TUT ***<br>// 各种的数按<br>// 各自的要素的<br>// 指针比较的函数</font>
qsort((void *) &object, level, sizeof(struct objects), (compfn)Compare );
}
</pre>
</font>
<table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td><img src="Tutorial_32_files/tl.png" height="28" width="28"></td><td width="100%"><img src="Tutorial_32_files/tc.png" height="28" width="100%"></td><td><img src="Tutorial_32_files/tr.png" height="28" width="28"></td></tr></tbody></table><table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td background="Tutorial_32_files/l.png"><img src="Tutorial_32_files/l.png"></td>
<td valign="top" width="100%">初始化的代码总是一样的. 首先的现两行取得我们window 的消息和我们建盘消息. 然后我们用
srand() 建一个基于时间的多样化的游戏. 之后我们调入 TGA 图片并用LoadTGA()转换到材质 . 先前的 5个图片是将穿过屏幕的物体.
Explode 是我们爆炸动画, 大地和天空 弥补现场背景, crosshair是你在屏幕上看到表现鼠标当前位置的十字光标, 最后, 用来显示分数,标题和士气值的字体的图片.
若任何调入图片的失误,则到返回 FALSE 值, 并程序结束. 值得注意的是这些基本代码不是返回整数型(INIT)的 FAILED 错误消息.
<br></td><td background="Tutorial_32_files/r.png"><img src="Tutorial_32_files/r.png"></td></tr></tbody></table><table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td><img src="Tutorial_32_files/bl.png" height="28" width="28"></td><td width="100%"><img src="Tutorial_32_files/bc.png" height="28" width="100%"></td><td><img src="Tutorial_32_files/br.png" height="28" width="28"></td></tr></tbody></table>
<font color="#aaffaa" size="3">
</font><pre><font color="#aaffaa" size="3">BOOL Initialize (GL_Window* window, Keys* keys) <font color="#ffffaa">// 任何 OpenGL 从这初始化</font>
{
g_window = window;
g_keys = keys;
srand( (unsigned)time( NULL ) ); <font color="#ffffaa">// 使随机化事件</font>
if ((!LoadTGA(&textures[0],"Data/BlueFace.tga")) || <font color="#ffffaa">// 调入蓝面材质</font>
(!LoadTGA(&textures[1],"Data/Bucket.tga")) || <font color="#ffffaa">// 调入水桶材质</font>
(!LoadTGA(&textures[2],"Data/Target.tga")) || <font color="#ffffaa">// 调入靶子材质</font>
(!LoadTGA(&textures[3],"Data/Coke.tga")) || <font color="#ffffaa">// 调入 可乐材质</font>
(!LoadTGA(&textures[4],"Data/Vase.tga")) || <font color="#ffffaa">// 调入 花瓶 材质</font>
(!LoadTGA(&textures[5],"Data/Explode.tga")) || <font color="#ffffaa">// 调入 爆炸材质</font>
(!LoadTGA(&textures[6],"Data/Ground.tga")) || <font color="#ffffaa">// 调入 地面 材质</font>
(!LoadTGA(&textures[7],"Data/Sky.tga")) || <font color="#ffffaa">// 调入 天空 材质</font>
(!LoadTGA(&textures[8],"Data/Crosshair.tga")) || <font color="#ffffaa">// 调入 十字光标 材质</font>
(!LoadTGA(&textures[9],"Data/Font.tga"))) <font color="#ffffaa">// 调入 字符 材质</font>
{
return FALSE; <font color="#ffffaa">// 若调入失败, 返回错误</font>
}
</font></pre>
<table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td><img src="Tutorial_32_files/tl.png" height="28" width="28"></td><td width="100%"><img src="Tutorial_32_files/tc.png" height="28" width="100%"></td><td><img src="Tutorial_32_files/tr.png" height="28" width="28"></td></tr></tbody></table><table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td background="Tutorial_32_files/l.png"><img src="Tutorial_32_files/l.png"></td>
<td valign="top" width="100%">若所有图片调入成功则轮到材质, 我们能继续初始化. 字体材质被调入, 因而保险能建立我们的字体.
我们跳入BuildFont()来做这些.
<p>然后我们设置OpenGL. 背景色为黑, alpha 也设为0.0f. 深度缓冲区设为激活小于或等于测试. </p>
<p>glBlendFunc() 是很重要的一行代码. 我们设混合函数(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA).
这些加上alpha变量的屏幕上的混合物体存在物体的材质. 在设置混合模式之后, 我们激活blending(混合). 然后我们打开 2D 材质贴图,
最后,打开 GL_CULL_FACE. 这是去除每个物体的后面( 没有一点浪费在一些我们看不到的循环 ). 画一些四边形逆时针卷动 ,因而精致而适当的面片.
</p>
<p>早先的教程我谈论使用glAlphaFunc()代替alpha 混合. 若你想用Alpha 函数, 注释出的两行混合代码和不注释的两行在glEnable(GL_BLEND)之下.
你也能注释出qsort()函数在 InitObject() 部分里的代码. </p>
<p>程序应该运行ok,但sky 材质将不在这. 因为sky的材质已是一个alpha 变量0.5f. 当早在我说关于Alpha函数, 我提及它只工作在alpha
变量0 或 1. 若你想它出现,你将不得不修改sky的材质alpha 通道! 再则, 若你决定用Alpha 函数代替, 你不得排序物体.两个方法都有好处!
再下而是从SGI 网站的快速引用: </p>
<p>"alpha 函数丢弃细节,代替画他们在结构缓冲器里. 因此排序原来的物体不是必须的 (除了一些其它像混合alpha模式是打开的).
不占优势的是象素必须完全白底或完全透明". </p>
<p><br>
</p></td><td background="Tutorial_32_files/r.png"><img src="Tutorial_32_files/r.png"></td></tr></tbody></table><table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td><img src="Tutorial_32_files/bl.png" height="28" width="28"></td><td width="100%"><img src="Tutorial_32_files/bc.png" height="28" width="100%"></td><td><img src="Tutorial_32_files/br.png" height="28" width="28"></td></tr></tbody></table>
<font color="#aaffaa" size="3">
</font><pre><font color="#aaffaa" size="3"> BuildFont(); <font color="#ffffaa">// 建立我们的字体显示列表</font>
glClearColor(0.0f, 0.0f, 0.0f, 0.0f); <font color="#ffffaa">// 黑色背景</font>
glClearDepth(1.0f); <font color="#ffffaa">// 安装深度缓冲器</font>
glDepthFunc(GL_LEQUAL); <font color="#ffffaa">// 深度的类型测试</font>
glEnable(GL_DEPTH_TEST); <font color="#ffffaa">// 打开深度测试</font>
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); <font color="#ffffaa"> // 打开 Alpha 混合</font>
glEnable(GL_BLEND); <font color="#ffffaa">// 打开混合</font>
glAlphaFunc(GL_GREATER,0.1f); <font color="#ffffaa">// 设 Alpha 测试</font>
glEnable(GL_ALPHA_TEST); <font color="#ffffaa">// 打开 Alpha 测试</font>
glEnable(GL_TEXTURE_2D); <font color="#ffffaa">// 打开材质贴图</font>
glEnable(GL_CULL_FACE); <font color="#ffffaa">// 去掉画物体的背面</font>
</font></pre>
<table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td><img src="Tutorial_32_files/tl.png" height="28" width="28"></td><td width="100%"><img src="Tutorial_32_files/tc.png" height="28" width="100%"></td><td><img src="Tutorial_32_files/tr.png" height="28" width="28"></td></tr></tbody></table><table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td background="Tutorial_32_files/l.png"><img src="Tutorial_32_files/l.png"></td>
<td valign="top" width="100%">在程序的这段, 还没有物体被定义,所以循环30个物体,每个物体都调InitObject().</td>
<td background="Tutorial_32_files/r.png"><img src="Tutorial_32_files/r.png"></td></tr></tbody></table><table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td><img src="Tutorial_32_files/bl.png" height="28" width="28"></td><td width="100%"><img src="Tutorial_32_files/bc.png" height="28" width="100%"></td><td><img src="Tutorial_32_files/br.png" height="28" width="28"></td></tr></tbody></table>
<font color="#aaffaa" size="3">
<pre> for (int loop=0; loop<30; loop++) <font color="#ffffaa">// 循环在 30 个物体Objects</font>
InitObject(loop); <font color="#ffffaa">// 初始化每个物体</font>
return TRUE; <font color="#ffffaa">// 返回正确 (设初值成功)</font>
}
</pre>
</font>
<table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td><img src="Tutorial_32_files/tl.png" height="28" width="28"></td><td width="100%"><img src="Tutorial_32_files/tc.png" height="28" width="100%"></td><td><img src="Tutorial_32_files/tr.png" height="28" width="28"></td></tr></tbody></table><table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td background="Tutorial_32_files/l.png"><img src="Tutorial_32_files/l.png"></td>
<td valign="top" width="100%">在初始化代码里, 调入BuildFont() 建立95 的显示列表. 所以这里在程序结束前删掉95显示列表</td>
<td background="Tutorial_32_files/r.png"><img src="Tutorial_32_files/r.png"></td></tr></tbody></table><table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td><img src="Tutorial_32_files/bl.png" height="28" width="28"></td><td width="100%"><img src="Tutorial_32_files/bc.png" height="28" width="100%"></td><td><img src="Tutorial_32_files/br.png" height="28" width="28"></td></tr></tbody></table>
<font color="#aaffaa" size="3">
<pre>void Deinitialize (void) <font color="#ffffaa">// 任何user 结束初始化从这</font>
{
glDeleteLists(base,95); <font color="#ffffaa">// 删掉所有95 字体显示列表</font>
}
</pre>
</font>
<table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td><img src="Tutorial_32_files/tl.png" height="28" width="28"></td><td width="100%"><img src="Tutorial_32_files/tc.png" height="28" width="100%"></td><td><img src="Tutorial_32_files/tr.png" height="28" width="28"></td></tr></tbody></table><table border="0" cellpadding="0" cellspacing="0" width="100%"><tbody><tr><td background="Tutorial_32_files/l.png"><img src="Tutorial_32_files/l.png"></td>
<td valign="top" width="100%">现在为急速原始物体... 是实际被选?形锾宓拇
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -