
Make Your Trains Run on Time – Automate Model Train Controls and Set it to Your Schedule with Arduino UNO
Make Your Trains Run on Time – Automate Model Train Controls and Set it to Your Schedule with Arduino UNO
Want to program your train set to run according to your schedule?
In this project, inspired by Steve Massikker of arduinorailwaycontrol.com, we will use Arduino Uno to create a simple scheme for automatic train control that can be reconfigured to generate any movement pattern.
Here’s what you’ll need:
- Arduino Uno (or any Arduino board) https://vilros.com/products/arduino-uno-micro-controller
- Arduino IDE https://www.arduino.cc/en/main/software
- Jumper Wires https://vilros.com/collections/arduino-accessories/products/jumper-wires
- An L298 motor driver module
That’s it!
Swing Script Code
The following code runs a script that will stop the train smoothly at the time you set, then after a pause begin moving in the opposite direction in a repeating cycle. Below we will break down the variables you can adjust to change the timing or create your own movement patterns.
// L298
#define L298_ENA 5
#define L298_IN1 6
#define L298_IN2 7
// SCRIPTS VARIABLES
int counterScheduler;
unsigned long timerScheduler = 0;
unsigned long timerLocal = 0;
byte speedAuto = 0;
void setup() {
// Initializing pins
pinMode(L298_ENA, OUTPUT);
pinMode(L298_IN1, OUTPUT);
pinMode(L298_IN2, OUTPUT);
// Set default direction to FORWARD
digitalWrite(L298_IN1, HIGH);
digitalWrite(L298_IN2, LOW);
}
void loop() {
// Start Scheduler
if (millis() > (timerScheduler + 1000)) { // Tick every 1 sec
counterScheduler++;
timerScheduler = millis();
}
// ------------- SCRIPT SWING
int brakingDelta = 5;
int accelerateDelta = 6;
// 1 | 0 > Time < 5 sec
if (counterScheduler <= 5) {
// Start train
if (millis() > (timerLocal + 100)) {
if (speedAuto < 240) speedAuto = speedAuto + accelerateDelta;
else speedAuto = 255;
analogWrite(L298_ENA, speedAuto);
timerLocal = millis();
}
}
// 2 | 10 sec > Time < 15 sec
if ((counterScheduler >= 10) && (counterScheduler <= 15)) { // Stop train after 10 sec
// Stop train
if (millis() > (timerLocal + 100)) {
if (speedAuto > 30) speedAuto = speedAuto - brakingDelta;
else speedAuto = 0;
analogWrite(L298_ENA, speedAuto);
timerLocal = millis();
}
}
// 3 | Change direction
if (counterScheduler == 16) {
digitalWrite(L298_IN1, LOW);
digitalWrite(L298_IN2, HIGH);
}
// 4 | 20 sec > Time < 30 sec
if ((counterScheduler >= 20) && (counterScheduler <= 30)) {
// Start train
if (millis() > (timerLocal + 100)) {
if (speedAuto < 240) speedAuto = speedAuto + accelerateDelta;
else speedAuto = 255;
analogWrite(L298_ENA, speedAuto);
timerLocal = millis();
}
}
// 5 | 31 sec > Time < 40 sec
if ((counterScheduler >= 31) && (counterScheduler <= 40)) { // Stop train
// Stop train
if (millis() > (timerLocal + 100)) {
if (speedAuto > 30) speedAuto = speedAuto - brakingDelta;
else speedAuto = 0;
analogWrite(L298_ENA, speedAuto);
timerLocal = millis();
}
}
// 6 | Return to Step 1
if (counterScheduler > 40) {
counterScheduler = 0;
digitalWrite(L298_IN1, HIGH);
digitalWrite(L298_IN2, LOW);
}
}
Altering the Schedule
By changing the following parameters in the above sketch, you can create any pattern of automatic movement you want for your train set.
Here’s how we’ll alter the time parameters:
// 1 | 0 > Time < 5 sec
if (counterScheduler <= 5) {
......
// 2 | 10 sec > Time < 15 sec
if ((counterScheduler >= 10) && (counterScheduler <= 15)) {
......
// 3 | Change direction
if (counterScheduler == 16) {
.... etc.
This sets a timetable. It controls when the train starts, how long it runs before it stops, and how long before it starts again.
Its direction is determined by the state of pins D6 and D7:
// Set default direction to FORWARD
digitalWrite(L298_IN1, HIGH);
digitalWrite(L298_IN2, LOW);
You can also reconfigure the train’s braking and acceleration with these variables:
int brakingDelta = 5;
int accelerateDelta = 6;
Note that these simple controls will start and stop the train purely as a function of time. While you can get your trains to do a lot of things by adjusting the above parameters, you can gain even greater control over their movements by adding various sensors to your circuit and programming them accordingly (for instance, to get your train to automatically stop every time it reaches a certain station). But this project should provide a good basis to get you started.
Wiring
Here is the schematic to wire your circuit:
Now that you’ve got your trains running on a schedule, see what else you can get them to do with Arduino… All aboard!
For more ideas you can try using Arduino and Raspberry Pi, be sure to check back here on our Vilros Projects blog for more fun electronics projects!