使用 React
React 是一個流行的庫,可讓您創建易於重用的 UI 組件。Hology Engine 提供了一個專門的庫,用於幫助將 React 組件與遊戲狀態和角色整合。
使用 Hology Scene Scene component組件
要在 React 應用程序中運行 Hology Engine,您可以簡單地使用 HologyScene
組件。
<HologyScene gameClass={Game} sceneName='demo' dataDir='data' shaders={shaders} actors={actors}>
</HologyScene>
這將使用給定的場景啟動 Hology Engine 運行時。您還需要為 Hology Engine 傳入一些參數,因為這些參數可能會根據您的項目設置而有所不同。如果您在創建新的 Hology 項目時使用默認的 React 項目模板,那麼上面代碼中顯示的值應該可以正常工作。
sceneName - 您想要加載的場景名稱
dataDir - 所有 Hology 遊戲數據所在文件夾的路徑
shaders - 包含著色器類的對象
actors - 包含角色類的對象
添加 UI 組件
在 HologyScene
組件內部,您可以放置應該顯示在渲染遊戲之上的組件。
function App() {
return (
<HologyScene gameClass={Game} sceneName='demo' dataDir='data' shaders={shaders} actors={actors}>
<p>This will be displayed over the game</p>
</HologyScene>
)
}
必需的 CSS
為了在使用 HologyScene
組件時正確處理指針事件,需要在您的項目中添加以下 CSS。這將確保可以在畫布上捕獲指針事件(由指針事件服務使用),同時也可以捕獲添加為組件子元素的 HTML 元素上的事件。
.hology-overlay {
pointer-events: none
}
.hology-overlay * {
pointer-events: auto;
}
Hology React hooks
在 HologyScene 組件內使用的組件可以使用像 useService
這樣的hooks來訪問遊戲實例中的任何遊戲服務。
function PlayerHealthDisplay() {
const playerState = useService(PlayerState)
return <h1>{playerState.health.value}</h1>
}
function App() {
return (
<HologyScene gameClass={Game} sceneName='demo' dataDir='data' shaders={shaders} actors={actors}>
<PlayerHealthDisplay></PlayerHealthDisplay>
</HologyScene>
)
}
useService - 獲取遊戲代碼中任何服務的實例。這對於持有一些全局遊戲狀態的服務很有用,您可能想要顯示這些狀態。
useActorQuery - 查詢當前添加到遊戲世界的角色。每當匹配查詢的角色被添加到世界或從世界中移除時,組件將重新渲染。
useRenderUpdate - 在每一frame之前執行給定的函數。
useRenderLaterUpdate - 在每一幀之前但在其他更新函數之後執行給定的函數。
當狀態改變時更新 UI
React 旨在僅在某些內容發生變化時才重新渲染,這對於高性能的用戶界面來說很好,但它需要知道什麼時候發生了變化。如果您想在用戶界面中顯示遊戲代碼中的某個值,您可以通過訪問服務或角色來讀取該值,但您需要讓 React 知道該值已經改變。
管理這種情況的一種方法是使用信號。信號是一個在 Web 前端開發中越來越流行的概念,它允許您以一種方式表示狀態,使得該狀態的消費者可以知道信號的值何時發生變化。當您創建一個新的 Hology Engine 項目並選擇 React 作為 UI 框架時,它會自動安裝一個名為 @preact/signals-react 的庫。
假設您的遊戲代碼中有一個如下所示的服務。我們在定義屬性時使用 signal 函數。
import { Service } from '@hology/core/gameplay'
import { signal } from "@preact/signals-react"
@Service()
class PlayerState {
health = signal(100)
}
export default PlayerState
現在我們可以在 React 組件中訪問這個健康信號,如下所示。首先,我們使用 useService hook來訪問 PlayerState 類的實例。可以使用 .value
屬性訪問健康信號的值。
function PlayerHealthDisplay() {
const playerState = useService(PlayerState)
return <h1>{playerState.health.value}</h1>
}
我們可以稍後通過為 value 屬性分配新值來更新信號的值。在下面的例子中,我們定義了一個方法,根據給定的傷害量更新健康信號。
import { Service } from '@hology/core/gameplay'
import { signal } from "@preact/signals-react"
@Service()
class PlayerState {
health = signal(100)
takeDamage(damage: number) {
this.health.value = Math.max(0, this.health.value - damage)
}
}
export default PlayerState
每當信號更新時,React 組件將自動重新渲染。
最后更新于