diff --git a/doc/guides/about_modems.md b/doc/guides/about_modems.md new file mode 100644 index 0000000000..b5524c3135 --- /dev/null +++ b/doc/guides/about_modems.md @@ -0,0 +1,44 @@ +--- +module: [kind=guide] about_modems +see: peripheral The full documentation of the peripheral API +see: rednet The full documentation of the rednet API +see: modem The full documentation of the modem API +see: basic_rednet For a guide of using rednet to send and receive messages +--- + +# A look at the different types of modems + + +The main traits and differences of modems that you may need to be aware of are: +* The two types of wired modem connect to things a bit differently, the smaller one can only connect to what it's placed on, the larger one can connect to everything that it's in contact with. + * Also, the smaller wired modem cannot be placed on everything. Kind of like torches, it needs to be placed on a solid block. This is more relevant when using wired modems to connect to peripherals. +* While both wired modems can use networking cables, the smaller wired modem needs a cable placed in its block space to become functional. +* Full block modems will allow the network to pass through them, effectively allowing them to double as networking cables. + * If you are running some cables though a wall then having a full block modem as part of the wall can be a nice aesthetic choice. + * This works even i the modem is only connected to networking cables. +* Wired modems and network cables have a max length of 256 blocks, after which connections will be ignored. + * This means that if another computer is further away then rednet messages will not reach it and it will not show up @{computer|as a peripheral}. + * This range cannot be changed in the config. +* Wired modems and wireless modems cannot talk to each other directly. A computer will need to relay messages heard on one modem to the other, there is a built in program that will do this for you it is called `repeat`. + * Wireless modems and ender modems can talk to each other though. + * The two types of wired modem also can talk to each other, provided that they are connected to each other. +* Wireless modems have a limited range, ender modems have a practically infinite range. +* By default, wireless modems have their range increase the higher they are in the world. The exact values can be set in the server side config file. + * The server side config file also allows for having wireless modem range reduce during thunderstorms, but this is not the default. + * The default range pre 1.18 near bedrock is 64 blocks and 384 blocks near the max build height. The max ranges after 1.18 are likely different now that Minecraft has negative y levels and a higher build limit. You can run the calculation yourself by checking the [source code]. +* Ender modems are the only modem that can send and receive messages from other dimensions. + +## Using modems as peripheral connectors +Only wired modems can be used as peripherals connectors. + +Place the wired modem on the peripheral block, if it doesn't place then try using a full block modem. Next you'll want to right click the modem to activate it's peripheral mode, if everything worked then you should see a message in the chat window displaying the network name of the peripheral. Make a note of this name, you'll need it to wrap the peripheral. Note that you can click on the message in the chat to copy the peripheral's network name to your clipboard. + +Next, connect your computer's modem to the peripheral modem with networking cables (if required). Then you can use the peripheral's network name in place of a side as if you had the peripheral on the computer. + +```lua +local monitor = peripheral.wrap("monitor_1") + +monitor.write("hello world") +``` + +[source code]: https://github.com/cc-tweaked/CC-Tweaked/blob/9d50d6414ce84ed2b442c933ca2fb60c97849c6b/src/main/java/dan200/computercraft/shared/peripheral/modem/wireless/WirelessModemPeripheral.java#L40-L57 "Wireless modem range calculation" diff --git a/doc/guides/basic_rednet.md b/doc/guides/basic_rednet.md new file mode 100644 index 0000000000..5858b10d64 --- /dev/null +++ b/doc/guides/basic_rednet.md @@ -0,0 +1,81 @@ +--- +module: [kind=guide] basic_rednet +see: peripheral The full documentation of the peripheral API +see: rednet The full documentation of the rednet API +see: about_modems The differences between the types of modems +--- + +# The basics of rednet messaging + +A modem's primary use is to send messages between two or more computers, all three kinds of modem do this slightly differently with the wired modem being the most different. Additionally, there are two APIs for using modems for sending messages, the modem API and the Rednet API. We are only going to cover the rednet API as it is simpler to use and has some additional ease of use features. The modem API is lower level and not as intuitive for just sending messages, if you are curious about the modem API then you can look up its documentation and/or check the Rednet API source code for how Rednet uses the lower-level API for its needs (FYI, the Rednet API sits on top of the modem API - i.e. it uses the modem API to do its stuff). + + +## Using modems to send messages between computers +No matter which type of modem you use, the process of sending rednet messages is the same. For the rest of this guide, we are going to assume that you have two computers, connected together by a single full block modem. + +![Two computers separated by a full block wired modem such that they are on the same network.](/images/rednet-example.png){.big-image} + +Before you begin, you are going to want to note the IDs of both computers that you are using. Rednet uses IDs to specify the *intended* recipient of a message, do note that every computer in range of the message (or connected via wired modems) will receive the message - we will explain this a bit more later. The easiest way to get the ID of a computer is to use the `id` command. + +The first thing that every computer needs to do before using rednet is to tell rednet what modem/s it's allowed to use, this is done with `rednet.open()` where `` is the side of the computer that the modem is on as a string. If your modem is on the top of the computer then you would do `rednet.open("top")`. Opening the same modem twice is not a problem, it will only open it once. Rednet cannot send and receive messages through modems that are not open. + +Next, you are going to want to set up one of the computers to receive a message. The easiest way to do this is with @{rednet.receive}, this will cause the computer to wait for a rednet message. You could also pull a @{rednet_message} event, but `rednet.receive` is simpler so we will be using that. While computers can hear every rednet message that they are in range of (as a `modem_message`), the rednet API will ignore those that it's not the intended recipient of. + +`rednet.receive()` has three return values but we are only interested in the first two, the id of the sender and the message. You will probably want to print out both of these values. It may also be helpful to put this in a while true loop. Your receiver code might end up looking something like this. + +```lua +while true do + local senderID, message = rednet.receive() + print("sender ID: "..senderID) + print("Message: "..message) + print() +end +``` + +Then on the other computer, we want to use @{rednet.send} to send a message. The first argument is the id of the computer that we want to send the message to, the second argument is the message that we want to send. There is a third argument, but we don't need to use it for this example. + +```lua +rednet.send(targetID, "Hello there!") +``` + +Just make sure to replace the targetID with the ID of the computer that you want to send the message to. + +Once both computers have code you'll want to start the receiver code first and then the sender code, this is because you need the receiver to be listening before you have the sender send a message. + +You now know the basics of sending and receiving rednet messages. @{rednet.broadcast} is similar to @{rednet.send} but it will send the message to every computer in range of the modem. + +:::note The repeat program +Ender modems are expensive to craft but wireless modems have a quite limited range. Thankfully there is a solution, the repeat program. To put simply, any rednet message that a computer running the repeat program hears will be resent from that computer. + +With a single ender modem on a single computer running the repeat program, you can send rednet messages to any computer in the server. Just make sure that this computer and modem stay chunk loaded. +::: + +:::note Computers can send rednet messages to themselves without a modem +Rednet has a loopback feature, computers can send rednet messages to themselves without having a modem attached. This is useful for allowing multiple programs on the same computer to communicate with each other. +::: + +:::note Rednet is not secure +Rednet is not secure. It is not designed to be. Anyone can easily listen to your messages even if they are not the intended recipient. Rednet protocols also are *not* a means of security. + +To demonstrate this, here is a very basic rednet sniffer. FYI, we are using the modem API here, specifically its `modem_message` event and `modem.open()`. +```lua +local modem = peripheral.find("modem") or error("No modem attached", 0) +modem.open(rednet.CHANNEL_REPEAT) + +while true do + local event, side, channel, replyChannel, message, distance = os.pullEvent("modem_message"); + print(("Message received on side %s on channel %d (reply to %d) from %f blocks away with message %s"):format(side, channel, replyChannel, distance, tostring(message))) +end +``` +To explain what this code is doing, we are exploiting the fact that all rednet messages are sent on two channels, the channel that the intended recipient is listening on and the channel that rednet repeaters listen on `rednet.CHANNEL_REPEAT`. + +Additionally, one can use the modem API to impersonate another computer by constructing a fake rednet message. + +If you want secure communication then look into encryption, there are a few implementations on the [old] and [new] forums, you may also be able to find some in the creations channel on the [discord]. +::: + +[old]: https://www.computercraft.info/forums2/ "The original computercraft forums" + +[new]: https://forums.computercraft.cc/index.php "The CC:T forums" + +[discord]: https://discord.computercraft.cc/ "The Minecraft Computer Mods Discord" diff --git a/doc/guides/fluid_transportation.md b/doc/guides/fluid_transportation.md new file mode 100644 index 0000000000..0a6a3ce8dd --- /dev/null +++ b/doc/guides/fluid_transportation.md @@ -0,0 +1,12 @@ +--- +module: [kind=guide] fluid_transportation +see: peripheral The full documentation of the peripheral API +see: fluid_storage The full documentation of generic fluid peripherals +see: about_modems The differences between the types of modems +--- + +# How to use ComputerCraft to move fluids around + +Please see the @{item_transportation|item transportation} guide, much of what it covers applies to fluid transportation too. + +Some blocks can have multiple tanks, think of these as multiple inventory slots. The quantity of fluid is like the number of items in the slot. diff --git a/doc/guides/item_transportation.md b/doc/guides/item_transportation.md new file mode 100644 index 0000000000..5cace5b0dc --- /dev/null +++ b/doc/guides/item_transportation.md @@ -0,0 +1,50 @@ +--- +module: [kind=guide] item_transportation +see: peripheral The full documentation of the peripheral API +see: inventory The full documentation of generic inventory peripherals +see: about_modems The differences between the types of modems +--- + +# How to use ComputerCraft to move items around + +There are two key limitations to keep in mind when using computercraft to move items. First, chests are peripherals and so are bound by the same limitations that peripherals. Second, the source and destination inventories must be on the same network. Technically both of these are limitations of peripherals and modems, but the second is more visible when trying to move items as a computer can easily bridge a rednet message to another network with the repeat program. + +This means that if you have two chests connected by different modems to a single computer you will not be able to move items between the two chests as the modems are their own networks. We are using red blocks in the image below to show that the chests cannot move items to each other. + +![Two chests connected to a single computer via two separate networks.](/images/separate-modem-networks.png){.big-image} + +Since the computer's direct sides count as a separate network, having one chest on a modem and the second directly on the computer also means that items can't move from one to the other. + +![Two chests connected to a single computer via two separate networks.](/images/separate-mixed-networks.png){.big-image} + +While cables are fine with peripherals, be aware of their length limit as it also applies to peripherals. + +Now for a few examples that will work. + +Having multiple chests connected through the same modem is fine. Just be aware that you will get one message for each chest in the chat with the chest's peripheral name. + +![Two chests connected to a single computer via single modem.](/images/shared-modem.png){.big-image} + +Having to separate modems is fine too. They can be connected via cables too. + +![Two chests connected to a single computer via two modems that are on the same network.](/images/two-modems-same-network.png){.big-image} + +Due to the sides of a computer being the same network, having chests directly connected to the computer allows items to move via the computer instead of via modems. This can be a bit confusing since they can't cross the computer if they are on a modem but it is how it is. + +![Two chests connected to a single computer directly.](/images/no-modems.png){.big-image} + +You can have modems on different sides of the computer as one network if you connect them via cables (or more modems). + +![Two chests connected to a single computer on different sides with cables joining them.](/images/bridging-cables.png){.big-image} + +If you are using a turtle and you are trying to use the chest peripheral to insert and/or extract items from the turtle then it's a little bit complicated. While turtles do count as inventories, they don't have the generic inventory peripheral, this means that they do not have the push and pull methods that chests and other inventories have. They are still valid targets for those methods though, which we will be looking at in a bit. + +First, I do want to mention that while the below can't use the generic inventory methods on the chest peripheral to push items into the turtle, the turtle can still @{turtle.suck|suck} items out of the chest with its turtle API. Since the chest can push items to itself you can use that to rearrange the items in the chest such that the first slot becomes what you want the turtle to suck as a way to circumvent the turtle's limitation of only being able to suck items from the first non-empty slot. + +In the screenshots, we are using yellow blocks to show that moving items is possible but requires workarounds. + +![A turtle connecting directly to a chest, turtle.suck still works.](/images/turtle-direct.png){.big-image} + +Now we'll look at a turtle and a chest connected via a modem. Here we can't use the turtle API anymore as the turtle isn't touching the chest, so we have to use the inventory methods. The turtle is a valid target for the chest to push to (and pull from) but we need to know the turtle's network name. This can be done by wrapping the modem and calling its @{modem.getNameLocal|getNameLocal} method, this gives the turtle's network name which is also the name that the chest will need to be able to push items into the turtle's inventory. + +![A turtle connecting to a chest via a modem.](/images/turtle-modem.png){.big-image} diff --git a/doc/images/bridging-cables.png b/doc/images/bridging-cables.png new file mode 100644 index 0000000000..aa7fbdabef Binary files /dev/null and b/doc/images/bridging-cables.png differ diff --git a/doc/images/no-modems.png b/doc/images/no-modems.png new file mode 100644 index 0000000000..902ff42262 Binary files /dev/null and b/doc/images/no-modems.png differ diff --git a/doc/images/rednet-example.png b/doc/images/rednet-example.png new file mode 100644 index 0000000000..84d6298bc1 Binary files /dev/null and b/doc/images/rednet-example.png differ diff --git a/doc/images/separate-mixed-networks.png b/doc/images/separate-mixed-networks.png new file mode 100644 index 0000000000..32e94d411d Binary files /dev/null and b/doc/images/separate-mixed-networks.png differ diff --git a/doc/images/separate-modem-networks.png b/doc/images/separate-modem-networks.png new file mode 100644 index 0000000000..cec26bc3b6 Binary files /dev/null and b/doc/images/separate-modem-networks.png differ diff --git a/doc/images/shared-modem.png b/doc/images/shared-modem.png new file mode 100644 index 0000000000..f69ae29513 Binary files /dev/null and b/doc/images/shared-modem.png differ diff --git a/doc/images/turtle-direct.png b/doc/images/turtle-direct.png new file mode 100644 index 0000000000..75c74fe95e Binary files /dev/null and b/doc/images/turtle-direct.png differ diff --git a/doc/images/turtle-modem.png b/doc/images/turtle-modem.png new file mode 100644 index 0000000000..c1209c963a Binary files /dev/null and b/doc/images/turtle-modem.png differ diff --git a/doc/images/two-modems-same-network.png b/doc/images/two-modems-same-network.png new file mode 100644 index 0000000000..0ea006d1ff Binary files /dev/null and b/doc/images/two-modems-same-network.png differ diff --git a/projects/forge/src/main/java/dan200/computercraft/shared/peripheral/generic/methods/FluidMethods.java b/projects/forge/src/main/java/dan200/computercraft/shared/peripheral/generic/methods/FluidMethods.java index aebd51b66d..657d322ef6 100644 --- a/projects/forge/src/main/java/dan200/computercraft/shared/peripheral/generic/methods/FluidMethods.java +++ b/projects/forge/src/main/java/dan200/computercraft/shared/peripheral/generic/methods/FluidMethods.java @@ -29,6 +29,7 @@ * Methods for interacting with tanks and other fluid storage blocks. * * @cc.module fluid_storage + * @cc.see fluid_transportation For a detailed guide on how to use these methods. * @cc.since 1.94.0 */ public class FluidMethods implements GenericPeripheral { diff --git a/projects/forge/src/main/java/dan200/computercraft/shared/peripheral/generic/methods/InventoryMethods.java b/projects/forge/src/main/java/dan200/computercraft/shared/peripheral/generic/methods/InventoryMethods.java index 1fead136b7..a6e8c9cefa 100644 --- a/projects/forge/src/main/java/dan200/computercraft/shared/peripheral/generic/methods/InventoryMethods.java +++ b/projects/forge/src/main/java/dan200/computercraft/shared/peripheral/generic/methods/InventoryMethods.java @@ -31,6 +31,7 @@ * Methods for interacting with inventories. * * @cc.module inventory + * @cc.see item_transportation For a detailed guide on how to use these methods. * @cc.since 1.94.0 */ public class InventoryMethods implements GenericPeripheral {