This is a read-only snapshot of the ComputerCraft forums, taken in April 2020.
Shehab19's profile picture

Help with modem integration into code

Started by Shehab19, 24 September 2014 - 03:52 PM
Shehab19 #1
Posted 24 September 2014 - 05:52 PM
Hey everyone, I am very new to the use of modems but i can do some lua programming in computercraft. i need help making my code work with a modem (tell a computer to do something and it sends the command to a turtle)

basically my code is sort of a delivery system with a turtle. it doesnt do much, it just travels a distance, drops blocks, and returns.

so here it is:

while true do
– Clear screen
term.clear()
term.setCursorPos(1,1)

print ("Pick an action:")
print ("1) Travel Distance.")
print ("2) Drop items.")
print ("3) Return turtle to starting point.")

– Option 1: Turtle move distance 5 blocks.
choice = tonumber(read())
if choice == 1 then
tfront = 0
while tfront < 5 do
turtle.forward()
tfront = tfront + 1
end
end
– Option 2: Drop items
if choice == 2 then
for sslot = 1,9 do
turtle.select(sslot)
for islot = 1,turtle.getItemCount(sslot) do
turtle.drop()
end
end
end
– Option 3: Return to start
if choice == 3 then
tback = 0
while tback < 5 do
turtle.back()
tback = tback + 1
end
end
end



i would be really greatful if someone could show me how to make with work from a computer giving comands to a wireless turtle. many of the tutorials i've googled havent helped much.
Ty!!
Bomb Bloke #2
Posted 25 September 2014 - 12:24 AM
The fun thing about turtle movement calls and rednet reception calls is that they both pull events to work. This makes it "interesting" to use them side by side.

I also recommend reading up on tables before proceeding.

First, consider a very basic pair of scripts:

Controller:
local turtleID = 34 -- Or whatever the turtle's ID number is.

do
	local peripherals = {peripheral.getNames()}                     -- Get all attached peripheral names, stick them in a table.
	for i=1,#peripherals do                                         -- For each entry in the table...
		if peripheral.getType(peripherals[i]) == "modem" then   -- ... if it's a modem...
			rednet.open(peripherals[i])                     -- ... then open it for rednet use.
		end
	end
end

while true do
	print("Enter a command to send to the turtle:")
	rednet.send(turtleID, read())  -- Prompt the user to type in something, and send it to the turtle.
end

Turtle:
do
	local peripherals = {peripheral.getNames()} 
	for i=1,#peripherals do
		if peripheral.getType(peripherals[i]) == "modem" then
			rednet.open(peripherals[i])
		end
	end
end

while true do
	local senderID, command = rednet.receive()
	
	if turtle[command] then  -- If a function by the specified name exists in the turtle table, then...
		print("I was asked to run turtle."..command.."(). Proceeding...")
		turtle[command]()
	else
		print("I was asked to run turtle."..command.."(), but that doesn't exist in the API.")
	end
end

Running both scripts and typing eg "turnLeft" into the computer should make the turtle turn left.

Now, that's all well and good, but what if a message is sent while the turtle is performing an action? The turtle movement call will "eat" the message, and so the following rednet.receive() call will miss it. So, we can use the parallel API to make sure we don't miss anything:

Turtle:
do
	local peripherals = {peripheral.getNames()} 
	for i=1,#peripherals do
		if peripheral.getType(peripherals[i]) == "modem" then
			rednet.open(peripherals[i])
		end
	end
end

local taskList = {}  -- Make a new, empty table.

local function doTask()
	while true do
		while #taskList > 0 do               -- So long as anything's in the taskList table...
			if turtle[taskList[1]] then  -- ... work on whatever's at the front of the table.
				print("I was asked to run turtle."..taskList[1].."(). Proceeding...")
				turtle[taskList[1]]()
			else
				print("I was asked to run turtle."..taskList[1].."(), but that doesn't exist in the API.")
			end
			
			table.remove(taskList, 1)  -- Remove the first entry from the table, moving all other entries down one.
		end
		
		os.pullEvent("doWork")  -- If the table is empty, sit and wait for an event from getTask().
	end
end

local function getTask()
	while true do
		local senderID, taskList[#taskList+1] = rednet.receive()  -- Stick any received commands at the end of the "taskList" table.
		os.queueEvent("doWork") -- Send an event for doTask() to pick up on.
	end
end

parallel.waitForAny(doTask, getTask)

Have a play, see what you make of it. Fair warning, I've not tested any of the above.
Shehab19 #3
Posted 05 October 2014 - 09:07 AM
The fun thing about turtle movement calls and rednet reception calls is that they both pull events to work. This makes it "interesting" to use them side by side.

I also recommend reading up on tables before proceeding.

First, consider a very basic pair of scripts:

Controller:
local turtleID = 34 -- Or whatever the turtle's ID number is.

do
	local peripherals = {peripheral.getNames()}					 -- Get all attached peripheral names, stick them in a table.
	for i=1,#peripherals do										 -- For each entry in the table...
		if peripheral.getType(peripherals[i]) == "modem" then   -- ... if it's a modem...
			rednet.open(peripherals[i])					 -- ... then open it for rednet use.
		end
	end
end

while true do
	print("Enter a command to send to the turtle:")
	rednet.send(turtleID, read())  -- Prompt the user to type in something, and send it to the turtle.
end

Turtle:
do
	local peripherals = {peripheral.getNames()}
	for i=1,#peripherals do
		if peripheral.getType(peripherals[i]) == "modem" then
			rednet.open(peripherals[i])
		end
	end
end

while true do
	local senderID, command = rednet.receive()
	
	if turtle[command] then  -- If a function by the specified name exists in the turtle table, then...
		print("I was asked to run turtle."..command.."(). Proceeding...")
		turtle[command]()
	else
		print("I was asked to run turtle."..command.."(), but that doesn't exist in the API.")
	end
end

Running both scripts and typing eg "turnLeft" into the computer should make the turtle turn left.

Now, that's all well and good, but what if a message is sent while the turtle is performing an action? The turtle movement call will "eat" the message, and so the following rednet.receive() call will miss it. So, we can use the parallel API to make sure we don't miss anything:

Turtle:
do
	local peripherals = {peripheral.getNames()}
	for i=1,#peripherals do
		if peripheral.getType(peripherals[i]) == "modem" then
			rednet.open(peripherals[i])
		end
	end
end

local taskList = {}  -- Make a new, empty table.

local function doTask()
	while true do
		while #taskList > 0 do			   -- So long as anything's in the taskList table...
			if turtle[taskList[1]] then  -- ... work on whatever's at the front of the table.
				print("I was asked to run turtle."..taskList[1].."(). Proceeding...")
				turtle[taskList[1]]()
			else
				print("I was asked to run turtle."..taskList[1].."(), but that doesn't exist in the API.")
			end
			
			table.remove(taskList, 1)  -- Remove the first entry from the table, moving all other entries down one.
		end
		
		os.pullEvent("doWork")  -- If the table is empty, sit and wait for an event from getTask().
	end
end

local function getTask()
	while true do
		local senderID, taskList[#taskList+1] = rednet.receive()  -- Stick any received commands at the end of the "taskList" table.
		os.queueEvent("doWork") -- Send an event for doTask() to pick up on.
	end
end

parallel.waitForAny(doTask, getTask)

Have a play, see what you make of it. Fair warning, I've not tested any of the above.
Ty!