|
|
发表于 2005-7-22 14:37:00
|
显示全部楼层
Re: 菜鸟弱弱的问一下:求飞行射击中子弹连发代码
我用VB.NET做的例子中有关于子弹的代码,可以参考
我发现了一个问题就是你们写游戏是建立在这么一个概念上,就是你们觉得我写一个绘制子弹的函数,然后调用一下,那么子弹就绘制出来了,这一做法有没有错误呢,没有,但是这种观念有没有问题呢,有。
我们把子弹看作一个对象,屏幕上有很多子弹对象,也可能一个也没有。VB里面我们把很多很多子弹对象叫做一个集合。
其实我们在游戏的绘图函数中是循环绘制的,也就是说每隔一段时间就重新绘制一下屏幕上的东西,我看你们常常用到Timer(暂且不说这个有没有问题)。
Private Sub Timer1_Timer()
For Each bulletObj In bulletCollection'遍历子弹集合
bulletObj.Draw '绘制子弹
Next
End Sub
这样大家看,子弹的绘制就解决了,不管有多少子弹或者没有子弹都行,我们现在所要解决的就是发射子弹怎么办?比如按一下空格键,很简单,按一下空格键我们往bulletCollection集合里Add一个新的子弹对象就可以了,这样的话子弹不是越来越多吗?那我们就要判断子弹是不是飞出屏幕或者碰到飞机爆炸了,如果飞出屏幕或者爆炸了,那么我们就把子弹从bulletCollection集合里Remove掉
Private Sub SendBullet() ' 发射子弹的函数
bulletCollection.Add newBulletObj
End Sub
把Timer函数改一下
Private Sub Timer1_Timer()
For Each bulletObj In bulletCollection'遍历子弹集合
If bulletObj.IsBomb Then ' 检测碰撞,子弹是不是撞倒飞机了
bulletCollection.Remove bulletObj ' 移出子弹
ElseIf bulletObj.IsOut Then '子弹飞出去了的判断函数
bulletCollection.Remove bulletObj ' 移出子弹
Else
bulletObj.Draw '绘制子弹
End If
Next
End Sub
这样一个发射子弹的功能就完成了,但就像我说的,VB的集合函数Remove将对象从集合中移出,并不能释放内存,这样随着子弹的增多,内存消耗越来越大,这个就不是很好了,那么我们就用一个数组来代替集合,我们可以计算一下,比如,发射子弹的间隔时间是0.3秒,1秒钟按4发计算,子弹的移动速度是1秒100像素,那么子弹从800*600屏幕底部移动到顶部需要6秒钟,6秒钟内最多有24发子弹,也就是说我们只要定义一个长度为24的数组就可以了,为了保险,我们就定义成30个
那上面的函数就要重新写了
Private Sub SendBullet() ' 发射子弹的函数
Dim i As Integer
For i = 0 To 29
If bulletArray(i).IsRemoved = False Then ' 找一个被移出了子弹
bulletArray(i).Init ' 初始化一个新的子弹
bulletArray(i).IsRemoved = True
Exit For
End If
Next i
End Sub
把Timer函数改一下
Private Sub Timer1_Timer()
Dim i As Integer
For i = 0 To 29
If bulletArray(i).IsRemoved = True Then ' 有效的子弹
If bulletArray(i).IsBomb Then ' 检测碰撞
bulletArray(i).IsRemoved = False
ElseIf bulletObj.IsOut Then '子弹飞出去了的判断函数
bulletArray(i).IsRemoved = False
Else
bulletArray(i).Update ' 注意我在这里加了一个函数
bulletArray(i).Draw '绘制子弹
End If
End If
Next i
End Sub
这样一个子弹框架就做好了,不管是什么样的子弹,不管子弹如何飞,我们只要改变子弹对象就好了,而不需要去改变这个框架,即使不是子弹是别的什么东西,比如导弹,也可以用这个框架,我们所要做的,就是实现一个子弹对象,下面我们来看看如何实现子弹对象,VB6中虽然没有继承,但是勉强也可以用。如果有继承完全可以从飞机对象继承,其实子弹不就是一个飞机吗?没办法VB6里我们只好重写一边(Copy也很快的,只不过飞机对象改了,子弹对象要重新Copy,别以为Copy可以替代继承)
Class CBullet
Public IsRemoved As Boolean ' 子弹是不是被移出了
Public X As Integer ' 子弹坐标
Public Y As Integer
' 子弹对象的函数,我们上面用到的
Public Sub Init() ' 初始化一个子弹对象,就是子弹的初始位置等等
End Sub
Public Sub IsOut() ' 子弹是不是飞出去了
End Sub
Public Sub IsBomb() ' 子弹是不是爆炸了
End Sub
Public Sub Draw() ' 绘制子弹
' 这里我也用一下Blt函数意思一下,不管是d3d,ddraw,API都行
BitBlt hdc1, X, Y, w, h, hdc2, 0, 0, flag
End Sub
Public Sub Update() ' 刚才上面我说要注意的函数
' 这个函数做什么用?
' 更新子弹的状态,实现子弹的逻辑
' 比如子弹一直往上飞
If timeDiff >= 0.1 Then ' 每隔0.1秒坐标往上移动10个像素
End Sub
End Class
|
|