实现更多的触发器

This commit is contained in:
flswld
2023-04-08 22:53:41 +08:00
parent 630c0444a0
commit e554b99e7e
14 changed files with 1065 additions and 364 deletions

View File

@@ -26,21 +26,24 @@ func (g *GMCmd) GMTeleportPlayer(userId, sceneId, dungeonId uint32, posX, posY,
return
}
dungeonPointId := uint32(0)
end := false
for _, pointData := range gdconf.GetScenePointMapBySceneId(int32(sceneId)) {
if end {
break
}
for _, v := range pointData.DungeonIds {
if uint32(v) == dungeonId {
dungeonPointId = uint32(pointData.Id)
end = true
if dungeonId != 0 {
end := false
for _, pointData := range gdconf.GetScenePointMapBySceneId(int32(sceneId)) {
if end {
break
}
for _, v := range pointData.DungeonIds {
if uint32(v) == dungeonId {
dungeonPointId = uint32(pointData.Id)
end = true
break
}
}
}
if dungeonPointId == 0 {
logger.Error("dungeon pointid not found, dungeonId: %v, uid: %v", dungeonId, userId)
return
}
}
if dungeonPointId == 0 {
return
}
GAME.TeleportPlayer(
player,
@@ -230,17 +233,17 @@ func (g *GMCmd) GMUnlockAllPoint(userId uint32, sceneId uint32) {
}
// GMCreateGadget 在玩家附近创建物件实体
func (g *GMCmd) GMCreateGadget(userId uint32, posX, posY, posZ float64, gadgetId, itemId, count uint32) {
func (g *GMCmd) GMCreateGadget(userId uint32, posX, posY, posZ float64, gadgetId uint32) {
player := USER_MANAGER.GetOnlineUser(userId)
if player == nil {
logger.Error("player is nil, uid: %v", userId)
return
}
GAME.CreateDropGadget(player, &model.Vector{
GAME.CreateGadget(player, &model.Vector{
X: posX,
Y: posY,
Z: posZ,
}, gadgetId, itemId, count)
}, gadgetId, nil)
}
// 系统级GM指令

View File

@@ -119,10 +119,10 @@ func (t *TickManager) userTimerHandle(userId uint32, action int, data []any) {
case UserTimerActionTest:
logger.Debug("UserTimerActionTest, data: %v, uid: %v", data[0], userId)
case UserTimerActionLuaCreateMonster:
logger.Debug("UserTimerActionLuaCreateMonster, groupId: %v, monsterConfigId: %v, uid: %v", data[0], data[1], userId)
logger.Debug("UserTimerActionLuaCreateMonster, groupId: %v, configId: %v, uid: %v", data[0], data[1], userId)
groupId := data[0].(uint32)
monsterConfigId := data[1].(uint32)
GAME.AddSceneGroupMonster(player, groupId, monsterConfigId)
configId := data[1].(uint32)
GAME.AddSceneGroupMonster(player, groupId, configId)
}
}

View File

@@ -5,7 +5,6 @@ import (
"time"
"hk4e/common/constant"
"hk4e/gdconf"
"hk4e/gs/model"
"hk4e/pkg/logger"
"hk4e/protocol/proto"
@@ -304,80 +303,19 @@ func (s *Scene) GetEntity(entityId uint32) *Entity {
return s.entityMap[entityId]
}
func (s *Scene) AddGroupSuiteMonster(groupId uint32, suiteId uint8, monsterConfigId uint32) uint32 {
group, exist := s.groupMap[groupId]
if !exist {
logger.Error("group not exist, groupId: %v", groupId)
return 0
}
suite, exist := group.suiteMap[suiteId]
if !exist {
logger.Error("suite not exist, suiteId: %v", suiteId)
return 0
}
groupConfig := gdconf.GetSceneGroup(int32(groupId))
if groupConfig == nil {
logger.Error("get scene group config is nil, groupId: %v", groupId)
return 0
}
monsterConfig, exist := groupConfig.MonsterMap[int32(monsterConfigId)]
if !exist {
logger.Error("monster config not exist, monsterConfigId: %v", monsterConfigId)
return 0
}
entityId := s.createConfigEntity(uint32(groupConfig.Id), monsterConfig)
entity := s.GetEntity(entityId)
suite.entityMap[entityId] = entity
return entityId
}
func (s *Scene) AddGroupSuite(groupId uint32, suiteId uint8) {
groupConfig := gdconf.GetSceneGroup(int32(groupId))
if groupConfig == nil {
logger.Error("get scene group config is nil, groupId: %v", groupId)
return
}
suiteConfig, exist := groupConfig.SuiteMap[int32(suiteId)]
if !exist {
logger.Error("invalid suiteId: %v", suiteId)
return
}
suite := &Suite{
entityMap: make(map[uint32]*Entity),
}
for _, monsterConfigId := range suiteConfig.MonsterConfigIdList {
monsterConfig, exist := groupConfig.MonsterMap[monsterConfigId]
if !exist {
logger.Error("monster config not exist, monsterConfigId: %v", monsterConfigId)
continue
}
entityId := s.createConfigEntity(uint32(groupConfig.Id), monsterConfig)
entity := s.GetEntity(entityId)
suite.entityMap[entityId] = entity
}
for _, gadgetConfigId := range suiteConfig.GadgetConfigIdList {
gadgetConfig, exist := groupConfig.GadgetMap[gadgetConfigId]
if !exist {
logger.Error("gadget config not exist, gadgetConfigId: %v", gadgetConfigId)
continue
}
entityId := s.createConfigEntity(uint32(groupConfig.Id), gadgetConfig)
entity := s.GetEntity(entityId)
suite.entityMap[entityId] = entity
}
for _, npcConfig := range groupConfig.NpcMap {
entityId := s.createConfigEntity(uint32(groupConfig.Id), npcConfig)
entity := s.GetEntity(entityId)
suite.entityMap[entityId] = entity
}
func (s *Scene) AddGroupSuite(groupId uint32, suiteId uint8, entityMap map[uint32]*Entity) {
group, exist := s.groupMap[groupId]
if !exist {
group = &Group{
id: groupId,
suiteMap: make(map[uint8]*Suite),
}
s.groupMap[groupId] = group
}
group.suiteMap[suiteId] = suite
group.suiteMap[suiteId] = &Suite{
id: suiteId,
entityMap: entityMap,
}
}
func (s *Scene) RemoveGroupSuite(groupId uint32, suiteId uint8) {
@@ -397,90 +335,20 @@ func (s *Scene) RemoveGroupSuite(groupId uint32, suiteId uint8) {
delete(group.suiteMap, suiteId)
}
// 创建配置表里的实体
func (s *Scene) createConfigEntity(groupId uint32, entityConfig any) uint32 {
switch entityConfig.(type) {
case *gdconf.Monster:
monster := entityConfig.(*gdconf.Monster)
return s.CreateEntityMonster(
&model.Vector{X: float64(monster.Pos.X), Y: float64(monster.Pos.Y), Z: float64(monster.Pos.Z)},
&model.Vector{X: float64(monster.Rot.X), Y: float64(monster.Rot.Y), Z: float64(monster.Rot.Z)},
uint32(monster.MonsterId), uint8(monster.Level), getTempFightPropMap(), uint32(monster.ConfigId), groupId,
)
case *gdconf.Npc:
npc := entityConfig.(*gdconf.Npc)
return s.CreateEntityNpc(
&model.Vector{X: float64(npc.Pos.X), Y: float64(npc.Pos.Y), Z: float64(npc.Pos.Z)},
&model.Vector{X: float64(npc.Rot.X), Y: float64(npc.Rot.Y), Z: float64(npc.Rot.Z)},
uint32(npc.NpcId), 0, 0, 0, uint32(npc.ConfigId), groupId,
)
case *gdconf.Gadget:
gadget := entityConfig.(*gdconf.Gadget)
// 70500000并不是实际的物件id 根据节点类型对应采集物配置表
if gadget.PointType != 0 && gadget.GadgetId == 70500000 {
gatherDataConfig := gdconf.GetGatherDataByPointType(gadget.PointType)
if gatherDataConfig == nil {
return 0
}
return s.CreateEntityGadgetNormal(
&model.Vector{X: float64(gadget.Pos.X), Y: float64(gadget.Pos.Y), Z: float64(gadget.Pos.Z)},
&model.Vector{X: float64(gadget.Rot.X), Y: float64(gadget.Rot.Y), Z: float64(gadget.Rot.Z)},
uint32(gatherDataConfig.GadgetId),
uint32(constant.GADGET_STATE_DEFAULT),
&GadgetNormalEntity{
isDrop: false,
itemId: uint32(gatherDataConfig.ItemId),
count: 1,
},
uint32(gadget.ConfigId),
groupId,
)
} else {
return s.CreateEntityGadgetNormal(
&model.Vector{X: float64(gadget.Pos.X), Y: float64(gadget.Pos.Y), Z: float64(gadget.Pos.Z)},
&model.Vector{X: float64(gadget.Rot.X), Y: float64(gadget.Rot.Y), Z: float64(gadget.Rot.Z)},
uint32(gadget.GadgetId),
uint32(gadget.State),
new(GadgetNormalEntity),
uint32(gadget.ConfigId),
groupId,
)
}
default:
return 0
}
}
// TODO 临时写死
func getTempFightPropMap() map[uint32]float32 {
fpm := map[uint32]float32{
constant.FIGHT_PROP_BASE_ATTACK: float32(50.0),
constant.FIGHT_PROP_CUR_ATTACK: float32(50.0),
constant.FIGHT_PROP_BASE_DEFENSE: float32(500.0),
constant.FIGHT_PROP_CUR_DEFENSE: float32(500.0),
constant.FIGHT_PROP_BASE_HP: float32(50.0),
constant.FIGHT_PROP_CUR_HP: float32(50.0),
constant.FIGHT_PROP_MAX_HP: float32(50.0),
constant.FIGHT_PROP_PHYSICAL_SUB_HURT: float32(0.1),
constant.FIGHT_PROP_ICE_SUB_HURT: float32(0.1),
constant.FIGHT_PROP_FIRE_SUB_HURT: float32(0.1),
constant.FIGHT_PROP_ELEC_SUB_HURT: float32(0.1),
constant.FIGHT_PROP_WIND_SUB_HURT: float32(0.1),
constant.FIGHT_PROP_ROCK_SUB_HURT: float32(0.1),
constant.FIGHT_PROP_GRASS_SUB_HURT: float32(0.1),
constant.FIGHT_PROP_WATER_SUB_HURT: float32(0.1),
}
return fpm
}
type Group struct {
id uint32
suiteMap map[uint8]*Suite
}
type Suite struct {
id uint8
entityMap map[uint32]*Entity
}
func (g *Group) GetId() uint32 {
return g.id
}
func (g *Group) GetSuiteById(suiteId uint8) *Suite {
return g.suiteMap[suiteId]
}
@@ -521,6 +389,10 @@ func (g *Group) DestroyEntity(entityId uint32) {
}
}
func (s *Suite) GetId() uint8 {
return s.id
}
func (s *Suite) GetEntityById(entityId uint32) *Entity {
return s.entityMap[entityId]
}

View File

@@ -110,10 +110,20 @@ func RegLuaScriptLibFunc() {
gdconf.RegScriptLibFunc("BeginCameraSceneLook", BeginCameraSceneLook)
gdconf.RegScriptLibFunc("GetGroupMonsterCount", GetGroupMonsterCount)
gdconf.RegScriptLibFunc("ChangeGroupGadget", ChangeGroupGadget)
gdconf.RegScriptLibFunc("GetGadgetStateByConfigId", GetGadgetStateByConfigId)
gdconf.RegScriptLibFunc("SetGadgetStateByConfigId", SetGadgetStateByConfigId)
gdconf.RegScriptLibFunc("MarkPlayerAction", MarkPlayerAction)
gdconf.RegScriptLibFunc("AddQuestProgress", AddQuestProgress)
gdconf.RegScriptLibFunc("CreateMonster", CreateMonster)
gdconf.RegScriptLibFunc("CreateGadget", CreateGadget)
gdconf.RegScriptLibFunc("KillEntityByConfigId", KillEntityByConfigId)
gdconf.RegScriptLibFunc("AddExtraGroupSuite", AddExtraGroupSuite)
gdconf.RegScriptLibFunc("GetGroupVariableValue", GetGroupVariableValue)
gdconf.RegScriptLibFunc("GetGroupVariableValueByGroup", GetGroupVariableValueByGroup)
gdconf.RegScriptLibFunc("SetGroupVariableValue", SetGroupVariableValue)
gdconf.RegScriptLibFunc("SetGroupVariableValueByGroup", SetGroupVariableValueByGroup)
gdconf.RegScriptLibFunc("ChangeGroupVariableValue", ChangeGroupVariableValue)
gdconf.RegScriptLibFunc("ChangeGroupVariableValueByGroup", ChangeGroupVariableValueByGroup)
}
func GetEntityType(luaState *lua.LState) int {
@@ -185,6 +195,7 @@ func BeginCameraSceneLook(luaState *lua.LState) int {
ntf := new(proto.BeginCameraSceneLookNotify)
gdconf.ParseLuaTableToObject(cameraLockInfo, ntf)
GAME.SendMsg(cmd.BeginCameraSceneLookNotify, player.PlayerID, player.ClientSeq, ntf)
logger.Debug("BeginCameraSceneLook, ntf: %v, uid: %v", ntf, player.PlayerID)
luaState.Push(lua.LNumber(0))
return 1
}
@@ -244,6 +255,44 @@ func ChangeGroupGadget(luaState *lua.LState) int {
return 1
}
func GetGadgetStateByConfigId(luaState *lua.LState) int {
ctx, ok := luaState.Get(1).(*lua.LTable)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
player := GetContextPlayer(ctx, luaState)
if player == nil {
luaState.Push(lua.LNumber(-1))
return 1
}
groupId := luaState.ToInt(2)
configId := luaState.ToInt(3)
world := WORLD_MANAGER.GetWorldByID(player.WorldId)
if world == nil {
luaState.Push(lua.LNumber(-1))
return 1
}
scene := world.GetSceneById(player.SceneId)
group := scene.GetGroupById(uint32(groupId))
if group == nil {
luaState.Push(lua.LNumber(-1))
return 1
}
entity := group.GetEntityByConfigId(uint32(configId))
if entity == nil {
luaState.Push(lua.LNumber(-1))
return 1
}
if entity.GetEntityType() != constant.ENTITY_TYPE_GADGET {
luaState.Push(lua.LNumber(-1))
return 1
}
gadgetEntity := entity.GetGadgetEntity()
luaState.Push(lua.LNumber(gadgetEntity.GetGadgetState()))
return 1
}
func SetGadgetStateByConfigId(luaState *lua.LState) int {
ctx, ok := luaState.Get(1).(*lua.LTable)
if !ok {
@@ -304,7 +353,7 @@ func AddQuestProgress(luaState *lua.LState) int {
return 1
}
type CreateMonsterInfo struct {
type LuaTableParam struct {
ConfigId int32 `json:"config_id"`
DelayTime int32 `json:"delay_time"`
}
@@ -325,15 +374,252 @@ func CreateMonster(luaState *lua.LState) int {
luaState.Push(lua.LNumber(-1))
return 1
}
createMonsterInfoTable, ok := luaState.Get(2).(*lua.LTable)
luaTable, ok := luaState.Get(2).(*lua.LTable)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
createMonsterInfo := new(CreateMonsterInfo)
gdconf.ParseLuaTableToObject[*CreateMonsterInfo](createMonsterInfoTable, createMonsterInfo)
TICK_MANAGER.CreateUserTimer(player.PlayerID, UserTimerActionLuaCreateMonster, uint32(createMonsterInfo.DelayTime),
uint32(groupId), uint32(createMonsterInfo.ConfigId))
luaTableParam := new(LuaTableParam)
gdconf.ParseLuaTableToObject[*LuaTableParam](luaTable, luaTableParam)
TICK_MANAGER.CreateUserTimer(player.PlayerID, UserTimerActionLuaCreateMonster, uint32(luaTableParam.DelayTime),
uint32(groupId), uint32(luaTableParam.ConfigId))
luaState.Push(lua.LNumber(0))
return 1
}
func CreateGadget(luaState *lua.LState) int {
ctx, ok := luaState.Get(1).(*lua.LTable)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
player := GetContextPlayer(ctx, luaState)
if player == nil {
luaState.Push(lua.LNumber(-1))
return 1
}
groupId, ok := luaState.GetField(ctx, "groupId").(lua.LNumber)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
luaTable, ok := luaState.Get(2).(*lua.LTable)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
luaTableParam := new(LuaTableParam)
gdconf.ParseLuaTableToObject[*LuaTableParam](luaTable, luaTableParam)
groupConfig := gdconf.GetSceneGroup(int32(groupId))
if groupConfig == nil {
luaState.Push(lua.LNumber(-1))
return 1
}
gadget := groupConfig.GadgetMap[luaTableParam.ConfigId]
if gadget == nil {
luaState.Push(lua.LNumber(-1))
return 1
}
GAME.CreateGadget(player, &model.Vector{X: float64(gadget.Pos.X), Y: float64(gadget.Pos.Y), Z: float64(gadget.Pos.Z)},
uint32(gadget.GadgetId), nil)
luaState.Push(lua.LNumber(0))
return 1
}
func KillEntityByConfigId(luaState *lua.LState) int {
ctx, ok := luaState.Get(1).(*lua.LTable)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
player := GetContextPlayer(ctx, luaState)
if player == nil {
luaState.Push(lua.LNumber(-1))
return 1
}
groupId, ok := luaState.GetField(ctx, "groupId").(lua.LNumber)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
luaTable, ok := luaState.Get(2).(*lua.LTable)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
luaTableParam := new(LuaTableParam)
gdconf.ParseLuaTableToObject[*LuaTableParam](luaTable, luaTableParam)
world := WORLD_MANAGER.GetWorldByID(player.WorldId)
if world == nil {
luaState.Push(lua.LNumber(-1))
return 1
}
scene := world.GetSceneById(player.SceneId)
group := scene.GetGroupById(uint32(groupId))
entity := group.GetEntityByConfigId(uint32(luaTableParam.ConfigId))
GAME.KillEntity(player, scene, entity.GetId(), proto.PlayerDieType_PLAYER_DIE_NONE)
luaState.Push(lua.LNumber(0))
return 1
}
func AddExtraGroupSuite(luaState *lua.LState) int {
ctx, ok := luaState.Get(1).(*lua.LTable)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
player := GetContextPlayer(ctx, luaState)
if player == nil {
luaState.Push(lua.LNumber(-1))
return 1
}
groupId := luaState.ToInt(2)
suiteId := luaState.ToInt(3)
GAME.AddSceneGroupSuite(player, uint32(groupId), uint8(suiteId))
luaState.Push(lua.LNumber(0))
return 1
}
func GetGroupVariableValue(luaState *lua.LState) int {
ctx, ok := luaState.Get(1).(*lua.LTable)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
player := GetContextPlayer(ctx, luaState)
if player == nil {
luaState.Push(lua.LNumber(-1))
return 1
}
groupId, ok := luaState.GetField(ctx, "groupId").(lua.LNumber)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
name := luaState.ToString(2)
dbWorld := player.GetDbWorld()
dbScene := dbWorld.GetSceneById(player.SceneId)
dbSceneGroup := dbScene.GetSceneGroupById(uint32(groupId))
value := dbSceneGroup.GetVariableByName(name)
luaState.Push(lua.LNumber(value))
return 1
}
func GetGroupVariableValueByGroup(luaState *lua.LState) int {
ctx, ok := luaState.Get(1).(*lua.LTable)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
player := GetContextPlayer(ctx, luaState)
if player == nil {
luaState.Push(lua.LNumber(-1))
return 1
}
name := luaState.ToString(2)
groupId := luaState.ToInt(3)
dbWorld := player.GetDbWorld()
dbScene := dbWorld.GetSceneById(player.SceneId)
dbSceneGroup := dbScene.GetSceneGroupById(uint32(groupId))
value := dbSceneGroup.GetVariableByName(name)
luaState.Push(lua.LNumber(value))
return 1
}
func SetGroupVariableValue(luaState *lua.LState) int {
ctx, ok := luaState.Get(1).(*lua.LTable)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
player := GetContextPlayer(ctx, luaState)
if player == nil {
luaState.Push(lua.LNumber(-1))
return 1
}
groupId, ok := luaState.GetField(ctx, "groupId").(lua.LNumber)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
name := luaState.ToString(2)
value := luaState.ToInt(3)
dbWorld := player.GetDbWorld()
dbScene := dbWorld.GetSceneById(player.SceneId)
dbSceneGroup := dbScene.GetSceneGroupById(uint32(groupId))
dbSceneGroup.SetVariable(name, int32(value))
luaState.Push(lua.LNumber(0))
return 1
}
func SetGroupVariableValueByGroup(luaState *lua.LState) int {
ctx, ok := luaState.Get(1).(*lua.LTable)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
player := GetContextPlayer(ctx, luaState)
if player == nil {
luaState.Push(lua.LNumber(-1))
return 1
}
name := luaState.ToString(2)
value := luaState.ToInt(3)
groupId := luaState.ToInt(4)
dbWorld := player.GetDbWorld()
dbScene := dbWorld.GetSceneById(player.SceneId)
dbSceneGroup := dbScene.GetSceneGroupById(uint32(groupId))
dbSceneGroup.SetVariable(name, int32(value))
luaState.Push(lua.LNumber(0))
return 1
}
func ChangeGroupVariableValue(luaState *lua.LState) int {
ctx, ok := luaState.Get(1).(*lua.LTable)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
player := GetContextPlayer(ctx, luaState)
if player == nil {
luaState.Push(lua.LNumber(-1))
return 1
}
groupId, ok := luaState.GetField(ctx, "groupId").(lua.LNumber)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
name := luaState.ToString(2)
change := luaState.ToInt(3)
dbWorld := player.GetDbWorld()
dbScene := dbWorld.GetSceneById(player.SceneId)
dbSceneGroup := dbScene.GetSceneGroupById(uint32(groupId))
value := dbSceneGroup.GetVariableByName(name)
dbSceneGroup.SetVariable(name, value+int32(change))
luaState.Push(lua.LNumber(0))
return 1
}
func ChangeGroupVariableValueByGroup(luaState *lua.LState) int {
ctx, ok := luaState.Get(1).(*lua.LTable)
if !ok {
luaState.Push(lua.LNumber(-1))
return 1
}
player := GetContextPlayer(ctx, luaState)
if player == nil {
luaState.Push(lua.LNumber(-1))
return 1
}
name := luaState.ToString(2)
change := luaState.ToInt(3)
groupId := luaState.ToInt(4)
dbWorld := player.GetDbWorld()
dbScene := dbWorld.GetSceneById(player.SceneId)
dbSceneGroup := dbScene.GetSceneGroupById(uint32(groupId))
value := dbSceneGroup.GetVariableByName(name)
dbSceneGroup.SetVariable(name, value+int32(change))
luaState.Push(lua.LNumber(0))
return 1
}

View File

@@ -8,8 +8,12 @@ import (
"hk4e/pkg/logger"
)
// SceneRegionTriggerCheck 场景区域触发器检测
func (g *Game) SceneRegionTriggerCheck(player *model.Player, scene *Scene, oldPos *model.Vector, newPos *model.Vector, entityId uint32) {
func forEachPlayerSceneGroup(player *model.Player, handleFunc func(suiteConfig *gdconf.Suite, groupConfig *gdconf.Group)) {
world := WORLD_MANAGER.GetWorldByID(player.WorldId)
if world == nil {
return
}
scene := world.GetSceneById(player.SceneId)
for groupId, group := range scene.GetAllGroup() {
groupConfig := gdconf.GetSceneGroup(int32(groupId))
if groupConfig == nil {
@@ -18,133 +22,12 @@ func (g *Game) SceneRegionTriggerCheck(player *model.Player, scene *Scene, oldPo
}
for suiteId := range group.GetAllSuite() {
suiteConfig := groupConfig.SuiteMap[int32(suiteId)]
for _, regionConfigId := range suiteConfig.RegionConfigIdList {
regionConfig := groupConfig.RegionMap[regionConfigId]
if regionConfig == nil {
continue
}
shape := alg.NewShape()
switch uint8(regionConfig.Shape) {
case constant.REGION_SHAPE_SPHERE:
shape.NewSphere(&alg.Vector3{X: regionConfig.Pos.X, Y: regionConfig.Pos.Y, Z: regionConfig.Pos.Z}, regionConfig.Radius)
case constant.REGION_SHAPE_CUBIC:
shape.NewCubic(&alg.Vector3{X: regionConfig.Pos.X, Y: regionConfig.Pos.Y, Z: regionConfig.Pos.Z},
&alg.Vector3{X: regionConfig.Size.X, Y: regionConfig.Size.Y, Z: regionConfig.Size.Z})
case constant.REGION_SHAPE_CYLINDER:
shape.NewCylinder(&alg.Vector3{X: regionConfig.Pos.X, Y: regionConfig.Pos.Y, Z: regionConfig.Pos.Z},
regionConfig.Radius, regionConfig.Height)
case constant.REGION_SHAPE_POLYGON:
vector2PointArray := make([]*alg.Vector2, 0)
for _, vector := range regionConfig.PointArray {
// z就是y
vector2PointArray = append(vector2PointArray, &alg.Vector2{X: vector.X, Z: vector.Y})
}
shape.NewPolygon(&alg.Vector3{X: regionConfig.Pos.X, Y: regionConfig.Pos.Y, Z: regionConfig.Pos.Z},
vector2PointArray, regionConfig.Height)
}
oldPosInRegion := shape.Contain(&alg.Vector3{X: float32(oldPos.X), Y: float32(oldPos.Y), Z: float32(oldPos.Z)})
newPosInRegion := shape.Contain(&alg.Vector3{X: float32(newPos.X), Y: float32(newPos.Y), Z: float32(newPos.Z)})
if !oldPosInRegion && newPosInRegion {
logger.Debug("player enter region: %v, uid: %v", regionConfig, player.PlayerID)
for _, triggerName := range suiteConfig.TriggerNameList {
triggerConfig := groupConfig.TriggerMap[triggerName]
if triggerConfig.Event != constant.LUA_EVENT_ENTER_REGION {
continue
}
if triggerConfig.Condition != "" {
cond := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Condition,
&LuaCtx{uid: player.PlayerID},
&LuaEvt{param1: regionConfig.ConfigId, targetEntityId: entityId})
if !cond {
continue
}
}
logger.Debug("scene group trigger fire, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
if triggerConfig.Action != "" {
logger.Debug("scene group trigger do action, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
ok := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Action,
&LuaCtx{uid: player.PlayerID},
&LuaEvt{})
if !ok {
logger.Error("trigger action fail, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
}
}
for _, triggerDataConfig := range gdconf.GetTriggerDataMap() {
if triggerDataConfig.TriggerName == triggerConfig.Name {
g.TriggerQuest(player, constant.QUEST_FINISH_COND_TYPE_TRIGGER_FIRE, "", triggerDataConfig.TriggerId)
}
}
}
} else if oldPosInRegion && !newPosInRegion {
logger.Debug("player leave region: %v, uid: %v", regionConfig, player.PlayerID)
for _, triggerName := range suiteConfig.TriggerNameList {
triggerConfig := groupConfig.TriggerMap[triggerName]
if triggerConfig.Event != constant.LUA_EVENT_LEAVE_REGION {
continue
}
if triggerConfig.Condition != "" {
cond := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Condition,
&LuaCtx{uid: player.PlayerID},
&LuaEvt{param1: regionConfig.ConfigId, targetEntityId: entityId})
if !cond {
continue
}
}
logger.Debug("scene group trigger fire, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
if triggerConfig.Action != "" {
logger.Debug("scene group trigger do action, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
ok := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Action,
&LuaCtx{uid: player.PlayerID},
&LuaEvt{})
if !ok {
logger.Error("trigger action fail, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
}
}
}
}
}
handleFunc(suiteConfig, groupConfig)
}
}
}
// MonsterDieTriggerCheck 怪物死亡触发器检测
func (g *Game) MonsterDieTriggerCheck(player *model.Player, groupId uint32, group *Group) {
groupConfig := gdconf.GetSceneGroup(int32(groupId))
if groupConfig == nil {
logger.Error("get group config is nil, groupId: %v, uid: %v", groupId, player.PlayerID)
return
}
for suiteId := range group.GetAllSuite() {
suiteConfig := groupConfig.SuiteMap[int32(suiteId)]
for _, triggerName := range suiteConfig.TriggerNameList {
triggerConfig := groupConfig.TriggerMap[triggerName]
if triggerConfig.Event != constant.LUA_EVENT_ANY_MONSTER_DIE {
continue
}
if triggerConfig.Condition != "" {
cond := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Condition,
&LuaCtx{uid: player.PlayerID, groupId: groupId},
&LuaEvt{})
if !cond {
continue
}
}
logger.Debug("scene group trigger fire, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
if triggerConfig.Action != "" {
logger.Debug("scene group trigger do action, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
ok := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Action,
&LuaCtx{uid: player.PlayerID, groupId: groupId},
&LuaEvt{})
if !ok {
logger.Error("trigger action fail, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
}
}
}
}
}
// QuestStartTriggerCheck 任务开始触发器检测
func (g *Game) QuestStartTriggerCheck(player *model.Player, questId uint32) {
func forEachPlayerSceneGroupTrigger(player *model.Player, handleFunc func(triggerConfig *gdconf.Trigger, groupConfig *gdconf.Group)) {
world := WORLD_MANAGER.GetWorldByID(player.WorldId)
if world == nil {
return
@@ -160,28 +43,244 @@ func (g *Game) QuestStartTriggerCheck(player *model.Player, questId uint32) {
suiteConfig := groupConfig.SuiteMap[int32(suiteId)]
for _, triggerName := range suiteConfig.TriggerNameList {
triggerConfig := groupConfig.TriggerMap[triggerName]
if triggerConfig.Event != constant.LUA_EVENT_QUEST_START {
continue
}
if triggerConfig.Condition != "" {
cond := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Condition,
&LuaCtx{uid: player.PlayerID},
&LuaEvt{param1: int32(questId)})
if !cond {
continue
}
}
logger.Debug("scene group trigger fire, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
if triggerConfig.Action != "" {
logger.Debug("scene group trigger do action, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
ok := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Action,
&LuaCtx{uid: player.PlayerID, groupId: groupId},
&LuaEvt{})
if !ok {
logger.Error("trigger action fail, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
}
}
handleFunc(triggerConfig, groupConfig)
}
}
}
}
func forEachGroupTrigger(player *model.Player, group *Group, handleFunc func(triggerConfig *gdconf.Trigger, groupConfig *gdconf.Group)) {
groupConfig := gdconf.GetSceneGroup(int32(group.GetId()))
if groupConfig == nil {
logger.Error("get group config is nil, groupId: %v, uid: %v", group.GetId(), player.PlayerID)
return
}
for suiteId := range group.GetAllSuite() {
suiteConfig := groupConfig.SuiteMap[int32(suiteId)]
for _, triggerName := range suiteConfig.TriggerNameList {
triggerConfig := groupConfig.TriggerMap[triggerName]
handleFunc(triggerConfig, groupConfig)
}
}
}
// SceneRegionTriggerCheck 场景区域触发器检测
func (g *Game) SceneRegionTriggerCheck(player *model.Player, oldPos *model.Vector, newPos *model.Vector, entityId uint32) {
forEachPlayerSceneGroup(player, func(suiteConfig *gdconf.Suite, groupConfig *gdconf.Group) {
for _, regionConfigId := range suiteConfig.RegionConfigIdList {
regionConfig := groupConfig.RegionMap[regionConfigId]
if regionConfig == nil {
continue
}
shape := alg.NewShape()
switch uint8(regionConfig.Shape) {
case constant.REGION_SHAPE_SPHERE:
shape.NewSphere(&alg.Vector3{X: regionConfig.Pos.X, Y: regionConfig.Pos.Y, Z: regionConfig.Pos.Z}, regionConfig.Radius)
case constant.REGION_SHAPE_CUBIC:
shape.NewCubic(&alg.Vector3{X: regionConfig.Pos.X, Y: regionConfig.Pos.Y, Z: regionConfig.Pos.Z},
&alg.Vector3{X: regionConfig.Size.X, Y: regionConfig.Size.Y, Z: regionConfig.Size.Z})
case constant.REGION_SHAPE_CYLINDER:
shape.NewCylinder(&alg.Vector3{X: regionConfig.Pos.X, Y: regionConfig.Pos.Y, Z: regionConfig.Pos.Z},
regionConfig.Radius, regionConfig.Height)
case constant.REGION_SHAPE_POLYGON:
vector2PointArray := make([]*alg.Vector2, 0)
for _, vector := range regionConfig.PointArray {
// z就是y
vector2PointArray = append(vector2PointArray, &alg.Vector2{X: vector.X, Z: vector.Y})
}
shape.NewPolygon(&alg.Vector3{X: regionConfig.Pos.X, Y: regionConfig.Pos.Y, Z: regionConfig.Pos.Z},
vector2PointArray, regionConfig.Height)
}
oldPosInRegion := shape.Contain(&alg.Vector3{X: float32(oldPos.X), Y: float32(oldPos.Y), Z: float32(oldPos.Z)})
newPosInRegion := shape.Contain(&alg.Vector3{X: float32(newPos.X), Y: float32(newPos.Y), Z: float32(newPos.Z)})
if !oldPosInRegion && newPosInRegion {
logger.Debug("player enter region: %v, uid: %v", regionConfig, player.PlayerID)
for _, triggerName := range suiteConfig.TriggerNameList {
triggerConfig := groupConfig.TriggerMap[triggerName]
if triggerConfig.Event != constant.LUA_EVENT_ENTER_REGION {
continue
}
if triggerConfig.Condition != "" {
cond := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Condition,
&LuaCtx{uid: player.PlayerID, groupId: uint32(groupConfig.Id)},
&LuaEvt{param1: regionConfig.ConfigId, targetEntityId: entityId})
if !cond {
continue
}
}
logger.Debug("scene group trigger fire, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
if triggerConfig.Action != "" {
logger.Debug("scene group trigger do action, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
ok := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Action,
&LuaCtx{uid: player.PlayerID, groupId: uint32(groupConfig.Id)},
&LuaEvt{})
if !ok {
logger.Error("trigger action fail, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
}
}
for _, triggerDataConfig := range gdconf.GetTriggerDataMap() {
if triggerDataConfig.TriggerName == triggerConfig.Name {
g.TriggerQuest(player, constant.QUEST_FINISH_COND_TYPE_TRIGGER_FIRE, "", triggerDataConfig.TriggerId)
}
}
}
} else if oldPosInRegion && !newPosInRegion {
logger.Debug("player leave region: %v, uid: %v", regionConfig, player.PlayerID)
for _, triggerName := range suiteConfig.TriggerNameList {
triggerConfig := groupConfig.TriggerMap[triggerName]
if triggerConfig.Event != constant.LUA_EVENT_LEAVE_REGION {
continue
}
if triggerConfig.Condition != "" {
cond := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Condition,
&LuaCtx{uid: player.PlayerID, groupId: uint32(groupConfig.Id)},
&LuaEvt{param1: regionConfig.ConfigId, targetEntityId: entityId})
if !cond {
continue
}
}
logger.Debug("scene group trigger fire, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
if triggerConfig.Action != "" {
logger.Debug("scene group trigger do action, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
ok := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Action,
&LuaCtx{uid: player.PlayerID, groupId: uint32(groupConfig.Id)},
&LuaEvt{})
if !ok {
logger.Error("trigger action fail, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
}
}
}
}
}
})
}
// MonsterDieTriggerCheck 怪物死亡触发器检测
func (g *Game) MonsterDieTriggerCheck(player *model.Player, group *Group) {
forEachGroupTrigger(player, group, func(triggerConfig *gdconf.Trigger, groupConfig *gdconf.Group) {
if triggerConfig.Event != constant.LUA_EVENT_ANY_MONSTER_DIE {
return
}
if triggerConfig.Condition != "" {
cond := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Condition,
&LuaCtx{uid: player.PlayerID, groupId: uint32(groupConfig.Id)},
&LuaEvt{})
if !cond {
return
}
}
if triggerConfig.Action != "" {
logger.Debug("scene group trigger do action, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
ok := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Action,
&LuaCtx{uid: player.PlayerID, groupId: uint32(groupConfig.Id)},
&LuaEvt{})
if !ok {
logger.Error("trigger action fail, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
}
}
})
}
// QuestStartTriggerCheck 任务开始触发器检测
func (g *Game) QuestStartTriggerCheck(player *model.Player, questId uint32) {
forEachPlayerSceneGroupTrigger(player, func(triggerConfig *gdconf.Trigger, groupConfig *gdconf.Group) {
if triggerConfig.Event != constant.LUA_EVENT_QUEST_START {
return
}
if triggerConfig.Condition != "" {
cond := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Condition,
&LuaCtx{uid: player.PlayerID, groupId: uint32(groupConfig.Id)},
&LuaEvt{param1: int32(questId)})
if !cond {
return
}
}
if triggerConfig.Action != "" {
logger.Debug("scene group trigger do action, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
ok := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Action,
&LuaCtx{uid: player.PlayerID, groupId: uint32(groupConfig.Id)},
&LuaEvt{})
if !ok {
logger.Error("trigger action fail, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
}
}
})
}
// GadgetCreateTriggerCheck 物件创建触发器检测
func (g *Game) GadgetCreateTriggerCheck(player *model.Player, group *Group, configId uint32) {
forEachGroupTrigger(player, group, func(triggerConfig *gdconf.Trigger, groupConfig *gdconf.Group) {
if triggerConfig.Event != constant.LUA_EVENT_GADGET_CREATE {
return
}
if triggerConfig.Condition != "" {
cond := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Condition,
&LuaCtx{uid: player.PlayerID, groupId: uint32(groupConfig.Id)},
&LuaEvt{param1: int32(configId)})
if !cond {
return
}
}
if triggerConfig.Action != "" {
logger.Debug("scene group trigger do action, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
ok := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Action,
&LuaCtx{uid: player.PlayerID, groupId: uint32(groupConfig.Id)},
&LuaEvt{})
if !ok {
logger.Error("trigger action fail, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
}
}
})
}
// GadgetStateChangeTriggerCheck 物件状态变更触发器检测
func (g *Game) GadgetStateChangeTriggerCheck(player *model.Player, group *Group, configId uint32, state uint8) {
forEachGroupTrigger(player, group, func(triggerConfig *gdconf.Trigger, groupConfig *gdconf.Group) {
if triggerConfig.Event != constant.LUA_EVENT_GADGET_STATE_CHANGE {
return
}
if triggerConfig.Condition != "" {
cond := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Condition,
&LuaCtx{uid: player.PlayerID, groupId: uint32(groupConfig.Id)},
&LuaEvt{param1: int32(state), param2: int32(configId)})
if !cond {
return
}
}
if triggerConfig.Action != "" {
logger.Debug("scene group trigger do action, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
ok := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Action,
&LuaCtx{uid: player.PlayerID, groupId: uint32(groupConfig.Id)},
&LuaEvt{})
if !ok {
logger.Error("trigger action fail, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
}
}
})
}
// GroupLoadTriggerCheck 场景组加载触发器检测
func (g *Game) GroupLoadTriggerCheck(player *model.Player, group *Group) {
forEachGroupTrigger(player, group, func(triggerConfig *gdconf.Trigger, groupConfig *gdconf.Group) {
if triggerConfig.Event != constant.LUA_EVENT_GROUP_LOAD {
return
}
if triggerConfig.Condition != "" {
cond := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Condition,
&LuaCtx{uid: player.PlayerID, groupId: uint32(groupConfig.Id)},
&LuaEvt{})
if !cond {
return
}
}
if triggerConfig.Action != "" {
logger.Debug("scene group trigger do action, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
ok := CallLuaFunc(groupConfig.GetLuaState(), triggerConfig.Action,
&LuaCtx{uid: player.PlayerID, groupId: uint32(groupConfig.Id)},
&LuaEvt{})
if !ok {
logger.Error("trigger action fail, trigger: %+v, uid: %v", triggerConfig, player.PlayerID)
}
}
})
}

View File

@@ -19,7 +19,7 @@ func (g *Game) HandlePlayerExpAdd(userId uint32) {
for {
playerLevel := player.PropertiesMap[constant.PLAYER_PROP_PLAYER_LEVEL]
// 读取玩家等级配置表
playerLevelConfig := gdconf.GetPlayerLevelDataById(int32(playerLevel))
playerLevelConfig := gdconf.GetPlayerLevelDataByLevel(int32(playerLevel))
if playerLevelConfig == nil {
// 获取不到代表已经到达最大等级
break

View File

@@ -167,7 +167,7 @@ func (g *Game) CombatInvocationsNotify(player *model.Player, payloadMsg pb.Messa
Z: float64(motionInfo.Pos.Z),
})
// 场景区域触发器检测
g.SceneRegionTriggerCheck(player, scene, player.Pos, &model.Vector{
g.SceneRegionTriggerCheck(player, player.Pos, &model.Vector{
X: float64(motionInfo.Pos.X),
Y: float64(motionInfo.Pos.Y),
Z: float64(motionInfo.Pos.Z),

View File

@@ -523,27 +523,33 @@ func (g *Game) KillEntity(player *model.Player, scene *Scene, entityId uint32, d
}
entity.lifeState = constant.LIFE_STATE_DEAD
ntf := &proto.LifeStateChangeNotify{
EntityId: entity.id,
LifeState: uint32(entity.lifeState),
EntityId: entity.GetId(),
LifeState: uint32(entity.GetLifeState()),
DieType: dieType,
MoveReliableSeq: entity.lastMoveReliableSeq,
MoveReliableSeq: entity.GetLastMoveReliableSeq(),
}
g.SendToWorldA(scene.world, cmd.LifeStateChangeNotify, 0, ntf)
g.RemoveSceneEntityNotifyBroadcast(scene, proto.VisionType_VISION_DIE, []uint32{entity.id})
g.RemoveSceneEntityNotifyBroadcast(scene, proto.VisionType_VISION_DIE, []uint32{entity.GetId()})
// 删除实体
scene.DestroyEntity(entity.GetId())
group := scene.GetGroupById(entity.groupId)
group := scene.GetGroupById(entity.GetGroupId())
if group == nil {
return
}
dbWorld := player.GetDbWorld()
dbScene := dbWorld.GetSceneById(scene.GetId())
dbSceneGroup := dbScene.GetSceneGroupById(entity.GetGroupId())
dbSceneGroup.AddKill(entity.GetConfigId())
group.DestroyEntity(entity.GetId())
// 怪物死亡触发器检测
if entity.GetEntityType() == constant.ENTITY_TYPE_MONSTER {
g.MonsterDieTriggerCheck(player, entity.GetGroupId(), group)
g.MonsterDieTriggerCheck(player, group)
}
}
// ChangeGadgetState 改变物件实体状态
// ChangeGadgetState 改变物件状态
func (g *Game) ChangeGadgetState(player *model.Player, entityId uint32, state uint32) {
world := WORLD_MANAGER.GetWorldByID(player.WorldId)
if world == nil {
@@ -568,6 +574,21 @@ func (g *Game) ChangeGadgetState(player *model.Player, entityId uint32, state ui
IsEnableInteract: true,
}
g.SendMsg(cmd.GadgetStateNotify, player.PlayerID, player.ClientSeq, ntf)
groupId := entity.GetGroupId()
group := scene.GetGroupById(groupId)
if group == nil {
logger.Error("group not exist, groupId: %v, uid: %v", groupId, player.PlayerID)
return
}
dbWorld := player.GetDbWorld()
dbScene := dbWorld.GetSceneById(scene.GetId())
dbSceneGroup := dbScene.GetSceneGroupById(groupId)
dbSceneGroup.ChangeGadgetState(entity.GetConfigId(), uint8(gadgetEntity.GetGadgetState()))
// 物件状态变更触发器检测
g.GadgetStateChangeTriggerCheck(player, group, entity.GetConfigId(), uint8(gadgetEntity.GetGadgetState()))
}
// GetVisionEntity 获取某位置视野内的全部实体
@@ -614,12 +635,31 @@ func (g *Game) AddSceneGroup(player *model.Player, scene *Scene, groupConfig *gd
logger.Error("invalid init suite id: %v, uid: %v", initSuiteId, player.PlayerID)
return
}
scene.AddGroupSuite(uint32(groupConfig.Id), uint8(initSuiteId))
g.AddSceneGroupSuiteCore(player, scene, uint32(groupConfig.Id), uint8(initSuiteId))
ntf := &proto.GroupSuiteNotify{
GroupMap: make(map[uint32]uint32),
}
ntf.GroupMap[uint32(groupConfig.Id)] = uint32(initSuiteId)
g.SendMsg(cmd.GroupSuiteNotify, player.PlayerID, player.ClientSeq, ntf)
dbWorld := player.GetDbWorld()
dbScene := dbWorld.GetSceneById(scene.GetId())
dbSceneGroup := dbScene.GetSceneGroupById(uint32(groupConfig.Id))
for _, variable := range groupConfig.VariableMap {
exist := dbSceneGroup.CheckVariableExist(variable.Name)
if exist && variable.NoRefresh {
continue
}
dbSceneGroup.SetVariable(variable.Name, variable.Value)
}
group := scene.GetGroupById(uint32(groupConfig.Id))
if group == nil {
logger.Error("group not exist, groupId: %v, uid: %v", groupConfig.Id, player.PlayerID)
return
}
// 场景组加载触发器检测
g.GroupLoadTriggerCheck(player, group)
}
// RemoveSceneGroup 卸载场景组
@@ -639,6 +679,152 @@ func (g *Game) RemoveSceneGroup(player *model.Player, scene *Scene, groupConfig
g.SendMsg(cmd.GroupUnloadNotify, player.PlayerID, player.ClientSeq, ntf)
}
func (g *Game) AddSceneGroupSuiteCore(player *model.Player, scene *Scene, groupId uint32, suiteId uint8) {
groupConfig := gdconf.GetSceneGroup(int32(groupId))
if groupConfig == nil {
logger.Error("get scene group config is nil, groupId: %v", groupId)
return
}
suiteConfig, exist := groupConfig.SuiteMap[int32(suiteId)]
if !exist {
logger.Error("invalid suiteId: %v", suiteId)
return
}
entityMap := make(map[uint32]*Entity)
for _, monsterConfigId := range suiteConfig.MonsterConfigIdList {
monsterConfig, exist := groupConfig.MonsterMap[monsterConfigId]
if !exist {
logger.Error("monster config not exist, monsterConfigId: %v", monsterConfigId)
continue
}
entityId := g.CreateConfigEntity(player, scene, uint32(groupConfig.Id), monsterConfig)
if entityId == 0 {
continue
}
entity := scene.GetEntity(entityId)
entityMap[entityId] = entity
}
for _, gadgetConfigId := range suiteConfig.GadgetConfigIdList {
gadgetConfig, exist := groupConfig.GadgetMap[gadgetConfigId]
if !exist {
logger.Error("gadget config not exist, gadgetConfigId: %v", gadgetConfigId)
continue
}
entityId := g.CreateConfigEntity(player, scene, uint32(groupConfig.Id), gadgetConfig)
if entityId == 0 {
continue
}
entity := scene.GetEntity(entityId)
entityMap[entityId] = entity
}
for _, npcConfig := range groupConfig.NpcMap {
entityId := g.CreateConfigEntity(player, scene, uint32(groupConfig.Id), npcConfig)
if entityId == 0 {
continue
}
entity := scene.GetEntity(entityId)
entityMap[entityId] = entity
}
scene.AddGroupSuite(groupId, suiteId, entityMap)
group := scene.GetGroupById(groupId)
for _, gadgetConfigId := range suiteConfig.GadgetConfigIdList {
// 物件创建触发器检测
GAME.GadgetCreateTriggerCheck(player, group, uint32(gadgetConfigId))
}
}
// CreateConfigEntity 创建配置表里的实体
func (g *Game) CreateConfigEntity(player *model.Player, scene *Scene, groupId uint32, entityConfig any) uint32 {
dbWorld := player.GetDbWorld()
dbScene := dbWorld.GetSceneById(scene.GetId())
dbSceneGroup := dbScene.GetSceneGroupById(groupId)
switch entityConfig.(type) {
case *gdconf.Monster:
monster := entityConfig.(*gdconf.Monster)
isKill := dbSceneGroup.CheckIsKill(uint32(monster.ConfigId))
if isKill {
return 0
}
return scene.CreateEntityMonster(
&model.Vector{X: float64(monster.Pos.X), Y: float64(monster.Pos.Y), Z: float64(monster.Pos.Z)},
&model.Vector{X: float64(monster.Rot.X), Y: float64(monster.Rot.Y), Z: float64(monster.Rot.Z)},
uint32(monster.MonsterId), uint8(monster.Level), getTempFightPropMap(), uint32(monster.ConfigId), groupId,
)
case *gdconf.Npc:
npc := entityConfig.(*gdconf.Npc)
return scene.CreateEntityNpc(
&model.Vector{X: float64(npc.Pos.X), Y: float64(npc.Pos.Y), Z: float64(npc.Pos.Z)},
&model.Vector{X: float64(npc.Rot.X), Y: float64(npc.Rot.Y), Z: float64(npc.Rot.Z)},
uint32(npc.NpcId), 0, 0, 0, uint32(npc.ConfigId), groupId,
)
case *gdconf.Gadget:
gadget := entityConfig.(*gdconf.Gadget)
isKill := dbSceneGroup.CheckIsKill(uint32(gadget.ConfigId))
if isKill {
return 0
}
// 70500000并不是实际的物件id 根据节点类型对应采集物配置表
if gadget.PointType != 0 && gadget.GadgetId == 70500000 {
gatherDataConfig := gdconf.GetGatherDataByPointType(gadget.PointType)
if gatherDataConfig == nil {
return 0
}
return scene.CreateEntityGadgetNormal(
&model.Vector{X: float64(gadget.Pos.X), Y: float64(gadget.Pos.Y), Z: float64(gadget.Pos.Z)},
&model.Vector{X: float64(gadget.Rot.X), Y: float64(gadget.Rot.Y), Z: float64(gadget.Rot.Z)},
uint32(gatherDataConfig.GadgetId),
uint32(constant.GADGET_STATE_DEFAULT),
&GadgetNormalEntity{
isDrop: false,
itemId: uint32(gatherDataConfig.ItemId),
count: 1,
},
uint32(gadget.ConfigId),
groupId,
)
} else {
state := uint8(gadget.State)
exist := dbSceneGroup.CheckGadgetExist(uint32(gadget.ConfigId))
if exist {
state = dbSceneGroup.GetGadgetState(uint32(gadget.ConfigId))
}
return scene.CreateEntityGadgetNormal(
&model.Vector{X: float64(gadget.Pos.X), Y: float64(gadget.Pos.Y), Z: float64(gadget.Pos.Z)},
&model.Vector{X: float64(gadget.Rot.X), Y: float64(gadget.Rot.Y), Z: float64(gadget.Rot.Z)},
uint32(gadget.GadgetId),
uint32(state),
new(GadgetNormalEntity),
uint32(gadget.ConfigId),
groupId,
)
}
default:
return 0
}
}
// TODO 临时写死
func getTempFightPropMap() map[uint32]float32 {
fpm := map[uint32]float32{
constant.FIGHT_PROP_BASE_ATTACK: float32(50.0),
constant.FIGHT_PROP_CUR_ATTACK: float32(50.0),
constant.FIGHT_PROP_BASE_DEFENSE: float32(500.0),
constant.FIGHT_PROP_CUR_DEFENSE: float32(500.0),
constant.FIGHT_PROP_BASE_HP: float32(50.0),
constant.FIGHT_PROP_CUR_HP: float32(50.0),
constant.FIGHT_PROP_MAX_HP: float32(50.0),
constant.FIGHT_PROP_PHYSICAL_SUB_HURT: float32(0.1),
constant.FIGHT_PROP_ICE_SUB_HURT: float32(0.1),
constant.FIGHT_PROP_FIRE_SUB_HURT: float32(0.1),
constant.FIGHT_PROP_ELEC_SUB_HURT: float32(0.1),
constant.FIGHT_PROP_WIND_SUB_HURT: float32(0.1),
constant.FIGHT_PROP_ROCK_SUB_HURT: float32(0.1),
constant.FIGHT_PROP_GRASS_SUB_HURT: float32(0.1),
constant.FIGHT_PROP_WATER_SUB_HURT: float32(0.1),
}
return fpm
}
// TODO Group和Suite的初始化和加载卸载逻辑还没完全理清 所以现在这里写得略答辩
func (g *Game) AddSceneGroupSuite(player *model.Player, groupId uint32, suiteId uint8) {
@@ -657,7 +843,7 @@ func (g *Game) AddSceneGroupSuite(player *model.Player, groupId uint32, suiteId
return
}
scene := world.GetSceneById(player.SceneId)
scene.AddGroupSuite(uint32(groupConfig.Id), suiteId)
g.AddSceneGroupSuiteCore(player, scene, groupId, suiteId)
ntf := &proto.GroupSuiteNotify{
GroupMap: make(map[uint32]uint32),
}
@@ -672,7 +858,7 @@ func (g *Game) AddSceneGroupSuite(player *model.Player, groupId uint32, suiteId
g.AddSceneEntityNotify(player, proto.VisionType_VISION_BORN, entityIdList, true, false)
}
func (g *Game) AddSceneGroupMonster(player *model.Player, groupId uint32, monsterConfigId uint32) {
func (g *Game) AddSceneGroupMonster(player *model.Player, groupId uint32, configId uint32) {
groupConfig := gdconf.GetSceneGroup(int32(groupId))
if groupConfig == nil {
logger.Error("get group config is nil, groupId: %v, uid: %v", groupId, player.PlayerID)
@@ -690,12 +876,39 @@ func (g *Game) AddSceneGroupMonster(player *model.Player, groupId uint32, monste
return
}
scene := world.GetSceneById(player.SceneId)
entityId := scene.AddGroupSuiteMonster(groupId, uint8(initSuiteId), monsterConfigId)
group, exist := scene.groupMap[groupId]
if !exist {
logger.Error("group not exist, groupId: %v", groupId)
return
}
suite, exist := group.suiteMap[uint8(initSuiteId)]
if !exist {
logger.Error("suite not exist, suiteId: %v", initSuiteId)
return
}
monsterConfig, exist := groupConfig.MonsterMap[int32(configId)]
if !exist {
logger.Error("monster config not exist, configId: %v", configId)
return
}
entityId := g.CreateConfigEntity(player, scene, uint32(groupConfig.Id), monsterConfig)
if entityId == 0 {
return
}
entity := scene.GetEntity(entityId)
suite.entityMap[entityId] = entity
g.AddSceneEntityNotify(player, proto.VisionType_VISION_BORN, []uint32{entityId}, true, false)
}
// CreateDropGadget 创建掉落物的物件实体
func (g *Game) CreateDropGadget(player *model.Player, pos *model.Vector, gadgetId, itemId, count uint32) {
// CreateGadget 创建物件实体
func (g *Game) CreateGadget(player *model.Player, pos *model.Vector, gadgetId uint32, normalEntity *GadgetNormalEntity) {
if normalEntity == nil {
normalEntity = &GadgetNormalEntity{
isDrop: false,
itemId: 0,
count: 0,
}
}
world := WORLD_MANAGER.GetWorldByID(player.WorldId)
if world == nil {
logger.Error("get world is nil, worldId: %v", player.WorldId)
@@ -708,16 +921,21 @@ func (g *Game) CreateDropGadget(player *model.Player, pos *model.Vector, gadgetI
pos, rot,
gadgetId,
constant.GADGET_STATE_DEFAULT,
&GadgetNormalEntity{
isDrop: true,
itemId: itemId,
count: count,
},
normalEntity,
0, 0,
)
g.AddSceneEntityNotify(player, proto.VisionType_VISION_BORN, []uint32{entityId}, true, false)
}
// CreateDropGadget 创建掉落物的物件实体
func (g *Game) CreateDropGadget(player *model.Player, pos *model.Vector, gadgetId, itemId, count uint32) {
g.CreateGadget(player, pos, gadgetId, &GadgetNormalEntity{
isDrop: true,
itemId: itemId,
count: count,
})
}
// 打包相关封装函数
var SceneTransactionSeq uint32 = 0

View File

@@ -1,12 +1,20 @@
package model
import (
"hk4e/common/constant"
"hk4e/gdconf"
)
type DbSceneGroup struct {
VariableMap map[string]int32
KillConfigMap map[uint32]bool
GadgetStateMap map[uint32]uint8
}
type DbScene struct {
SceneId uint32
UnlockPointMap map[uint32]bool
SceneGroupMap map[uint32]*DbSceneGroup
}
type DbWorld struct {
@@ -31,6 +39,7 @@ func NewScene(sceneId uint32) *DbScene {
r := &DbScene{
SceneId: sceneId,
UnlockPointMap: make(map[uint32]bool),
SceneGroupMap: make(map[uint32]*DbSceneGroup),
}
return r
}
@@ -70,3 +79,59 @@ func (s *DbScene) CheckPointUnlock(pointId uint32) bool {
_, exist := s.UnlockPointMap[pointId]
return exist
}
func (s *DbScene) GetSceneGroupById(groupId uint32) *DbSceneGroup {
dbSceneGroup, exist := s.SceneGroupMap[groupId]
if !exist {
dbSceneGroup = &DbSceneGroup{
VariableMap: make(map[string]int32),
KillConfigMap: make(map[uint32]bool),
GadgetStateMap: make(map[uint32]uint8),
}
s.SceneGroupMap[groupId] = dbSceneGroup
}
return dbSceneGroup
}
func (g *DbSceneGroup) GetVariableByName(name string) int32 {
return g.VariableMap[name]
}
func (g *DbSceneGroup) SetVariable(name string, value int32) {
g.VariableMap[name] = value
}
func (g *DbSceneGroup) CheckVariableExist(name string) bool {
_, exist := g.VariableMap[name]
return exist
}
func (g *DbSceneGroup) AddKill(configId uint32) {
g.KillConfigMap[configId] = true
}
func (g *DbSceneGroup) CheckIsKill(configId uint32) bool {
_, exist := g.KillConfigMap[configId]
return exist
}
func (g *DbSceneGroup) RemoveAllKill() {
g.KillConfigMap = make(map[uint32]bool)
}
func (g *DbSceneGroup) GetGadgetState(configId uint32) uint8 {
state, exist := g.GadgetStateMap[configId]
if !exist {
return constant.GADGET_STATE_DEFAULT
}
return state
}
func (g *DbSceneGroup) ChangeGadgetState(configId uint32, state uint8) {
g.GadgetStateMap[configId] = state
}
func (g *DbSceneGroup) CheckGadgetExist(configId uint32) bool {
_, exist := g.GadgetStateMap[configId]
return exist
}