Arduino Nano
Rain-Sensing Stepper Motor System
Automatically closes windows, covers, or shelters when rain is detected. Precise NEMA 17 stepper control via A4988 driver with smooth AccelStepper acceleration.
What This System Does
The Arduino Nano Rain-Sensing Stepper Motor System is a smart weather-responsive automation project. A rain sensor module continuously monitors rainfall. When water droplets are detected, the Arduino Nano drives a NEMA 17 stepper motor via an A4988 microstepping driver to close a window, cover, or retractable rack — and automatically reopens it when the rain stops.
The system uses the AccelStepper library for smooth trapezoidal motion profiles, protecting both the mechanism and the motor from sudden jerks, making it suitable for real-world deployments like greenhouses, clotheslines, and solar panel covers.
stepper.run() called every loop is non-blocking — the motor continuously smooths toward its target while the sensor can be re-read, preventing the system from freezing mid-motion.Key Components
How the System Works
Rain Sensor Detects Water Droplets
The rain sensor PCB has conductive traces exposed to rainfall. Water bridges these traces and changes resistance, producing a variable analog voltage (0–1023) on the AO pin connected to A0.
Arduino Reads & Compares Against Threshold
The Nano reads analogRead(A0) each second. The raw value is compared to the threshold (default 500). Values above 500 indicate rain; values below indicate dry conditions.
Rain Detected → Motor Closes Cover
When rain is detected, stepper.moveTo(10000) is called. The A4988 receives STEP pulses on pin D2 and direction on D3. The NEMA 17 rotates precisely 50 revolutions (10000 ÷ 200) to close the cover with smooth acceleration.
No Rain → Motor Returns to Home
When rain stops, stepper.moveTo(0) is called. The motor reverses direction and smoothly returns to its home position at step 0, reopening the window or cover automatically.
Serial.println(sensorValue) while placing water droplets on the sensor to find your ideal threshold value.Why Use the A4988 Driver?
The A4988 sits between the Arduino and NEMA 17, handling the high current the motor needs (up to 2A per phase) while protecting the Nano's 40mA GPIO pins. It also provides microstepping for smoother, quieter motion.
Wiring Diagram & Pin Connections
Wiring: Arduino Nano → Rain Sensor (A0) · A4988 STEP/DIR (D2/D3) · NEMA 17 · 12V External Supply
Rain Sensor → Arduino Nano
| Rain Sensor Pin | Arduino Nano Pin | Notes |
|---|---|---|
| VCC | 5V | Power from Nano |
| GND | GND | Common ground |
| AO (Analog Out) | A0 | 0–1023 analog value |
A4988 Driver → Arduino Nano
| A4988 Pin | Connected To | Notes |
|---|---|---|
| STEP | D2 (Arduino) | Step pulses from AccelStepper |
| DIR | D3 (Arduino) | Direction signal |
| ENABLE | GND | Pull LOW to enable driver always |
| VDD | 5V (Arduino) | Logic power for A4988 |
| GND (logic) | GND | Common ground |
| VMOT | 12V External PSU + | Motor power — do NOT use Arduino 5V |
| GND (motor) | 12V PSU − + Arduino GND | Shared common ground |
| 1A,1B,2A,2B | NEMA 17 motor coils | Check coil pairs with multimeter |
Step-by-Step Instructions
Install the AccelStepper Library
In Arduino IDE: Sketch → Include Library → Manage Libraries. Search for AccelStepper by Mike McCauley and install it. This library provides smooth acceleration/deceleration profiles essential for this project.
Set the A4988 Current Limit (Vref)
Before connecting the motor, set the A4988 Vref potentiometer. Formula: Vref = I_max × 8 × 0.1Ω. For a 1A NEMA 17, set Vref ≈ 0.8V. Measure between the Vref pin and GND with a multimeter while adjusting the pot. This prevents motor overheating.
Wire the Rain Sensor
Connect the rain sensor module's VCC → Nano 5V, GND → Nano GND, and AO → Nano A0. The sensor PCB should face upward and be placed where it will be exposed to rainfall. The comparator module (DO pin) is not used in this analog version.
Wire the A4988 Driver
Connect STEP → D2, DIR → D3, ENABLE → GND (always enabled), VDD → 5V, GND → common GND. Do this with the power fully off. Add the 100µF capacitor across VMOT/GND before connecting the 12V supply.
Connect the NEMA 17 Motor
Identify the two coil pairs using a multimeter (resistance between paired wires ≈ 1–5Ω; different coils read open). Connect coil 1 to A4988 pins 1A/1B and coil 2 to 2A/2B. Incorrect pairing just reverses direction — it won't damage the motor.
Connect the 12V External Power Supply
Connect 12V PSU positive to A4988 VMOT through the 100µF capacitor. Connect PSU negative to a common GND rail shared with the Arduino Nano. Power on the PSU, then the Arduino separately — never connect motor power without the capacitor.
Calibrate the Rain Threshold
Uncomment Serial.println(sensorValue) in the code and upload. Open Serial Monitor at 9600 baud. Observe values with the sensor dry, then apply a few drops of water. Set the threshold between the dry and wet readings in the code.
Adjust Steps for Your Mechanism
Modify stepsFor5Meter (default 10000) to match your mechanism's travel distance. 200 steps = 1 full revolution. If using a leadscrew with 2mm pitch, 1000 steps ≈ 10mm of linear travel. Test with low speed first.
Complete Arduino Code
Uses the AccelStepper library for smooth motion. Install it via Library Manager before uploading:
/* * Arduino Nano Rain-Sensing Stepper Motor System * MakeMindz.com | makemindz.com/arduino-nano-rain-sensing-stepper-motor * * Hardware: * Rain sensor AO → A0 (analog input) * A4988 STEP → D2 * A4988 DIR → D3 * A4988 ENABLE → GND (always enabled) * A4988 VMOT → 12V external supply * 100µF cap across VMOT/GND (essential!) * * Library required: AccelStepper by Mike McCauley * Install via: Sketch → Include Library → Manage Libraries */ #include <AccelStepper.h> // ── Rain Sensor Configuration ───────────────────── const int rainSensorPin = A0; // Analog output of rain sensor module const int THRESHOLD = 500; // Rain if value > threshold; calibrate for your sensor // ── Stepper Motor Configuration ─────────────────── const int STEPS_PER_REV = 200; // Full steps per revolution for NEMA 17 const long CLOSED_POS = 10000; // Steps to close fully (50 revs × 200 steps) // Adjust based on your mechanism travel distance // ── A4988 Pins ──────────────────────────────────── // AccelStepper::DRIVER = external driver mode (STEP + DIR) AccelStepper stepper(AccelStepper::DRIVER, 2, 3); // STEP=D2, DIR=D3 // ── State Tracking ──────────────────────────────── bool lastRainState = false; // ───────────────────────────────────────────────── void setup() { pinMode(rainSensorPin, INPUT); // AccelStepper motion parameters stepper.setMaxSpeed(1000); // Max steps/second (reduce if motor skips steps) stepper.setAcceleration(500); // Steps/second² — smooth start/stop Serial.begin(9600); Serial.println("Rain-Sensing Stepper System Ready"); Serial.print("Threshold: "); Serial.println(THRESHOLD); } // ───────────────────────────────────────────────── void loop() { int sensorValue = analogRead(rainSensorPin); // Uncomment next line to calibrate threshold: // Serial.println(sensorValue); bool isRaining = (sensorValue > THRESHOLD); if (isRaining) { // ── Rain detected: move to closed position ──── if (stepper.currentPosition() != CLOSED_POS) { stepper.moveTo(CLOSED_POS); if (!lastRainState) { Serial.println("RAIN detected → Closing cover..."); lastRainState = true; } } } else { // ── No rain: return to home position ────────── if (stepper.currentPosition() != 0) { stepper.moveTo(0); if (lastRainState) { Serial.println("Rain STOPPED → Opening cover..."); lastRainState = false; } } } // Non-blocking motor movement — must be called every loop stepper.run(); // Short delay reduces noise; remove if motor motion is jerky delay(10); }
moveTo(pos) sets target position · run() executes one step if needed (non-blocking) · currentPosition() returns current step count · setAcceleration() enables smooth ramping.
Comments
Post a Comment