Advertisement
KTRD

World eater turtle

Feb 21st, 2025
486
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Lua 7.42 KB | None | 0 0
  1. -- World eater turtle
  2. -- Mock APIs for editor support
  3. --[[
  4. local rednet = {
  5.     open = function(_) end,
  6.     broadcast = function(_) end,
  7.     receive = function()
  8.         return 0, ""
  9.     end,
  10. }
  11. local fs = {
  12.     open = function(_, _)
  13.         return {
  14.             close = function(_) end,
  15.             readLine = function(_)
  16.                 return ""
  17.             end,
  18.         }
  19.     end,
  20. }
  21. local turtle = {
  22.     turnLeft = function() end,
  23.     turnRight = function() end,
  24.     dig = function() end,
  25.     digDown = function() end,
  26.     digUp = function() end,
  27.     place = function() end,
  28.     placeDown = function() end,
  29.     placeUp = function() end,
  30.     suck = function() end,
  31.     suckDown = function() end,
  32.     suckUp = function() end,
  33.     refuel = function() end,
  34.     getFuelLevel = function()
  35.         return 0
  36.     end,
  37.     forward = function()
  38.         return false
  39.     end,
  40.     back = function()
  41.         return false
  42.     end,
  43.     down = function()
  44.         return false
  45.     end,
  46.     up = function()
  47.         return false
  48.     end,
  49. }
  50. local gps = {
  51.     locate = function(_)
  52.         return 0, 0, 0
  53.     end,
  54. }
  55. local os = {
  56.     sleep = function(_) end,
  57. }
  58. local peripheral = {
  59.     isPresent = function(_)
  60.         return false
  61.     end,
  62. }
  63. local parallel = {
  64.     waitForAll = function(...)
  65.         _ = ...
  66.         return 1
  67.     end,
  68.     waitForAny = function(...)
  69.         _ = ...
  70.     end,
  71. }
  72. --]]
  73.  
  74. local function refuel(y)
  75.     if turtle.getFuelLevel() < 100 then
  76.         turtle.select(1)
  77.         if (y ~= nil) and (y > 10) then
  78.             turtle.digDown()
  79.             turtle.placeDown()
  80.             turtle.suckDown()
  81.             turtle.refuel()
  82.             while turtle.getFuelLevel() < 100 do
  83.                 print("Waiting for fuel...")
  84.                 os.sleep(10)
  85.                 turtle.suckDown()
  86.                 turtle.refuel()
  87.             end
  88.             turtle.digDown()
  89.         else
  90.             turtle.placeUp()
  91.             turtle.suckUp()
  92.             turtle.refuel()
  93.             while turtle.getFuelLevel() < 100 do
  94.                 print("Waiting for fuel...")
  95.                 os.sleep(10)
  96.                 turtle.suckUp()
  97.                 turtle.refuel()
  98.             end
  99.             turtle.digUp()
  100.         end
  101.     end
  102. end
  103.  
  104. local function unload(y)
  105.     if turtle.getItemCount(15) > 0 then
  106.         if (y ~= nil) and (y > 10) then
  107.             turtle.digDown()
  108.             turtle.select(2)
  109.             turtle.placeDown()
  110.             for i = 3, 16 do
  111.                 if turtle.getItemCount(i) > 0 then
  112.                     turtle.select(i)
  113.                     turtle.dropDown()
  114.                 end
  115.             end
  116.             turtle.digDown()
  117.         else
  118.             turtle.digUp()
  119.             turtle.select(2)
  120.             turtle.placeUp()
  121.             for i = 3, 16 do
  122.                 if turtle.getItemCount(i) > 0 then
  123.                     turtle.select(i)
  124.                     turtle.dropUp()
  125.                 end
  126.             end
  127.             turtle.digUp()
  128.         end
  129.     end
  130. end
  131.  
  132. local function digToBedrock(y)
  133.     turtle.dig()
  134.     turtle.digDown()
  135.     unload(y)
  136.     refuel(y)
  137.     while turtle.down() do
  138.         if y ~= nil then
  139.             y = y - 1
  140.         end
  141.         turtle.dig()
  142.         turtle.digDown()
  143.         unload(y)
  144.         refuel(y)
  145.     end
  146.     return y
  147. end
  148.  
  149. local function comeUp(y, y0)
  150.     for _ = y, y0 - 1, 1 do
  151.         turtle.up()
  152.         refuel(y)
  153.     end
  154. end
  155.  
  156. local function forward()
  157.     while not turtle.forward() do
  158.         if not peripheral.isPresent("front") then
  159.             turtle.dig()
  160.         else
  161.             local solution = parallel.waitForAny(function()
  162.                 local f = false
  163.                 while not f do
  164.                     f = turtle.forward()
  165.                 end
  166.             end, function()
  167.                 os.sleep(math.random(100) * 0.05)
  168.                 turtle.down()
  169.             end)
  170.             if solution == 2 then
  171.                 local f = false
  172.                 while not f do
  173.                     os.sleep(0.2)
  174.                     f = turtle.up()
  175.                 end
  176.                 turtle.forward()
  177.             end
  178.         end
  179.     end
  180.     refuel(11)
  181. end
  182.  
  183. local function back()
  184.     while not turtle.back() do
  185.         os.sleep(0.2)
  186.     end
  187. end
  188.  
  189. local function getOrientation(x, z)
  190.     forward()
  191.     local x1, _, z1 = gps.locate(1)
  192.     back()
  193.     if x1 > x then
  194.         return "east"
  195.     elseif x1 < x then
  196.         return "west"
  197.     elseif z1 > z then
  198.         return "south"
  199.     else
  200.         return "north"
  201.     end
  202. end
  203.  
  204. local function turnTo(orientation, current_orientation)
  205.     if orientation == "north" then
  206.         if current_orientation == "east" then
  207.             turtle.turnLeft()
  208.         elseif current_orientation == "south" then
  209.             turtle.turnLeft()
  210.             turtle.turnLeft()
  211.         elseif current_orientation == "west" then
  212.             turtle.turnRight()
  213.         end
  214.     elseif orientation == "east" then
  215.         if current_orientation == "south" then
  216.             turtle.turnLeft()
  217.         elseif current_orientation == "west" then
  218.             turtle.turnLeft()
  219.             turtle.turnLeft()
  220.         elseif current_orientation == "north" then
  221.             turtle.turnRight()
  222.         end
  223.     elseif orientation == "south" then
  224.         if current_orientation == "west" then
  225.             turtle.turnLeft()
  226.         elseif current_orientation == "north" then
  227.             turtle.turnLeft()
  228.             turtle.turnLeft()
  229.         elseif current_orientation == "east" then
  230.             turtle.turnRight()
  231.         end
  232.     elseif orientation == "west" then
  233.         if current_orientation == "north" then
  234.             turtle.turnLeft()
  235.         elseif current_orientation == "east" then
  236.             turtle.turnLeft()
  237.             turtle.turnLeft()
  238.         elseif current_orientation == "south" then
  239.             turtle.turnRight()
  240.         end
  241.     end
  242. end
  243.  
  244. local function go_to(x, z, xt, zt, orientation)
  245.     if x < xt then
  246.         turnTo("east", orientation)
  247.         orientation = "east"
  248.         while x < xt do
  249.             forward()
  250.             x = x + 1
  251.         end
  252.     elseif x > xt then
  253.         turnTo("west", orientation)
  254.         orientation = "west"
  255.         while x > xt do
  256.             forward()
  257.             x = x - 1
  258.         end
  259.     end
  260.     if z < zt then
  261.         turnTo("south", orientation)
  262.         while z < zt do
  263.             forward()
  264.             z = z + 1
  265.         end
  266.     elseif z > zt then
  267.         turnTo("north", orientation)
  268.         while z > zt do
  269.             forward()
  270.             z = z - 1
  271.         end
  272.     end
  273.     turnTo("east", orientation)
  274. end
  275.  
  276. local SETTINGS_FILE_NAME = ".eater_settings"
  277. local TASK_FILE_NAME = ".eater_task"
  278.  
  279. rednet.open("right")
  280.  
  281. local x, y, z = gps.locate(1)
  282. local x0, y0, z0, master_id = nil, nil, nil, nil
  283.  
  284. if fs.exists(SETTINGS_FILE_NAME) then
  285.     local f = fs.open(SETTINGS_FILE_NAME, "r")
  286.     x0 = tonumber(f.readLine())
  287.     y0 = tonumber(f.readLine())
  288.     z0 = tonumber(f.readLine())
  289.     master_id = tonumber(f.readLine())
  290.     f.close()
  291. else
  292.     rednet.broadcast("eater_turtle search")
  293.     while master_id == nil do
  294.         local id, msg = rednet.receive()
  295.         if msg:sub(1, #"eater_master zero") == "eater_master zero" then
  296.             master_id = id
  297.             x0, y0, z0 = msg:match("eater_master zero (-?%d+) (-?%d+) (-?%d+)")
  298.             x0, y0, z0 = tonumber(x0), tonumber(y0), tonumber(z0)
  299.             print("Master with id " .. master_id .. " found at " .. x0 .. " " .. y0 .. " " .. z0)
  300.         else
  301.             print("Received unknown message, ignoring")
  302.         end
  303.     end
  304.     local f = fs.open(SETTINGS_FILE_NAME, "w")
  305.     f.writeLine(x0)
  306.     f.writeLine(y0)
  307.     f.writeLine(z0)
  308.     f.writeLine(master_id)
  309.     f.close()
  310. end
  311.  
  312. if (y == nil) or (y < y0) then
  313.     y = digToBedrock(y)
  314.     while y == nil do
  315.         turtle.up()
  316.         x, y, z = gps.locate(1)
  317.     end
  318.     comeUp(y, y0)
  319. elseif y > y0 then
  320.     refuel(y)
  321.     while y > y0 do
  322.         turtle.digDown()
  323.         turtle.down()
  324.         y = y - 1
  325.     end
  326.     local orientation = getOrientation(x, z)
  327.     turnTo(orientation, "east")
  328. elseif fs.exists(TASK_FILE_NAME) then
  329.     local f = fs.open(TASK_FILE_NAME, "r")
  330.     local xt, zt = tonumber(f.readLine()) + x0, tonumber(f.readLine()) + z0
  331.     f.close()
  332.     go_to(x, z, xt, zt, getOrientation(x, z))
  333.     y = digToBedrock(y)
  334.     comeUp(y, y0)
  335. end
  336.  
  337. local done = false
  338. while not done do
  339.     rednet.send(master_id, "eater_turtle ready")
  340.     local xt, zt = nil, nil
  341.     while (xt == nil) and not done do
  342.         local id, m = rednet.receive()
  343.         if id == master_id then
  344.             if m:sub(1, #"eater_master done") == "eater_master done" then
  345.                 done = true
  346.             else
  347.                 xt, zt = m:match("eater_master go (-?%d+) (-?%d+)")
  348.                 xt, zt = tonumber(xt), tonumber(zt)
  349.                 print("Received task: " .. xt .. " " .. zt)
  350.                 local f = fs.open(TASK_FILE_NAME, "w")
  351.                 f.writeLine(xt)
  352.                 f.writeLine(zt)
  353.                 f.close()
  354.             end
  355.         end
  356.     end
  357.     if not done then
  358.         go_to(x, z, xt + x0, zt + z0, "east")
  359.         x, z = xt + x0, zt + z0
  360.         y = digToBedrock(y)
  361.         comeUp(y, y0)
  362.     end
  363. end
  364.  
  365. print("Done")
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement