Complete of Schematic Diagram Arduino Igbo Market Display
If you grew up in Igboland, you already know that the week doesn’t always mean seven days. Long before Nigeria adopted the Gregorian calendar, Igbo communities were already tracking time using a four-day market cycle: Eke, Orie, Afor, and Nkwo. Markets, festivals, naming ceremonies, and even some traditional titles are still scheduled around this cycle today, in towns and villages where the rhythm of trade never fully switched over to Monday-to-Sunday.
The problem is that almost nothing in modern electronics speaks that language. Every clock module, every calendar library, every off-the-shelf digital clock kit assumes a seven-day week, because that’s what the rest of the world standardized on. So when I set out to build a desk display that shows the date, the time, and today’s Igbo market day, I quickly realized there was no example code to copy. I had to build the conversion logic myself, on top of an Arduino Uno, a pair of P10 LED dot-matrix panels, and a small real-time clock module.
This post walks through exactly how I built it: the hardware, the wiring, and — the part I’m most proud of — the math that converts a normal Gregorian date into its corresponding Igbo market day. By the end, you’ll have everything you need to build your own version, whether that’s for your desk, your shop counter, or as a gift for someone who still plans their week around Eke and Afor.
The finished build is a small digital sign built from two P10 LED panels wired side by side, controlled by an Arduino Uno and kept accurate by a DS3231 real-time clock (RTC) module. In normal operation, it does two things in a loop:
First, it displays the current Gregorian date and time, refreshed continuously from the RTC. This part behaves like any ordinary digital clock — you’ll always know exactly what day and time it is on the standard calendar.
Then, after a few seconds, the display clears and scrolls a short message announcing the current Igbo market day — for example, “Eke market day” — before looping back to the date and time. There’s no manual input needed once it’s set up. The RTC keeps time even when the Arduino is unplugged, and the market day is recalculated fresh every single loop, so the display is always correct without you having to touch it.
It’s a small project, but it sits at an interesting intersection: modern microcontroller electronics applied to a centuries-old African timekeeping tradition that most digital tools have simply never accounted for.
To make the connections, it would be wise to first connect the P10 Module to the Arduino Uno board. The connections are made as judiciously as shown in the schematic diagram shown above. Alternatively, you can follow the table I just dropped below to ensure you get it right.
The P10 Dot Matrix Display (DMD) connection to the Arduino Uno needs to be made exactly like this. The CKL pin on the P10 Module is connected to the pin 8 on the Arduino Uno whereas the SCLK pin is connected to the pin 13.
Before touching any code, it’s worth understanding exactly what we’re trying to calculate, because the logic only makes sense once you see why a simple lookup table won’t work.
The Gregorian calendar most of the world uses today runs on a seven-day week: Sunday through Saturday, repeating indefinitely. The traditional Igbo calendar, by contrast, is built around a four-day market week called izu, made up of Eke, Orie, Afor, and Nkwo, in that fixed order. Traditionally, seven of these four-day weeks make up one month (onwa, 28 days), and thirteen months make up one year, with an extra day added at the end to keep things aligned — a system entirely independent of the Gregorian one.
Here’s the part that trips people up: because four does not divide evenly into seven, the Igbo market day for any given Gregorian date shifts constantly. If today is Eke, four days from now will also be Eke, but next Gregorian “Monday” will not be Eke, because Mondays and market days drift relative to one another. This is very different from something like a lunar phase or a fixed offset — there’s no shortcut formula based on the day-of-week or day-of-month alone. You cannot simply say “every Monday is Eke” because that relationship changes as the weeks progress.
The only reliable way to convert between the two systems is to anchor your calculation to one date whose market day is already confirmed, and then count forward or backward in exact four-day steps from there. This is conceptually similar to how you’d calculate a day of the week far in the future using a known reference date — the difference is that instead of dividing by seven, you divide by four.
For this build, the anchor point used is 5 September 2026, confirmed as an Eke day against published Igbo market calendars. From that single reference point, every other date — past or future — can be calculated by counting the number of days between it and the anchor, then finding the remainder when that count is divided by four. A remainder of 0 lands back on Eke, 1 lands on Orie, 2 lands on Afor, and 3 lands on Nkwo, cycling endlessly in both directions.
This is the entire trick behind the code: convert both the anchor date and today’s date into a simple day count (which the RTC library gives us almost for free via Unix time), subtract one from the other, and take the result modulo four.
#include <SPI.h>
#include <DMD.h>
#include <TimerOne.h>
#include <SystemFont5x7.h>
#include <Arial_Black_16.h>
#include <Wire.h>
#include "RTClib.h"
#define DISPLAYS_ACROSS 2
#define DISPLAYS_DOWN 1
DMD dmd(DISPLAYS_ACROSS, DISPLAYS_DOWN);
RTC_DS3231 rtc;
// Igbo 4-day market cycle, in order
char marketDays[4][8] = {"Eke", "Orie", "Afor", "Nkwo"};
// Anchor: 5 September 2026 is confirmed as Eke (index 0)
const int REF_YEAR = 2026, REF_MONTH = 9, REF_DAY = 5;
void ScanDMD() {
dmd.scanDisplayBySPI();
}
int getMarketDayIndex(DateTime now) {
DateTime ref(REF_YEAR, REF_MONTH, REF_DAY, 0, 0, 0);
long daysNow = now.unixtime() / 86400L;
long daysRef = ref.unixtime() / 86400L;
long diff = daysNow - daysRef;
// keep it positive even for dates before the anchor
int idx = (int)(((diff % 4) + 4) % 4);
return idx;
}
void setup() {
Serial.begin(9600);
if (!rtc.begin()) {
Serial.println("Couldn't find RTC");
while (1);
}
if (rtc.lostPower()) {
rtc.adjust(DateTime(F(__DATE__), F(__TIME__)));
// Re-upload with this line commented out once the time is set,
// otherwise every power loss resets it to compile time again.
}
Timer1.initialize(2000);
Timer1.attachInterrupt(ScanDMD);
dmd.clearScreen(true);
}
void showDateTime(DateTime now) {
dmd.clearScreen(true);
dmd.selectFont(SystemFont5x7);
char dateStr[9];
sprintf(dateStr, "%02d/%02d/%02d", now.day(), now.month(), now.year() % 100);
char timeStr[9];
sprintf(timeStr, "%02d:%02d:%02d", now.hour(), now.minute(), now.second());
// top half of the combined 64x16 panel = date, bottom half = time
dmd.drawString(0, 0, dateStr, strlen(dateStr), GRAPHICS_NORMAL);
dmd.drawString(0, 8, timeStr, strlen(timeStr), GRAPHICS_NORMAL);
}
void scrollMarketDay(String text) {
dmd.clearScreen(true);
dmd.selectFont(Arial_Black_16);
char buf[32];
int len = text.length();
text.toCharArray(buf, len + 1);
dmd.drawMarquee(buf, len, (32 * DISPLAYS_ACROSS) - 1, 0);
long timer = millis();
boolean ret = false;
while (!ret) {
if ((timer + 30) < millis()) {
ret = dmd.stepMarquee(-1, 0);
timer = millis();
}
}
}
void loop() {
DateTime now = rtc.now();
showDateTime(now);
delay(5000);
int idx = getMarketDayIndex(now);
String msg = String(marketDays[idx]) + " market day";
scrollMarketDay(msg);
}
With the parts list gathered and the logic understood, assembling the hardware is straightforward. The DS3231 communicates with the Arduino Uno over I2C, so it only needs four connections: power, ground, SDA, and SCL, shared on the same bus the Arduino already uses for other I2C peripherals if you have any. The two P10 panels are chained together and driven over SPI, with a separate timer interrupt handling the constant screen refresh in the background so the display doesn’t flicker while the rest of your code runs.
The one detail that catches people out is power. Two P10 panels drawing full brightness can pull more current than USB or the Arduino’s onboard 5V regulator can comfortably provide, which shows up as dim, flickering, or randomly resetting displays. Powering the panels from a dedicated 5V supply, with a shared ground back to the Arduino, solves this almost every time.
Once wired, the Arduino Uno is flashed with a sketch that merges two responsibilities: reading the current date and time from the DS3231, and driving the P10 panels to display first the date and time, and then the scrolling market day message, on a repeating loop.
The DS3231 keeps its own time using a small backup battery, but the very first time you power it up — or after that battery has been removed for a while — it won’t know the correct date and time. The code handles this automatically the first time it detects a power loss, setting the clock to match the time your computer compiled the sketch. After that first run, it’s worth re-uploading the sketch with that auto-set line disabled, so that a future power blip doesn’t quietly reset your clock to whatever time you happened to compile the code, rather than the actual current time.
This is almost always either a power problem or a timing conflict. Check that your panels have their own adequate 5V supply rather than pulling current through the Arduino, and make sure nothing else in your sketch is blocking the loop for long stretches, since the display refresh depends on a timer interrupt firing consistently in the background.
Cross-check the output of your display against a published Igbo market calendar for today’s date, and again for a date a week or two away. If both match, your anchor date and modulo-4 logic are working correctly. If they’re off by a fixed number of days every time, double-check the anchor date and its known market day.
The general approach — anchoring to a known date and counting forward in modulo arithmetic — works for any fixed-length repeating cycle, not just this one. You’d need a different cycle length and a different confirmed reference date, but the underlying method is the same.
One panel is enough to get either the date/time or the scrolling market day working on its own; you’ll just have less room to lay things out, and may need to adjust the DISPLAYS_ACROSS value and text positioning in the code accordingly.
No. Once the DS3231 has been set with the correct date and time, it keeps ticking on its own, backed by its onboard battery, with no internet or external time source required.
What started as a way to avoid manually checking a market calendar turned into a small tribute to a timekeeping system that predates the electronics used to display it. There’s something satisfying about an Arduino — a piece of hardware built entirely around binary logic and Gregorian assumptions — correctly announcing “Eke market day” without ever being told what an Eke is, just because the math underneath happens to be sound.
If you build your own version of this Arduino Igbo market day display, I’d love to see it. Traditional calendars like this one are worth preserving in whatever form keeps them visible and useful, and a blinking LED sign on your desk is as good a form as any.
Introduction: Can Fungi Really Feed the Future? Mycoprotein When people first hear about protein made…
Introduction Imagine this: your neighbor needs a 3D printer for a weekend project, while you’ve…
Introduction Imagine walking onto a small farm or a nature reserve, where tiny devices quietly…
Introduction Imagine handing your child an Interactive Personalized Storybook where they are the hero of…
Introduction Imagine waking up one morning to find your company’s entire IT infrastructure compromised—servers down,…
Introduction: Can AI Really Help You Create a Course? Let’s start with the question almost…
This website uses cookies.