<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          Go:使用 Ebiten 在 2D 視頻游戲中進行圖像渲染

          共 4060字,需瀏覽 9分鐘

           ·

          2021-04-06 19:39

          點擊上方藍色“Go語言中文網”關注,每天一起學 Go

          插圖由創(chuàng)作原始 Go Gopher 作品的 Renee French 為“ Go 的旅程”創(chuàng)作。

          本文基于 Ebiten 1.10。

          Ebiten[1] 是由 Hajime Hosh[2] 用 Go 語言編寫的成熟的 2D 游戲庫。它是 Apple Store 上一些手機游戲如 Bear's Restaurant[3] 或桌面游戲如 OpenDiablo2[4] 的引擎,OpenDiablo2 是 Go 版本暗黑 2 的開源實現?,F在,讓我們深入了解電子游戲中的一些基本概念以及它們在 Ebiten 中的實現。

          動畫制作

          在電子游戲世界中,Ebiten 通過分離的靜態(tài)圖像來渲染動畫。這些圖像集合被組合成一個更大的圖像,通常稱為“紋理圖集[5]”,也稱為“精靈圖”。這是 網站[6] 上提供的示例:

          image1

          然后,經過簡單的數學運算,這張圖被加載到內存中,然后被一部分一部分地渲染。在前面的示例中,每個部分的寬度為 32 個像素。渲染每個圖像非常簡單,只需將 X 坐標移動 32 個像素。這是第一步:

          image2
          image3

          渲染動畫時,只需要當前圖像的值即可渲染精靈圖的正確部分。Ebiten 提供了所有的 API 來輕松地渲染它,下面是之前第一步中精靈圖的示例:

          screen.DrawImage(
             // 在坐標上繪制子畫面的子圖像
             // x=0 to x=32 and y=32 to y=64
             runnerImg.SubImage(image.Rect(0323264)).(*ebiten.Image),
             // 在該位置之前聲明的變量定義了屏幕上的位置
             op,
          )

          Ebiten 的創(chuàng)建者 Hajime Hosh 還開發(fā)了“ file2byteslice[7]”,該工具可將任何圖像轉換為字符串,并允許將任何文件嵌入到 Go 中。它可以通過注釋 go:generate 與 Go 工具輕松集成,自動將圖像轉儲到 Go 文件中。下面是一個例子:

          //go:generate file2byteslice
            -package=img
            -input=./images/sprite.png
            -output=./images/sprite.go -var=Runner_png

          現在可以從以下代碼的 img.Runner_png 變量中獲取精靈圖:

          image4

          然后,必須先對圖像進行解碼,然后再由 Ebiten 加載并在游戲中進行渲染。讓我們轉到另一種渲染較大背景圖像的方法,該圖像由循環(huán)元素組成。

          瓷磚背景

          渲染背景使用相同的技術,將主要地圖集分為許多小圖像,稱為“瓷磚”。這是網站上提供的紋理圖集的示例:

          tiles1

          該圖集可以被 16 像素的圖塊分割 ,這是使用 Tiled[8] 軟件創(chuàng)建的圖塊集合:

          tiles2

          每個圖塊將分配一個數字,從 0 開始,逐次加 1。由于每行都有相同數量的圖塊,因此可以通過除法和取模來獲取圖塊的坐標。這是藍色花朵的示例:

          tiles3

          藍色花朵的編號為 303,這意味著它們位于第 4 列(303 以每行的圖塊數為模,例如 303%25 = 3)和第 13 行(303 除以每行的圖塊數,例如,303/25 = 12)。

          現在,我們可以使用索引數組來構建地圖:

          map_array

          從這張地圖上繪制圖像可以得到主要裝飾:

          bg1

          但是缺少背景。我們必須構建一個表示背景的類似數組。結果如下:

          bg2

          現在,這些圖層已經準備好了,我們只需要迭代兩個圖層就可以得到最終結果:

          bg3

          此示例中的代碼可在 Ebiten 網站[9] 上找到。

          生成圖像后,Ebiten 必須管理屏幕更新并將指令發(fā)送到圖形卡片。

          屏幕更新

          Ebiten 提供了 iOS(使用 Metal)和 Android(使用 OpenGL ES)使用的驅動程序的抽象,這使開發(fā)更加容易。它還允許您定義一個函數,該函數可以更新屏幕并繪制所有更改。但是,出于性能原因,該庫會將源打包在一起,并將這些更改存儲在緩沖區(qū)中,然后再發(fā)送給驅動程序:

          screen_update1

          該緩沖區(qū)還能夠合并繪圖指令,以減少對 GPU 的調用次數。在上圖中,這三個指令現在可以合并為一個:

          screen_update2

          這項改進很重要,因為它可以減少發(fā)送指令時的開銷。這是合并指令的性能:

          perf1

          通過逐個發(fā)送指令,性能會大大降低:

          perf2

          Ebiten 還提供了對屏幕刷新的控制,這有助于調整性能。

          TPS 管理

          Ebiten 的默認 TPS 是 60。但是,這可以用 Ebiten 提供的 API ebiten.SetMaxTPS() 來輕松配置。它有助于減少機器上的壓力。這是具有 25 TPS 的簡單程序:

          tps1

          TPS(每秒 tick 數)與 FPS(每秒幀數)不同。Hajime Hosh[10] 很好地描述了這些差異:

          幀代表圖形更新。這取決于用戶顯示屏上的刷新率。那么 FPS 可能是 60、70、120,依此類推。這個數字基本上是不可控制的。Ebiten 可以打開或關閉 vsync。如果關閉了 vsync,則 Ebiten 會嘗試盡可能多地更新圖形,那么 FPS 可以為 1000 左右。tick 表示邏輯更新。TPS 表示每秒調用更新功能的次數。默認情況下固定為 60。游戲開發(fā)人員可以通過 SetMaxTPS 配置 TPS。如果設置了 UncappedTPS,則 Ebiten 會嘗試盡可能多地調用更新函數。

          當窗口在后臺運行時,Ebiten 為渲染帶來了另一種優(yōu)化。失去焦點時,游戲將進入休眠狀態(tài),直到重新獲得焦點。它實際上 sleep 了 1/60 秒,然后再次檢查焦點。這是保存的資源的示例:

          tps2

          盡管可以關閉此優(yōu)化,但是運行的系統可能會限制游戲的運行。例如,在 Firefox[11],Chrome[12] 或其他瀏覽器上的后臺標簽中運行時,在瀏覽器中運行的游戲會受到限制。

          Ebiten 在 Github[13] 上接受贊助。如果您希望看到更多 Go 編寫的游戲,請隨時貢獻力量。


          via: https://medium.com/a-journey-with-go/go-image-rendering-in-2d-video-games-with-ebiten-912cc2360c4f

          作者:Vincent Blanchon[14]譯者:alandtsang[15]校對:polaris1119[16]

          本文由 GCTT[17] 原創(chuàng)編譯,Go 中文網[18] 榮譽推出

          參考資料

          [1]

          Ebiten: https://ebiten.org/

          [2]

          Hajime Hosh: https://github.com/hajimehoshi

          [3]

          Bear's Restaurant: https://daigostudio.com/bearsrestaurant/en/

          [4]

          OpenDiablo2: https://github.com/OpenDiablo2

          [5]

          紋理圖集: https://en.wikipedia.org/wiki/Texture_atlas

          [6]

          網站: https://ebiten.org/examples/animation.html

          [7]

          file2byteslice: https://github.com/hajimehoshi/file2byteslice

          [8]

          Tiled: https://www.mapeditor.org/

          [9]

          Ebiten 網站: https://ebiten.org/examples/tiles.html

          [10]

          Hajime Hosh: https://github.com/hajimehoshi

          [11]

          Firefox: https://hacks.mozilla.org/2018/01/firefox-58-the-quantum-era-continues/

          [12]

          Chrome: https://developers.google.com/web/updates/2017/03/background_tabs

          [13]

          Github: https://github.com/sponsors/hajimehoshi

          [14]

          Vincent Blanchon: https://medium.com/@blanchon.vincent

          [15]

          alandtsang: https://github.com/alandtsang

          [16]

          polaris1119: https://github.com/polaris1119

          [17]

          GCTT: https://github.com/studygolang/GCTT

          [18]

          Go 中文網: https://studygolang.com/



          推薦閱讀


          福利

          我為大家整理了一份從入門到進階的Go學習資料禮包,包含學習建議:入門看什么,進階看什么。關注公眾號 「polarisxu」,回復 ebook 獲??;還可以回復「進群」,和數萬 Gopher 交流學習。

          瀏覽 69
          點贊
          評論
          收藏
          分享

          手機掃一掃分享

          分享
          舉報
          評論
          圖片
          表情
          推薦
          點贊
          評論
          收藏
          分享

          手機掃一掃分享

          分享
          舉報
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  伊人天堂视频 | 五月丁香中文字幕成人网在线 | 人人草视频在线播放 | 亚洲a片在线免费观看 | 国产免费A黄片 |