Advertisement
Ubidibity

Ultimate Crafting Turtle (ENG) v.6

Jan 5th, 2024 (edited)
1,176
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. -- Adapted from Marval's pastebin b2fc4912 but converted to English via ChatGPT
  2. -- All credit goes to Marval.  This v.5 is untested as of yet, and likely needs some post-AI tweaking.
  3. -- This version was ran through GPTv3.5 'improvement' as it works with the code as a whole, and GPTv4 wants to break everything
  4. -- into small chunks.
  5.  
  6. local peripheralAnalyzer = peripheral.wrap("right")
  7. local craftingSlots = {1, 2, 3, 5, 6, 7, 9, 10, 11}
  8. local tCraft = {}
  9.  
  10. local function dropAllItems()
  11.     for i = 1, 16 do
  12.         if turtle.getItemCount(i) > 0 then
  13.             turtle.select(i)
  14.             turtle.drop()
  15.         end
  16.     end
  17. end
  18.  
  19. local function countItems(craftingGrid)
  20.     local countList = {}
  21.     for i = 1, 9 do
  22.         countList[i] = {ID = nil, META = nil, COUNT = 0}
  23.     end
  24.  
  25.     local startIndex = 0
  26.     for i = 1, 9 do
  27.         if craftingGrid[i][1] then
  28.             countList[1].ID = craftingGrid[i][1]
  29.             countList[1].META = craftingGrid[i][2]
  30.             countList[1].COUNT = 1
  31.             startIndex = i
  32.             break
  33.         end
  34.     end
  35.  
  36.     local itemCount = 1
  37.     for i = startIndex + 1, 9 do
  38.         if craftingGrid[i][1] then
  39.             local itemId = craftingGrid[i][1]
  40.             local itemMeta = craftingGrid[i][2]
  41.  
  42.             local itemFound = false
  43.             for j = 1, itemCount do
  44.                 if itemId == countList[j].ID and itemMeta == countList[j].META then
  45.                     countList[j].COUNT = countList[j].COUNT + 1
  46.                     itemFound = true
  47.                     break
  48.                 end
  49.             end
  50.  
  51.             if not itemFound then
  52.                 itemCount = itemCount + 1
  53.                 countList[itemCount].ID = itemId
  54.                 countList[itemCount].META = itemMeta
  55.                 countList[itemCount].COUNT = 1
  56.             end
  57.         end
  58.     end
  59.  
  60.     return countList, itemCount
  61. end
  62.  
  63. local function checkAvailability(items, recordCount)
  64.     local isAvailable = true
  65.     local missingItem = nil
  66.  
  67.     for i = 1, recordCount do
  68.         local slot = 0
  69.         local itemId = 0
  70.         local itemMeta = 0
  71.         local itemCount = 0
  72.  
  73.         repeat
  74.             slot = slot + 1
  75.             itemId = peripheralAnalyzer.getBlockIdAt(slot)
  76.             itemMeta = peripheralAnalyzer.getBlockMetadataAt(slot)
  77.  
  78.             if itemId == items[i].ID and (items[i].META == nil or itemMeta == items[i].META) then
  79.                 itemCount = itemCount + peripheralAnalyzer.getBlockCountAt(slot)
  80.             end
  81.         until slot == 109
  82.  
  83.         if itemCount < items[i].COUNT then
  84.             isAvailable = false
  85.             missingItem = items[i].META == nil and items[i].ID or (items[i].ID .. ":" .. items[i].META)
  86.             print("Missing item ID: " .. missingItem .. " in quantity: " .. items[i].COUNT - itemCount)
  87.             break
  88.         end
  89.     end
  90.  
  91.     return isAvailable, missingItem
  92. end
  93.  
  94. local function craft(items)
  95.     for i = 1, 9 do
  96.         if items[i][1] then
  97.             local slot = 0
  98.             repeat
  99.                 slot = slot + 1
  100.                 local itemId = peripheralAnalyzer.getBlockIdAt(slot)
  101.                 local itemMeta = peripheralAnalyzer.getBlockMetadataAt(slot)
  102.             until (itemId == items[i][1] and (items[i][2] == nil or itemMeta == items[i][2]))
  103.  
  104.             local itemCount = peripheralAnalyzer.getBlockCountAt(slot)
  105.             turtle.select(craftingSlots[i])
  106.             peripheralAnalyzer.takeAt(slot)
  107.             turtle.drop(itemCount - 1)
  108.         end
  109.     end
  110.  
  111.     turtle.craft()
  112.     dropAllItems()
  113. end
  114.  
  115. local function manageCrafting(recipe)
  116.     print("Crafting " .. b)
  117.     local isReadyToCraft = false
  118.  
  119.     while not isReadyToCraft do
  120.         local countList, itemCount = countItems(recipe)
  121.         isReadyToCraft, missingItem = checkAvailability(countList, itemCount)
  122.  
  123.         if not isReadyToCraft then
  124.             print("Missing " .. missingItem)
  125.             missingItem = tostring(missingItem)
  126.             crafting()
  127.         else
  128.             craft(recipe)
  129.         end
  130.     end
  131. end
  132.  
  133. local function crafting(b)
  134.     if tCraft[b] then
  135.         manageCrafting(tCraft[b])
  136.     else
  137.         print("Missing: " .. b)
  138.         os.pullEvent()
  139.     end
  140. end
  141.  
  142. local function startCrafting()
  143.     local file = io.open("receptury", "r")
  144.     while true do
  145.         local line = file:read()
  146.         if line == nil then break end
  147.  
  148.         local item, recipeParts = string.match(line, "([%w%:]+)=(.+)")
  149.  
  150.         tCraft[item] = {}
  151.         for i = 1, 9 do
  152.             local part = select(i, string.match(recipeParts, "([^;]+)"))
  153.             if part == "0" then
  154.                 tCraft[item][i] = {nil}
  155.             elseif string.find(part, ":") then
  156.                 local id, meta = string.match(part, "(%d+):(%d+)")
  157.                 tCraft[item][i] = {tonumber(id), tonumber(meta)}
  158.             else
  159.                 tCraft[item][i] = {tonumber(part)}
  160.             end
  161.         end
  162.     end
  163.     file:close()
  164.  
  165.     print("What to craft? Enter ID or ID:META")
  166.     local b = read()
  167.     local originalItem = b
  168.     print("How many?")
  169.     local quantity = tonumber(read())
  170.  
  171.     for zz = 1, quantity do
  172.         crafting(b)
  173.         b = originalItem
  174.     end
  175. end
  176.  
  177. local function displayMenu()
  178.     term.clear()
  179.     local option = 2
  180.  
  181.     term.setCursorPos(1, 1)
  182.     term.write("Ultimate Crafting Program")
  183.     local menuOptions = {
  184.         "Start Crafting",
  185.         "Add Recipe by Scanning",
  186.         "Add Recipe Manually"
  187.     }
  188.  
  189.     for i, optionText in ipairs(menuOptions) do
  190.         term.setCursorPos(1, i + 1)
  191.         term.write("[ ] " .. optionText)
  192.     end
  193. end
  194.  
  195. local function refreshMenu(option)
  196.     for i = 2, 4 do
  197.         term.setCursorPos(2, i)
  198.         term.write(" ")
  199.     end
  200.     term.setCursorPos(2, option)
  201.     term.write("X")
  202. end
  203.  
  204. local function saveScannedRecipe()
  205.     print("Arrange the recipe in the turtle's inventory")
  206.     os.pullEvent()
  207.  
  208.     local recipe = {}
  209.     for i = 1, 9 do
  210.         turtle.select(craftingSlots[i])
  211.         local id = peripheralAnalyzer.getBlockId()
  212.         if id then
  213.             recipe[i] = {ID = id, META = peripheralAnalyzer.getBlockMetadata()}
  214.         else
  215.             recipe[i] = {ID = nil}
  216.         end
  217.     end
  218.  
  219.     local recipeString = {}
  220.     for i = 1, 9 do
  221.         if recipe[i].ID == nil then
  222.             recipeString[i] = "0"
  223.         elseif recipe[i].META == nil then
  224.             recipeString[i] = tostring(recipe[i].ID)
  225.         else
  226.             recipeString[i] = recipe[i].ID .. ":" .. recipe[i].META
  227.         end
  228.     end
  229.  
  230.     turtle.craft()
  231.     turtle.select(11)
  232.     local craftedItem = peripheralAnalyzer.getBlockId() .. ":" .. peripheralAnalyzer.getBlockMetadata()
  233.     local file = io.open("receptury", "a")
  234.     file:write(string.format("%s=%s;%s;%s;%s;%s;%s;%s;%s;%s\n", craftedItem, unpack(recipeString)))
  235.     file:close()
  236. end
  237.  
  238. local function inputAndSaveRecipe()
  239.     term.clear()
  240.     print("Enter the recipe in the format: ")
  241.     print("ID:META=ID:META;ID:META; ... ;ID:META")
  242.     print("You can also input IDs without metadata")
  243.     local newRecipe = read()
  244.  
  245.     local file = io.open("receptury", "a")
  246.     file:write(newRecipe .. "\n")
  247.     file:close()
  248. end
  249.  
  250. local function main()
  251.     displayMenu()
  252.     local option = 2
  253.     refreshMenu(option)
  254.  
  255.     while true do
  256.         local event, keyCode = os.pullEvent("key")
  257.  
  258.         if keyCode == 208 and option < 4 then
  259.             option = option + 1
  260.         elseif keyCode == 200 and option > 2 then
  261.             option = option - 1
  262.         end
  263.  
  264.         if keyCode == 28 then
  265.             term.clear()
  266.             term.setCursorPos(1, 1)
  267.             if option == 2 then
  268.                 startCrafting()
  269.             elseif option == 3 then
  270.                 saveScannedRecipe()
  271.             elseif option == 4 then
  272.                 inputAndSaveRecipe()
  273.             end
  274.             displayMenu()
  275.             refreshMenu(option)
  276.         end
  277.     end
  278. end
  279.  
  280. main()
  281.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement