]> git.lizzy.rs Git - hydra-dragonfire.git/blobdiff - map.go
Merge pull request #4 from Minetest-j45/master
[hydra-dragonfire.git] / map.go
diff --git a/map.go b/map.go
index 08b97ec1bef9eb736078292c6cc8a329b9c2d59c..32dd7c39a4b7a51efdfec09f2d1b072eb275d34d 100644 (file)
--- a/map.go
+++ b/map.go
@@ -1,83 +1,84 @@
 package main
 
 import (
-       "github.com/anon55555/mt"
        "github.com/dragonfireclient/hydra-dragonfire/convert"
+       "github.com/dragonfireclient/mt"
        "github.com/yuin/gopher-lua"
        "sync"
 )
 
+type MapBlk struct {
+       data      *mt.MapBlk
+       pathNodes map[[3]int16]*PathNode
+}
+
 type Map struct {
-       client   *Client
        mu       sync.Mutex
-       blocks   map[[3]int16]*mt.MapBlk
+       pathfind bool
+       blocks   map[[3]int16]*MapBlk
        userdata *lua.LUserData
 }
 
 var mapFuncs = map[string]lua.LGFunction{
-       "clear": l_map_clear,
        "block": l_map_block,
        "node":  l_map_node,
+       "path":  l_map_path,
 }
 
-func getMap(l *lua.LState) *Map {
-       return l.CheckUserData(1).Value.(*Map)
-}
-
-func (mtmap *Map) create(client *Client, l *lua.LState) {
-       mtmap.client = client
-       mtmap.blocks = map[[3]int16]*mt.MapBlk{}
-       mtmap.userdata = l.NewUserData()
-       mtmap.userdata.Value = mtmap
-       l.SetMetatable(mtmap.userdata, l.GetTypeMetatable("hydra.map"))
-}
-
-func (mtmap *Map) push() lua.LValue {
-       return mtmap.userdata
+func getMap(l *lua.LState, idx int) *Map {
+       return l.CheckUserData(idx).Value.(*Map)
 }
 
-func (mtmap *Map) connect() {
+func newMap(l *lua.LState) *Map {
+       mp := &Map{}
+       mp.blocks = map[[3]int16]*MapBlk{}
+       mp.userdata = l.NewUserData()
+       mp.userdata.Value = mp
+       l.SetMetatable(mp.userdata, l.GetTypeMetatable("hydra.map"))
+       return mp
 }
 
-func (mtmap *Map) process(pkt *mt.Pkt) {
+func (mp *Map) process(client *Client, pkt *mt.Pkt) {
        switch cmd := pkt.Cmd.(type) {
        case *mt.ToCltBlkData:
-               mtmap.mu.Lock()
-               mtmap.blocks[cmd.Blkpos] = &cmd.Blk
-               mtmap.client.conn.SendCmd(&mt.ToSrvGotBlks{Blks: [][3]int16{cmd.Blkpos}})
-               mtmap.mu.Unlock()
-       }
-}
+               mp.mu.Lock()
+               defer mp.mu.Unlock()
 
-func l_map_clear(l *lua.LState) int {
-       mtmap := getMap(l)
+               blk := &MapBlk{}
+               blk.data = &cmd.Blk
 
-       mtmap.mu.Lock()
-       defer mtmap.mu.Unlock()
+               if mp.pathfind {
+                       if oldblk, ok := mp.blocks[cmd.Blkpos]; ok {
+                               pathRemoveBlock(oldblk)
+                       }
 
-       var cmd mt.ToSrvDeletedBlks
-       for pos := range mtmap.blocks {
-               cmd.Blks = append(cmd.Blks, pos)
-       }
+                       pathAddBlock(mp, blk, cmd.Blkpos)
+               }
 
-       mtmap.blocks = map[[3]int16]*mt.MapBlk{}
+               mp.blocks[cmd.Blkpos] = blk
 
-       mtmap.client.conn.SendCmd(&cmd)
+               client.conn.SendCmd(&mt.ToSrvGotBlks{Blks: [][3]int16{cmd.Blkpos}})
+       }
+}
 
-       return 0
+func l_map(l *lua.LState) int {
+       mp := newMap(l)
+       mp.pathfind = l.ToBool(1)
+       l.Push(mp.userdata)
+       return 1
 }
 
 func l_map_block(l *lua.LState) int {
-       mtmap := getMap(l)
+       mp := getMap(l, 1)
        var blkpos [3]int16
        convert.ReadVec3Int16(l, l.Get(2), &blkpos)
 
-       mtmap.mu.Lock()
-       defer mtmap.mu.Unlock()
+       mp.mu.Lock()
+       defer mp.mu.Unlock()
 
-       block, ok := mtmap.blocks[blkpos]
+       blk, ok := mp.blocks[blkpos]
        if ok {
-               l.Push(convert.PushMapBlk(l, *block))
+               l.Push(convert.PushMapBlk(l, *blk.data))
        } else {
                l.Push(lua.LNil)
        }
@@ -86,26 +87,26 @@ func l_map_block(l *lua.LState) int {
 }
 
 func l_map_node(l *lua.LState) int {
-       mtmap := getMap(l)
+       mp := getMap(l, 1)
 
        var pos [3]int16
        convert.ReadVec3Int16(l, l.Get(2), &pos)
        blkpos, i := mt.Pos2Blkpos(pos)
 
-       mtmap.mu.Lock()
-       defer mtmap.mu.Unlock()
+       mp.mu.Lock()
+       defer mp.mu.Unlock()
 
-       block, block_exists := mtmap.blocks[blkpos]
-       if block_exists {
-               meta, meta_exists := block.NodeMetas[i]
-               if !meta_exists {
+       blk, blk_ok := mp.blocks[blkpos]
+       if blk_ok {
+               meta, meta_ok := blk.data.NodeMetas[i]
+               if !meta_ok {
                        meta = &mt.NodeMeta{}
                }
 
                lnode := l.NewTable()
-               l.SetField(lnode, "param0", lua.LNumber(block.Param0[i]))
-               l.SetField(lnode, "param1", lua.LNumber(block.Param1[i]))
-               l.SetField(lnode, "param2", lua.LNumber(block.Param2[i]))
+               l.SetField(lnode, "param0", lua.LNumber(blk.data.Param0[i]))
+               l.SetField(lnode, "param1", lua.LNumber(blk.data.Param1[i]))
+               l.SetField(lnode, "param2", lua.LNumber(blk.data.Param2[i]))
                l.SetField(lnode, "meta", convert.PushNodeMeta(l, *meta))
                l.Push(lnode)
        } else {
@@ -114,3 +115,20 @@ func l_map_node(l *lua.LState) int {
 
        return 1
 }
+
+func l_map_path(l *lua.LState) int {
+       mp := getMap(l, 1)
+       if !mp.pathfind {
+               panic("map not configured to support path finding")
+       }
+
+       var src, dst [3]int16
+       convert.ReadVec3Int16(l, l.Get(2), &src)
+       convert.ReadVec3Int16(l, l.Get(3), &dst)
+
+       mp.mu.Lock()
+       defer mp.mu.Unlock()
+
+       l.Push(pathFind(mp, [2][3]int16{src, dst}, l))
+       return 1
+}