You write the code, everything compiles, the button should do something — but nothing happens. Or worse: the button triggers on its own without being touched. Variables jump randomly between 0 and 1. The code seems wrong, but the code isn't the problem.

A floating input is the problem. And you fix it with two cents' worth of resistors.

What is a floating input?

A digital input reads high or low. But if it isn't firmly connected to anything — not to supply voltage, not to ground — it floats. It randomly picks up interference from the environment: electromagnetic noise, capacitive coupling with other signals, even your hand getting close. The result is unpredictable behaviour that has nothing to do with your code.

Pull-up: default high, goes low on action

A pull-up resistor connects the input through a resistor to the supply voltage. Without any action, the input reads high. Press a button that pulls the input to ground and the signal goes low.

This is the most common circuit for buttons on microcontrollers. The logic is inverted — pressed is LOW, released is HIGH — but you get used to it quickly and it's the standard pattern in Arduino code with INPUT_PULLUP.

A typical resistor value is 10 kΩ. The CRG0805F10K (10 kΩ, 1%, 0805) or the CRGH0805F10K (10 kΩ, 1%, 0805, higher power) are both good choices.

Pull-down: default low, goes high on action

A pull-down resistor connects the input through a resistor to ground. Without any action, the input reads low. Connect the input to the supply voltage — via a button or sensor — and the signal goes high. The logic is straightforward: active is HIGH.

Quiet desk with open notebook showing pull-up circuit and breadboard with pushbutton

Which value to choose?

Too high (above 100 kΩ) and the input is susceptible to noise. Too low (below 1 kΩ) and unnecessary current flows, which matters in battery-powered systems. For most buttons and sensors, 10 kΩ is the standard.

With I2C — the communication bus used by many sensors — pull-ups are needed on the SDA and SCL lines. The optimal value depends partly on bus speed: at 100 kHz, 4.7 kΩ is common; at 400 kHz, closer to 2.2 kΩ. Check the datasheet of the slowest device on the bus.

Internal pull-ups: useful, but not always enough

Most microcontrollers have built-in pull-up resistors that you enable in software. The value is typically between 20 kΩ and 50 kΩ. That's fine for a pushbutton on a short wire. For longer cables, I2C, or noise-sensitive applications, an external 10 kΩ resistor close to the pin is preferable.

Common mistake

The mistake isn't choosing the wrong value — it's forgetting entirely that an input needs a defined state. Make sure every digital input is always pulled somewhere. Floating is not an option.