Advertisement
Guest User

Untitled

a guest
Jan 18th, 2018
63
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 5.14 KB | None | 0 0
  1. local component = require("component")
  2. local computer = require("computer")
  3. local robot = require("robot")
  4. local shell = require("shell")
  5. local sides = require("sides")
  6.  
  7. if not component.isAvailable("robot") then
  8. io.stderr:write("can only run on robots")
  9. return
  10. end
  11.  
  12. local args, options = shell.parse(...)
  13. if #args < 1 then
  14. io.write("Usage: dig [-s] \n")
  15. io.write(" -s: shutdown when done.")
  16. return
  17. end
  18.  
  19. local size = tonumber(args[1])
  20. local maxDeph = tonumber(args[2])
  21. local startDeph = tonumber(args[3])
  22. if not size then
  23. io.stderr:write("invalid size")
  24. return
  25. end
  26.  
  27. if not maxDeph then
  28. io.stderr:write("invalid max deph")
  29. return
  30. end
  31.  
  32. if not startDeph then
  33. startDeph = 0
  34. end
  35.  
  36. local r = component.robot
  37. local x, y, z, f = 0, 0, 0, 0
  38. local dropping = false -- avoid recursing into drop()
  39. local delta = {[0] = function() x = x + 1 end, [1] = function() y = y + 1 end,
  40. [2] = function() x = x - 1 end, [3] = function() y = y - 1 end}
  41.  
  42. local function turnRight()
  43. robot.turnRight()
  44. f = (f + 1) % 4
  45. end
  46.  
  47. local function turnLeft()
  48. robot.turnLeft()
  49. f = (f - 1) % 4
  50. end
  51.  
  52. local function turnTowards(side)
  53. if f == side - 1 then
  54. turnRight()
  55. else
  56. while f ~= side do
  57. turnLeft()
  58. end
  59. end
  60. end
  61.  
  62. local checkedDrop -- forward declaration
  63.  
  64. local function clearBlock(side, cannotRetry)
  65. while r.suck(side) do
  66. checkedDrop()
  67. end
  68. local result, reason = r.swing(side)
  69. if result then
  70. checkedDrop()
  71. else
  72. local _, what = r.detect(side)
  73. if cannotRetry and what ~= "air" and what ~= "entity" then
  74. return false
  75. end
  76. end
  77. return true
  78. end
  79.  
  80. local function tryMove(side)
  81. side = side or sides.forward
  82. local tries = 10
  83. while not r.move(side) do
  84. tries = tries - 1
  85. if not clearBlock(side, tries < 1) then
  86. return false
  87. end
  88. end
  89. if side == sides.down then
  90. z = z + 1
  91. elseif side == sides.up then
  92. z = z - 1
  93. else
  94. delta[f]()
  95. end
  96. return true
  97. end
  98.  
  99. local function moveTo(tx, ty, tz, backwards)
  100. local axes = {
  101. function()
  102. while z > tz do
  103. tryMove(sides.up)
  104. end
  105. while z < tz do
  106. tryMove(sides.down)
  107. end
  108. end,
  109. function()
  110. if y > ty then
  111. turnTowards(3)
  112. repeat tryMove() until y == ty
  113. elseif y < ty then
  114. turnTowards(1)
  115. repeat tryMove() until y == ty
  116. end
  117. end,
  118. function()
  119. if x > tx then
  120. turnTowards(2)
  121. repeat tryMove() until x == tx
  122. elseif x < tx then
  123. turnTowards(0)
  124. repeat tryMove() until x == tx
  125. end
  126. end
  127. }
  128. if backwards then
  129. for axis = 3, 1, -1 do
  130. axes[axis]()
  131. end
  132. else
  133. for axis = 1, 3 do
  134. axes[axis]()
  135. end
  136. end
  137. end
  138.  
  139. function checkedDrop(force)
  140. local empty = 0
  141. for slot = 1, 16 do
  142. if robot.count(slot) == 0 then
  143. empty = empty + 1
  144. end
  145. end
  146. if not dropping and empty == 0 or force and empty < 16 then
  147. local ox, oy, oz, of = x, y, z, f
  148. dropping = true
  149. moveTo(0, 0, 0)
  150. turnTowards(2)
  151.  
  152. for slot = 1, 16 do
  153. if robot.count(slot) > 0 then
  154. robot.select(slot)
  155. local wait = 1
  156. repeat
  157. if not robot.drop() then
  158. os.sleep(wait)
  159. wait = math.min(10, wait + 1)
  160. end
  161. until robot.count(slot) == 0
  162. end
  163. end
  164. robot.select(1)
  165.  
  166. dropping = false
  167. moveTo(ox, oy, oz, true)
  168. turnTowards(of)
  169. end
  170. end
  171.  
  172. local function step()
  173. clearBlock(sides.down)
  174. if not tryMove() then
  175. return false
  176. end
  177. clearBlock(sides.up)
  178. return true
  179. end
  180.  
  181. local function turn(i)
  182. if i % 2 == 1 then
  183. turnRight()
  184. else
  185. turnLeft()
  186. end
  187. end
  188.  
  189. local function digLayer()
  190. --[[ We move in zig-zag lines, clearing three layers at a time. This means we
  191. have to differentiate at the end of the last line between even and odd
  192. sizes on which way to face for the next layer:
  193. For either size we rotate once to the right. For even sizes this will
  194. cause the next layer to be dug out rotated by ninety degrees. For odd
  195. ones the return path is symmetrical, meaning we just turn around.
  196.  
  197. Examples for two layers:
  198.  
  199. s--x--x e--x--x s--x--x--x x--x x--x
  200. | | | | | | |
  201. x--x--x -> x--x--x x--x--x--x x x x x
  202. | | | -> | | | |
  203. x--x--e x--x--s x--x--x--x x x x x
  204. | | | | |
  205. e--x--x--x s x--x e
  206.  
  207. Legend: s = start, x = a position, e = end, - = a move
  208. ]]
  209. for i = 1, size do
  210. for j = 1, size - 1 do
  211. if not step() then
  212. return false
  213. end
  214. end
  215. if i < size then
  216. -- End of a normal line, move the "cap".
  217. turn(i)
  218. if not step() then
  219. return false
  220. end
  221. turn(i)
  222. else
  223. turnRight()
  224. if size % 2 == 1 then
  225. turnRight()
  226. end
  227. for i = 1, 3 do
  228. if not tryMove(sides.down) or z >= maxDeph then
  229. return false
  230. end
  231. end
  232. end
  233. end
  234. return true
  235. end
  236.  
  237. while z > startDeph do
  238. tryMove(sides.down)
  239. end
  240.  
  241. repeat until not digLayer()
  242. moveTo(0, 0, 0, true)
  243. turnTowards(0)
  244. checkedDrop(true)
  245.  
  246. if options.s then
  247. computer.shutdown()
  248. end
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement