// FreqCountMeasureSwScope
// https://wokwi.com/projects/391735383151098881
// Based on WokwiMegaScope setup: https://wokwi.com/projects/390819455604080641
// for https://forum.arduino.cc/t/looking-for-guidance-in-frequency-measurement/1232046
#include <FreqCount.h> // https://www.pjrc.com/teensy/td_libs_Count.html
#include <FreqMeasure.h> // https://www.pjrc.com/teensy/td_libs_FreqMeasure.html
// wiring
const byte MeasurePin = 49; // ICP4 on a Mega // doesn't work on Wokwi
const byte CountPin = 47; // T5 on a Mega
const byte TonePin = 13; //
// measure vars
unsigned long count = 0;
unsigned long sum = 0;
// the setup function runs once when you press reset or power the board
void setup() {
Serial.begin(115200);
// initialize digital pin LED_BUILTIN as an output.
pinMode(LED_BUILTIN, OUTPUT);
FreqMeasure.begin(); //
FreqCount.begin(1000); // 1000ms
Serial.print("FreqMeasure on pin ");
Serial.print(MeasurePin);
Serial.print("FreqCount on pin ");
Serial.print(CountPin);
// tone(TonePin,1000);
pinMode(TonePin, OUTPUT);
}
// the loop function runs over and over again forever
void loop() {
if (FreqMeasure.available()) {
// Won't work on Wokwi because ICP not implemented
// average several reading together
sum = sum + FreqMeasure.read();
count = count + 1;
if (count > 30) {
float frequency = FreqMeasure.countToFrequency(sum / count);
Serial.println(frequency);
sum = 0;
count = 0;
}
}
if (FreqCount.available()) {
unsigned long count = FreqCount.read();
Serial.print(" Count:");
Serial.println(count);
}
pinUsToggler(500); // 13us >> 38461Hz 65535us >> 7.629Hz
SwFreqMeasure(47);
}
void pinUsToggler(uint32_t interval) {
// toggle a pin every interval us
const byte pin = TonePin;
static uint32_t last = 0;
static byte pinState = LOW;
if (micros() - last >= interval) {
pinState = pinState != LOW ? LOW : HIGH;
digitalWrite(pin, pinState);
last += interval; // account for x%4 jitter from micros()
}
}
void SwFreqMeasure(byte pin) {
// monitor changes on a pin and report their frequency
const uint32_t reportInterval = 1000;
static int8_t lastState = -1;
static uint32_t lastUs = 0, lastReportMs = -(reportInterval/2);
int8_t pinState = digitalRead(pin);
if (lastState != pinState) {
if ( pinState == HIGH) {
uint32_t nowUs = micros();
if (millis() - lastReportMs >= reportInterval) {
lastReportMs += reportInterval;
uint32_t periodUs = nowUs - lastUs;
Serial.print("SwMeasure Us:");
Serial.print(periodUs);
Serial.print(" freq:");
Serial.print(1.0e6 / periodUs,4);
Serial.print(" \n");
}
lastUs = nowUs; // last rising edge
}
lastState = pinState; // last change
}
}