Unity ↔ Web 串接協定規格書 v0.1 草稿待審

2026-07-19|製程守門員 起草|供蔡與 Unity 端團隊審閱|定案前不動工(開放問題見 §9)

1. 架構總覽

🎰 安卓板機(不接網路)
Unity 主程式(既有彩票機框架)=機台管家
機率・遊戲紀錄・投幣出票 IO・硬體錯誤・彩票機狀態・操作員選單
👉 錢向決策的「單一真相源」,全部在這裡算
▲▼ 訊息橋(JSON 雙向,本文件定義)+ 本地供檔(localhost,不需網路)
WebView 全螢幕=Web 遊戲(純表演層)
畫面、操作、演出。可隨時重載、換技術,不影響錢向核心
核心原則(表演與判定分離):Web 只回報「發生了什麼事件」,票數由 Unity 依事件流+自己的機率紀錄計算。Web 永遠不自行決定中獎與票數。

2. 通用訊息格式

{ "v": 1, "type": "game_start", "seq": 123, "ts": 1789000000000, "payload": { ... } } v 協定版本(不相容變更 +1)|seq 遞增序號(去重、斷序偵測)|ts 毫秒時間戳|一律 JSON 字串,由橋接層(§7)處理兩端序列化

3. Unity → Web 訊息(7 種)

typepayload說明
initlang, playerCount, assetVersion, presentation{...}WebView 載入後第一包;帶演出參數(音量、特效強度等操作員設定)
coin_insertedplayer, credits, energy投幣;能量由 Unity 依操作員設定換算好再給
game_startroundId, players[], outcome{...}開局。outcome=機率端算好的本局結果參數(形式=開放問題 1)
pause / resumereasonoperator_menu/hardware_error/door_open
hardware_errorcode, message, blockingblocking=true 時 Web 顯示錯誤畫面並凍結
payout_resultroundId, tickets, ok出票完成 → Web 演出「出票完成」
config_updatepresentation{...}操作員選單改設定即時生效

4. Web → Unity 訊息(6 種)

typepayload說明
readygameVersion, protocolV資源載入完成、可開局(對接預載完成點)
heartbeatseq, fps每 1 秒一包(§6 防呆依據)
round_eventroundId, event, data局內事件流:kill/boss_kill/chest/skill…(Unity 記錄+計票依據)
round_endroundId, summary局結束;summary 只供比對,票數以 Unity 端計算為準
request_ticket_view玩家按出票鍵(實際出票由 Unity 決定與執行)
errormessage, stackWeb 端例外上報(Unity 寫入紀錄)

5. 標準時序(正常局)

Unityinit(開機、給設定)
Webready(資源載完,可開局)
Unitycoin_inserted(玩家投幣)
Unitygame_start{roundId、本局 outcome}
局內循環
Webround_event(殺怪/開箱/放技…)
Webheartbeat(每秒報平安)
Webround_end{summary}
Unity依事件流+機率紀錄計票(單一真相源)→ 驅動出票硬體
Unitypayout_result{tickets}→ Web 演出出票 → 回待機

中斷流程:pause(operator_menu) 任意時點可插入;hardware_error(blocking) 時 Web 凍結、Unity 保留局狀態,恢復後 resume 或走 §6 重載回復。

6. 防呆與回復(機台不可變磚)

  1. 心跳監控:Unity 連續 3 秒沒收到 heartbeat → 記錄 → 自動重載 WebView
  2. 局中回復:重載後 Unity 重送 init+game_start(帶 resume 與事件快照)→ Web 回到局中狀態。玩家投的幣、已得事件不消失(都記在 Unity)
  3. 去重:seq 重複或倒退的訊息直接丟棄並記 log
  4. 超時:開局後 N 秒沒有任何事件/心跳 → 視同 Web 卡死 → 走重載流程
  5. 版本握手:ready 的協定版本與 Unity 不合 → 顯示維護畫面、拒絕開局(防半套更新)

7. 橋接層抽象(換套件不改遊戲)

UnityBridge.send(type, payload) // 底層自動走 gree 或 UniWebView UnityBridge.on(type, handler) Web 端只有一個入口 UnityBridge(新檔,不碰遊戲邏輯)。gree 的 Unity.call/UniWebView 6 的 Channel Messages 差異全封在裡面——POC 用免費 gree、正式換 UniWebView,遊戲程式一行不改。桌面開發時掛 mock(鍵盤模擬投幣),現有開發流程不變。

8. 驗收條件(協定本身)

9. 開放問題(定案前必答)

  1. outcome 的形式(最關鍵):機率端給的是「總票數上限+機率參數」還是「逐事件腳本」?決定 Web 演出怎麼對應結果。需機率+企劃共同定義。(現況:web 端 applyDamageToZombie 內含機率擊殺+硬上限,搬 Unity 後參數怎麼餵要一起定)
  2. 多人局中加入:局進行中投幣,直接插入本局還是等下一局?
  3. 操作員選單:Unity 原生畫面蓋在 WebView 上(有套件疊層限制)還是暫時切走 WebView?
  4. 斷電回復:既有框架的斷電回復粒度到哪?Web 局中狀態要不要納入?
  5. 供檔方式:localhost 小伺服器 vs 套件內建 asset 映射——套件 POC 後定案