refactor: 重构战斗系统动作提交和竞技场锁定逻辑
Some checks failed
ci/woodpecker/push/my-first-workflow Pipeline failed
Some checks failed
ci/woodpecker/push/my-first-workflow Pipeline failed
This commit is contained in:
@@ -1,14 +1,11 @@
|
||||
package fight
|
||||
|
||||
import (
|
||||
"blazing/cool"
|
||||
"blazing/logic/service/common"
|
||||
"blazing/logic/service/fight/action"
|
||||
"blazing/logic/service/fight/info"
|
||||
"blazing/logic/service/fight/input"
|
||||
"blazing/modules/player/model"
|
||||
"context"
|
||||
"time"
|
||||
|
||||
"github.com/jinzhu/copier"
|
||||
)
|
||||
@@ -26,6 +23,83 @@ func (*FightC) Compare(a, b action.BattleActionI) (action.BattleActionI, action.
|
||||
return a, b // 速度相同时,发起方优先
|
||||
}
|
||||
|
||||
const maxPendingActionsPerPlayer = 2
|
||||
|
||||
func (f *FightC) openActionWindow() {
|
||||
f.actionMu.Lock()
|
||||
f.acceptActions = true
|
||||
f.pendingActions = f.pendingActions[:0]
|
||||
f.actionMu.Unlock()
|
||||
}
|
||||
|
||||
func (f *FightC) closeActionWindow() {
|
||||
f.actionMu.Lock()
|
||||
f.acceptActions = false
|
||||
f.pendingActions = f.pendingActions[:0]
|
||||
f.actionMu.Unlock()
|
||||
}
|
||||
|
||||
func (f *FightC) submitAction(act action.BattleActionI) {
|
||||
if act == nil || f.closefight {
|
||||
return
|
||||
}
|
||||
|
||||
f.actionMu.Lock()
|
||||
if !f.acceptActions {
|
||||
f.actionMu.Unlock()
|
||||
return
|
||||
}
|
||||
count := 0
|
||||
replaceIndex := -1
|
||||
for i, pending := range f.pendingActions {
|
||||
if pending == nil || pending.GetPlayerID() != act.GetPlayerID() {
|
||||
continue
|
||||
}
|
||||
count++
|
||||
replaceIndex = i
|
||||
}
|
||||
if count >= maxPendingActionsPerPlayer && replaceIndex >= 0 {
|
||||
f.pendingActions[replaceIndex] = act
|
||||
} else {
|
||||
f.pendingActions = append(f.pendingActions, act)
|
||||
}
|
||||
notify := f.actionNotify
|
||||
f.actionMu.Unlock()
|
||||
|
||||
if notify == nil {
|
||||
return
|
||||
}
|
||||
|
||||
select {
|
||||
case notify <- struct{}{}:
|
||||
default:
|
||||
}
|
||||
}
|
||||
|
||||
func (f *FightC) nextAction() action.BattleActionI {
|
||||
f.actionMu.Lock()
|
||||
if len(f.pendingActions) == 0 {
|
||||
f.actionMu.Unlock()
|
||||
return nil
|
||||
}
|
||||
|
||||
act := f.pendingActions[0]
|
||||
copy(f.pendingActions, f.pendingActions[1:])
|
||||
f.pendingActions = f.pendingActions[:len(f.pendingActions)-1]
|
||||
hasMore := len(f.pendingActions) > 0
|
||||
notify := f.actionNotify
|
||||
f.actionMu.Unlock()
|
||||
|
||||
if hasMore && notify != nil {
|
||||
select {
|
||||
case notify <- struct{}{}:
|
||||
default:
|
||||
}
|
||||
}
|
||||
|
||||
return act
|
||||
}
|
||||
|
||||
// 玩家逃跑/无响应/掉线
|
||||
func (f *FightC) Over(c common.PlayerI, res model.EnumBattleOverReason) {
|
||||
if f.closefight {
|
||||
@@ -75,15 +149,7 @@ func (f *FightC) ChangePet(c common.PlayerI, id uint32) {
|
||||
BaseAction: action.NewBaseAction(c.GetInfo().UserID),
|
||||
Cid: id,
|
||||
}
|
||||
select {
|
||||
case f.actionChan <- ret:
|
||||
// 发送成功,可选记录日志
|
||||
// log.Printf("send skill success, userID: %d, skillID: %d", c.GetInfo().UserID, id)
|
||||
case <-time.After(time.Second * 60):
|
||||
// 通道满时的降级处理
|
||||
cool.Logger.Printf(context.Background(), "actionChan is full, failed to send skill, userID: %d, skillID: %d",
|
||||
c.GetInfo().UserID, id)
|
||||
}
|
||||
f.submitAction(ret)
|
||||
|
||||
}
|
||||
|
||||
@@ -116,16 +182,7 @@ func (f *FightC) UseSkill(c common.PlayerI, id uint32) {
|
||||
}
|
||||
|
||||
}
|
||||
// 非阻塞发送,避免goroutine永久阻塞
|
||||
select {
|
||||
case f.actionChan <- ret:
|
||||
// 发送成功,可选记录日志
|
||||
// log.Printf("send skill success, userID: %d, skillID: %d", c.GetInfo().UserID, id)
|
||||
case <-time.After(time.Second * 60):
|
||||
// 通道满时的降级处理
|
||||
cool.Logger.Printf(context.Background(), "actionChan is full, failed to send skill, userID: %d, skillID: %d",
|
||||
c.GetInfo().UserID, id)
|
||||
}
|
||||
f.submitAction(ret)
|
||||
}
|
||||
|
||||
// 玩家使用技能
|
||||
@@ -134,15 +191,7 @@ func (f *FightC) Capture(c common.PlayerI, id uint32) {
|
||||
|
||||
return
|
||||
}
|
||||
select {
|
||||
case f.actionChan <- &action.UseItemAction{BaseAction: action.NewBaseAction(c.GetInfo().UserID), ItemID: id}:
|
||||
// 发送成功,可选记录日志
|
||||
// log.Printf("send skill success, userID: %d, skillID: %d", c.GetInfo().UserID, id)
|
||||
case <-time.After(time.Second * 60):
|
||||
// 通道满时的降级处理
|
||||
cool.Logger.Printf(context.Background(), "actionChan is full, failed to send Capture, userID: %d ",
|
||||
c.GetInfo().UserID)
|
||||
}
|
||||
f.submitAction(&action.UseItemAction{BaseAction: action.NewBaseAction(c.GetInfo().UserID), ItemID: id})
|
||||
|
||||
}
|
||||
|
||||
@@ -151,20 +200,12 @@ func (f *FightC) UseItem(c common.PlayerI, cacthid, itemid uint32) {
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
if f.Info.Mode== info.BattleMode.PET_MELEE {
|
||||
go f.UseSkill(c, 0)
|
||||
return
|
||||
}
|
||||
select {
|
||||
case f.actionChan <- &action.UseItemAction{BaseAction: action.NewBaseAction(c.GetInfo().UserID), ItemID: itemid, CacthTime: cacthid}:
|
||||
// 发送成功,可选记录日志
|
||||
// log.Printf("send skill success, userID: %d, skillID: %d", c.GetInfo().UserID, id)
|
||||
case <-time.After(time.Second * 60):
|
||||
// 通道满时的降级处理
|
||||
cool.Logger.Printf(context.Background(), "actionChan is full, failed to send UseItem, userID: %d, skillID: %d",
|
||||
c.GetInfo().UserID, cacthid)
|
||||
|
||||
if f.Info.Mode == info.BattleMode.PET_MELEE {
|
||||
go f.UseSkill(c, 0)
|
||||
return
|
||||
}
|
||||
f.submitAction(&action.UseItemAction{BaseAction: action.NewBaseAction(c.GetInfo().UserID), ItemID: itemid, CacthTime: cacthid})
|
||||
}
|
||||
|
||||
// ReadyFight 处理玩家战斗准备逻辑,当满足条件时启动战斗循环
|
||||
|
||||
Reference in New Issue
Block a user