Files
bl/logic/controller/pet_繁殖.go
xinian d83cf365ac
Some checks failed
ci/woodpecker/push/my-first-workflow Pipeline failed
更新说明
2026-04-05 23:13:06 +08:00

209 lines
5.7 KiB
Go

package controller
import (
"blazing/common/socket/errorcode"
"blazing/logic/service/fight"
"blazing/logic/service/pet"
"blazing/logic/service/player"
"blazing/modules/config/service"
"blazing/modules/player/model"
"time"
"github.com/gogf/gf/v2/util/grand"
"github.com/yudeguang/ratelimit"
)
// GetBreedInfo 获取繁殖信息协议
// 前端到后端无数据 请求协议
func (ctl Controller) GetBreedInfo(
data *pet.C2S_GET_BREED_INFO, player *player.Player) (result *model.S2C_GET_BREED_INFO, err errorcode.ErrorCode) { //这个时候player应该是空的
result = &model.S2C_GET_BREED_INFO{}
r := player.Service.Egg.Get()
if r == nil {
return
}
result = &r.Data
// TODO: 实现获取繁殖信息的具体逻辑
return result, 0
}
// GetBreedPet 获取繁殖精灵
// 前端到后端
func (ctl Controller) GetBreedPet(
data *pet.C2S_GET_BREED_PET, playerObj *player.Player) (result *pet.S2C_GET_BREED_PET, err errorcode.ErrorCode) { //这个时候player应该是空的
_, malePet, found := playerObj.FindPet(data.MaleCatchTime)
if !found || !canBreedPet(malePet, 1) {
return nil, errorcode.ErrorCodes.ErrPokemonNotExists
}
result = &pet.S2C_GET_BREED_PET{}
compatibleFemaleIDs := buildBreedPetIDSet(service.NewEggService().GetData(malePet.ID))
if len(compatibleFemaleIDs) == 0 {
return result, 0
}
result.FemaleList = make([]uint32, 0, len(playerObj.Info.PetList))
for i := range playerObj.Info.PetList {
femalePet := &playerObj.Info.PetList[i]
if !canBreedPet(femalePet, 2) {
continue
}
if _, ok := compatibleFemaleIDs[femalePet.ID]; !ok {
continue
}
result.FemaleList = append(result.FemaleList, femalePet.CatchTime)
}
return result, 0
}
// StartBreed 开始繁殖协议
// 前端到后端
func (ctl Controller) StartBreed(
data *pet.C2S_START_BREED, player *player.Player) (result *fight.NullOutboundInfo, err errorcode.ErrorCode) { //这个时候player应该是空的
if data.Male == data.Female {
return nil, errorcode.ErrorCodes.ErrCannotPerformAction
}
_, malePet, found := player.FindPet(data.Male)
if !found || !canBreedPet(malePet, 1) {
return nil, errorcode.ErrorCodes.ErrPokemonNotExists
}
_, femalePet, found := player.FindPet(data.Female)
if !found || !canBreedPet(femalePet, 2) {
return nil, errorcode.ErrorCodes.ErrPokemonNotExists
}
if !canBreedPair(malePet.ID, femalePet.ID) {
return nil, errorcode.ErrorCodes.ErrCannotPerformAction
}
if !player.GetCoins(breedCost) {
return nil, errorcode.ErrorCodes.ErrSunDouInsufficient10016
}
result = &fight.NullOutboundInfo{}
if !player.Service.Egg.StartBreed(malePet, femalePet) {
return nil, errorcode.ErrorCodes.ErrCannotPerformAction
}
player.Info.Coins -= breedCost
malePet.Generation++
femalePet.Generation++
if grand.Meet(1, 2) {
malePet.Gender = 0
} else {
femalePet.Gender = 0
}
return result, 0
}
// GetEggList 获取精灵蛋数组
// 前端到后端无数据 请求协议
func canBreedPet(p *model.PetInfo, gender int) bool {
return p != nil && p.Level >= breedMinLevel && p.Gender == gender && p.Generation <= breedMaxGeneration
}
func buildBreedPetIDSet(ids []int32) map[uint32]struct{} {
ret := make(map[uint32]struct{}, len(ids))
for _, id := range ids {
ret[uint32(id)] = struct{}{}
}
return ret
}
func canBreedPair(maleID, femaleID uint32) bool {
_, ok := buildBreedPetIDSet(service.NewEggService().GetData(maleID))[femaleID]
return ok
}
// GetEggList 处理控制器请求。
func (ctl Controller) GetEggList(
data *pet.C2S_GET_EGG_LIST, player *player.Player) (result *pet.S2C_GET_EGG_LIST, err errorcode.ErrorCode) { //这个时候player应该是空的
result = &pet.S2C_GET_EGG_LIST{}
// TODO: 实现获取精灵蛋列表的逻辑
// 示例数据,实际应从玩家数据中获取
r := player.Service.Egg.Get()
if r == nil {
return
}
result.EggList = append(result.EggList, r.EggList...)
return result, 0
}
const (
breedMinLevel = 50
breedMaxGeneration = 9
breedCost = 1000
)
var limiter *ratelimit.Rule = ratelimit.NewRule()
// 简单规则案例
func init() {
//步骤二:增加一条或者多条规则组成复合规则,此复合规则必须至少包含一条规则
limiter.AddRule(time.Second*1, 1)
//步骤三:调用函数判断某用户是否允许访问 allow:= r.AllowVisit(user)
}
// EffectHatch 精灵蛋互动协议
// 前端到后端
func (ctl Controller) EffectHatch(
data *pet.C2S_EFFECT_HATCH, playerObj *player.Player) (result *pet.S2C_EFFECT_HATCH, err errorcode.ErrorCode) {
if !limiter.AllowVisit(data.Head.UserID) {
return nil, errorcode.ErrorCodes.ErrCannotPerformAction
}
result = &pet.S2C_EFFECT_HATCH{}
tt := uint32(grand.N(1, 4))
if tt == data.Index {
result.Intimacy = playerObj.Service.Egg.EffectHatch()
}
return result, 0
}
// StartHatch 开始孵化精灵蛋
// 前端到后端
func (ctl Controller) StartHatch(
data *pet.C2S_START_HATCH, playerObj *player.Player) (result *pet.S2C_START_HATCH, err errorcode.ErrorCode) {
// TODO: 实现开始孵化精灵蛋的具体逻辑
result = &pet.S2C_START_HATCH{}
r := playerObj.Service.Egg.StartEgg(data.OwnerID, data.EggCatchTime)
if !r {
return nil, errorcode.ErrorCodes.ErrCannotPerformAction
}
return result, 0
}
// GetHatchPet 获得孵化精灵协议
// 前端到后端无数据内容 请求协议
func (ctl Controller) GetHatchPet(
data *pet.C2S_GET_HATCH_PET, playerObj *player.Player) (result *pet.S2C_GET_HATCH_PET, err errorcode.ErrorCode) {
result = &pet.S2C_GET_HATCH_PET{}
// TODO: 实现获得孵化精灵的具体逻辑,这里暂时返回默认值
r := playerObj.Service.Egg.GetEgg()
if r == nil {
return nil, errorcode.ErrorCodes.ErrSystemError
}
playerObj.Service.Pet.PetAdd(r, 0)
result.PetID = r.ID
result.CatchTime = r.CatchTime
return result, 0
}