In my opinion this is the least accurate solution, but it is something to start with.
Using Arduino Uno.
unsigned long previousMicros;
const unsigned long interval = 12500;
bool active = false;
const int ledPin = 13;
const int outputPin = 2;
void setup()
{
pinMode( ledPin, OUTPUT);
pinMode( outputPin, OUTPUT); // not required for 'tone()'
}
void loop()
{
unsigned long currentMicros = micros(); // 4 microseconds accuracy on Arduino Uno
if( currentMicros - previousMicros >= interval)
{
previousMicros += interval; // special code to keep in sync with time
if( active)
{
digitalWrite( ledPin, LOW);
noTone( outputPin);
}
else
{
digitalWrite( ledPin, HIGH);
tone( outputPin, 8000);
}
active = !active;
}
}
You can see this in action in the Wokwi simulator:
The Wokwi simulator has a simulated Logic Analyzer which can capture the signals. It does not matter how slow or how fast your computer is, the generated signals are exactly as a real Arduino Uno board. That means you can measure the timing of the created VCD file in PulseView.
Just a few measurements at random places:
Timing of the 40Hz : 24.9856ms, 25.00096ms
Timing of the 8kHz : 8.00256kHz, 7.992327kHz
That is pretty good, but there is a interrupt running in the background (Arduino uses Timer0 interrupt), that has influence on the timing.
