不能交换的情况处理

This commit is contained in:
meixiongfeng 2023-10-23 16:52:15 +08:00
parent 90a1daf23a
commit da4b238cb9
4 changed files with 93 additions and 67 deletions

View File

@ -15,7 +15,7 @@ const (
MaxPs = 2 // 最大体力 MaxPs = 2 // 最大体力
MaxRound = 7 // 最大回合数 MaxRound = 7 // 最大回合数
MaxTime = 1800 // 游戏操作时间 MaxTime = 1800 // 游戏操作时间
AITime = 4 // AI延迟操作时间操作时间 随机+-3 // AITime = 4 // AI延迟操作时间操作时间 随机+-3
) )
//游戏房间 //游戏房间
@ -29,7 +29,7 @@ type Room struct {
module *Entertainment module *Entertainment
round int32 // 轮数 round int32 // 轮数
operatetimer *timewheel.Task //操作倒计时定时器 operatetimer *timewheel.Task //操作倒计时定时器
aiTimer *timewheel.Task //AI操作随机做个延时 //aiTimer *timewheel.Task //AI操作随机做个延时
curPower string // 当前操作的玩家 curPower string // 当前操作的玩家
NexPower string // 下一个操作的玩家 NexPower string // 下一个操作的玩家
} }
@ -56,16 +56,12 @@ func (this *Room) operateTimeOut(task *timewheel.Task, args ...interface{}) {
} // 回合+1 } // 回合+1
this.operatetimer = timewheel.Add(time.Second*MaxTime, this.operateTimeOut) // 开启新的定时器 this.operatetimer = timewheel.Add(time.Second*MaxTime, this.operateTimeOut) // 开启新的定时器
} }
if this.round > MaxRound { // 游戏结束
this.GameOver()
return
}
var szMap []*pb.MapData var szMap []*pb.MapData
szMap = append(szMap, &pb.MapData{ szMap = append(szMap, &pb.MapData{
Data: this.chessboard.Plat, Data: this.chessboard.Plat,
}) })
if err := this.module.SendMsgToSession(string(this.module.GetType()), "operatorrst", &pb.EntertainOperatorRstPush{ if err := this.module.SendMsgSyncToSession(string(this.module.GetType()), "operatorrst", &pb.EntertainOperatorRstPush{
Mpadata: szMap, Mpadata: szMap,
Power: this.NexPower, Power: this.NexPower,
Curpower: this.curPower, Curpower: this.curPower,
@ -78,6 +74,10 @@ func (this *Room) operateTimeOut(task *timewheel.Task, args ...interface{}) {
} }
// 变更权限 // 变更权限
this.curPower = this.NexPower this.curPower = this.NexPower
if this.round > MaxRound { // 游戏结束
this.GameOver()
return
}
} }
func (this *Room) InitRoom(module *Entertainment, s1 comm.IUserSession, s2 comm.IUserSession, p1 *pb.PlayerData, p2 *pb.PlayerData) *Room { func (this *Room) InitRoom(module *Entertainment, s1 comm.IUserSession, s2 comm.IUserSession, p1 *pb.PlayerData, p2 *pb.PlayerData) *Room {
@ -103,7 +103,7 @@ func (this *Room) InitRoom(module *Entertainment, s1 comm.IUserSession, s2 comm.
} }
// AI 操作了 // AI 操作了
func (this *Room) AiTimeOut(task *timewheel.Task, args ...interface{}) { func (this *Room) AiOperator() {
var ( var (
curScore int32 curScore int32
szMap []*pb.MapData szMap []*pb.MapData
@ -115,35 +115,20 @@ func (this *Room) AiTimeOut(task *timewheel.Task, args ...interface{}) {
this.NexPower = this.player1.Uid this.NexPower = this.player1.Uid
} }
this.player1.Ps = MaxPs this.player1.Ps = MaxPs
if this.aiTimer != nil {
timewheel.Remove(this.aiTimer)
}
// 交换元素 // 交换元素
if bSwap, m := this.chessboard.AiSwapGirde(); bSwap { if bSwap, m := this.chessboard.AiSwapGirde(); bSwap {
szMap = append(szMap, m...) szMap = append(szMap, m...)
} }
if this.NexPower != this.curPower { if this.NexPower != this.curPower {
// 清理旧的计时器 开启一个新的
if this.operatetimer != nil {
timewheel.Remove(this.operatetimer)
}
this.operatetimer = timewheel.Add(time.Second*MaxTime, this.operateTimeOut) // 开启新的定时器
this.round++ this.round++
if this.round > MaxRound { // 游戏结束
this.GameOver()
return
} }
}
this.player2.Score += curScore this.player2.Score += curScore
// 广播消息 // 广播消息
if err := this.module.SendMsgToSession(string(this.module.GetType()), "operatorrst", &pb.EntertainOperatorRstPush{ if err := this.module.SendMsgSyncToSession(string(this.module.GetType()), "operatorrst", &pb.EntertainOperatorRstPush{
Mpadata: szMap, Mpadata: szMap,
Power: this.curPower, Power: this.NexPower,
Curpower: this.curPower,
Score: curScore, Score: curScore,
Round: this.round, Round: this.round,
User1: this.player1, User1: this.player1,
@ -151,6 +136,14 @@ func (this *Room) AiTimeOut(task *timewheel.Task, args ...interface{}) {
}, this.szSession...); err != nil { }, this.szSession...); err != nil {
this.Errorln(err) this.Errorln(err)
} }
if this.round > MaxRound { // 游戏结束
this.GameOver()
return
}
this.curPower = this.NexPower
if len(this.szSession) == 1 && this.curPower == this.player2.Uid {
this.AiOperator()
}
} }
func (this *Room) ReceiveMessage(session comm.IUserSession, stype string, msg proto.Message) (errdata *pb.ErrorData) { func (this *Room) ReceiveMessage(session comm.IUserSession, stype string, msg proto.Message) (errdata *pb.ErrorData) {
@ -158,6 +151,7 @@ func (this *Room) ReceiveMessage(session comm.IUserSession, stype string, msg pr
case "operator": // 操作消息 case "operator": // 操作消息
var ( var (
curScore int32 curScore int32
AIOperator bool
) )
var szMap []*pb.MapData var szMap []*pb.MapData
req := msg.(*pb.EntertainOperatorReq) req := msg.(*pb.EntertainOperatorReq)
@ -171,7 +165,7 @@ func (this *Room) ReceiveMessage(session comm.IUserSession, stype string, msg pr
} }
// 交换元素 // 交换元素
if b, _ := this.chessboard.SwapGirde(req.Curid, req.Targetid, 1); !b { // 交换格子 if b := this.chessboard.SwapGirde(req.Curid, req.Targetid); !b { // 交换格子
errdata = &pb.ErrorData{ errdata = &pb.ErrorData{
Code: pb.ErrorCode_EntertainCantSwap, // 不能交换 直接返回 Code: pb.ErrorCode_EntertainCantSwap, // 不能交换 直接返回
Title: pb.ErrorCode_EntertainCantSwap.ToString(), Title: pb.ErrorCode_EntertainCantSwap.ToString(),
@ -182,54 +176,49 @@ func (this *Room) ReceiveMessage(session comm.IUserSession, stype string, msg pr
if score, m, _ := this.chessboard.CheckMap(1); score > 0 { if score, m, _ := this.chessboard.CheckMap(1); score > 0 {
curScore += score curScore += score
szMap = append(szMap, m...) szMap = append(szMap, m...)
} else { // 不能消除
this.chessboard.SwapGirde(req.Targetid, req.Curid) // 换到原来的位置
errdata = &pb.ErrorData{
Code: pb.ErrorCode_EntertainCantSwap, // 不能交换 直接返回
Title: pb.ErrorCode_EntertainCantSwap.ToString(),
}
return
} }
//this.player2.Score += curScore if this.curPower == this.player1.Uid { //权限校验
// 开启新的定时器
if this.NexPower == this.player1.Uid { //权限校验
this.player1.Score += curScore this.player1.Score += curScore
this.player1.Ps-- this.player1.Ps--
if this.player1.Ps <= 0 { // 权限给下一个人 if this.player1.Ps <= 0 { // 权限给下一个人
this.NexPower = this.player2.Uid this.NexPower = this.player2.Uid
this.curPower = this.player1.Uid
if len(this.szSession) == 1 { // 校验2号玩家是不是AI if len(this.szSession) == 1 { // 校验2号玩家是不是AI
// 起一个定时器 AIOperator = true
if this.aiTimer != nil {
timewheel.Remove(this.aiTimer)
}
this.aiTimer = timewheel.Add(time.Second*AITime, this.AiTimeOut)
} }
} }
this.player2.Ps = MaxPs this.player2.Ps = MaxPs
} else if this.NexPower == this.player2.Uid { } else if this.curPower == this.player2.Uid {
this.player2.Score += curScore this.player2.Score += curScore
this.player2.Ps-- this.player2.Ps--
if this.player2.Ps <= 0 { // 权限给下一个人 if this.player2.Ps <= 0 { // 权限给下一个人
this.NexPower = this.player1.Uid this.NexPower = this.player1.Uid
this.curPower = this.player2.Uid //当前操作的玩家
} }
this.player1.Ps = MaxPs this.player1.Ps = MaxPs
} else { // err 未知权限 } else { // err 未知权限
return return
} }
if this.NexPower == this.curPower { if this.NexPower != this.curPower {
this.round++ this.round++
if this.operatetimer != nil { if this.operatetimer != nil {
timewheel.Remove(this.operatetimer) timewheel.Remove(this.operatetimer)
this.operatetimer = timewheel.Add(time.Second*MaxTime, this.operateTimeOut) // 开启新的定时器 this.operatetimer = timewheel.Add(time.Second*MaxTime, this.operateTimeOut) // 开启新的定时器
} }
} }
if this.round > MaxRound { // 游戏结束
this.GameOver()
return
}
// 广播消息 // 广播消息
if err := this.module.SendMsgToSession(string(this.module.GetType()), "operatorrst", &pb.EntertainOperatorRstPush{ if err := this.module.SendMsgSyncToSession(string(this.module.GetType()), "operatorrst", &pb.EntertainOperatorRstPush{
Mpadata: szMap, Mpadata: szMap,
Power: this.curPower, Power: this.NexPower,
Curpower: this.NexPower, Curpower: this.curPower,
Score: curScore, Score: curScore,
Round: this.round, Round: this.round,
User1: this.player1, User1: this.player1,
@ -237,15 +226,22 @@ func (this *Room) ReceiveMessage(session comm.IUserSession, stype string, msg pr
}, this.szSession...); err != nil { }, this.szSession...); err != nil {
this.Errorln(err) this.Errorln(err)
} }
if this.round > MaxRound { // 游戏结束
this.GameOver()
return
}
// 变更权限 // 变更权限
this.curPower = this.NexPower this.curPower = this.NexPower
if AIOperator { // AI操作
this.AiOperator()
}
case "ready": case "ready":
if len(this.szSession) == 1 { // AI对战的话直接开始游戏 if len(this.szSession) == 1 { // AI对战的话直接开始游戏
this.NexPower = this.player1.Uid this.NexPower = this.player1.Uid
this.curPower = this.player1.Uid this.curPower = this.player1.Uid
this.player1.Ps = MaxPs this.player1.Ps = MaxPs
this.player2.Ps = MaxPs this.player2.Ps = MaxPs
if err := this.module.SendMsgToSession(string(this.module.GetType()), "startgame", &pb.EntertainStartGamePush{ if err := this.module.SendMsgSyncToSession(string(this.module.GetType()), "startgame", &pb.EntertainStartGamePush{
User1: this.player1, User1: this.player1,
User2: this.player2, User2: this.player2,
Mpadata: &pb.MapData{Data: this.chessboard.Plat}, Mpadata: &pb.MapData{Data: this.chessboard.Plat},
@ -265,13 +261,10 @@ func (this *Room) ReceiveMessage(session comm.IUserSession, stype string, msg pr
// 游戏结束 // 游戏结束
func (this *Room) GameOver() (errdata *pb.ErrorData) { func (this *Room) GameOver() (errdata *pb.ErrorData) {
if this.aiTimer != nil {
timewheel.Remove(this.aiTimer)
}
if this.operatetimer != nil { if this.operatetimer != nil {
timewheel.Remove(this.operatetimer) timewheel.Remove(this.operatetimer)
} }
this.module.SendMsgToSession(string(this.module.GetType()), "gameover", &pb.EntertainGameOverPush{ this.module.SendMsgSyncToSession(string(this.module.GetType()), "gameover", &pb.EntertainGameOverPush{
User1: this.player1, User1: this.player1,
User2: this.player2, User2: this.player2,
Mpadata: &pb.MapData{ Mpadata: &pb.MapData{

View File

@ -64,7 +64,7 @@ func (this *MapData) InitMap(module *Entertainment) {
} }
// 交换2个元素(参数 oid ) // 交换2个元素(参数 oid )
func (this *MapData) SwapGirde(oldId, newId int32, color int32) (bSwap bool, xCount int32) { func (this *MapData) SwapGirde(oldId, newId int32) (bSwap bool) {
this.operElem = []int32{} // 初始化 this.operElem = []int32{} // 初始化
if (oldId%Height+1 < Total && oldId+1 == newId) || if (oldId%Height+1 < Total && oldId+1 == newId) ||
(oldId%Height > 0 && oldId-1 == newId) || (oldId%Height > 0 && oldId-1 == newId) ||
@ -499,9 +499,8 @@ func (this *MapData) AiSwapGirde() (bSwap bool, szMap []*pb.MapData) {
for pos := 0; pos < Total; pos++ { for pos := 0; pos < Total; pos++ {
y := pos % Height y := pos % Height
if y < Height-1 { if y < Height-1 {
if b, _ := this.SwapGirde(int32(pos), int32(pos+1), 2); b { if b := this.SwapGirde(int32(pos), int32(pos+1)); b {
if s, m, _ := this.CheckMap(2); s == 0 { if s, m, _ := this.CheckMap(2); s == 0 {
this.SwapGirde(int32(pos+1), int32(pos), 2)
this.operElem = []int32{} this.operElem = []int32{}
} else { } else {
szMap = append(szMap, m...) szMap = append(szMap, m...)
@ -512,9 +511,9 @@ func (this *MapData) AiSwapGirde() (bSwap bool, szMap []*pb.MapData) {
} }
} }
if pos/Width+1 < Width { if pos/Width+1 < Width {
if b, _ := this.SwapGirde(int32(pos), int32(pos+Width), 2); b { if b := this.SwapGirde(int32(pos), int32(pos+Width)); b {
if s, m, _ := this.CheckMap(2); s == 0 { if s, m, _ := this.CheckMap(2); s == 0 {
this.SwapGirde(int32(pos+Width), int32(pos), 2) this.SwapGirde(int32(pos+Width), int32(pos))
this.operElem = []int32{} this.operElem = []int32{}
} else { } else {
szMap = append(szMap, m...) szMap = append(szMap, m...)

View File

@ -90,7 +90,7 @@ func Test_Main(t *testing.T) {
if bSwap, m := m.AiSwapGirde(); bSwap { if bSwap, m := m.AiSwapGirde(); bSwap {
szMap = append(szMap, m...) szMap = append(szMap, m...)
} }
m.SwapGirde(1, 8, 1) m.SwapGirde(1, 8)
m.DropGirde() m.DropGirde()
@ -98,7 +98,7 @@ func Test_Main(t *testing.T) {
szMap = append(szMap, m...) szMap = append(szMap, m...)
} }
m.SwapGirde(1, 11, 1) m.SwapGirde(1, 11)
m.DropGirde() m.DropGirde()
m.CheckMap(1) m.CheckMap(1)

View File

@ -308,6 +308,40 @@ func (this *ModuleBase) SendMsgToSession(mainType, subType string, msg proto.Mes
} }
return return
} }
func (this *ModuleBase) SendMsgSyncToSession(mainType, subType string, msg proto.Message, users ...comm.IUserSession) (err error) {
var (
gateways map[string]map[string][]string = make(map[string]map[string][]string)
cluster map[string][]string = make(map[string][]string)
gateway []string
ok bool
)
for _, v := range users {
if cluster, ok = gateways[v.GetServiecTag()]; !ok {
cluster = make(map[string][]string)
gateways[v.GetServiecTag()] = cluster
}
if gateway, ok = cluster[v.GetGatewayServiceId()]; !ok {
gateway = make([]string, 0)
cluster[v.GetGatewayServiceId()] = gateway
}
cluster[v.GetGatewayServiceId()] = append(cluster[v.GetGatewayServiceId()], v.GetSessionId())
}
data, _ := anypb.New(msg)
for k, v := range gateways {
for k1, v1 := range v {
ctx, _ := context.WithTimeout(context.Background(), time.Second*5)
if err = this.service.AcrossClusterRpcCall(ctx, k, fmt.Sprintf("%s/%s", comm.Service_Gateway, k1), string(comm.Rpc_GatewaySendBatchMsg), &pb.BatchMessageReq{
UserSessionIds: v1,
MainType: mainType,
SubType: subType,
Data: data,
}, nil); err != nil {
log.Errorf("SendMsgToUsers:%s.%s->%s.%s err:%v", k1, k, mainType, subType, err)
}
}
}
return
}
// 只校验资源 参数 atn格式 // 只校验资源 参数 atn格式
func (this *ModuleBase) CheckRes(session comm.IUserSession, res []*cfg.Gameatn) (errdata *pb.ErrorData) { func (this *ModuleBase) CheckRes(session comm.IUserSession, res []*cfg.Gameatn) (errdata *pb.ErrorData) {