feat: first version of inferium harvester

This commit is contained in:
Guillaume ARM 2024-05-19 16:34:28 +02:00
parent 0c2b64beb8
commit f811031db5
3 changed files with 320 additions and 19 deletions

174
inferium-harvester.lua Normal file
View File

@ -0,0 +1,174 @@
local config = {
length = 8
firstCropZ = 2
}
local MIN_FUEL_NEEDED = (10 + config.firstCropZ + config.length) * 2
local VERSION = "0.1.0"
local IDLE_TIME = 2
local turtleUtils = require('libs/turtle-utils')
-- UTILS
local function waitForMatureCrop()
return turtleUtils.waitFor(function()
return turtleUtils.isMatureCrop(turtle.inspectDown)
end, IDLE_TIME)
end
local function assertEnoughFuel()
if turtle.getFuelLevel() < MIN_FUEL_NEEDED then
error('Not enough fuel')
end
end
local function retrieveChestFuelOrientation()
local inventoryFound = false
for i=1, 4, 1 do
if turtleUtils.getInventory('front') then
inventoryFound = true
break
end
turtle.turnRight()
end
if not inventoryFound then
error('chest fuel not found')
end
end
-- Implementations
local function retrieveHomePositionProcedure()
if turtleUtils.getInventory('bottom') then
retrieveChestFuelOrientation()
turtle.turnLeft()
end
turtle.turnRight()
if turtle.inspect() then
turtle.turnRight()
end
while true do
if turtleUtils.getInventory('bottom') then
return
end
if turtle.inspect() then
break
else
turtle.forward()
end
end
turtle.turnLeft()
turtle.turnLeft()
while true do
if turtleUtils.getInventory('bottom') then
return
end
if turtle.inspect() then
error('Cannot retrieve home position')
else
turtle.forward()
end
end
end
local function dropAllProcedure()
for i=1, 16, 1 do
local count = turtle.getItemCount(i)
if count > 0 then
while not turtleUtils.dropSlot(i, turtle.dropDown) do
os.sleep(IDLE_TIME)
end
end
end
end
local function refuelProcedure()
turtle.turnLeft()
turtleUtils.waitForInventory('front')
turtleUtils.refuel(MIN_FUEL_NEEDED, turtle.suck)
turtle.turnLeft()
end
local function goToHarvestPoint()
for i=1, config.firstCropZ, 1 do
turtle.forward()
end
end
local function goBackToHome()
for i=1, config.firstCropZ - 1, 1 do
turtle.forward()
end
end
local function harvestDown()
local cropName = waitForMatureCrop()
if not turtle.digDown() then
error('turtle cannot harvest crop')
end
if not turtleUtils.selectItemByName(cropName) then
error('turtle cannot find any crop to place')
end
if not turtleUtils.placeDown() then
error('turtle cannot place crop')
end
end
local function forward()
if not turtle.forward() then
error('turtle is blocked')
end
end
local function harvestProcedure()
for i=1, config.length, 1 do
harvestDown()
forward()
end
turtle.turnLeft()
turtle.turnLeft()
for i=1, config.length, 1 do
harvestDown()
forward()
end
end
-- Main procedure
local function main()
print("Starting Trap's inferium harvester v" .. VERSION)
turtleUtils.refuelAllFromInventory()
assertEnoughFuel()
print("> retrieving home position")
retrieveHomePositionProcedure()
print("> start the harvesting process")
while true do
dropAllProcedure()
refuelProcedure()
goToHarvestPoint()
harvestProcedure()
goBackToHome()
end
end
main()

View File

@ -1,7 +1,8 @@
local LIST_FILES = {
'miner.lua',
'old/simple-harvester.lua',
'inferium-upgrader.lua'
'inferium-upgrader.lua',
'inferium-harvester.lua'
};
local LIST_LIBS_FILES = {

View File

@ -1,45 +1,102 @@
local turtleUtils = {}
local IDLE_TIME = 2
local DEFAULT_IDLE_TIME = 2
turtleUtils.waitForInventory = function(side)
local inv = nil
turtleUtils.getInventory = function(side)
side = side or 'front'
local inv = peripheral.wrap(side)
while true do
inv = peripheral.wrap(side)
if inv and peripheral.hasType(inv, 'inventory') then
break
end
os.sleep(IDLE_TIME)
if peripheral.hasType(inv, 'inventory') then
return inv
end
return inv
return nil
end
function waitFor(predicate, sleepTime)
sleepTime = sleepTime or DEFAULT_IDLE_TIME
while true do
local result = predicate()
if result ~= nil and result ~= false then
return result
end
os.sleep(sleepTime)
end
end
turtleUtils.waitForInventory = function(side, sleepTime)
return waitFor(function()
return turtleUtils.getInventory(side)
end, sleepTime)
end
turtleUtils.trySuck = function(suckFn, sleepTime)
suckFn = suckFn or turtle.suck
sleepTime = sleepTime or DEFAULT_IDLE_TIME
while not suckFn() do
os.sleep(sleepTime)
end
end
turtleUtils.trySuckUp = function()
while not turtle.suckUp() do
os.sleep(IDLE_TIME)
end
return turtleUtils.trySuck(turtle.suckUp)
end
turtleUtils.tryDrop = function()
turtleUtils.trySuckDown = function()
return turtleUtils.trySuck(turtle.suckDown)
end
turtleUtils.tryDrop = function(dropFn, sleepTime)
dropFn = dropFn or turtle.drop
sleepTime = sleepTime or DEFAULT_IDLE_TIME
while true do
if turtle.getItemCount() == 0 then
return false
end
local dropOk = turtle.drop();
local dropOk = dropFn();
if (dropOk) then
return true
end
os.sleep(IDLE_TIME)
os.sleep(sleepTime)
end
end
turtleUtils.tryDropUp = function()
return turtleUtils.tryDrop(turtle.dropUp)
end
turtleUtils.tryDropDown = function()
return turtleUtils.tryDrop(turtle.dropDown)
end
turtleUtils.dropSlot = function(slotIndex, dropFn)
dropFn = dropFn or turtle.drop
if turtle.getItemCount(slotIndex) == 0 then
return false
end
if turtle.getSelectedSlot() ~= slotIndex then
turtle.select(slotIndex)
end
local ok, err = dropFn()
if not ok then
return false
end
return true
end
turtleUtils.digAll = function()
while turtle.dig() do end
end
@ -60,4 +117,73 @@ turtleUtils.getFuelPercentage = function()
return (turtle.getFuelLevel() / turtle.getFuelLimit()) * 100
end
turtleUtils.isMatureCrop = function(inspectFn)
inspectFn = inspectFn or turtle.inspect
return function()
local isBlock, block = inspectFn()
local blockStateAge = block and block.state and block.state.age
return blockStateAge == 7
end
end
turtleUtils.selectFirstEmptySlot = function()
for i = 1, 16, 1 do
if turtle.getItemCount(i) == 0 then
turtle.select(i)
return true
end
end
return false
end
turtleUtils.selectItemByName = function(itemName)
for i = 1, 16, 1 do
local item = turtle.getItemDetail(i)
if item and item.name == itemName then
turtle.select(i)
return true
end
end
return false
end
turtleUtils.refuel = function(minFuel, suckFn)
suckFn = suckFn or turtle.suck
if not turtleUtils.selectFirstEmptySlot() then
return false
end
while turtle.getFuelLevel() < minFuel do
suckFn()
local ok = turtle.refuel()
if not ok then
return false
end
end
return true
end
turtleUtils.refuelAllFromInventory = function()
local initialSelectedSlot = turtle.getSelectedSlot()
for i=1, 16, 1 do
if turtle.getItemCount(i) > 0 then
turtle.select(i)
turtle.refuel()
end
end
if turtle.getSelectedSlot() ~= initialSelectedSlot then
turtle.select(initialSelectedSlot)
end
end
return turtleUtils