Advertisement
Marikc0

AFK Turtle Excavator

Nov 14th, 2013
102
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Lua 7.49 KB | None | 0 0
  1. --[[ I do not know who created this. It was not myself. There are no comments in the original code to indicate any ownership. Usage: f#r#d# (ie: f16r16d60 would dig a 16x16 square 60 deep). Give the turtle 2-3 stacks of coal with /refuel 64 (x3). Put an enderchest down and place the turtle next to it with the chest behind it (pickaxe on the left). Doing this you can place four turtles around it. ]]
  2.  
  3. local tArgs = { ... }
  4.  
  5. function sign(num)  
  6.   return not num and 0 or num>0 and 1 or -1
  7. end  
  8.  
  9. function printArray(arr)
  10.   if arr then
  11.     for i,v in pairs(arr) do
  12.       write(i .. "=" .. v .. " ")
  13.     end
  14.   end
  15.   print("")
  16. end
  17.  
  18. local goto, checkOverflow, dig, turn, advance
  19.  
  20. local planMatrix
  21. local max
  22. local min
  23. local size
  24. local excavating = false
  25. local slot={junk={}, ignore={}, fuel={}}
  26.  
  27. function designate(n, type)
  28.   print("Designate "..n.." as "..type)
  29.   slot[n].designation = type
  30.   table.insert(slot[type],n)
  31. end
  32.  
  33. function plan(block)
  34.     local ind = (block.x or 0)*100000000 + (block.y or 0)*10000 + (block.z or 0)
  35.     planMatrix[ind] = planMatrix[ind] or {}
  36.     return planMatrix[ind]
  37. end
  38.  
  39.  
  40. --[[
  41. if #tArgs ~= 1 then
  42.     print( "Usage= excavate <diameter>" )
  43.     return
  44. end
  45. ]]
  46.    
  47. up={name="up", dig=turtle.digUp, move=turtle.up, detect=turtle.detectUp, place=turtle.placeUp, attack=turtle.attackUp, dy}
  48. forward={name="forward", dig=turtle.dig, move=turtle.forward, detect=turtle.detect, place=turtle.place, attack=turtle.attack}
  49. down={name="down",dig=turtle.digDown, move=turtle.down, detect=turtle.detectDown, place=turtle.placeDown, attack=turtle.attackDown}
  50.  
  51. fwd = worward
  52.  
  53. local at = {x=0,y=0,z=0}
  54. local d = {x=0,z=1}
  55.  
  56. forward.at = function()  
  57.   return {x=at.x+d.x, y=at.y, z=at.z+d.z}
  58. end
  59.  
  60. up.at = function()
  61.   return {x=at.x, y=at.y+1, z=at.z}
  62. end
  63.  
  64. down.at = function()
  65.   return {x=at.x, y=at.y-1, z=at.z}
  66. end
  67.  
  68. function shouldDig(block)
  69.   if not min or not max then
  70.     return true
  71.   end
  72.   return block.x>=min.x and block.x<=max.x and block.y>=min.y and block.y<=max.y and block.z>=min.z and block.z<=max.z
  73. end
  74.  
  75. function left()
  76.     turtle.turnLeft()
  77.     d.x, d.z = -d.z, d.x
  78. end
  79.  
  80. function right()
  81.     turtle.turnRight()
  82.   d.x, d.z = d.z, -d.x
  83. end
  84.  
  85. function turn(to)
  86.   x,z = sign(to.x), sign(to.z)
  87.   if x == d.x and z == d.z then
  88.     return
  89.   elseif x == -d.x and z == -d.z then
  90.     left()
  91.     left()
  92.   elseif z ~= 0 then
  93.     if z == -d.x then right() else left() end
  94.   elseif x ~= 0 then
  95.     if x == d.z then right() else left() end
  96.   end  
  97. end
  98.  
  99. function refuel()
  100.   for i,n in ipairs(slot.fuel) do
  101.     turtle.select(n)
  102.     if turtle.refuel(1) then
  103.       turtle.select(1)
  104.       return true
  105.     end
  106.   end
  107.   turtle.select(1)
  108.   return false
  109. end
  110.  
  111. function distanceToBase()
  112.   return math.abs(at.x) + math.abs(at.y) + math.abs(at.z)
  113. end
  114.  
  115. function checkFuel()
  116.   if turtle.getFuelLevel()<10 then
  117.     while not refuel() do
  118.       print("Need fuel...")
  119.       if not slot[1].designation then
  120.         designate(1,"fuel")
  121.       end
  122.       sleep(3)
  123.     end
  124.   end
  125. end
  126.  
  127. function move(dir)
  128.   checkFuel()
  129.   if dir.move() then
  130.     at = dir.at()
  131.     return true
  132.   else
  133.     return false
  134.   end
  135. end
  136.  
  137. function disposeJunk()
  138.   for i,n in ipairs(slot.junk) do
  139.     if turtle.getItemCount(n) >60 then
  140.       turtle.select(n)
  141.       turtle.drop(turtle.getItemCount(n)-1)
  142.     end
  143.   end
  144. end
  145.  
  146. function dig(dir)
  147.   local result = true
  148.   if shouldDig(dir.at()) then
  149.     turtle.select(5)
  150.     result = dir.dig()
  151.     disposeJunk()
  152.     checkOverflow()
  153.     return result
  154.   end  
  155. end
  156.  
  157. function advance(dir, steps)
  158.   if steps == nil then
  159.     steps = 1
  160.   end  
  161.   for step = 1,steps do
  162.     while not move(dir) do
  163.       if dir.detect() then
  164.         if not dig(dir) then
  165.           print("oops")
  166.           return false
  167.         end
  168.       elseif not dir.attack() then
  169.         sleep(0.5)
  170.       end
  171.     end
  172.   end
  173. end
  174.  
  175. function goto(to)
  176.   to = {x=to.x or 0,y=to.y or 0,z=to.z or 0}
  177.   if to.y>at.y then
  178.     advance(up, to.y-at.y)
  179.   elseif to.y<at.y then
  180.     advance(down, at.y-to.y)
  181.   end
  182.  
  183.   if to.x ~= at.x then
  184.     turn({x=to.x-at.x})
  185.     advance(forward, math.abs(to.x-at.x))
  186.   end  
  187.   if to.z ~= at.z then
  188.     turn({z=to.z-at.z})
  189.     advance(forward, math.abs(to.z-at.z))
  190.   end
  191. end
  192.  
  193. function moveDir(to)
  194.   if to.y then
  195.     advance(to.y>0 and up or down, math.abs(to.y))
  196.   else
  197.     turn(to)
  198.     advance(forward, math.abs(to.x or to.z))
  199.   end
  200. end
  201.  
  202. function dropLoot()
  203.   local stoppedAt = {x=at.x, y=at.y, z=at.z}
  204.   goto({})
  205.   turn({z=-1})
  206.   for n=1,16 do
  207.     turtle.select(n)
  208.     if slot[n].designation then
  209.       if slot[n].designation ~= "fuel" then
  210.         turtle.drop(turtle.getItemCount(n)-1)
  211.       end
  212.     else
  213.       turtle.drop()
  214.     end
  215.   end
  216.   turtle.select(1)
  217.   goto(stoppedAt)
  218.   return true
  219. end
  220.  
  221. function checkOverflow()
  222.   if not excavating then
  223.     return
  224.   end
  225.   if turtle.getItemCount(16)==0 then
  226.     return false
  227.   end  
  228.   excavating = false
  229.   dropLoot()
  230.   excavating = true
  231.   return true
  232. end
  233.  
  234. function makePlan()  
  235.   planMatrix = {}
  236.   local layer1 = max.y - (math.fmod(size.y,3)==0 and 1 or 0)
  237.   local evenLayer = true
  238.   local y = layer1
  239.   local widthIsEven = math.fmod(size.x,2)==0
  240.   if(layer1<max.y) then
  241.     plan({y=max.y}).dir={y=-1}
  242.   end
  243.   while y>=min.y do
  244.     for x=min.x,max.x do
  245.       local zDir = (evenLayer == (math.fmod(x-min.x, 2)==0)) and 1 or -1
  246.       for z=min.z,max.z do
  247.         plan({x=x,y=y,z=z}).dir = {z=zDir}
  248.       end      
  249.       plan({x=x,y=y,z=(zDir==1 and max.z or min.z)}).dir = {x=evenLayer and 1 or -1}
  250.     end
  251.     local finishAt = {}
  252.     finishAt.x = evenLayer and max.x or min.x
  253.     finishAt.z = widthIsEven and min.z or (evenLayer and max.z or min.z)    
  254.     finishAt.y = y
  255.    
  256.     if(y-2>=min.y) then
  257.       for descent=0,2 do
  258.         --printArray({x=finishAt.x,y=finishAt.y-descent, z=finishAt.z})
  259.         plan({x=finishAt.x,y=finishAt.y-descent, z=finishAt.z}).dir = {y=-1}
  260.       end
  261.     else
  262.       plan(finishAt).dir = nil
  263.     end
  264.     y = y - 3
  265.     evenLayer = not evenLayer
  266.   end
  267. end
  268.  
  269. function digAround()
  270.   dig(up)
  271.   dig(down)
  272. end
  273.  
  274. function main()
  275.   arg = {}
  276.  
  277.   local command = tArgs[1] or ""
  278.  
  279.   for argbit in string.gmatch(command, '%a[%d-]*') do
  280.     argletter = string.sub(argbit,1,1)
  281.     argnum = string.sub(argbit,2)
  282.     arg[argletter] = tonumber(argnum)
  283.   end
  284.  
  285.   local commands = {
  286.     back = function() turn({z=-1}) end,
  287.     right = function() turn({x=1}) end,
  288.     left = function() turn({x=-1}) end,
  289.     fuel = function() print("Fuel: " .. turtle.getFuelLevel()) end,
  290.   }
  291.  
  292.   for n=1,16 do
  293.     slot[n] = {}
  294.     if turtle.getItemCount(n) > 0 then
  295.       turtle.select(n)
  296.       if n<=4 then      
  297.         if turtle.getItemCount(n)>1 then
  298.           designate(n,"fuel")
  299.         end
  300.       elseif n<=8 then
  301.         designate(n,"junk")
  302.       --elseif n<=12 then
  303.       --  designate(n,"skip")
  304.       end
  305.     end
  306.   end  
  307.  
  308.   if commands[command] then
  309.     commands[command]()
  310.   elseif arg.x or arg.y or arg.z then
  311.     goto(arg)
  312.   else
  313.     print("Fuel: " .. turtle.getFuelLevel())
  314.  
  315.     max = {x=(arg.r or 1) - 1, y=(arg.u or 1) - 1, z=(arg.f or 1) - 1}
  316.     min = {x=-(arg.l or 1) + 1, y=-(arg.d or 1) + 1, z=-(arg.b or 1) + 1}
  317.     size = {x=max.x-min.x+1, y=max.y-min.y+1, z=max.z-min.z+1}
  318.  
  319.     excavating = true
  320.     makePlan()  
  321.     goto({x=min.x, z=min.z, y=max.y})
  322.     digAround()
  323.     while(plan(at).dir) do
  324.       moveDir(plan(at).dir)
  325.       digAround()
  326.     end
  327.     print("End plan")
  328.     goto({})
  329.     dropLoot()
  330.   end
  331. end
  332.  
  333. main()
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement