How to Connect an HMI to an Industrial Arduino
Expose live I/O and process values to a touchscreen HMI over Modbus RTU or I²C, with register mapping examples.
7 min read
The Goal: Live I/O on an Operator Screen
Connecting an HMI to an MPINO industrial Arduino means making the controller's physical world, its inputs, relays, transistors, and analog channels, visible and controllable from an operator panel. The HMI shows live input states, lets an operator command outputs, and trends analog values, all without the operator ever touching the controller directly.
The MPINO exposes its I/O to an HMI primarily over Modbus RTU on RS-485, the protocol nearly every HMI speaks natively. An on-board I²C bus is also available on every listed model for shorter-range connections to local peripherals or a companion processor when that better fits the panel architecture.
The pattern is the same regardless of model size. Whether you deploy a compact MPINO-8A8R-S or a fully populated MPINO-16A8R8T, you publish a register and coil map, run the ILIB Modbus slave, and bind HMI objects to those addresses. The rest of this guide walks through that mapping and the firmware that backs it.
Choosing the Transport: Modbus RTU or I²C
For an operator HMI, Modbus RTU over RS-485 is almost always the right transport. It runs over long, noise-tolerant cable, every major HMI brand includes a Modbus RTU driver, and the request-response model maps directly onto reading inputs and writing coils. The MPINO auto-direction transceiver and the ILIB slave stack make the MPINO a clean Modbus node with no driver-enable timing to manage.
I²C suits a different role. It is a short-range, multi-device bus intended for communication on the same panel or board, for example between an MPINO and a local display controller, an expander, or a supervisory microcontroller. Every listed MPINO exposes I²C alongside its serial interfaces, so a designer can combine a long-haul Modbus link to the HMI with a local I²C link to nearby devices.
Choose Modbus RTU when the HMI is a standalone operator panel some distance from the controller, which is the typical industrial case. Reserve I²C for tightly coupled, in-cabinet peripherals where its short reach and simple two-wire bus are an advantage rather than a constraint.
Designing the Register and Coil Map
The register map is the single most important artifact in an HMI integration because it defines exactly what each address means. Lay it out before writing firmware and treat it as a published interface. Inputs that the HMI only reads belong in discrete inputs and input registers; outputs the HMI commands belong in coils and holding registers.
For an MPINO-8A8R a clear map reads: coils 0-7 drive the 8 relays, discrete inputs 0-7 report the 8 digital inputs, and input registers 0-3 carry the 4 analog channels as raw 0-1023 counts from the EXTERNAL-referenced ADC. Document units and scaling next to each register so the HMI builder configures display scaling correctly.
For a richer controller such as the MPINO-16A8R8T, extend the same scheme: discrete inputs 0-15 for the 16 digital inputs, coils 0-7 for relays and coils 8-15 for the 8 transistor outputs, input registers for the 4 analog inputs and 2 NTC channels, and holding registers for the 2 analog outputs. A stable, well-labeled map lets the HMI integrator work in parallel with firmware development.
Firmware: Reading Inputs and Writing Relay Coils
With the map fixed, the firmware reduces to a tight loop: copy the live digital and analog inputs into the slave's discrete-input and input-register tables, service the master with a poll call, then apply any coil values the master has written to the physical relays and transistor outputs.
The sketch below implements exactly this for an MPINO-16A8R8T acting as a Modbus RTU slave. It refreshes 16 discrete inputs and 4 analog input registers, calls poll() so the HMI master can read them and write coils, and then drives 8 relays and 8 transistor outputs from coils 0-15. Note analogReference(EXTERNAL), which the MPINO analog front end requires for correct ADC readings.
This structure keeps input data fresh every scan and applies operator commands deterministically right after the poll, so what the HMI displays and what it commands stay tightly synchronized with the physical I/O.
#include <ILIB.h>
// MPINO-16A8R8T Modbus RTU slave for HMI access
ModbusSlave mb;
const uint8_t DI[16] = {22,23,24,25,26,27,28,29,
30,31,32,33,34,35,36,37};
const uint8_t RELAY[8] = {38,39,40,41,42,43,44,45};
const uint8_t TR[8] = {46,47,48,49,2,3,4,5};
const uint8_t AI[4] = {A0,A1,A2,A3};
void setup() {
analogReference(EXTERNAL); // required for MPINO analog
for (uint8_t i=0;i<16;i++) pinMode(DI[i], INPUT);
for (uint8_t i=0;i<8;i++) pinMode(RELAY[i], OUTPUT);
for (uint8_t i=0;i<8;i++) pinMode(TR[i], OUTPUT);
mb.begin(1, 19200); // slave id 1
}
void loop() {
// Inputs -> discrete inputs 0..15
for (uint8_t i=0;i<16;i++)
mb.setDiscreteInput(i, digitalRead(DI[i]));
// Analog -> input registers 0..3 (raw 0..1023)
for (uint8_t i=0;i<4;i++)
mb.setInputRegister(i, analogRead(AI[i]));
mb.poll(); // HMI reads inputs, writes coils
// Coils 0..7 -> relays, 8..15 -> transistor outputs
for (uint8_t i=0;i<8;i++) digitalWrite(RELAY[i], mb.getCoil(i));
for (uint8_t i=0;i<8;i++) digitalWrite(TR[i], mb.getCoil(8+i));
}Configuring the HMI Side
On the HMI, create a Modbus RTU serial driver whose baud rate, data bits, parity, and stop bits exactly match the MPINO begin() call. Add a device entry for the MPINO at its slave address, then create tags that point at the published addresses: discrete-input tags for the input lamps, coil tags for the output buttons, and register tags for analog displays.
Bind screen widgets to those tags. A momentary or maintained pushbutton writes a coil; an indicator lamp reads a discrete input; a numeric display or trend reads an input register and applies the scaling you documented in the map. Because coils are read/write, the HMI can both command a relay and read back its commanded state for confirmation.
Set a sensible poll interval, commonly 100-500 ms, and group adjacent addresses so the HMI reads them in single Modbus transactions. This minimizes bus traffic and keeps screen updates smooth even when an ATmega128 or ATmega2560 is servicing the full I/O complement of the controller.
Validation, Safety, and Real Values
Before handing the panel to operators, validate every mapped point end to end. Toggle each physical input and confirm the matching HMI lamp follows; press each HMI button and confirm the corresponding relay or transistor output actuates. Verify analog displays track a known reference applied to each channel and that the documented scaling produces correct engineering units.
Never let the MPINO publish placeholder or zero values that an HMI alarm or interlock could act on as if real. Initialize outputs to a defined safe state in setup(), and design coil logic so that a loss of communication leaves the machine in a safe condition rather than latching the last commanded state indefinitely.
For any output that can affect personnel safety, do not rely on the HMI-over-Modbus path alone. Keep hardwired emergency stop and safety interlocks independent of the controller and the network. The MPINO and its HMI provide supervisory control and visibility; functional safety remains the domain of dedicated, hardwired safety circuits.
Controllers covered

MPINO-8A8R-S
MPINO-8A8R-S Industrial Arduino Controller

MPINO-16A8R8T
MPINO-16A8R8T Industrial Arduino Controller
Related guides
FAQ
Should I connect my HMI to the MPINO over Modbus RTU or I²C?▾
Use Modbus RTU over RS-485 for a standalone operator HMI; it runs over long, noise-tolerant cable and every major HMI supports it. Reserve I²C for short-range, in-cabinet links between the MPINO and local peripherals such as a display controller or expander.
How does the HMI command an MPINO relay?▾
The HMI writes a Modbus coil mapped to that relay. In firmware the ILIB slave exposes coils 0-7 for the 8 relays; after poll() the sketch calls digitalWrite() with mb.getCoil(i), so a button press on the HMI energizes or de-energizes the physical relay.
Can I read analog values on the HMI?▾
Yes. Map each analog channel to an input register; the firmware publishes the EXTERNAL-referenced 0-1023 ADC count and the HMI applies your documented scaling to show engineering units. The MPINO-16A8R8T also exposes its 2 NTC temperature channels the same way.
