宠物皮毛功能开发

This commit is contained in:
hahwu 2026-02-28 18:36:29 +08:00
parent cf5f30cebb
commit b3689ca93d
11 changed files with 317 additions and 2 deletions

View File

@ -0,0 +1,57 @@
package fur_cfg
import (
"server/game/mod/item"
"server/gamedata"
)
const (
CFG_FUR_CONST = "FurShopConst"
CFG_FUR_SHOP = "FurShop"
)
func init() {
gamedata.InitCfg(CFG_FUR_CONST)
gamedata.InitCfg(CFG_FUR_SHOP)
}
func GetFurShopCost(id int) []*item.Item {
data, err := gamedata.GetDataByIntKey(CFG_FUR_SHOP, id)
if err != nil {
return nil
}
return gamedata.GetItemList(data, "Cost")
}
func GetFurShopFreeTimes() int {
data, err := gamedata.GetDataByKey(CFG_FUR_CONST, "free_unlock")
if err != nil {
return 0
}
return gamedata.GetIntValue(data, "Value")
}
func GetFurShopTag(id int) int {
data, err := gamedata.GetDataByIntKey(CFG_FUR_SHOP, id)
if err != nil {
return 0
}
return gamedata.GetIntValue(data, "TAG")
}
func GetFurShopItem(id int) []*item.Item {
data, err := gamedata.GetDataByIntKey(CFG_FUR_SHOP, id)
if err != nil {
return nil
}
itemId := gamedata.GetIntValue(data, "ItemID")
if itemId == 0 {
return nil
}
return []*item.Item{
{
Id: itemId,
Num: 1,
},
}
}

View File

@ -454,6 +454,7 @@ func (ad *GameLogic) GetResFriendPlayerByUid(Id int) *msg.ResFriendPlayerSimple
Physiology: GoUtil.MapIntToInt32(player.Physiology), Physiology: GoUtil.MapIntToInt32(player.Physiology),
Last: last, Last: last,
PetName: player.PetName, PetName: player.PetName,
PetFur: int32(player.PetFur),
} }
} }
@ -840,6 +841,9 @@ func (ad *GameLogic) RegisterNetWorkFunc() {
RegisterMsgProcessFunc("ReqPlayroomTaskReward", ReqPlayroomTaskReward) // 领取任务奖励 RegisterMsgProcessFunc("ReqPlayroomTaskReward", ReqPlayroomTaskReward) // 领取任务奖励
RegisterMsgProcessFunc("ReqPlayroomGameShowReward", ReqPlayroomGameShowReward) // 展示游戏结果数据 RegisterMsgProcessFunc("ReqPlayroomGameShowReward", ReqPlayroomGameShowReward) // 展示游戏结果数据
RegisterMsgProcessFunc("ReqPlayroomGuide", ReqPlayroomGuide) // 展示游戏结果数据 RegisterMsgProcessFunc("ReqPlayroomGuide", ReqPlayroomGuide) // 展示游戏结果数据
RegisterMsgProcessFunc("ReqPetFur", ReqPetFur) // 宠物毛皮信息
RegisterMsgProcessFunc("ReqPetFurBuy", ReqPetFurBuy) // 宠物毛皮商店购买
RegisterMsgProcessFunc("ReqFurSet", ReqFurSet) //宠物毛皮设置
// 宠物宝藏 // 宠物宝藏
RegisterMsgProcessFunc("ReqFriendTreasure", ReqFriendTreasure) // 请求好友宝藏数据 RegisterMsgProcessFunc("ReqFriendTreasure", ReqFriendTreasure) // 请求好友宝藏数据
RegisterMsgProcessFunc("ReqFriendTreasureStart", ReqFriendTreasureStart) // 开始游戏 RegisterMsgProcessFunc("ReqFriendTreasureStart", ReqFriendTreasureStart) // 开始游戏

View File

@ -39,6 +39,7 @@ type PlayerSimpleData struct {
Physiology map[int]int Physiology map[int]int
Lang int Lang int
Account string Account string
PetFur int
} }
type VarGoldCard struct { type VarGoldCard struct {

View File

@ -0,0 +1,84 @@
package fur
import (
"fmt"
fur_cfg "server/conf/fur"
"server/game/mod/item"
"server/msg"
)
type FurMod struct {
Set int
List map[int]*FurInfo
Free int
}
type FurInfo struct {
Id int
AddTime int64
EndTime int64
}
func (f *FurMod) InitData() {
if f.List == nil {
f.List = make(map[int]*FurInfo)
}
}
// 获取毛皮信息
func (f *FurMod) GetFurInfo(id int) *FurInfo {
info, ok := f.List[id]
if !ok {
return nil
}
return info
}
// 增加毛皮
func (f *FurMod) AddFurInfo(id int, addTime, endTime int64) {
f.List[id] = &FurInfo{
Id: id,
AddTime: addTime,
EndTime: endTime,
}
}
func (f *FurMod) GetFurBuyCost(id int) ([]*item.Item, []*item.Item) {
freeCount := fur_cfg.GetFurShopFreeTimes()
if f.Free < freeCount {
f.Free++
return nil, fur_cfg.GetFurShopItem(id)
}
return fur_cfg.GetFurShopCost(id), fur_cfg.GetFurShopItem(id)
}
// 设置毛皮
func (f *FurMod) SetFur(id int) error {
if id == 0 {
f.Set = 0
return nil
}
if _, ok := f.List[id]; !ok {
return fmt.Errorf("fur id not found")
}
f.Set = id
return nil
}
func (f *FurMod) GetFurSet() int {
return f.Set
}
// 消息返回
func (f *FurMod) BackData() *msg.ResPetFur {
freeCount := fur_cfg.GetFurShopFreeTimes()
furId := make([]int32, 0, len(f.List))
for id := range f.List {
furId = append(furId, int32(id))
}
return &msg.ResPetFur{
FurId: furId,
FurSet: int32(f.Set),
FreeCount: int32(freeCount - f.Free),
}
}

View File

@ -58,6 +58,7 @@ const (
ITEM_TYPE_PLAYROOM_DRESS_SET = 114 // playroom服饰套装 ITEM_TYPE_PLAYROOM_DRESS_SET = 114 // playroom服饰套装
ITEM_TYPE_PLAYROOM_BOX = 115 // playroom宝箱 ITEM_TYPE_PLAYROOM_BOX = 115 // playroom宝箱
ITEM_TYPE_ACT_PASS = 116 // 通行证活动道具 ITEM_TYPE_ACT_PASS = 116 // 通行证活动道具
ITEM_TYPE_PET_FUR = 117 // 宠物毛皮
) )
func (i *ItemMod) InitData() { func (i *ItemMod) InitData() {

View File

@ -7,6 +7,7 @@ import (
"server/game/mod/chess" "server/game/mod/chess"
"server/game/mod/decorate" "server/game/mod/decorate"
"server/game/mod/endless" "server/game/mod/endless"
"server/game/mod/fur"
limitedTimeEvent "server/game/mod/limited_time_event" limitedTimeEvent "server/game/mod/limited_time_event"
"server/game/mod/mail" "server/game/mod/mail"
"server/game/mod/order" "server/game/mod/order"
@ -57,3 +58,7 @@ func (p *Player) GetSevenLoginMod() *sevenLogin.SevenLoginMod {
func (p *Player) GetOrderMod() *order.OrderMod { func (p *Player) GetOrderMod() *order.OrderMod {
return p.PlayMod.getOrderMod() return p.PlayMod.getOrderMod()
} }
func (p *Player) GetFurMod() *fur.FurMod {
return p.PlayMod.getFurMod()
}

View File

@ -582,6 +582,9 @@ func (p *Player) GetAgentByPlayer() gate.Agent {
// 处理物品 // 处理物品
func (p *Player) HandleLoseItem(itemList []*item.Item, Label string) error { func (p *Player) HandleLoseItem(itemList []*item.Item, Label string) error {
if itemList == nil {
return nil
}
for _, v := range itemList { for _, v := range itemList {
if v.Num > 0 { if v.Num > 0 {
v.Num = -v.Num v.Num = -v.Num
@ -590,7 +593,7 @@ func (p *Player) HandleLoseItem(itemList []*item.Item, Label string) error {
return p.HandleItem(itemList, Label) return p.HandleItem(itemList, Label)
} }
func (p *Player) HandleItem(itemList []*item.Item, Label string) error { func (p *Player) HandleItem(itemList []*item.Item, Label string) error {
if len(itemList) == 0 { if itemList == nil {
return nil return nil
} }
is_update := false is_update := false
@ -892,6 +895,11 @@ func (p *Player) HandleItem(itemList []*item.Item, Label string) error {
PassMod := p.PlayMod.getPassMod() PassMod := p.PlayMod.getPassMod()
PassMod.AddExp(v.Num) PassMod.AddExp(v.Num)
p.ActPassBackData() p.ActPassBackData()
case item.ITEM_TYPE_PET_FUR:
FurMod := p.PlayMod.getFurMod()
Effect := itemCfg.GetItemEffect(v.Id)
FurMod.AddFurInfo(Effect, GoUtil.Now(), 0)
BackDataType[item.ITEM_TYPE_PET_FUR] = struct{}{}
default: default:
err := ItemMod.AddItem(v.Id, v.Num) err := ItemMod.AddItem(v.Id, v.Num)
p.TeLog("asset_change", map[string]interface{}{ p.TeLog("asset_change", map[string]interface{}{
@ -931,6 +939,9 @@ func (p *Player) HandleItem(itemList []*item.Item, Label string) error {
item.ITEM_TYPE_PLAYROOM_DECORATION_SET, item.ITEM_TYPE_PLAYROOM_DECORATION_SET,
item.ITEM_TYPE_PLAYROOM_DRESS_SET: item.ITEM_TYPE_PLAYROOM_DRESS_SET:
p.PlayroomBackData() p.PlayroomBackData()
case item.ITEM_TYPE_PET_FUR:
FurMod := p.PlayMod.getFurMod()
p.PushClientRes(FurMod.BackData())
} }
} }
p.PetItemUseLog(itemList) p.PetItemUseLog(itemList)
@ -1063,6 +1074,7 @@ func (p *Player) UpdateUserInfo() {
simple.Physiology = p.PlayMod.getPlayroomMod().GetPhysiologyList() simple.Physiology = p.PlayMod.getPlayroomMod().GetPhysiologyList()
simple.Lang = int(p.PlayMod.getBaseMod().Lang) simple.Lang = int(p.PlayMod.getBaseMod().Lang)
simple.Account = p.PlayMod.getBaseMod().Account simple.Account = p.PlayMod.getBaseMod().Account
simple.PetFur = p.PlayMod.getFurMod().GetFurSet()
//TODO 存储到redis 在新版本中将优化成gob进行压缩 //TODO 存储到redis 在新版本中将优化成gob进行压缩
value, _ := json.Marshal(simple) value, _ := json.Marshal(simple)
IdStr := GoUtil.String(p.M_DwUin) IdStr := GoUtil.String(p.M_DwUin)

View File

@ -23,6 +23,7 @@ import (
"server/game/mod/face" "server/game/mod/face"
"server/game/mod/friend" "server/game/mod/friend"
friendTreasure "server/game/mod/friend_treasure.go" friendTreasure "server/game/mod/friend_treasure.go"
"server/game/mod/fur"
guesscolor "server/game/mod/guess_color" guesscolor "server/game/mod/guess_color"
"server/game/mod/guide" "server/game/mod/guide"
guideTask "server/game/mod/guide_task" guideTask "server/game/mod/guide_task"
@ -120,6 +121,7 @@ type PlayerModList struct {
Catnip catnip.CatnipMod // 猫草大作战 Catnip catnip.CatnipMod // 猫草大作战
GuideTask guideTask.GuideTaskMod // 引导任务 GuideTask guideTask.GuideTaskMod // 引导任务
Pass pass.PassMod // 通行证 Pass pass.PassMod // 通行证
Fur fur.FurMod // 毛皮
} }
func (p *PlayerModData) LoadDataFromDB(dwUin interface{}) bool { func (p *PlayerModData) LoadDataFromDB(dwUin interface{}) bool {
@ -221,6 +223,7 @@ func (p *PlayerModData) InitMod(player *Player) (bool, error) {
p.ModList.Compensation.InitData() p.ModList.Compensation.InitData()
p.ModList.GuideTask.InitData() p.ModList.GuideTask.InitData()
p.ModList.Pass.InitData() p.ModList.Pass.InitData()
p.ModList.Fur.InitData()
return is_update, nil return is_update, nil
} }
@ -439,3 +442,7 @@ func (p *PlayerMod) getGuideTaskMod() *guideTask.GuideTaskMod {
func (p *PlayerMod) getPassMod() *pass.PassMod { func (p *PlayerMod) getPassMod() *pass.PassMod {
return &p.mod_list.Pass return &p.mod_list.Pass
} }
func (p *PlayerMod) getFurMod() *fur.FurMod {
return &p.mod_list.Fur
}

View File

@ -0,0 +1,52 @@
package game
import (
"server/msg"
"google.golang.org/protobuf/proto"
)
func ReqPetFur(player *Player, buf []byte) error {
FurMod := player.GetFurMod()
player.PushClientRes(FurMod.BackData())
return nil
}
func ReqPetFurBuy(player *Player, buf []byte) error {
var req msg.ReqPetFurBuy
err := proto.Unmarshal(buf, &req)
if err != nil {
return err
}
FurMod := player.GetFurMod()
costList, AddItem := FurMod.GetFurBuyCost(int(req.FurId))
// 扣除物品
err = player.HandleLoseItem(costList, msg.ITEM_POP_LABEL_PetFurShop.String())
if err != nil {
return err
}
// 增加物品
err = player.HandleItem(AddItem, msg.ITEM_POP_LABEL_PetFurShop.String())
if err != nil {
return err
}
player.PlayMod.save()
return nil
}
func ReqFurSet(player *Player, buf []byte) error {
var req msg.ReqFurSet
err := proto.Unmarshal(buf, &req)
if err != nil {
return err
}
FurMod := player.GetFurMod()
err = FurMod.SetFur(int(req.FurId))
if err != nil {
return err
}
player.UpdateUserInfo()
player.PlayMod.save()
player.PushClientRes(FurMod.BackData())
return nil
}

View File

@ -106,7 +106,7 @@ func TestNotify(t *testing.T) {
// titlekey, infokey := notification_cfg.GetPetroomGameNotificationMsg() // titlekey, infokey := notification_cfg.GetPetroomGameNotificationMsg()
// title := languageCfg.GetLanguage(msg.LANG_TYPE(1), titlekey) // title := languageCfg.GetLanguage(msg.LANG_TYPE(1), titlekey)
// info := languageCfg.GetLanguage(msg.LANG_TYPE(1), infokey) // info := languageCfg.GetLanguage(msg.LANG_TYPE(1), infokey)
GoUtil.NotifyPlayer(10130, 2, title, fmt.Sprintf(info, "猫猫")) GoUtil.NotifyPlayer(3625212, 2, title, fmt.Sprintf(info, "猫猫"))
// GoUtil.NotifyPlayer(19246, 1, "Test Notification", "This is a test notification from the server.") // GoUtil.NotifyPlayer(19246, 1, "Test Notification", "This is a test notification from the server.")
} }

View File

@ -0,0 +1,92 @@
package test
import (
"fmt"
fur_cfg "server/conf/fur"
"server/game"
"server/msg"
"testing"
"google.golang.org/protobuf/proto"
)
func TestGetFurShopCost(t *testing.T) {
cost := fur_cfg.GetFurShopCost(1)
fmt.Printf("cost: %v", cost)
}
func TestGetFurShopFreeTimes(t *testing.T) {
freeTimes := fur_cfg.GetFurShopFreeTimes()
fmt.Printf("freeTimes: %d", freeTimes)
}
func TestGetFurShopTag(t *testing.T) {
tag := fur_cfg.GetFurShopTag(1)
fmt.Printf("tag: %d", tag)
}
func TestReqPetFur(t *testing.T) {
player := new(game.Player)
err := game.ReqPetFur(player, nil)
if err != nil {
t.Errorf("ReqPetFur error: %v", err)
}
}
func TestReqPetFurBuy(t *testing.T) {
player := new(game.Player)
player.InitPlayerByUid(100001)
m := msg.ReqPetFurBuy{
FurId: 1,
}
buf, err := proto.Marshal(&m)
if err != nil {
t.Errorf("marshal error: %v", err)
}
err = game.ReqPetFurBuy(player, buf)
if err != nil {
t.Errorf("ReqPetFurBuy error: %v", err)
}
m = msg.ReqPetFurBuy{
FurId: 2,
}
buf, err = proto.Marshal(&m)
if err != nil {
t.Errorf("marshal error: %v", err)
}
err = game.ReqPetFurBuy(player, buf)
if err != nil {
t.Errorf("ReqPetFurBuy error: %v", err)
}
}
func TestReqFurSet(t *testing.T) {
player := new(game.Player)
player.InitPlayerByUid(100001)
m := msg.ReqFurSet{
FurId: 1,
}
buf, err := proto.Marshal(&m)
if err != nil {
t.Errorf("marshal error: %v", err)
}
FurMod := player.GetFurMod()
FurMod.AddFurInfo(1, 0, 0)
err = game.ReqFurSet(player, buf)
if err != nil {
t.Errorf("ReqFurSet error: %v", err)
}
m = msg.ReqFurSet{
FurId: 0,
}
buf, err = proto.Marshal(&m)
if err != nil {
t.Errorf("marshal error: %v", err)
}
err = game.ReqFurSet(player, buf)
if err != nil {
t.Errorf("ReqFurSet error: %v", err)
}
}