服务器玩家在线信息同步

This commit is contained in:
flswld
2023-03-17 14:30:49 +08:00
parent 658b577c20
commit 7de1d2e765
19 changed files with 286 additions and 77 deletions

View File

@@ -25,34 +25,32 @@ func NewHandle(messageQueue *mq.MessageQueue) (r *Handle) {
}
func (h *Handle) run() {
for i := 0; i < 1; i++ {
go func() {
for {
netMsg := <-h.messageQueue.GetNetMsg()
if netMsg.MsgType != mq.MsgTypeGame {
continue
}
if netMsg.EventId != mq.NormalMsg {
continue
}
if netMsg.OriginServerType != api.GATE {
continue
}
gameMsg := netMsg.GameMsg
switch gameMsg.CmdId {
case cmd.QueryPathReq:
h.QueryPath(gameMsg.UserId, netMsg.OriginServerAppId, gameMsg.PayloadMessage)
case cmd.ObstacleModifyNotify:
h.ObstacleModifyNotify(gameMsg.UserId, netMsg.OriginServerAppId, gameMsg.PayloadMessage)
}
go func() {
for {
netMsg := <-h.messageQueue.GetNetMsg()
if netMsg.MsgType != mq.MsgTypeGame {
continue
}
}()
}
if netMsg.EventId != mq.NormalMsg {
continue
}
if netMsg.OriginServerType != api.GATE {
continue
}
gameMsg := netMsg.GameMsg
switch gameMsg.CmdId {
case cmd.QueryPathReq:
h.QueryPath(gameMsg.UserId, netMsg.OriginServerAppId, gameMsg.PayloadMessage)
case cmd.ObstacleModifyNotify:
h.ObstacleModifyNotify(gameMsg.UserId, netMsg.OriginServerAppId, gameMsg.PayloadMessage)
}
}
}()
}
// SendMsg 发送消息给客户端
func (h *Handle) SendMsg(cmdId uint16, userId uint32, gateAppId string, payloadMsg pb.Message) {
if userId < 100000000 || payloadMsg == nil {
if payloadMsg == nil {
return
}
gameMsg := new(mq.GameMsg)

View File

@@ -1,7 +1,7 @@
package handle
import (
"hk4e/pathfinding/pfalg"
"hk4e/pkg/alg"
"hk4e/pkg/logger"
"hk4e/protocol/cmd"
"hk4e/protocol/proto"
@@ -9,15 +9,15 @@ import (
pb "google.golang.org/protobuf/proto"
)
func (h *Handle) ConvPbVecToMeshVec(pbVec *proto.Vector) pfalg.MeshVector {
return pfalg.MeshVector{
func (h *Handle) ConvPbVecToMeshVec(pbVec *proto.Vector) alg.MeshVector {
return alg.MeshVector{
X: int16(pbVec.X),
Y: int16(pbVec.Y),
Z: int16(pbVec.Z),
}
}
func (h *Handle) ConvMeshVecToPbVec(meshVec pfalg.MeshVector) *proto.Vector {
func (h *Handle) ConvMeshVecToPbVec(meshVec alg.MeshVector) *proto.Vector {
return &proto.Vector{
X: float32(meshVec.X),
Y: float32(meshVec.Y),
@@ -25,15 +25,15 @@ func (h *Handle) ConvMeshVecToPbVec(meshVec pfalg.MeshVector) *proto.Vector {
}
}
func (h *Handle) ConvPbVecListToMeshVecList(pbVecList []*proto.Vector) []pfalg.MeshVector {
ret := make([]pfalg.MeshVector, 0)
func (h *Handle) ConvPbVecListToMeshVecList(pbVecList []*proto.Vector) []alg.MeshVector {
ret := make([]alg.MeshVector, 0)
for _, pbVec := range pbVecList {
ret = append(ret, h.ConvPbVecToMeshVec(pbVec))
}
return ret
}
func (h *Handle) ConvMeshVecListToPbVecList(meshVecList []pfalg.MeshVector) []*proto.Vector {
func (h *Handle) ConvMeshVecListToPbVecList(meshVecList []alg.MeshVector) []*proto.Vector {
ret := make([]*proto.Vector, 0)
for _, meshVec := range meshVecList {
ret = append(ret, h.ConvMeshVecToPbVec(meshVec))
@@ -45,7 +45,7 @@ func (h *Handle) QueryPath(userId uint32, gateAppId string, payloadMsg pb.Messag
req := payloadMsg.(*proto.QueryPathReq)
logger.Debug("query path req: %v, uid: %v, gateAppId: %v", req, userId, gateAppId)
var ok = false
var path []pfalg.MeshVector = nil
var path []alg.MeshVector = nil
for _, destinationPos := range req.DestinationPos {
ok, path = h.worldStatic.Pathfinding(h.ConvPbVecToMeshVec(req.SourcePos), h.ConvPbVecToMeshVec(destinationPos))
if ok {

View File

@@ -1,200 +0,0 @@
package pfalg
import (
"hk4e/pkg/alg"
)
const (
NODE_NONE = iota
NODE_START
NODE_END
NODE_BLOCK
)
type PathNode struct {
x int16
y int16
z int16
visit bool
state int
parent *PathNode
}
type BFS struct {
gMap map[int16]map[int16]map[int16]*PathNode
startPathNode *PathNode
endPathNode *PathNode
}
func NewBFS() (r *BFS) {
r = new(BFS)
return r
}
func (b *BFS) InitMap(terrain map[MeshVector]bool, start MeshVector, end MeshVector, extR int16) {
xLen := end.X - start.X
yLen := end.Y - start.Y
zLen := end.Z - start.Z
dx := int16(1)
dy := int16(1)
dz := int16(1)
if xLen < 0 {
dx = -1
xLen *= -1
}
if yLen < 0 {
dy = -1
yLen *= -1
}
if zLen < 0 {
dz = -1
zLen *= -1
}
b.gMap = make(map[int16]map[int16]map[int16]*PathNode)
for x := start.X - extR*dx; x != end.X+extR*dx; x += dx {
b.gMap[x] = make(map[int16]map[int16]*PathNode)
for y := start.Y - extR*dy; y != end.Y+extR*dy; y += dy {
b.gMap[x][y] = make(map[int16]*PathNode)
for z := start.Z - extR*dz; z != end.Z+extR*dz; z += dz {
state := -1
if x == start.X && y == start.Y && z == start.Z {
state = NODE_START
} else if x == end.X && y == end.Y && z == end.Z {
state = NODE_END
} else {
_, exist := terrain[MeshVector{
X: x,
Y: y,
Z: z,
}]
if exist {
state = NODE_NONE
} else {
state = NODE_BLOCK
}
}
node := &PathNode{
x: x,
y: y,
z: z,
visit: false,
state: state,
parent: nil,
}
b.gMap[x][y][z] = node
if node.state == NODE_START {
b.startPathNode = node
} else if node.state == NODE_END {
b.endPathNode = node
}
}
}
}
}
func (b *BFS) GetNeighbor(node *PathNode) []*PathNode {
neighborList := make([]*PathNode, 0)
dir := [][3]int16{
//
{1, 0, 0},
{-1, 0, 0},
{0, 1, 0},
{0, -1, 0},
{0, 0, 1},
{0, 0, -1},
//
{1, 1, 0},
{-1, 1, 0},
{-1, -1, 0},
{1, -1, 0},
//
{1, 0, 1},
{-1, 0, 1},
{-1, 0, -1},
{1, 0, -1},
//
{0, 1, 1},
{0, -1, 1},
{0, -1, -1},
{0, 1, -1},
//
{1, 1, 1},
{1, 1, -1},
{1, -1, 1},
{1, -1, -1},
{-1, 1, 1},
{-1, 1, -1},
{-1, -1, 1},
{-1, -1, -1},
}
for _, v := range dir {
x := node.x + v[0]
y := node.y + v[1]
z := node.z + v[2]
if _, exist := b.gMap[x]; !exist {
continue
}
if _, exist := b.gMap[x][y]; !exist {
continue
}
if _, exist := b.gMap[x][y][z]; !exist {
continue
}
neighborNode := b.gMap[x][y][z]
neighborList = append(neighborList, neighborNode)
}
return neighborList
}
func (b *BFS) GetPath() []*PathNode {
path := make([]*PathNode, 0)
if b.endPathNode.parent == nil {
return nil
}
node := b.endPathNode
for {
if node == nil {
break
}
path = append(path, node)
node = node.parent
}
if len(path) == 0 {
return nil
}
return path
}
func (b *BFS) Pathfinding() []MeshVector {
queue := alg.NewALQueue[*PathNode]()
b.startPathNode.visit = true
queue.EnQueue(b.startPathNode)
for queue.Len() > 0 {
head := queue.DeQueue()
neighborList := b.GetNeighbor(head)
for _, neighbor := range neighborList {
if !neighbor.visit && neighbor.state != NODE_BLOCK {
neighbor.visit = true
neighbor.parent = head
queue.EnQueue(neighbor)
if neighbor.state == NODE_END {
break
}
}
}
}
path := b.GetPath()
if path == nil {
return nil
}
pathVectorList := make([]MeshVector, 0)
for i := len(path) - 1; i >= 0; i-- {
node := path[i]
pathVectorList = append(pathVectorList, MeshVector{
X: node.x,
Y: node.y,
Z: node.z,
})
}
return pathVectorList
}

View File

@@ -1,7 +0,0 @@
package pfalg
type MeshVector struct {
X int16
Y int16
Z int16
}

View File

@@ -5,18 +5,18 @@ import (
"encoding/gob"
"os"
"hk4e/pathfinding/pfalg"
"hk4e/pkg/alg"
"hk4e/pkg/logger"
)
type WorldStatic struct {
// x y z -> if terrain exist
terrain map[pfalg.MeshVector]bool
terrain map[alg.MeshVector]bool
}
func NewWorldStatic() (r *WorldStatic) {
r = new(WorldStatic)
r.terrain = make(map[pfalg.MeshVector]bool)
r.terrain = make(map[alg.MeshVector]bool)
return r
}
@@ -52,7 +52,7 @@ func (w *WorldStatic) SaveTerrain() bool {
}
func (w *WorldStatic) GetTerrain(x int16, y int16, z int16) (exist bool) {
pos := pfalg.MeshVector{
pos := alg.MeshVector{
X: x,
Y: y,
Z: z,
@@ -62,7 +62,7 @@ func (w *WorldStatic) GetTerrain(x int16, y int16, z int16) (exist bool) {
}
func (w *WorldStatic) SetTerrain(x int16, y int16, z int16) {
pos := pfalg.MeshVector{
pos := alg.MeshVector{
X: x,
Y: y,
Z: z,
@@ -70,13 +70,13 @@ func (w *WorldStatic) SetTerrain(x int16, y int16, z int16) {
w.terrain[pos] = true
}
func (w *WorldStatic) Pathfinding(startPos pfalg.MeshVector, endPos pfalg.MeshVector) (bool, []pfalg.MeshVector) {
bfs := pfalg.NewBFS()
func (w *WorldStatic) Pathfinding(startPos alg.MeshVector, endPos alg.MeshVector) (bool, []alg.MeshVector) {
bfs := alg.NewBFS()
bfs.InitMap(
w.terrain,
startPos,
endPos,
100,
0,
)
pathVectorList := bfs.Pathfinding()
if pathVectorList == nil {