startNextRound.go 6.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209
  1. package teen
  2. import (
  3. "math/rand"
  4. "server/common"
  5. "server/game"
  6. "server/game/room"
  7. "server/msg"
  8. "time"
  9. "github.com/name5566/leaf/log"
  10. )
  11. // 向每个玩家发送当前回合的房间信息和玩家信息
  12. func sendCurrentRoundInfo(teenPattiRoom *room.Room) {
  13. for _, player := range teenPattiRoom.Players {
  14. if player.Agent != nil {
  15. nextRoundInfo := &msg.NextRound{
  16. Info: &msg.ReqJoinRoom{
  17. UserId: player.Id, // 设置当前玩家的 ID
  18. GameId: "teen_patti",
  19. RoomId: teenPattiRoom.Id,
  20. SitPos: player.SitPos,
  21. RoomInfo: buildRoom(teenPattiRoom), // 获取房间信息
  22. },
  23. }
  24. // 发送 NextRound 消息
  25. player.Agent.WriteMsg(nextRoundInfo)
  26. log.Debug("Sent current round info to player %v in room %v", player.Id, teenPattiRoom.Id)
  27. }
  28. }
  29. }
  30. // 打印 teenPattiRoom.Players 的详细信息
  31. func printPlayersInfo(teenPattiRoom *room.Room) {
  32. // 打印房间中的每个玩家
  33. for i, player := range teenPattiRoom.Players {
  34. if player != nil {
  35. log.Debug("Player %d: ID=%v, SitPos=%v, IsRobot=%v, Nickname=%v",
  36. i, player.Id, player.SitPos, player.IsRobot)
  37. } else {
  38. log.Debug("Player %d: Empty", i)
  39. }
  40. }
  41. }
  42. // 获取房间中所有空闲的座位号
  43. func getAvailableSitPos(teenPattiRoom *room.Room) []int32 {
  44. // 假设一个房间最多有 5 个座位
  45. maxSeats := int32(5)
  46. availableSitPos := []int32{}
  47. // 创建一个已占用座位的集合
  48. occupiedSeats := make(map[int32]bool)
  49. // 遍历当前房间的所有玩家
  50. for _, player := range teenPattiRoom.Players {
  51. if player != nil {
  52. occupiedSeats[player.SitPos] = true // 标记已占用的座位
  53. }
  54. }
  55. // 检查哪些座位没有被占用
  56. for i := int32(0); i < maxSeats; i++ { // 使用 int32 类型
  57. if !occupiedSeats[i] {
  58. availableSitPos = append(availableSitPos, i) // 如果座位没有被占用,加入空闲座位列表
  59. }
  60. }
  61. // 返回空闲座位的列表
  62. return availableSitPos
  63. }
  64. func removeOfflinePlayers(teenPattiRoom *room.Room) {
  65. // 遍历玩家列表,找出离线玩家
  66. for _, player := range teenPattiRoom.Players {
  67. if !player.IsRobot && player.Agent != nil {
  68. userData, ok := player.Agent.UserData().(*common.UserData)
  69. if !ok || userData == nil {
  70. continue // 避免崩溃
  71. }
  72. // 判断是否离线
  73. if userData.Status == 0 {
  74. // 直接调用 LeaveTeenPattiRoom 移除玩家
  75. LeaveTeenPattiRoom(teenPattiRoom, player.Id, "0")
  76. }
  77. }
  78. }
  79. }
  80. // 过滤出非机器人的玩家
  81. func filterNonRobotPlayers(teenPattiRoom *room.Room) []*room.Player {
  82. var players []*room.Player
  83. for _, player := range teenPattiRoom.Players {
  84. if !player.IsRobot {
  85. players = append(players, player)
  86. }
  87. }
  88. return players
  89. }
  90. // 初始化游戏
  91. func startNextRound(teenPattiRoom *room.Room) {
  92. teenPattiRoom.Status = room.RoomStatusWaiting
  93. var currentDealerSitPos int32 = -1
  94. removeOfflinePlayers(teenPattiRoom)
  95. // 计算房间内的非机器人玩家数量
  96. nonRobotPlayers := filterNonRobotPlayers(teenPattiRoom)
  97. if len(nonRobotPlayers) == 0 {
  98. // 没有真人玩家了,解散房间
  99. log.Debug("Room %v dissolved due to no players left.", teenPattiRoom.Id)
  100. // 执行解散房间的逻辑,比如通知玩家、释放资源等
  101. dissolveRoom(teenPattiRoom)
  102. return
  103. }
  104. // 加减机器人
  105. adjustRobotCount(teenPattiRoom)
  106. // 清理上一回合的玩家状态
  107. for _, player := range teenPattiRoom.Players {
  108. // 如果该玩家是庄家,记录下座位号
  109. if player.IsDealer {
  110. currentDealerSitPos = player.SitPos
  111. }
  112. player.IsPacked = false
  113. player.IsSeen = false
  114. player.IsShow = false
  115. player.IsDealer = false // 清空上一回合的庄家状态
  116. player.CanShow = false
  117. player.HandCards = []*msg.ReqCard{}
  118. }
  119. // 增加回合计数
  120. teenPattiRoom.Round++
  121. // 更新回合信息
  122. // teenPattiRoom.GameRound.Rounds = append(teenPattiRoom.GameRound.Rounds, &msg.ReqRound{
  123. // Round: int32(teenPattiRoom.Round),
  124. // })
  125. // 初始化回合数据
  126. // 旧的需要入库吗?
  127. teenPattiRoom.GameRound.Rounds = []*msg.ReqRound{}
  128. teenPattiRoom.GameRound.TotalBet = 0 // 重置总下注
  129. // 重置下注金额区间
  130. confInfo := loadTeemConf(teenPattiRoom.ConfId)
  131. teenPattiRoom.GameRound.ResBet = confInfo
  132. // 更新座位状态,假设 SelfSitPos 和 RoundSitPos 已正确设置
  133. teenPattiRoom.RoundSitPos = 0 // 开始新回合,座位重置
  134. // 设置新的庄家
  135. setNextDealerSitPos(teenPattiRoom, currentDealerSitPos)
  136. // 开始下一回合
  137. log.Debug("Starting round %d for room %s", teenPattiRoom.Round, teenPattiRoom.Id)
  138. // 向每个玩家发送当前回合的玩家信息
  139. sendCurrentRoundInfo(teenPattiRoom)
  140. // room.SaveRoomToRedis(teenPattiRoom)
  141. // 2秒后开始发牌
  142. game.Module.Skeleton.AfterFunc(time.Second*2, func() {
  143. log.Debug("---------------------------------------------------------------------------------------")
  144. log.Debug("startDealCard(teenPattiRoom) %v in room %v")
  145. printPlayersInfo(teenPattiRoom)
  146. go startDealCard(teenPattiRoom) // 继续发牌
  147. })
  148. }
  149. // 调整房间中的机器人数量
  150. func adjustRobotCount(teenPattiRoom *room.Room) {
  151. // 初始化随机数生成器
  152. random := rand.New(rand.NewSource(time.Now().UnixNano()))
  153. // 随机加减人数,确保人数在2到5之间
  154. currentPlayerCount := len(teenPattiRoom.Players)
  155. newPlayerCount := currentPlayerCount
  156. // 生成随机数来决定是否加人或减人
  157. if random.Intn(2) == 0 && newPlayerCount < 5 { // 50%几率加一个玩家,且最多不超过5人
  158. newPlayerCount++
  159. } else if random.Intn(3) == 0 && newPlayerCount > 2 { // 如果有更多于2个玩家,且随机选择去除玩家
  160. newPlayerCount--
  161. }
  162. // 打印 currentPlayerCount 和 newPlayerCount
  163. log.Debug("currentPlayerCount: %v", currentPlayerCount)
  164. log.Debug("newPlayerCount: %v", newPlayerCount)
  165. // 如果人数发生变化,则调整玩家数量
  166. if newPlayerCount != currentPlayerCount {
  167. if newPlayerCount > currentPlayerCount {
  168. // 获取空闲的座位
  169. availableSitPos := getAvailableSitPos(teenPattiRoom)
  170. // 如果没有空座位,不能再加入机器人
  171. if len(availableSitPos) == 0 {
  172. log.Debug("No available seats for new robot in room %v", teenPattiRoom.Id)
  173. return
  174. }
  175. // 加入新机器人
  176. addNewRobot(teenPattiRoom, availableSitPos)
  177. log.Debug("addNewRobot: %v")
  178. } else {
  179. // 随机去除一个机器人
  180. removeRandomRobot(teenPattiRoom)
  181. log.Debug("removeRandomRobot: %v")
  182. }
  183. }
  184. }