Advertisement
Forecaster

Reactor Program (Plutonium)

Jul 31st, 2017
103
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Lua 9.45 KB | None | 0 0
  1. local computer = require("computer")
  2. local c = require("component")
  3. local sides = require("sides")
  4. local event = require("event")
  5. local term = require("term")
  6. local fs = require("filesystem")
  7. local shell = require("shell")
  8. local crafting = c.crafting
  9. local inv = c.inventory_controller
  10. local rob = c.robot
  11. local rs = c.redstone
  12.  
  13. local args, options = shell.parse(...)
  14.  
  15. local run = true
  16. local width, height = c.gpu.getResolution()
  17.  
  18. local resumePath = os.getenv("_") .. ".resume"
  19. local resume = 0
  20. local slotMem = 0
  21.  
  22. local res = fs.open(resumePath, "r")
  23.  
  24. if res ~= nil then
  25.     resume = tonumber(res:read(5))
  26.     res:close()
  27. end
  28. if resume == nil then
  29.     resume = 0
  30. end
  31. if resume > 0 then
  32.     print("Resume to " .. tostring(resume))
  33. end
  34.  
  35. local items = { ["238"] = "Uranium 238", plutonium = "Plutonium", rod = "Fuel Rod (MOX)", dualroddepleted = "Dual Fuel Rod (Depleted MOX)", plate = "Iron Plate", mox = "MOX Nuclear Fuel", ["238Block"] = "Uranium Block" }
  36. local recipes = { enrich = {items["238"],items["238"],items["238"],items["plutonium"],items["plutonium"],items["plutonium"],items["238"],items["238"],items["238"]}, dualrod = {items["rod"],items["plate"],items["rod"]}, ["Uranium 238"] = {items["238Block"]} }
  37.  
  38. local craftSlots = {1,2,3,5,6,7,9,10,11}
  39. local slotPlaceBlacklist = {4}
  40.  
  41. function setResume(from)
  42.     local res = fs.open(resumePath, "w")
  43.     res:write(tostring(from))
  44.     res:close()
  45.     checkPower()
  46. end
  47.  
  48. function checkPower()
  49.     local level = computer.energy() / computer.maxEnergy()
  50.     level = level * 100
  51.     print("Power level " .. level .. "%")
  52.     if level < 50  and args[1] == nil or args[1] ~= "true" then
  53.         print("Power level too low, shutting down!")
  54.         computer.shutdown()
  55.     end
  56. end
  57.  
  58. function inTable(table, value)
  59.     for k,v in pairs(table) do
  60.         if v == value then
  61.             return true
  62.         end
  63.     end
  64.     return false
  65. end
  66.  
  67. function findEmptySlot(internal, start, item)
  68.     local slot = start
  69.     local size = 1
  70.     if internal then
  71.         size = rob.inventorySize()
  72.     else
  73.         size = inv.getInventorySize(sides.front)
  74.     end
  75.     if item ~= nil then
  76.         while slot <= size do
  77.             local content = nil
  78.             if internal then
  79.                 content = inv.getStackInInternalSlot(slot)
  80.             else
  81.                 content = inv.getStackInSlot(sides.front, slot)
  82.             end
  83.             if inTable(craftSlots, slot) == false and inTable(slotPlaceBlacklist, slot) == false then
  84.                 if content ~= nil and content.label == item and content.size ~= content.maxSize then
  85.                     return slot
  86.                 end
  87.             end
  88.             slot = slot + 1
  89.         end
  90.         slot = start
  91.     end
  92.     while slot <= size do
  93.         local content = nil
  94.         if internal then
  95.             content = inv.getStackInInternalSlot(slot)
  96.         else
  97.             content = inv.getStackInSlot(sides.front, slot)
  98.         end
  99.         if inTable(craftSlots, slot) == false and inTable(slotPlaceBlacklist, slot) == false then
  100.             if content == nil then
  101.                 return slot
  102.             end
  103.         end
  104.         slot = slot + 1
  105.     end
  106.     return nil
  107. end
  108.  
  109. function findAndCount(item, internal)
  110.     if internal then
  111.         size = rob.inventorySize()
  112.     else
  113.         size = inv.getInventorySize(sides.front)
  114.     end
  115.     local slot = 1
  116.     local total = 0
  117.     local content
  118.     while slot < size do
  119.         if internal then
  120.             content = inv.getStackInInternalSlot(slot)
  121.         else
  122.             content = inv.getStackInSlot(sides.front, slot)
  123.         end
  124.         if content ~= nil and content.label == item then
  125.             total = total + content.size
  126.         end
  127.         slot = slot + 1
  128.     end
  129.     return total
  130. end
  131.  
  132. function getLabelForItemInSlot(slot, internal)
  133.     if internal then
  134.         content = inv.getStackInInternalSlot(slot)
  135.     else
  136.         content = inv.getStackInSlot(sides.front, slot)
  137.     end
  138.     if content ~= nil then
  139.         return content.label
  140.     end
  141.     return nil
  142. end
  143.  
  144. function craft(recipe)
  145.     print("Processing recipe")
  146.     if recipe == nil then
  147.         print("Recipe does not exist!")
  148.         error()
  149.     end
  150.     local outputSlot = 1
  151.     if #recipe > 3 then
  152.         outputSlot = 4
  153.     else
  154.         outputSlot = #recipe + 1
  155.     end
  156.     local components = {}
  157.     print("Count required components...")
  158.     for key,item in pairs(recipe) do
  159.         if components[item] == nil then
  160.             components[item] = 1
  161.         else
  162.             components[item] = components[item] + 1
  163.         end
  164.     end
  165.     print("Look for required components...")
  166.     for key,count in pairs(components) do
  167.         print("Need " .. count .. " of " .. key)
  168.         local found = findAndCount(key, true)
  169.         print("Found " .. found)
  170.         if found < count then
  171.             print("Could not find sufficent amount of " .. key)
  172.             if recipes[key] ~= nil then
  173.                 print("Attempt to craft missing component " .. key)
  174.                 craft(recipes[key])
  175.             else
  176.                 print(key .. " does not have a valid recipe registered.")
  177.             end
  178.         end
  179.     end
  180.     for key,item in pairs(recipe) do
  181.         local targetSlot = craftSlots[key]
  182.         print("Move item " .. item .. " to slot " .. targetSlot .. " for craft")
  183.         findAndMoveTo(item, targetSlot, 1, true, 10, false)
  184.     end
  185.     rob.select(outputSlot)
  186.     crafting.craft()
  187.     print("Clearing output slot")
  188.     local slot = findEmptySlot(true, 1, getLabelForItemInSlot(outputSlot, true))
  189.     if slot ~= nil then
  190.         moveItem(outputSlot, slot, 64, true)
  191.         rob.select(slot)
  192.     end
  193. end
  194.  
  195. function moveItem(from, to, amount, internal)
  196.     if internal then
  197.         rob.select(from)
  198.         rob.transferTo(to, amount)
  199.     else
  200.         rob.select(to)
  201.         inv.suckFromSlot(sides.front, from, amount)
  202.     end
  203. end
  204.  
  205. function findAndMoveTo(item, targetSlot, amount, internal, repeatUntilSuccess, searchAllSlots)
  206.     local found = false
  207.     local slot = 1
  208.     local size = 1
  209.     if internal then
  210.         size = rob.inventorySize()
  211.     else
  212.         size = inv.getInventorySize(sides.front)
  213.     end
  214.     print("Looking for " .. item)
  215.     print("Until found: " .. tostring(repeatUntilSuccess) .. " Internally: " .. tostring(internal))
  216.     while found == false do
  217.         slot = 1
  218.         while slot <= size do
  219.             term.setCursor(1, height)
  220.             term.clearLine()
  221.             term.write("Slot " .. slot)
  222.             local content = nil
  223.             if internal then
  224.                 content = inv.getStackInInternalSlot(slot)
  225.             else
  226.                 content = inv.getStackInSlot(sides.front, slot)
  227.             end
  228.             local sourceSlotOk = true
  229.             if searchAllSlots == false then
  230.                 if inTable(craftSlots, slot) == true then
  231.                     sourceSlotOk = false
  232.                 end
  233.             end
  234.             local targetSlotOk = true
  235.             if inTable(slotPlaceBlacklist, targetSlot) then
  236.                 targetSlotOk = false
  237.             end
  238.             if sourceSlotOk and targetSlotOk and content and content.label == item then
  239.                 print()
  240.                 print("Taking item from slot " .. tostring(slot))
  241.                 moveItem(slot, targetSlot, amount, internal)
  242.                 rob.setLightColor(0xFFFF00)
  243.                 return
  244.             else
  245.                 if content and sourceSlotOk == false and content.label == item then
  246.                     print()
  247.                     print("Ignoring matching item in inaccessible slot")
  248.                 end
  249.             end
  250.             slot = slot + 1
  251.         end
  252.         checkPower()
  253.         if repeatUntilSuccess == 0 then
  254.             return false
  255.         else
  256.             term.setCursor(1, height)
  257.             term.clearLine()
  258.             term.write("No item found, holding " .. tostring(repeatUntilSuccess) .. " seconds")
  259.             rob.setLightColor(0x990000)
  260.             local ev = event.pull(repeatUntilSuccess, "interrupted")
  261.             if ev == "interrupted" then
  262.                 print()
  263.                 error("Interrupted in findAndMoveLoop")
  264.             end
  265.         end
  266.     end
  267. end
  268.  
  269. rob.setLightColor(0x00DB00)
  270. rs.setOutput(sides.front, 15)
  271. while run do
  272.     slotMem = findEmptySlot(true, 1)
  273.     if slotMem ~= false then
  274.         if resume == 0 then
  275.             findAndMoveTo(items["dualroddepleted"], slotMem, 1, false, 60, false)
  276.             rs.setOutput(sides.left, 0)
  277.             rob.setLightColor(0xFFFF00)
  278.             findAndMoveTo(items["dualroddepleted"], slotMem, 1, false, 0, false)
  279.             findAndMoveTo(items["dualroddepleted"], slotMem, 1, false, 0, false)
  280.             findAndMoveTo(items["dualroddepleted"], slotMem, 1, false, 0, false)
  281.             rob.select(slotMem)
  282.            
  283.             rob.turn(true)
  284.             rob.turn(true)
  285.         end
  286.        
  287.         slotMem = findEmptySlot(false, 5)
  288.         if slotMem ~= false then
  289.             inv.dropIntoSlot(sides.front, slotMem)
  290.            
  291.             slotMem = findEmptySlot(true, 1)
  292.             if slotMem ~= false then
  293.                 setResume(1)
  294.                 if resume <= 1 then
  295.                     findAndMoveTo(items["plutonium"], slotMem, 64, true, 10, true)
  296.                 end
  297.                
  298.                 setResume(2)
  299.                 if resume <= 2 then
  300.                     craft(recipes["enrich"])
  301.                     craft(recipes["enrich"])
  302.                     craft(recipes["enrich"])
  303.                     craft(recipes["enrich"])
  304.                     craft(recipes["enrich"])
  305.                     craft(recipes["enrich"])
  306.                     craft(recipes["enrich"])
  307.                     craft(recipes["enrich"])
  308.                 end
  309.                
  310.                 slotMem = findEmptySlot(false, 5)
  311.                 if slotMem ~= false then
  312.                     inv.dropIntoSlot(sides.front, slotMem, 64)
  313.                     slotMem = findEmptySlot(true, 5)
  314.                     if slotMem ~= false then
  315.                         setResume(3)
  316.                         if resume <= 3 then
  317.                             findAndMoveTo(items["rod"], slotMem, 64, true, 10, true)
  318.                         end
  319.                        
  320.                         setResume(4)
  321.                         if resume <= 4 then
  322.                             craft(recipes["dualrod"])
  323.                             craft(recipes["dualrod"])
  324.                             craft(recipes["dualrod"])
  325.                             craft(recipes["dualrod"])
  326.                         end
  327.                        
  328.                         rob.turn(true)
  329.                         rob.turn(true)
  330.                        
  331.                         setResume(5)
  332.                         inv.dropIntoSlot(sides.front, findEmptySlot(false, 1))
  333.                         inv.dropIntoSlot(sides.front, findEmptySlot(false, 1))
  334.                         inv.dropIntoSlot(sides.front, findEmptySlot(false, 1))
  335.                         inv.dropIntoSlot(sides.front, findEmptySlot(false, 1))
  336.                         print("Refuelling operation complete!")
  337.                         rs.setOutput(sides.left, 15)
  338.                         rob.setLightColor(0x00DB00)
  339.                     else
  340.                         error("No empty slots in sorter")
  341.                     end
  342.                 else
  343.                     error("No empty slots in sorter")
  344.                 end
  345.             else
  346.                 error("No empty slots in robot")
  347.             end
  348.         else
  349.             error("No empty slots in sorter")
  350.         end
  351.     else
  352.         error("No empty slots in robot")
  353.     end
  354.    
  355.     local ev = event.pull(1, "interrupted")
  356.    
  357.     if ev == "interrupted" then
  358.         error("Interrupted in main")
  359.     end
  360.     setResume(0)
  361. end
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement