实现游戏房(基于NERoom)

更新时间: 2023/12/06 02:37:35

网易云信基于 NERoom 房间组件搭建了一套开源的游戏房客户端和游戏房服务端,您可以基于示例项目源码,在语聊房的基础上快速实现游戏房。本文介绍游戏房的实现思路。

开发环境要求

开发环境要求如下:

环境要求 说明
iOS 版本 11.0 及以上的 iPhone 或者 iPad 真机
CPU 架构 ARM64、ARMV7
IDE XCode
其他 安装 CocoaPods

前提条件

示例项目源码

游戏房的示例项目源码地址请参见 游戏房示例项目源码

示例项目的目录结构和跑通示例项目的步骤请参见跑通示例项目

API 时序图

sequenceDiagram
    autonumber
    participant hostClientA as 主播 
    participant roomA as NERoom
    participant room_server as NERoom_Server 
    participant roomB as NERoom  
    participant audienceB as 观众  

    note over hostClientA,audienceB:创建游戏房
    hostClientA ->> room_server:创建房间 
    room_server-->> hostClientA:创建成功
    hostClientA->> roomA:加入房间(joinRoom)
    roomA->>room_server:加入房间(joinRoom)
    room_server-->>roomA:success
    roomA-->>hostClientA:success
    hostClientA->>roomA:上麦(submitSeatRequest)
    roomA->>room_server:上麦(submitSeatRequest)
    room_server-->>roomA:success
    roomA-->>hostClientA:success

    audienceB->> roomB:加入房间(joinRoom)
    roomB->>room_server:加入房间(joinRoom)
    room_server-->>roomB:success
    roomB-->>audienceB:success
    audienceB->>roomB:申请上麦(submitSeatRequest)
    roomB->>room_server:申请上麦(submitSeatRequest)
    room_server-->>roomB:success
    roomB-->>audienceB:success
sequenceDiagram
    autonumber

    participant hostClientA as 主播 
    participant kitA as GameKit
    participant app_server as 游戏房_Server 
    participant kitB as GameKit  
    participant audienceB as 观众  

    note over hostClientA,audienceB:选择并创建游戏
    hostClientA ->> kitA:获取游戏列表(getGameList)
    kitA -->> app_server:调用游戏房Server的http接口获取游戏列表<br>(/nemo/game/list)
    kitA -->> hostClientA:返回相关信息,<br>包括游戏 ID、游戏名称、游戏规则等
    hostClientA ->> kitA:选择一款游戏,创建游戏(createGame)
    kitA ->> app_server:调用游戏房Server的http接口创建游戏<br>(/nemo/game/create)
    app_server ->> kitA:开始游戏(1102)
    kitA ->> hostClientA:主播开启了XX游戏(onGameCreated)
    app_server ->> kitB:开始游戏(1102)
    kitB ->> audienceB:主播开启了XX游戏(onGameCreated)
    hostClientA->>kitA:加载游戏(loadGame) 
    kitA-->>hostClientA:success
    hostClientA-->>hostClientA:加载游戏画面,刷新UI

    audienceB->>kitB:加载游戏(loadGame) 
    kitB-->>audienceB:success
    audienceB-->>audienceB:加载游戏画面,刷新UI


    note over hostClientA,audienceB:参与游戏

    note over hostClientA,app_server:主播参与游戏
    hostClientA ->> kitA:参与游戏(joinGame)
    kitA ->> app_server:调用游戏房Server的http接口参与游戏<br>(/nemo/game/join)
    app_server -->> kitA:success
    kitA -->> hostClientA:success
    hostClientA ->> hostClientA:刷新UI<br>麦位状态变为“已准备”,按钮从“参与游戏”变为“退出”
    note over app_server,audienceB: 观众参与游戏 
    audienceB ->> kitB:参与游戏(joinGame)
    kitB ->> app_server:调用游戏房Server的http接口参与游戏<br>(/nemo/game/join)
    alt 已上麦
        app_server -->> kitB:success
        kitB -->> audienceB:success
    end
    alt 满足游戏开始规则
    app_server -->>hostClientA:发送游戏成员已准备OK
    hostClientA -> hostClientA: 游戏页面"开始游戏"高亮
    end

sequenceDiagram
    autonumber

    participant hostClientA as 主播 
    participant kitA as GameKit
    participant app_server as 游戏房_Server 
    participant kitB as GameKit
    participant audienceB as 观众 

    note over hostClientA,audienceB:主播点击"开始游戏"按钮
    hostClientA ->>kitA:开始游戏(startGame)
    kitA ->>app_server:调用游戏房Server的http接口开始游戏<br>(/nemo/game/start)
    alt 人数不足
        app_server -->>kitA:failed
        kitA -->>hostClientA:failed
        hostClientA ->>hostClientA:提示"参与人数不足,无法开启游戏"

 
    else 人数满足
        app_server -->>kitA:success
        app_server->>kitA:GAME_START(1102,"开始游戏")
        kitA->>hostClientA:游戏已开始(onGameStarted)
        hostClientA->>kitA:加载游戏(loadGame) 
        kitA-->>hostClientA:success
        hostClientA-->>hostClientA:加载游戏画面,刷新UI
        app_server->>kitB:GAME_START(1102,"开始游戏")
        kitB->>audienceB:onGameStarted
        audienceB->>kitB:加载游戏(loadGame) 
        kitB-->>audienceB:success
        audienceB-->>audienceB:加载游戏画面,刷新UI
    end
    note over hostClientA,audienceB:结束游戏
    hostClientA ->>kitA:结束游戏(endGame)
    kitA ->>app_server:调用游戏房Server的http接口开始游戏<br>(/nemo/game/end)
    app_server ->>kitA:主播结束了XX游戏(onGameEnded)
    kitA ->>hostClientA:主播结束了XX游戏(onGameEnded)
    app_server ->>kitB:主播结束了XX游戏(onGameEnded)
    kitB ->>audienceB:主播结束了XX游戏(onGameEnded)
    hostClientA->>kitA:销毁游戏(unloadGame)
    audienceB->>kitB:销毁游戏(unloadGame)  

实现方法

步骤1 下载并引入游戏房源码

  1. 下载 游戏房示例项目源码,拷贝 NEGameKitNEGameUIKitNEUIKitNEVoiceRoomKitNEVoiceRoomBaseUIKitLottieSwiftNESocialUIKit目录至本地工程中。

  2. Podfile文件中添加如下命令,添加依赖库。

    # 源码依赖
    pod 'NEUIKit', :path => '本地路径/.../NEUIKit.podspec'
    pod 'NEGameKit', :path => '本地路径/.../NEGameKit.podspec'
    pod 'NEGameUIKit', :path => '本地路径/.../NEGameUIKit.podspec'
    pod 'NEVoiceRoomKit', :path => '本地路径/.../NEVoiceRoomKit.podspec'
    pod 'NEVoiceRoomBaseUIKit',:path => '本地路径/.../NEVoiceRoomBaseUIKit.podspec'
    pod 'LottieSwift', :path => '本地路径/.../LottieSwift.podspec'
    pod 'NESocialUIKit', :path => '本地路径/.../NESocialUIKit.podspec'
    
  3. 从 Terminal 进入 Podfile 文件所在目录,执行以下命令安装依赖库。

    bashpod install   
    
  • 请在 Xcode 设置中使用企业证书,保持默认的 Bundle Identifier 设置。

GameRoomNote.png

  • 实现游戏房除了游戏房特有的步骤,还需要实现语聊房的基础功能,包括登录鉴权、主播开播、观众进入房间、麦位管理,具体请参见实现语聊房

步骤2 初始化 GameKit

  1. 请在加入 NERoom 房间之后,调用 initialize 接口初始化 GameKit。

示例代码

swiftlet options = NEGameKitOptions()
options.appKey = "your appKey"
options.roomUuid = "your roomUuid"
options.baseUrl = "your baseUrl"
let loginInfo = NEGameLoginInfo()
loginInfo.account = account
loginInfo.token = token
NEGameKit.getInstance().initialize(config: options, info: loginInfo) {  code, msg, obj in
    guard let self = self else { return }
    if code == 0 {
        // 初始化成功
    } else {
        // 初始化失败
    }
}
  1. 注册监听小游戏事件。

    调用 addGameListener 接口注册监听小游戏事件。

示例代码

swiftNEGameKit.getInstance().addGameListener(self)

@objc public protocol NEGameListener: NSObjectProtocol {
  /**
   * 游戏创建成功       tips:对应服务端协议 createGame(1104,"创建游戏")
   * @param gameInfo 房间内游戏信息
   */
  @objc optional func onGameCreated(event: NEGameCreatedEvent)

  /**
   * 游戏开始通知        tips:对应服务端协议 gameStart(1102,"开始游戏")
   */
  @objc optional func onGameStarted(event: NEGameStartedEvent)

  /**
   * 游戏结束通知       tips:对应服务端协议 gameEnd(1103,"游戏结束")
   */
  @objc optional func onGameEnded(event: NEGameEndedEvent)

  /**
   * 成员参与游戏回调    tips:对应服务端协议 joinGame(1100,"加入游戏")
   * @param members 成员列表
   */
  @objc optional func onMemberJoinGame(members: [NERoomMember])

  /**
   * 成员离开游戏回调    tips:对应服务端协议 leaveGame(1101,"离开游戏")
   * @param members 成员列表
   */
  @objc optional func onMemberLeaveGame(members: [NERoomMember])

  /**
   * 点击关闭按钮回调
   */

  @objc optional func onGameSelfClickGameSettleClose()

  /**
   * 游戏异常回调
   * @param code 错误码
   * @param msg 错误信息
   */
  @objc optional func onGameError(code: Int, msg: String)

  /**
   * 游戏公屏消息回调
   * @param event 事件
   */
  @objc optional func onGamePublicMessage(event: GamePublicMessageEvent)

  /**
   * 关键词状态消息回调
   * @param event 事件
   */
  @objc optional func onGameKeyWordToHit(event: GameKeyWordToHitEvent)

  /**
   * 成员作画中状态消息回调
   * @param event 事件
   */
  @objc optional func onMemberPainting(event: GameMemberPaintingEvent)

  // 配置获取游戏界面
  @objc optional func onGetGameViewInfo(_ handle: ISudFSMStateHandle, dataJson: String)
}

步骤3 主播选择并创建游戏

  1. 主播调用 getGameList 接口获取游戏列表。

    返回相关信息,包括游戏 ID、游戏名称、游戏规则等。

  2. (可选) 获取游戏详细信息。

    调用 getRoomGameInfo 接口获取房间内游戏的详细信息,包括最大支持玩家数量等。

  3. 主播选择一款游戏,调用 createGame 接口创建游戏。

  4. 游戏创建后,会促发 onGameCreated 事件,通知语聊房内的用户,主播已经开启了游戏。

  5. 调用 loadGame 接口加载游戏。

    游戏加载完成后,即可开始玩游戏。

示例代码

swift// 获取游戏列表
NEGameKit.getInstance().getGameList { code, msg, gameList ->
    if (code == 0) {
        // 请求成功
    } else {
        // 请求失败
    }
}

//获取游戏详细信息
NEGameKit.getInstance().getRoomGameInfo { code, msg, obj in
    if code == 0 {
        //请求成功
    } else {
        //请求失败
    }
}

// 创建游戏
let createGameParams = NECreateGameParams()
createGameParams.gameId = gameId
NEGameKit.getInstance().createGame(createGameParams) { code, msg, obj in
    if code == 0 {
        // 创建成功
        
    } else {
        // 创建失败
    }
}

//游戏创建完成事件回调
public func onGameCreated(event: NEGameCreatedEvent) {
    
}

//加载游戏
NEGameKit.getInstance().loadGame(gameParams, callback: { code, msg, obj in
    if code == 0 {
        //加载成功
    } else {
        //加载失败
    }
})

步骤4 主播和玩家参与游戏

  • (可选)主播参与游戏

    主播可以参与游戏进行带玩,也可以不参与游戏。

    1. 主播调用 joinGame 接口参与游戏。
    2. 参与游戏后,会触发 onMemberJoinGame 回调,通知语聊房内的所有用户。

    示例代码

    swift// 参与游戏
    let joinGameParams = NEJoinGameParams()
    joinGameParams.gameId = gameId
    NEGameKit.getInstance().joinGame(joinGameParams) { code, msg, obj in
        DispatchQueue.main.async {
            if code == 0 {
              // 参与游戏成功
            } else {
              // 参与游戏失败
            }
        }
    }
    
    //事件回调
    public func onMemberJoinGame(members: [NERoomMember]) {}
    
  • 玩家参与游戏

    1. 玩家上麦。

      玩家调用 submitSeatRequest 接口申请上麦。

    2. 玩家在收到 onGameCreated 事件后,调用 joinGame 接口参与游戏。

    3. 参与游戏后,会触发 onMemberJoinGame 回调,通知语聊房内的所有用户。

    示例代码

    swiftroomContext.seatController.submitSeatRequest(seatIndex) { code, msg in
        if code == 0 {
            //申请成功
        } else {
            //申请失败
        }
    }
    
    //游戏创建完成事件回调
    public func onGameCreated(event: NEGameCreatedEvent) {}
    //用户加入游戏事件回调
    public func onMemberJoinGame(members: [NERoomMember]) {}
    

步骤5 主播开始游戏

  1. 主播调用 startGame 接口开始游戏。
  2. 游戏开始后,会触发 onGameStarted 回调,通知语聊房内的所有用户游戏已开始。

示例代码

swiftlet startGameParams = NEStartGameParams()
startGameParams.gameId = gameId
NEGameKit.getInstance().startGame(startGameParams) { code, msg, obj in
    if code == 0 {
        // 游戏正常开始 
    } else {
        // 开始发生错误,跳出提示
        DispatchQueue.main.async {
            if code == 403 {
                //参与人数不足,无法开始游戏
            } else {
                //发生其他错误
            }
        }
    }
}

//游戏开始回调
public func onGameStarted(event: NEGameStartedEvent) {}

步骤6 主播结束游戏

  1. 主播调用 endGame 接口结束游戏。
  2. 游戏结束后,会触发 onGameEnded 回调,通知语聊房内的所有用户游戏已结束。

示例代码

swiftNEGameKit.getInstance().endGame { code, msg, obj in
    if code == 0 {
        // 结束成功
    } else {
        // 结束失败
    }
}

// 游戏结束事件回调
public func onGameEnded(event: NEGameEndedEvent) {}

步骤7 销毁游戏,清理游戏资源

主播和玩家分别调用 destroy 接口销毁游戏。

示例代码

swiftNEGameKit.getInstance().destroy()
此文档是否对你有帮助?
有帮助
去反馈
  • 开发环境要求
  • 前提条件
  • 示例项目源码
  • API 时序图
  • 实现方法
  • 步骤1 下载并引入游戏房源码
  • 步骤2 初始化 GameKit
  • 步骤3 主播选择并创建游戏
  • 步骤4 主播和玩家参与游戏
  • 步骤5 主播开始游戏
  • 步骤6 主播结束游戏
  • 步骤7 销毁游戏,清理游戏资源