Guest User

A* Pathfinder in lua

a guest
Feb 7th, 2013
126
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Lua 25.66 KB | None | 0 0
  1. --[[ Created by TehPers' Automatic Installer Maker ]]--
  2. local root = {
  3. ["pathfinder"] = { ["deepcopy"] = [===[
  4. --[[ deepcopy.lua
  5.    
  6.     Deep-copy function for Lua - v0.2
  7.     ==============================
  8.       - Does not overflow the stack.
  9.       - Maintains cyclic-references
  10.       - Copies metatables
  11.       - Maintains common upvalues between copied functions (for Lua 5.2 only)
  12.    
  13.     TODO
  14.     ----
  15.       - Document usage (properly) and provide examples
  16.       - Implement handling of LuaJIT FFI ctypes
  17.       - Provide option to only set metatables, not copy (as if they were
  18.         immutable)
  19.       - Find a way to replicate `debug.upvalueid` and `debug.upvaluejoin` in
  20.         Lua 5.1
  21.       - Copy function environments in Lua 5.1 and LuaJIT
  22.         (Lua 5.2's _ENV is actually a good idea!)
  23.       - Handle C functions
  24.    
  25.     Usage
  26.     -----
  27.         copy = table.deecopy(orig)
  28.         copy = table.deecopy(orig, params, customcopyfunc_list)
  29.    
  30.     `params` is a table of parameters to inform the copy functions how to
  31.     copy the data. The default ones available are:
  32.       - `value_ignore` (`table`/`nil`): any keys in this table will not be
  33.         copied (value should be `true`). (default: `nil`)
  34.       - `value_translate` (`table`/`nil`): any keys in this table will result
  35.         in the associated value, rather than a copy. (default: `nil`)
  36.         (Note: this can be useful for global tables: {[math] = math, ..})
  37.       - `metatable_immutable` (`boolean`): assume metatables are immutable and
  38.         do not copy them (only set). (default: `false`)
  39.       - `function_immutable` (`boolean`): do not copy function values; instead
  40.         use the original value. (default: `false`)
  41.       - `function_env` (`table`/`nil`): Set the enviroment of functions to
  42.         this value (via fourth arg of `loadstring`). (default: `nil`)
  43.         this value. (default: `nil`)
  44.       - `function_upvalue_isolate` (`boolean`): do not join common upvalues of
  45.         copied functions (only applicable for Lua 5.2 and LuaJIT). (default:
  46.         `false`)
  47.       - `function_upvalue_dontcopy` (`boolean`): do not copy upvalue values
  48.         (does not stop joining). (default: `false`)
  49.    
  50.     `customcopyfunc_list` is a table of typenames to copy functions.
  51.     For example, a simple solution for userdata:
  52.     { ["userdata"] = function(stack, orig, copy, state, arg1, arg2)
  53.         if state == nil then
  54.             copy = orig
  55.             local orig_uservalue = debug.getuservalue(orig)
  56.             if orig_uservalue ~= nil then
  57.                 stack:recurse(orig_uservalue)
  58.                 return copy, 'uservalue'
  59.             end
  60.             return copy, true
  61.         elseif state == 'uservalue' then
  62.             local copy_uservalue = arg2
  63.             if copy_uservalue ~= nil then
  64.                 debug.setuservalue(copy, copy_uservalue)
  65.             end
  66.             return copy, true
  67.         end
  68.     end }
  69.     Any parameters passed to the `params` are available in `stack`.
  70.     You can use custom paramter names, but keep in mind that numeric keys and
  71.     string keys prefixed with a single underscore are reserved.
  72.    
  73.     License
  74.     -------
  75.     Copyright (C) 2012 Declan White
  76.    
  77.     Permission is hereby granted, free of charge, to any person obtaining a
  78.     copy of this software and associated documentation files (the "Software"),
  79.     to deal in the Software without restriction, including without limitation
  80.     the rights to use, copy, modify, merge, publish, distribute, sublicense,
  81.     and/or sell copies of the Software, and to permit persons to whom the
  82.     Software is furnished to do so, subject to the following conditions:
  83.    
  84.     The above copyright notice and this permission notice shall be included in
  85.     all copies or substantial portions of the Software.
  86.    
  87.     THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  88.     IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  89.     FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
  90.     THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  91.     LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
  92.     FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
  93.     DEALINGS IN THE SOFTWARE.
  94. ]]
  95. do
  96.     local type = rawtype or type
  97.     local rawget = rawget
  98.     local rawset = rawset
  99.     local next = rawnext or next
  100.     local getmetatable = debug and debug.getmetatable or getmetatable
  101.     local setmetatable = debug and debug.setmetatable or setmetatable
  102.     local debug_getupvalue = debug and debug.getupvalue or nil
  103.     local debug_setupvalue = debug and debug.setupvalue or nil
  104.     local debug_upvalueid = debug and debug.upvalueid or nil
  105.     local debug_upvaluejoin = debug and debug.upvaluejoin or nil
  106.     local unpack = unpack
  107.     local table = table
  108.     table.deepcopy_copyfunc_list = {
  109.       --["type"] = function(stack, orig, copy, state, temp1, temp2, temp..., tempN)
  110.       --    
  111.       --    -- When complete:
  112.       --    state = true
  113.       --
  114.       --    -- Store temporary variables between iterations using these:
  115.       --    -- (Note: you MUST NOT call these AFTER recurse)
  116.       --    stack:_push(tempN+1, tempN+2, tempN+..., tempN+M)
  117.       --    stack:_pop(K)
  118.       --    -- K is the number to pop.
  119.       --    -- If you wanted to pop two from the last state and push four new ones:
  120.       --    stack:_pop(2)
  121.       --    stack:_push('t', 'e', 's', 't')
  122.       --    
  123.       --    -- To copy a child value:
  124.       --    -- (Note: any calls to push or pop MUST be BEFORE a call to this)
  125.       --    state:recurse(childvalue_orig)
  126.       --    -- This will leave two temp variables on the stack for the next iteration
  127.       --    -- .., childvalue_orig, childvalue_copy
  128.       --    -- which are available via the varargs (temp...)
  129.       --    -- (Note: the copy may be nil if it was not copied (because caller
  130.       --    -- specified it not to be)).
  131.       --    -- You can only call this once per iteration.
  132.       --    
  133.       --    -- Return like this:
  134.       --    -- (Temp variables are not part of the return list due to optimisation.)
  135.       --    return copy, state
  136.       --    
  137.       --end,
  138.         _plainolddata = function(stack, orig, copy, state)
  139.             return orig, true
  140.         end,
  141.         ["table"] = function(stack, orig, copy, state, arg1, arg2, arg3, arg4)
  142.             local orig_prevkey, grabkey = nil, false
  143.             if state == nil then -- 'init'
  144.                 -- Initial state, check for metatable, or get first key
  145.                 -- orig, copy:nil, state
  146.                 copy = stack[orig]
  147.                 if copy ~= nil then -- Check if already copied
  148.                     return copy, true
  149.                 else
  150.                     copy = {} -- Would be nice if you could preallocate sizes!
  151.                     stack[orig] = copy
  152.                     local orig_meta = getmetatable(orig)
  153.                     if orig_meta ~= nil then -- This table has a metatable, copy it
  154.                         if not stack.metatable_immutable then
  155.                             stack:_recurse(orig_meta)
  156.                             return copy, 'metatable'
  157.                         else
  158.                             setmetatable(copy, orig_meta)
  159.                         end
  160.                     end
  161.                 end
  162.                 -- No metatable, go straight to copying key-value pairs
  163.                 orig_prevkey = nil -- grab first key
  164.                 grabkey = true --goto grabkey
  165.             elseif state == 'metatable' then
  166.                 -- Metatable has been copied, set it and get first key
  167.                 -- orig, copy:{}, state, metaorig, metacopy
  168.                 local copy_meta = arg2--select(2, ...)
  169.                 stack:_pop(2)
  170.                
  171.                 if copy_meta ~= nil then
  172.                     setmetatable(copy, copy_meta)
  173.                 end
  174.                
  175.                 -- Now start copying key-value pairs
  176.                 orig_prevkey = nil -- grab first key
  177.                 grabkey = true --goto grabkey
  178.             elseif state == 'key' then
  179.                 -- Key has been copied, now copy value
  180.                 -- orig, copy:{}, state, keyorig, keycopy
  181.                 local orig_key = arg1--select(1, ...)
  182.                 local copy_key = arg2--select(2, ...)
  183.                
  184.                 if copy_key ~= nil then
  185.                     -- leave keyorig and keycopy on the stack
  186.                     local orig_value = rawget(orig, orig_key)
  187.                     stack:_recurse(orig_value)
  188.                     return copy, 'value'
  189.                 else -- key not copied? move onto next
  190.                     stack:_pop(2) -- pop keyorig, keycopy
  191.                     orig_prevkey = orig_key
  192.                     grabkey = true--goto grabkey
  193.                 end
  194.             elseif state == 'value' then
  195.                 -- Value has been copied, set it and get next key
  196.                 -- orig, copy:{}, state, keyorig, keycopy, valueorig, valuecopy
  197.                 local orig_key   = arg1--select(1, ...)
  198.                 local copy_key   = arg2--select(2, ...)
  199.               --local orig_value = arg3--select(3, ...)
  200.                 local copy_value = arg4--select(4, ...)
  201.                 stack:_pop(4)
  202.                
  203.                 if copy_value ~= nil then
  204.                     rawset(copy, copy_key, copy_value)
  205.                 end
  206.                
  207.                 -- Grab next key to copy
  208.                 orig_prevkey = orig_key
  209.                 grabkey = true --goto grabkey
  210.             end
  211.             --return
  212.             --::grabkey::
  213.             if grabkey then
  214.                 local orig_key, orig_value = next(orig, orig_prevkey)
  215.                 if orig_key ~= nil then
  216.                     stack:_recurse(orig_key) -- Copy key
  217.                     return copy, 'key'
  218.                 else
  219.                     return copy, true -- Key is nil, copying of table is complete
  220.                 end
  221.             end
  222.             return
  223.         end,
  224.         ["function"] = function(stack, orig, copy, state, arg1, arg2, arg3)
  225.             local grabupvalue, grabupvalue_idx = false, nil
  226.             if state == nil then
  227.                 -- .., orig, copy, state
  228.                 copy = stack[orig]
  229.                 if copy ~= nil then
  230.                     return copy, true
  231.                 elseif stack.function_immutable then
  232.                     copy = orig
  233.                     return copy, true
  234.                 else
  235.                     copy = loadstring(string.dump(orig), nil, nil, stack.function_env)
  236.                     stack[orig] = copy
  237.                    
  238.                     if debug_getupvalue ~= nil and debug_setupvalue ~= nil then
  239.                         grabupvalue = true
  240.                         grabupvalue_idx = 1
  241.                     else
  242.                         -- No way to get/set upvalues!
  243.                         return copy, true
  244.                     end
  245.                 end
  246.             elseif this_state == 'upvalue' then
  247.                 -- .., orig, copy, state, uvidx, uvvalueorig, uvvaluecopy
  248.                 local orig_upvalue_idx   = arg1
  249.               --local orig_upvalue_value = arg2
  250.                 local copy_upvalue_value = arg3
  251.                 stack:_pop(3)
  252.                
  253.                 debug_setupvalue(copy, orig_upvalue_idx, copy_upvalue_value)
  254.                
  255.                 grabupvalue_idx = orig_upvalue_idx+1
  256.                 stack:_push(grabupvalue_idx)
  257.                 grabupvalue = true
  258.             end
  259.             if grabupvalue then
  260.                 -- .., orig, copy, retto, state, uvidx
  261.                 local upvalue_idx_curr = grabupvalue_idx
  262.                 for upvalue_idx = upvalue_idx_curr, math.huge do
  263.                     local upvalue_name, upvalue_value_orig = debug_getupvalue(orig, upvalue_idx)
  264.                     if upvalue_name ~= nil then
  265.                         local upvalue_handled = false
  266.                         if not stack.function_upvalue_isolate and debug_upvalueid ~= nil and debug_upvaluejoin ~= nil then
  267.                             local upvalue_uid = debug.upvalueid(orig, upvalue_idx)
  268.                             -- Attempting to store an upvalueid of a function as a child of root is UB!
  269.                             local other_orig = stack[upvalue_uid]
  270.                             if other_orig ~= nil then
  271.                                 for other_upvalue_idx = 1, math.huge do
  272.                                     if upvalue_uid == debug_upvalueid(other_orig, other_upvalue_idx) then
  273.                                         local other_copy = stack[other_orig]
  274.                                         debug_upvaluejoin(
  275.                                             copy, upvalue_idx,
  276.                                             other_copy, other_upvalue_idx
  277.                                         )
  278.                                         break
  279.                                     end
  280.                                 end
  281.                                 upvalue_handled = true
  282.                             else
  283.                                 stack[upvalue_uid] = orig
  284.                             end
  285.                         end
  286.                         if not stack.function_upvalue_dontcopy and not upvalue_handled and upvalue_value_orig ~= nil then
  287.                             stack:_recurse(upvalue_value_orig)
  288.                             return copy, 'upvalue'
  289.                         end
  290.                     else
  291.                         stack:_pop(1) -- pop uvidx
  292.                         return copy, true
  293.                     end
  294.                 end
  295.             end
  296.         end,
  297.         ["userdata"] = nil,
  298.         ["lightuserdata"] = nil,
  299.         ["thread"] = nil,
  300.     }
  301.     table.deepcopy_copyfunc_list["number" ] = table.deepcopy_copyfunc_list._plainolddata
  302.     table.deepcopy_copyfunc_list["string" ] = table.deepcopy_copyfunc_list._plainolddata
  303.     table.deepcopy_copyfunc_list["boolean"] = table.deepcopy_copyfunc_list._plainolddata
  304.     -- `nil` should never be encounted... but just in case:
  305.     table.deepcopy_copyfunc_list["nil"    ] = table.deepcopy_copyfunc_list._plainolddata
  306.    
  307.     do
  308.         local ORIG, COPY, RETTO, STATE, SIZE = 0, 1, 2, 3, 4
  309.         function table.deepcopy_push(...)
  310.             local arg_list_len = select('#', ...)
  311.             local stack_offset = stack._top+1
  312.             for arg_i = 1, arg_list_len do
  313.                 stack[stack_offset+arg_i] = select(arg_i, ...)
  314.             end
  315.             stack._top = stack_top+arg_list_len
  316.         end
  317.         function table.deepcopy_pop(stack, count)
  318.             stack._top = stack._top-count
  319.         end
  320.         function table.deepcopy_recurse(stack, orig)
  321.             local retto = stack._ptr
  322.             local stack_top = stack._top
  323.             local stack_ptr = stack_top+1
  324.             stack._top = stack_top+SIZE
  325.             stack._ptr = stack_ptr
  326.             stack[stack_ptr+ORIG ] = orig
  327.             stack[stack_ptr+COPY ] = nil
  328.             stack[stack_ptr+RETTO] = retto
  329.             stack[stack_ptr+STATE] = nil
  330.         end
  331.         function table.deepcopy(root, params, customcopyfunc_list)
  332.             local stack = params or {}
  333.             --orig,copy,retto,state,[temp...,] partorig,partcopy,partretoo,partstate
  334.             stack[1+ORIG ] = root stack[1+COPY ] = nil
  335.             stack[1+RETTO] = nil  stack[1+STATE] = nil
  336.             stack._ptr = 1 stack._top = 4
  337.             stack._push = table.deepcopy_push stack._pop = table.deepcopy_pop
  338.             stack._recurse = table.deepcopy_recurse
  339.             --[[local stack_dbg do -- debug
  340.                 stack_dbg = stack
  341.                 stack = setmetatable({}, {
  342.                     __index = stack_dbg,
  343.                     __newindex = function(t, k, v)
  344.                         stack_dbg[k] = v
  345.                         if tonumber(k) then
  346.                             local stack = stack_dbg
  347.                             local line_stack, line_label, line_stptr = "", "", ""
  348.                             for stack_i = 1, math.max(stack._top, stack._ptr) do
  349.                                 local s_stack = (
  350.                                         (type(stack[stack_i]) == 'table' or type(stack[stack_i]) == 'function')
  351.                                             and string.gsub(tostring(stack[stack_i]), "^.-(%x%x%x%x%x%x%x%x)$", "<%1>")
  352.                                     or  tostring(stack[stack_i])
  353.                                 ), type(stack[stack_i])
  354.                                 local s_label = ""--dbg_label_dict[stack_i] or "?!?"
  355.                                 local s_stptr = (stack_i == stack._ptr and "*" or "")..(stack_i == k and "^" or "")
  356.                                 local maxlen = math.max(#s_stack, #s_label, #s_stptr)+1
  357.                                 line_stack = line_stack..s_stack..string.rep(" ", maxlen-#s_stack)
  358.                                 --line_label = line_label..s_label..string.rep(" ", maxlen-#s_label)
  359.                                 line_stptr = line_stptr..s_stptr..string.rep(" ", maxlen-#s_stptr)
  360.                             end
  361.                             io.stdout:write(
  362.                                           line_stack
  363.                                 --..  "\n"..line_label
  364.                                 ..  "\n"..line_stptr
  365.                                 ..  ""
  366.                             )
  367.                             io.read()
  368.                         elseif false then
  369.                             io.stdout:write(("stack.%s = %s"):format(
  370.                                 k,
  371.                                 (
  372.                                         (type(v) == 'table' or type(v) == 'function')
  373.                                             and string.gsub(tostring(v), "^.-(%x%x%x%x%x%x%x%x)$", "<%1>")
  374.                                     or  tostring(v)
  375.                                 )
  376.                             ))
  377.                             io.read()
  378.                         end
  379.                     end,
  380.                 })
  381.             end]]
  382.             local copyfunc_list = table.deepcopy_copyfunc_list
  383.             repeat
  384.                 local stack_ptr = stack._ptr
  385.                 local this_orig = stack[stack_ptr+ORIG]
  386.                 local this_copy, this_state
  387.                 stack[0] = stack[0]
  388.                 if stack.value_ignore and stack.value_ignore[this_orig] then
  389.                     this_copy = nil
  390.                     this_state = true --goto valuefound
  391.                 else
  392.                     if stack.value_translate then
  393.                         this_copy = stack.value_translate[this_orig]
  394.                         if this_copy ~= nil then
  395.                             this_state = true --goto valuefound
  396.                         end
  397.                     end
  398.                     if not this_state then
  399.                         local this_orig_type = type(this_orig)
  400.                         local copyfunc = (
  401.                                 customcopyfunc_list and customcopyfunc_list[this_orig_type]
  402.                             or  copyfunc_list[this_orig_type]
  403.                             or  error(("cannot copy type %q"):format(this_orig_type), 2)
  404.                         )
  405.                         this_copy, this_state = copyfunc(
  406.                             stack,
  407.                             this_orig,
  408.                             stack[stack_ptr+COPY],
  409.                             unpack(stack--[[_dbg]], stack_ptr+STATE, stack._top)
  410.                         )
  411.                     end
  412.                 end
  413.                 stack[stack_ptr+COPY] = this_copy
  414.                 --::valuefound::
  415.                 if this_state == true then
  416.                     local retto = stack[stack_ptr+RETTO]
  417.                     stack._top = stack_ptr+1 -- pop retto, state, temp...
  418.                     -- Leave orig and copy on stack for parent object
  419.                     stack_ptr = retto -- return to parent's stack frame
  420.                     stack._ptr = stack_ptr
  421.                 else
  422.                     stack[stack_ptr+STATE] = this_state
  423.                 end
  424.             until stack_ptr == nil
  425.             return stack[1+COPY]
  426.         end
  427.     end
  428. end
  429.  
  430.  ]===],
  431.  ["MinHeap"] = [===[
  432. dofile("pathfinder/deepcopy")
  433.  
  434. function new()
  435.  r = {}
  436.  
  437.  function r:hasNext() return self.curNode ~= nil end
  438.  
  439.  function r:add(item)
  440.   local curNode = self.curNode
  441.   if curNode == nil then
  442.    curNode = item
  443.   elseif curNode.next == nil and item.cost < curNode.cost then
  444.    item.nextListElem = curNode
  445.    curNode = item
  446.   else
  447.    local ptr = curNode
  448.    while ptr.nextListElem ~= nil and ptr.nextListElem.cost < item.cost do
  449.     ptr = ptr.nextListElem
  450.    end
  451.    item.nextListElem = ptr.nextListElem
  452.    ptr.nextListElem = item
  453.   end
  454.   self.curNode = curNode
  455.  end
  456.  
  457.  function r:extractFirst()
  458.   local result = self.curNode
  459.   self.curNode = self.curNode.nextListElem
  460.   return result
  461.  end
  462.  
  463.  return r
  464. end
  465.  
  466.  ]===],
  467.  ["PathFinder"] = [===[
  468. os.loadAPI("pathfinder/Point")
  469. os.loadAPI("pathfinder/SearchNode")
  470. os.loadAPI("pathfinder/MinHeap")
  471. os.loadAPI("pathfinder/Surr")
  472.  
  473. local surrounding = {
  474.  Surr.new(1, 0, 0), Surr.new(0, 1, 0), Surr.new(0, 0, 1),
  475.  Surr.new(-1, 0, 0), Surr.new(0, -1, 0), Surr.new(0, 0, -1)
  476. }
  477.  
  478. -- Flips path so you can follow it by pulling the last node off
  479. function findPath(getCost, start, finish)
  480.  return findPathReversed(getCost, finish, start)
  481. end
  482.  
  483. function contains(t, value)
  484.  for k, v in pairs(t) do if v == value then return true end end
  485. end
  486.  
  487. function findPathReversed(getCost, start, finish)
  488.  local startNode = SearchNode.new(start, start:getDistanceSquared(finish), 0)
  489.  
  490.  local openList = MinHeap.new()
  491.  openList:add(startNode)
  492.  
  493.  brWorld = {}
  494.  while openList:hasNext() do
  495.   local current = openList:extractFirst()
  496.  
  497.   if current.position:getDistanceSquared(finish) <= 0 then
  498.    return SearchNode.new(finish, current.pathCost + 1, current.cost + 1, current);
  499.   end
  500.  
  501.   for i = 1, #surrounding do
  502.    local surr = surrounding[i]
  503.    local tmp = Point.new(current.position, surr.point)
  504.    -- If surrounding node is passable and has not been calculated already
  505.    if getCost(tmp.x, tmp.y, tmp.z) ~= nil and not brWorld[tmp:tostring()] then
  506.     brWorld[tmp:tostring()] = true
  507.     local pathCost = current.pathCost + getCost(tmp.x, tmp.y, tmp.z)
  508.     local cost = pathCost + tmp:getDistanceSquared(finish)
  509.     node = SearchNode.new(tmp, cost, pathCost, current);
  510.     openList:add(node);
  511.    end
  512.   end
  513.  end
  514.  
  515.  return nil
  516. end
  517.  
  518.  ]===],
  519.  ["pathfindTest"] = [===[
  520. print(os.loadAPI("pathfinder/PathFinder"))
  521. print(os.loadAPI("pathfinder/Point"))
  522.  
  523. world = {
  524.  {1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
  525.  {1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
  526.  {1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
  527.  {1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
  528.  {1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
  529.  {1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
  530.  {1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
  531.  {1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
  532.  {1, 1, 1, 1, 1, 1, 1, 1, 1, 0},
  533.  {1, 1, 1, 1, 1, 1, 1, 1, 0, 0}
  534. }
  535.  
  536. sX, sY = 1, 1
  537.  
  538. function getCost(x, y)
  539.  return world[y][x]
  540. end
  541.  
  542. function getCost(x, y, z)
  543.  if z and z ~= 0 then return nil end
  544.  if world[y] then
  545.   if world[y][x] then
  546.    if world[y][x] == 0 then return nil end
  547.    return world[y][x]
  548.   end
  549.  end
  550.  return nil
  551. end
  552.  
  553. function isPath(x, y)
  554.  return world[y][x] < 0
  555. end
  556.  
  557. function redraw()
  558.  --term.clear()
  559.  for x = 1, #world[1] do
  560.   for y = 1, #world do
  561.    local c = isPath(x, y) and colors.green or colors.black
  562.    local g = getCost(x, y)
  563.    g = g and math.abs(g) or 0
  564.    if g == 0 then c = colors.red g = " " end
  565.    term.setCursorPos(x, y)
  566.    term.setBackgroundColor(c)
  567.    write(g)
  568.   end
  569.  end
  570. end
  571.  
  572. term.clear()
  573. term.setCursorPos(1, 1)
  574. path = PathFinder.findPath(getCost, Point.new(1, 1), Point.new(10, 10))
  575. while path do
  576.  if world[path.position.y] and world[path.position.y][path.position.x] and world[path.position.y][path.position.x] > 0 then
  577.   world[path.position.y][path.position.x] = -world[path.position.y][path.position.x]
  578.  end
  579.  path = path.next
  580. end
  581. term.clear()
  582. redraw()
  583.  
  584.  ]===],
  585.  ["Point"] = [===[
  586. function new(a1, a2, a3)
  587.  if type(a1) == "table" then
  588.   local x = a1.x + a2.x
  589.   local y = a1.y + a2.y
  590.   local z = (a1.z and a2.z) and (a1.z + a2.z) or 0
  591.   return new(x, y, z)
  592.  end
  593.  
  594.  local r = {
  595.   x = a1,
  596.   y = a2,
  597.   z = a3,
  598.  }
  599.  
  600.  function r:getDistanceSquared(point)
  601.   local dx = math.abs(self.x - point.x)
  602.   local dy = math.abs(self.y - point.y)
  603.   local dz = 0
  604.   if self.z and point.z then dz = math.abs(self.z - point.z) end
  605.   return dx + dy + dz
  606.  end
  607.  
  608.  function r:equals(p)
  609.   return p.x == self.x and p.y == self.y and p.z == self.z
  610.  end
  611.  
  612.  function r:tostring()
  613.   return self.x .. ", " .. self.y .. (self.z and (", " .. self.z) or "")
  614.  end
  615.  
  616.  function r:addX(n)
  617.   return new(self.x + n, self.y, self.z)
  618.  end
  619.  
  620.  function r:addY(n)
  621.   return new(self.x, self.y + n, self.z)
  622.  end
  623.  
  624.  function r:addZ(n)
  625.   return new(self.x, self.y, self.z + n)
  626.  end
  627.  
  628.  return r
  629. end
  630.  
  631. zero = new(0, 0, 0)
  632.  
  633.  ]===],
  634.  ["SearchNode"] = [===[
  635. function new(_position, _cost, _pathCost, _next)
  636.  return {
  637.   position = _position,
  638.   cost = _cost,
  639.   pathCost = _pathCost,
  640.   next = _next
  641.  }
  642. end
  643.  
  644.  ]===],
  645.  ["Surr"] = [===[
  646. function new(x, y, z)
  647.  return {point = Point.new(x, y, z), cost = 1}
  648. end
  649.  
  650.  ]===]
  651. },
  652. }
  653. local function extractDirectory(directory, tDirectory)
  654.  for name, contents in pairs(tDirectory) do
  655.   local curPath = fs.combine(directory, name)
  656.   if type(contents) == "table" then
  657.    print("Creating directory " .. curPath)
  658.    fs.makeDir(curPath)
  659.    extractDirectory(curPath, contents)
  660.   elseif type(contents) == "string" then
  661.    print("Creating file " .. curPath)
  662.    local file = io.open(curPath, "w")
  663.    file:write(contents)
  664.    file:close()
  665.   else
  666.    print("Passing over " .. curPath)
  667.   end
  668.  end
  669. end
  670. extractDirectory("", root)
Advertisement
Add Comment
Please, Sign In to add comment