65.9K
CodeProject 正在变化。 阅读更多。
Home

使用 Ring 编程语言构建 Flappy Bird 3000

starIconstarIcon
emptyStarIcon
starIcon
emptyStarIconemptyStarIcon

2.87/5 (5投票s)

2016 年 10 月 12 日

CPOL

10分钟阅读

viewsIcon

12897

downloadIcon

199

开始 2D 游戏开发,并使用 Ring 编程语言构建 Flappy Bird 3000 游戏。

引言

在本文中,我们将学习如何使用 Ring 编程语言进行 2D 游戏开发,还将创建 Flappy Bird 游戏。我们的版本允许您在获得 3000 分时获胜,因此我将其命名为 Flappy Bird 3000 游戏。

Ring 语言简单,力求自然,鼓励组织,并具有透明和可视化的实现。它具有紧凑的语法和一组功能,使程序员能够花费极少的时间来创建自然界面和声明式领域特定语言。它非常小巧、快速,并且配备了一个智能垃圾回收器,可以将内存置于程序员的控制之下。它支持多种编程范式,并附带了有用实用的库。该语言旨在提高生产力,并开发可扩展的高质量解决方案。

您可以通过此链接下载 Ring

背景

查看有关 Ring 的下一篇文章

(1) Ring 编程语言

(2) Ring 语言的语法灵活性

还可以查看以下教程

(1) 入门

(2) 控制结构

(3) 函数

(4) 列表

(5) 

(6) 函数式编程

(7) 声明式编程 

关于 Ring 语言

如果您是 Ring 新手,以下注释将帮助您快速理解 Ring 代码

* 动态语言 

* 不区分大小写

* 使用 'Load' 命令加载库

* 支持使用 'Main' 函数

* 使用 'New' 关键字创建新对象

* 使用大括号 {} 访问对象属性和方法 

* 在 # 之后编写注释 

* 配备垃圾回收器 

 

使用 Ring 游戏引擎

要开始使用游戏引擎,请使用 "gameengine.ring" 库

然后创建一个 Game 类的对象 

Load "gameengine.ring"  # Give Control to the Game Engine

func main               # Called by the Game Engine

        oGame = New Game        # Create the Game Object
        {
                        # Game Code
        }                       

在接下来的示例中,我们将学习使用 "gameengine.ring" 提供的许多功能

下表展示了 Game 类属性。

属性 描述
帧率 (FPS) Number 决定 draw() 方法每秒被调用的次数。
FixedFPS Number 决定 animate() 方法每秒被调用的次数。
标题 String 决定游戏的窗口标题。
aObjects List 包含游戏中的所有对象
关闭 True/False 值用于结束游戏循环。

下表展示了类方法。

方法 描述
refresh() 删除对象。
settitle(cTitle) 使用字符串参数设置窗口标题。
shutdown() 关闭应用程序。

下表展示了一组由类定义的关键字。

关键字 描述
sprite 创建新的 Sprite 对象并将其添加到游戏对象中。
文本 创建新的 Text 对象并将其添加到游戏对象中。
animate 创建新的 Animate 对象并将其添加到游戏对象中。
sound 创建新的 Sound 对象并将其添加到游戏对象中。
map 创建新的 Map 对象并将其添加到游戏对象中。

创建游戏窗口

下一个示例使用 (New Game) 创建 Game 对象,对象名为 oGame。

使用大括号 {},我们访问 oGame 对象属性和方法。

我们将 'title' 属性值设置为 "My First Game"

Load "gameengine.ring"  # Give Control to the Game Engine

func main               # Called by the Game Engine

        oGame = New Game        # Create the Game Object
        {
                title = "My First Game"
        }                       # Start the Events Loop

绘制文本

要绘制文本,我们需要使用 Text 类

类名: Text

父类: Sprite Class

下表展示了类属性。

属性  描述
size                                  Number 决定字体大小
font                                  String 决定字体文件名
text                                     String 决定要显示的文本
color                                  Number 决定颜色

下表展示了类方法。

方法 描述
Draw(oGame)                                             绘制对象

 

下一个示例使用 'Load' 命令加载游戏引擎

执行从 main 函数开始

在 main 函数内部,我们从 Game Class 创建新对象

创建的对象名为 oGame,我们使用大括号访问此对象以修改对象属性和方法。

在对象 (oGame) 内部,我们使用 text {} 创建了一个 Text 类的对象

'test' 关键字由 Game 类定义,用于创建新对象并返回该对象,我们可以使用大括号 {} 访问该对象

我们将 text 属性设置为 "game development using ring is very fun!"

并使用 file 属性设置字体文件名: "fonts/pirulen.ttf"

字体大小为 20

使用 color 属性,我们将文本颜色设置为黑色,使用 rgb(0,0,0)

Load "gameengine.ring"  # Give Control to the Game Engine

func main               # Called by the Game Engine

        oGame = New Game        # Create the Game Object
        {
                title = "My First Game"
                text {
                        x = 10  y=50
                        animate = false
                        size = 20
                        file = "fonts/pirulen.ttf"
                        text = "game development using ring is very fun!"
                        color = rgb(0,0,0)
                }
        }               # Start the Events Loop

下一个屏幕截图展示了应用程序在运行时的情况。

移动文本

下一个示例使用 Text 类显示文本并使其在屏幕上移动

要移动文本,我们将 'animate' 属性设置为 True

我们有 'direction' 属性,将其设置为 GE_DIRECTION_INCVERTICAL,文本将从上到下移动。

'point' 属性决定了移动何时停止。我们有 y=150,它将一直增加直到 y = point 属性值(即 400)。

Load "gameengine.ring"  # Give Control to the Game Engine

func main               # Called by the Game Engine

        oGame = New Game        # Create the Game Object
        {
                title = "My First Game"
                text {
                        x = 10  y=50
                        animate = false
                        size = 20
                        file = "fonts/pirulen.ttf"
                        text = "game development using ring is very fun!"
                        color = rgb(0,0,0)      # Color = black
                }
                text {
                        x = 10  y=150
                        # Animation Part =====================================
                        animate = true                  # Use Animation
                        direction = GE_DIRECTION_INCVERTICAL    # Increase y
                        point = 400                     # Continue until y=400
                        nStep = 3                       # Each time y+= 3
                        #=====================================================
                        size = 20
                        file = "fonts/pirulen.ttf"
                        text = "welcome to the real world!"
                        color = rgb(0,0,255)            # Color = Blue
                }
        }                                       # Start the Events Loop

播放声音

类名: Sound

父类: GameObject Class

下表展示了类属性。

属性 描述
文件 String 决定声音文件名。
once True/False 决定是播放一次文件还是循环播放。

下表展示了类方法。

方法 描述
playsound()                                     播放声音文件

 

下一个示例使用 sound {} 创建一个声音对象来播放声音文件

示例将使用 'file' 属性确定声音文件名

我们将 'file' 属性值设置为 "sound/music1.wav"

Load "gameengine.ring"  # Give Control to the Game Engine

func main               # Called by the Game Engine

        oGame = New Game        # Create the Game Object
        {
                title = "My First Game"
                text {
                        x = 10  y=50
                        animate = false
                        size = 20
                        file = "fonts/pirulen.ttf"
                        text = "game development using ring is very fun!"
                        color = rgb(0,0,0)      # Color = black
                }
                text {
                        x = 10  y=150
                        # Animation Part ======================================
                        animate = true                          # Use Animation
                        direction = GE_DIRECTION_INCVERTICAL    # Increase y
                        point = 400             # Continue until y=400
                        nStep = 3               # Each time y+= 3
                        #======================================================
                        size = 20
                        file = "fonts/pirulen.ttf"
                        text = "welcome to the real world!"
                        color = rgb(0,0,255)    # Color = Blue
                }
                Sound {                                 # Play Sound
                        file = "sound/music1.wav"       # Sound File Name
                }
        }                                       # Start the Events Loop

 动画

类名: Animate

父类: Sprite Class

下表展示了类属性。

属性 描述
frames                                  Number 决定帧数
frame                                  Number 决定活动帧
framewidth                                  Number 决定帧的宽度。
animate                                  True/False 决定是否使用动画。
scaled                                  True/False 决定是否缩放图像。

下表展示了类方法。

方法 描述
Draw(oGame)                                             绘制对象

 

下一个示例使用 animate {} 创建一个 animate 类的对象。

此类将播放一系列图像 

我们有一张图像文件 "images/fire.png",将使用 'file' 属性指定。

使用 framewidth 属性,我们将确定每帧的宽度(framewidth = 40)

我们有 13 帧要显示。

Load "gameengine.ring"  # Give Control to the Game Engine

func main               # Called by the Game Engine

  oGame = New Game      # Create the Game Object
  {
        title = "My First Game"

        animate {
          file = "images/fire.png"
          x = 100
          y = 200
          framewidth = 40
          height = 42
          nStep = 3      # Used for delay
          transparent = true
          state = func oGame,oSelf {  # Called by engine each frame
                oSelf {
                  nStep--
                  if nStep = 0
                        nStep = 3
                        if frame < 13      # we have 13 frames in animation
                          frame++   # move to next frame
                        else
                          oGame.remove(oself.nIndex)   # remove object
                        ok
                  ok
                }
          }
         }


  }          # Start the Events Loop

动画与函数

我们可以调用函数来创建新对象

通过在 for 循环中调用此函数,我们可以创建许多对象 

在下一个示例中,我们有一个 showfire() 函数,它创建 (animate) 类型的对象。

Load "gameengine.ring"  # Give Control to the Game Engine

func main               # Called by the Game Engine

  oGame = New Game      # Create the Game Object
  {
        title = "My First Game"
        for x = 70 to 700 step 50
          for y = 70 to 500 step 50
                showfire(oGame,x,y)
          next
        next

  }          # Start the Events Loop

func showfire oGame,nX,nY
  oGame {
        animate {
          file = "images/fire.png"
          x = nX
          y = nY
          framewidth = 40
          height = 42
          nStep = 3      # Used for delay
          transparent = true
          state = func oGame,oSelf {  # Called by engine each frame
                oSelf {
                  nStep--
                  if nStep = 0
                        nStep = 3
                        if frame < 13      # we have 13 frames in animation
                          frame++   # move to next frame
                        else
                          frame=1
                        ok
                  ok
                }
          }
         }
  }

下一个屏幕截图展示了应用程序在运行时的情况。

Sprite - 使用键盘自动移动

在下一个示例中,我们将使用 sprite {} 创建 Sprite 类的新对象。

通过将 'Move' 属性设置为 'True',我们可以使用键盘箭头移动精灵 

Load "gameengine.ring"                          # Give control to the game engine

func main                                       # Called by the Game Engine

        oGame = New Game                        # Create the Game Object
        {
                title = "My First Game"
                sprite
                {
                        type = GE_TYPE_PLAYER           # Just for our usage
                        x=400 y=400 width=100 height=100
                        file = "images/player.png"
                        transparent = true
                        Animate=false
                        Move=true       # we can move it using keyboard arrows
                        Scaled=true
                }
        }                                       # Start the Events Loop

Sprite - 按键事件

下一个示例创建一个 Sprite 对象,但通过将 'Move' 属性设置为 False 来显示默认移动。

使用 Keypress 属性,我们可以定义一个匿名函数,在按下按键时调用它

匿名函数将接收诸如 Game 对象 (oGame)、Sprite 对象 (oSelf) 和按下的键代码 (nKey) 等参数

我们可以使用 Switch 语句检查按下的键值,然后根据按下的键更新 x 和 y 值。

Load "gameengine.ring"                          # Give control to the game engine

func main                                       # Called by the Game Engine

        oGame = New Game                        # Create the Game Object
        {
                title = "My First Game"
                sprite
                {
                        type = GE_TYPE_PLAYER           # Just for our usage
                        x=400 y=400 width=100 height=100
                        file = "images/player.png"
                        transparent = true
                        Animate=false
                        Move=false                      # Custom Movement
                        Scaled=true
                        keypress = func oGame,oSelf,nKey {
                                oSelf {
                                        Switch nKey
                                        on KEY_LEFT
                                                x -= 10
                                        on KEY_RIGHT
                                                x += 10
                                        on KEY_UP
                                                y -= 10
                                        on KEY_DOWN
                                                y += 10
                                        off
                                }
                        }
                }
        }                                       # Start the Events Loop

Sprite - 鼠标事件

下一个示例使用 sprite {} 创建一个 sprite 对象,然后使用 Mouse 属性确定一个匿名函数,当发生鼠标事件时调用该函数来处理。

匿名函数将接收 4 个参数: oGame, oSelf, nType, aMouseList

oGame = Game 对象

oSelf = Sprite 对象

nType = 事件类型

aMouseList = 鼠标信息 (x,y)

Load "gameengine.ring"                          # Give control to the game engine

func main                                       # Called by the Game Engine

        oGame = New Game                        # Create the Game Object
        {
                title = "My First Game"
                sprite
                {
                        type = GE_TYPE_PLAYER           # Just for our usage
                        x=400 y=400 width=100 height=100
                        file = "images/player.png"
                        transparent = true
                        Animate=false
                        Move=false                      # Custom Movement
                        Scaled=true
                        keypress = func oGame,oSelf,nKey {
                                oSelf {
                                        Switch nKey
                                        on KEY_LEFT
                                                x -= 10
                                        on KEY_RIGHT
                                                x += 10
                                        on KEY_UP
                                                y -= 10
                                        on KEY_DOWN
                                                y += 10
                                        off
                                }
                        }
                        mouse = func oGame,oSelf,nType,aMouseList {
                                if nType = GE_MOUSE_UP
                                        oSelf {
                                                x = aMouseList[GE_MOUSE_X]
                                                y = aMouseList[GE_MOUSE_Y]
                                        }
                                ok
                        }
                }
        }                                       # Start the Events Loop

Sprite - 状态事件

下一个示例展示了如何在 Sprite 类中使用 state 属性定义匿名函数,该函数将在每次帧更新时调用。

下一个示例使用 State 和匿名函数来防止对象/精灵移出屏幕。

Load "gameengine.ring"                          # Give control to the game engine

func main                                       # Called by the Game Engine

        oGame = New Game                        # Create the Game Object
        {
                title = "My First Game"
                sprite
                {
                        type = GE_TYPE_PLAYER           # Just for our usage
                        x=400 y=400 width=100 height=100
                        file = "images/player.png"
                        transparent = true
                        Animate=false
                        Move=false                      # Custom Movement
                        Scaled=true
                        keypress = func oGame,oSelf,nKey {
                                oSelf {
                                        Switch nKey
                                        on KEY_LEFT
                                                x -= 10
                                        on KEY_RIGHT
                                                x += 10
                                        on KEY_UP
                                                y -= 10
                                        on KEY_DOWN
                                                y += 10
                                        off
                                }
                        }
                        mouse = func oGame,oSelf,nType,aMouseList {
                                if nType = GE_MOUSE_UP
                                        oSelf {
                                                x = aMouseList[GE_MOUSE_X]
                                                y = aMouseList[GE_MOUSE_Y]
                                        }
                                ok
                        }
                        state = func oGame,oSelf {
                                oself {
                                        if x < 0 x = 0 ok
                                        if y < 0 y = 0 ok
                                        if x > ogame.width-width
                                                x= ogame.width - width ok
                                        if y > ogame.height-height
                                                y=ogame.height - height ok
                                }
                        }
                }
        }                                       # Start the Events Loop

 

Animate - 事件

与 sprites 一样,Animate Class 支持使用 KeyPress、Mouse 和 State 事件

下一个示例展示了这一点。

我们将创建鸟,使其动画化,并在按下空格键后向上移动它。

此外,在按下空格键后的几帧后,鸟会自动向下移动。

Load "gameengine.ring"                          # Give control to the game engine

func main                                       # Called by the Game Engine

        oGame = New Game                        # Create the Game Object
        {
                title = "My First Game"

                animate {

                        file = "images/fbbird.png"
                        x = 10
                        y = 10
                        framewidth = 20
                        scaled = true
                        height = 50
                        width = 50
                        nStep = 3
                        transparent = true

                        state = func oGame,oSelf {
                                oSelf {

                                        # Animation
                                                nStep--
                                                if nStep = 0
                                                        nStep = 3
                                                        if frame < 3
                                                                frame++
                                                        else
                                                                frame=1
                                                        ok
                                                ok

                                        # Move Down
                                                y += 3
                                                if y > 550 y=550 ok

                                }

                        }

                        keypress = func ogame,oself,nKey {
                                oself {
                                        if nkey = key_space
                                                y -= 55
                                                if y<=0 y=0 ok
                                        ok
                                }
                        }

                        mouse = func ogame,oself,nType,aMouseList {
                                if nType = GE_MOUSE_UP
                                        cFunc = oself.keypress
                                        call cFunc(oGame,oSelf,Key_Space)
                                ok
                        }
                }
        }                                       # Start the Events Loop

下一个屏幕截图展示了应用程序在运行时的情况。

映射

类名: Map

父类: Sprite Class

下表展示了类属性。

属性 描述
aMap                                    List 使用数字确定地图内容。
aImages                                    List 决定地图中每个数字使用的图像。
BlockWidth                                    Number 决定块的宽度(默认 = 32)。
BlockHeight                                    Number 决定块的高度(默认 = 32)。
Animate                                     True/False 决定动画状态。

下表展示了类方法。

方法 描述
getvalue(x,y)       根据可见部分返回地图中的项目值

 

使用 Map 类,我们可以显示和移动地图

地图使用列表通过数字确定地图内容

每个数字代表一个用于绘制的图像。

下一个示例创建了一个地图并将其向左移动

Load "gameengine.ring"        # Give control to the game engine

func main          # Called by the Game Engine

oGame = New Game      # Create the Game Object
{
  title = "My First Game"

  Map {

        blockwidth = 80
        blockheight = 80

        aMap = [
                [0,0,0,0,0,0,0,0,0,1,0,0,0,3,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0],
                [0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0],
                [0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,2,0,0,0,1,0,0,0],
                [0,0,0,0,0,0,0,0,0,1,0,0,0,2,0,0,0,3,0,0,0,1,0,0,0,1,0,0,0],
                [0,0,0,0,0,0,0,0,0,3,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,3,0,0,0],
                [0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0],
                [0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0],
                [0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0]
        ]

        aImages = ["images/fbwall.png",
                 "images/fbwallup.png",
                 "images/fbwalldown.png"]

        state = func oGame,oSelf {
          oSelf {
                x -= 3
                if x < - 2100  x = 0  ok
          }
        }

  }
}          # Start the Events Loop

下一个屏幕截图展示了应用程序在运行时的情况。

地图事件

我们可以为地图定义事件以采取行动并响应环境

下一个示例使用 mouse 属性定义一个匿名函数,当用户单击地图上的某个位置时会调用该函数。

如果用户单击了一个带有图像的位置,图像将消失

如果用户单击了一个没有图像的位置,则会将一个图像添加到地图中。

Load "gameengine.ring"        # Give control to the game engine

func main          # Called by the Game Engine

  oGame = New Game      # Create the Game Object
  {
        title = "My First Game"

        Map {

          blockwidth = 80
          blockheight = 80

          aMap = [
                   [0,0,0,0,0,0,0,0,0,1,0,0,0,3,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0],
                  [0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0],
                  [0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,2,0,0,0,1,0,0,0],
                  [0,0,0,0,0,0,0,0,0,1,0,0,0,2,0,0,0,3,0,0,0,1,0,0,0,1,0,0,0],
                  [0,0,0,0,0,0,0,0,0,3,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,3,0,0,0],
                  [0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0],
                  [0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0],
                  [0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0]
          ]

          aImages = ["images/fbwall.png",
                         "images/fbwallup.png",
                         "images/fbwalldown.png"]

          state = func oGame,oSelf {
                oSelf {
                  x -= 3
                  if x < - 2100  x = 0  ok
                }
          }

          mouse = func ogame,oself,nType,aMouseList {
                if nType = GE_MOUSE_UP
                  oSelf {
                        mX = aMouseList[GE_MOUSE_X]
                        mY = aMouseList[GE_MOUSE_Y]
                        nValue = GetValue(mX,mY)
                        nRow = GetRow(mX,mY)
                        nCol = GetCol(mX,mY)
                        Switch nValue
                        On 1  aMap[nRow][nCol] = 0
                        On 2  aMap[nRow][nCol] = 0
                        On 3  aMap[nRow][nCol] = 0
                        On 0  aMap[nRow][nCol] = 1
                        Off
                  }
                ok
          }

        }
  }          # Start the Events Loop

下一个屏幕截图展示了应用程序在运行时的情况。

Flappy Bird 3000 游戏

在理解了前面的示例之后,我们可以看到并理解这个游戏

Flappy Bird 3000 游戏源代码

游戏中还有 GameState 类,用于存储我们游戏的自定义信息。

以下代码用于启动游戏和显示游戏信息

还支持(再玩一次)功能

oGameState = NULL

Load "gameengine.ring"

func main

  oGame = New Game


  while true

        oGameState = New GameState

        oGame {
          title = "Flappy Bird 3000"
          sprite
          {
                file = "images/fbback.png"
                x = 0 y=0 width=800 height = 600 scaled = true animate = false
                keypress = func ogame,oself,nKey {
                  if nkey = key_esc or nKey = GE_AC_BACK
                        ogame.shutdown()
                  but nKey = key_space
                        oGameState.startplay=true
                        ogame.shutdown=true
                  ok
                }
                mouse = func ogame,oself,nType,aMouseList {
                  if nType = GE_MOUSE_UP
                        cFunc = oself.keypress
                        call cFunc(oGame,oSelf,Key_Space)
                  ok
                }
          }
          text {
                animate = false
                size = 35
                file = "fonts/pirulen.ttf"
                text = "Flappy Bird 3000"
                x = 150  y=50
          }
          text {
                animate = false
                size = 25
                file = "fonts/pirulen.ttf"
                text = "Version 1.0"
                x = 280  y=100
          }
          text {
                animate = false
                size = 16
                file = "fonts/pirulen.ttf"
                text = "(C) 2016, Mahmoud Fayed"
                x = 245  y=140
          }

          text {
                animate = false
                size = 25
                file = "fonts/pirulen.ttf"
                text = "To Win Get Score = 3000"
                x = 150  y=270
          }

          text {
                animate = false
                size = 25
                file = "fonts/pirulen.ttf"
                text = "Press Space to start"
                x = 190  y=470
          }
          text {
                animate = false
                size = 20
                file = "fonts/pirulen.ttf"
                text = "Press Esc to Exit"
                x = 260  y=510
          }

          animate {
                file = "images/fbbird.png"
                x = 200
                y = 200
                framewidth = 20
                scaled = true
                height = 50
                width = 50
                nStep = 3
                transparent = true
                animate = true
                direction = ge_direction_random
                state = func oGame,oSelf {
                  oSelf {
                        nStep--
                        if nStep = 0
                          nStep = 3
                          if frame < 3
                                frame++
                          else
                                frame=1
                          ok
                        ok
                        if x <= 0 x=0 ok
                        if y <= 0 y=0 ok
                        if x >= 750 x= 750 ok
                        if y > 550 y=550 ok
                  }
                }
          }

          Sound {
                file = "sound/music2.wav"
          }
        }
        if oGameState.startplay
          oGame.refresh()
          playstart(oGame)
          oGame.refresh()
        ok

  end

下一个函数 playstart() 包含实际玩游戏的代码

 

func playstart oGame

    oGame {
        FPS = 60
        FixedFPS = 120
        Title = "Flappy Bird 3000"
        Sprite {
            file = "images/fbback.png"
            x = 0 y=0 width=800 height = 600 scaled = true animate = false
            keypress = func ogame,oself,nKey {
                if nkey = key_esc or nKey = GE_AC_BACK
                    ogame.shutdown()
                ok
            }
        }

        Map {
            blockwidth = 80
            blockheight = 80
            aMap = [
                     [0,0,0,0,0,0,0,0,0,1,0,0,0,3,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0],
                    [0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0],
                    [0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,2,0,0,0,1,0,0,0],
                    [0,0,0,0,0,0,0,0,0,1,0,0,0,2,0,0,0,3,0,0,0,1,0,0,0,1,0,0,0],
                    [0,0,0,0,0,0,0,0,0,3,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,3,0,0,0],
                    [0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0],
                    [0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0],
                    [0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0]
                ]
            newmap(aMap)
            aImages = ["images/fbwall.png","images/fbwallup.png",
                    "images/fbwalldown.png"]
            state = func oGame,oSelf {
                if oGameState.gameresult = false
                    px = oGame.aObjects[3].x
                    py = oGame.aObjects[3].y
                    oSelf {
                        x -=  3
                        if x < - 2100
                            x = 0
                            newmap(aMap)
                        ok
                        nCol =  getcol(px,0)
                        if nCol=11 or nCol=15 or nCol=19 or nCol=23 or nCol=27
                            if nCol != oGameState.lastcol
                                oGameState.lastcol = nCol
                                oGameState.Score += 100
                                oGame { Sound {
                                    once = true
                                    file = "sound/sfx_point.wav"
                                } }
                                checkwin(oGame)
                            ok
                        ok
                    }
                    if  oSelf.getvalue(px+40,py) != 0 or
                        oSelf.getvalue(px+40,py+40) != 0 or
                        oSelf.getvalue(px,py) != 0 or
                        oSelf.getvalue(px,py+40) != 0
                        oGameState.gameresult = true
                        oGame {
                            text {
                                point = 550
                                size = 30
                                nStep = 3
                                file = "fonts/pirulen.ttf"
                                text = "Game Over !!!"
                                x = 500    y=10
                                state = func ogame,oself {
                                    if oself.y >= 550
                                            ogame.shutdown = true
                                    ok
                                        if oself.y = 90
                                        ogame {
                                            Sound {
                                                once = true
                                                file = "sound/sfx_die.wav"
                                            }
                                        }
                                    ok
                                }
                            }
                            Sound {
                                once = true
                                file = "sound/sfx_hit.wav"
                            }
                        }
                    ok
                ok
            }
        }

        animate {
            file = "images/fbbird.png"
            x = 10
            y = 10
            framewidth = 20
            scaled = true
            height = 50
            width = 50
            nStep = 3
            transparent = true
            state = func oGame,oSelf {
                oSelf {
                    nStep--
                    if nStep = 0
                        nStep = 3
                        if frame < 3
                            frame++
                        else
                            frame=1
                        ok
                    ok
                }

                if not oGameState.playerwin
                    oGameState.down --
                    if oGameState.down = 0
                        oGameState.down = 3
                        oself {
                            y += 25
                            if y > 550 y=550 ok
                        }
                    ok
                ok

            }
            keypress = func ogame,oself,nKey {
                if oGameState.gameresult = false
                    oself {
                        if nkey = key_space
                            y -= 55
                            oGameState.down = 60
                            if y<=0 y=0 ok
                        ok
                    }
                ok
            }
            mouse = func ogame,oself,nType,aMouseList {
                if nType = GE_MOUSE_UP
                    cFunc = oself.keypress
                    call cFunc(oGame,oSelf,Key_Space)
                ok
            }
        }

        text {
            animate = false
            point = 400
            size = 30
            file = "fonts/pirulen.ttf"
            text = "Score : " + oGameState.score
            x = 500    y=10
            state = func oGame,oSelf {
                oSelf { text = "Score : " + oGameState.score }
            }
        }

    }

下一个函数 newmap() 用于创建新地图(随机地图)

 

func newmap aMap
    aV = [
    [1,1,3,0,0,2,1,1],
    [1,3,0,0,0,2,1,1],
    [1,1,1,3,0,2,1,1],
    [1,1,1,3,0,0,0,0],
    [0,0,0,0,2,1,1,1],
    [0,0,2,1,1,1,1,1],
    [0,0,0,2,1,1,1,1],
    [1,1,1,3,0,2,1,1],
    [1,1,1,1,1,3,0,0],
    [3,0,0,2,1,1,1,1],
    [3,0,0,2,3,0,0,2]
    ]
    for x = 10 to 24 step 4
        aVar = aV[ (random(10)+1) ]
        for y = 1 to 8
            aMap[y][x] = aVar[y]
        next
    next

下一个函数 checkwin() 用于检查玩家是否获胜

我们通过检查分数来做到这一点

如果分数等于 300,玩家获胜。

func checkwin ogame
    if oGameState.score = 3000
        oGameState.gameresult = true
        oGameState.playerwin = true
        oGame {
            text {
                point = 400
                size = 30
                nStep = 3
                file = "fonts/pirulen.ttf"
                text = "You Win !!!"
                x = 500    y=10
                state = func ogame,oself {
                    if oself.y >= 400
                        ogame.shutdown = true
                        oGameState.value = 0
                    ok
                }
            }
        }
    ok

下一个类用于存储游戏状态和重要信息,如分数。

Class GameState
    down = 3
    gameresult = false
    Score = 0
    startplay=false
    lastcol = 0
    playerwin = false

 

下一个屏幕截图展示了游戏在运行时的情况。

关注点

Ring 是一种新语言,游戏引擎也是新的,许多东西都可以添加以使 Ring 和引擎成为更好的作品,您也可以提供帮助和贡献

一旦您了解了如何使用游戏引擎,您就可以在短时间内创建许多游戏。游戏引擎用于提高生产力。Ring 游戏引擎可用于原型设计游戏。

© . All rights reserved.