BLYNK
HOME       📲 GETTING STARTED       📗 DOCS       ❓HELP CENTER       👉 SKETCH BUILDER

Geiger counter

I am trying to create a code for analyzing data from a geiger counter. There is a fairly simple internet code that works very basic. However, it does not seem to be suitable for Blynk, since the calculation of cpm overloads the void loop. I tried creating a code that could work without overloading void loop, but I could not make it work at all. I tried several variants for my code and none worked. Thanks if anyone can help me understand what’s going on. The two codes are attached; the first one works and is available on the internet, the second one is one of the variants that I tried to make work.

First one

// This #include statement was automatically added by the Particle IDE.
#include <blynk.h>
 /* Geiger.ino
 * 
 * This code interacts with the Alibaba RadiationD-v1.1 (CAJOE) Geiger counter board 
 * and reports readings in CPM (Counts Per Minute).
 * 
 * Author: Mark A. Heckler (@MkHeck, mark.heckler@gmail.com)
 * 
 * License: MIT License
 * 
 * Please use freely with attribution. Thank you!
 */
#include <SPI.h>

char auth[] = "";
#define LOG_PERIOD5 5000 //Logging period in milliseconds, recommended value 15000-60000.
#define LOG_PERIOD30 30000
#define MAX_PERIOD 60000 //Maximum logging period

//int pulsePin = D2;
volatile unsigned long counts = 0;                       // GM Tube events
unsigned long cpm5 = 0;  
unsigned long cpm30 = 0;// CPM
const unsigned int multiplier5 = MAX_PERIOD / LOG_PERIOD5; // Calculates/stores CPM
const unsigned int multiplier30 = MAX_PERIOD / LOG_PERIOD30;
//const unsigned int multiplier60 = MAX_PERIOD / MAX_PERIOD;
unsigned long previousMillis;                            // Time measurement
const int pin = 2;

void tube_impulse() { // Captures count of events from Geiger counter board
    counts++;
}

void setup() {
    Serial.begin(9600);                                               // Start serial monitor
    pinMode(pin, INPUT);                                                // Set pin to input for capturing GM Tube events
    interrupts();                                                       // Enable interrupts (in case they were previously disabled)
    attachInterrupt(digitalPinToInterrupt(pin), tube_impulse, FALLING);// Define external interrupts
    Blynk.begin(auth);
}
void loop() {
    Blynk.run();
    
    unsigned long currentMillis = millis();
    
    if(currentMillis - previousMillis > LOG_PERIOD5) {
    previousMillis = currentMillis;
    cpm5 = counts * multiplier5;
    Serial.println(cpm5);
    Blynk.virtualWrite(V1,cpm5); 
    counts = 0;
}
} 

Second one

// This #include statement was automatically added by the Particle IDE.
#include <blynk.h>
//#include <SPI.h>
#include <SPI.h>

#define LOG_PERIOD 5000 //Logging period in milliseconds, recommended value 15000-60000.
#define MAX_PERIOD 60000 //Maximum logging period
#define BLYNK_PRINT Seria

char auth[] = "";
unsigned long previousMillis;
unsigned long cpm = 0;
int times;
volatile int counts;
const int pin = 2;
const unsigned int multiplier = MAX_PERIOD / LOG_PERIOD;

BlynkTimer timer; 

void countPulse(){
    detachInterrupt(0);
    counts++;
    while(digitalRead(2)==0){
    }
    attachInterrupt(0,countPulse,FALLING);
}

void myTimerEvent() {
    unsigned long currentMillis = millis();
    if(currentMillis - previousMillis > LOG_PERIOD) {
    previousMillis = currentMillis;
    cpm = counts * multiplier;
    Serial.println(cpm);
    Blynk.virtualWrite(V1,cpm); 
    counts = 0;
    times++;
    }
}

    void InitializeApplication(){
    Serial.begin(9600);
    pinMode(D7, OUTPUT);
 }
 
void setup() {
    delay(10);
    pinMode(pin, INPUT); 
    Blynk.begin(auth);
    timer.setInterval(1000L, myTimerEvent); 
    counts = 0; 
    times = 0;
}
void loop() {
    Blynk.run();
    timer.run(); 
}

Your second piece of code looks more Blynk friendly.
However, your timer logic is a bit odd.

This piece of code in your MyTimerEvent function is totally redundant:

You should remove this code then simply set your timer interval to 5000ms instead of every 1000ms.

Exactly what does happen when you run the second piece of code?

Pete.

PeteKnight,

Blynk works partially but does not display the count. The timeline advances in time intervals as defined in the code, but remains with null counting. I already tried changing the time interval, already removed the redundancy before and already tried to regroup the functions in different void. It simply does not display pulse count.
On the other hand, the first code that is not suitable for Blynk, works and displays the counts. This is somewhat disconcerting, since I’m trying to do it the right way without overloading void loop.

Cesar.

Can you post your latest code?

Pete.

After remove the redundance;

// This #include statement was automatically added by the Particle IDE.
#include <blynk.h>
//#include <SPI.h>
#include <SPI.h>

#define LOG_PERIOD 5000 //Logging period in milliseconds, recommended value 15000-60000.
#define MAX_PERIOD 60000 //Maximum logging period
#define BLYNK_PRINT Seria

char auth[] = "6f11f01bc09643f4a6c0571f7be3806f";
unsigned long previousMillis;
unsigned long cpm = 0;
int times;
volatile int counts;
const int pin = 2;
const unsigned int multiplier = MAX_PERIOD / LOG_PERIOD;

BlynkTimer timer; 

void countPulse(){
    detachInterrupt(0);
    counts++;
    while(digitalRead(2)==0){
    }
    attachInterrupt(0,countPulse,FALLING);
}

void myTimerEvent() {
   // unsigned long currentMillis = millis();
   // if(currentMillis - previousMillis > LOG_PERIOD) {
   // previousMillis = currentMillis;
    cpm = counts * multiplier;
    Serial.println(cpm);
    Blynk.virtualWrite(V1,cpm); 
    counts = 0;
    times++;
//}
}

    void InitializeApplication(){
    Serial.begin(9600);
    pinMode(D7, OUTPUT);
 }
 
void setup() {
    delay(10);
    pinMode(pin, INPUT); 
    Blynk.begin(auth);
    timer.setInterval(5000L, myTimerEvent); // 1 sec
    counts = 0; 
    times = 0;
}
void loop() {
    Blynk.run();
    timer.run(); 
}


i can’t see where your countPulse function is being called within the code (I’m viewing the code on my iPad, so might be missing something)

Pete.

I am a beginner at Photon and Blynk. My code was designed based on the first code and some basic Blynk instructions. So I suppose the pulse call is not much different from the first code, but I may be totally wrong. Even so I’ve tried several variants and none worked. I did not find anything on geiger counter with Photon and Blynk on the net.

Cesar

your using pin 2 for input, I’m not familiar with the pinout of the photon but on a wemos that pin operates the onboard led and should not be used for sensors readouts. Point in case: it might not be the cause of your issue but I would at least check the pinout of the photon and check which ones are best to use for a readout.

other stuff:

  • InitializeApplication is not called anywhere so is never used. you should at least move the serial.begin inside the setup().
  • you’re using both pin numbers and d-pin numbers which is also a potential bug hazard (2 and D7 in your code) stick with one or the other
  • countpulse() is also never called (i see that pete pointed that out already)

also the geiger muller counter your using does that return an analogue or digital output?
And finally, perhaps it would help if you describe how your code should work?

e.g.: “every 5 seconds I want to do a single digital readout of the GMC?” or “I want to sample the analogue output of the GMC in 1s samples, process that and then readout the next” or "…

and finally: what on earth do you need a GMC for? keep in mind that electronics degrade a lot faster in a stronger radioactive environment.

First I would like to thank PeteKnight and wolph42 for the suggestions. As you said the main problem was that countpulse () is also never was called. I found the correct correlation as found in the code below. The count is being made correctly in the sampling of considered time, second, minute and hour. However, I am trying to insert a turn on and turn off button as it shows the part of the code that is shifted to the right. I did not succeed. I do not know exactly what can disable the counting. Could you guys help me with this?..

#include <blynk.h>
// This #include statement was automatically added by the Particle IDE.
#include <blynk.h>
//#include <SPI.h>
#include <SPI.h>
#define BLYNK_PRINT Serial
char auth[] = "";
int times;
                                                        int Value;
volatile int sec_count;
volatile int min_count;
volatile int hour_count;
const int pin = 2;
                                                                                  
BlynkTimer timer; 

                                                        BLYNK_CONNECTED() // Every time we connect to the cloud.
                                                        {
                                                        Blynk.syncVirtual(V0);
                                                        }
                                                        BLYNK_WRITE(V0)
                                                        {
                                                        int Value = param.asInt(); // assigning incoming value from pin V0 to a variable
                                                        if (Value==1){ 
                                                        timer.enable(times);
                                                        }
                                                        else (Value=0);{
                                                            timer.disable(times);
                                                        }
                                                        }

void ISR_impulse() { // Captures count of events from Geiger counter board
    sec_count++;
    min_count++;
    hour_count++;
}
 // 1 minute
void myTimerEvent() {
    Blynk.virtualWrite(V2, min_count);
    BLYNK_LOG("Minutes: %04d", min_count);
    min_count = 0;
    times++;

  // 1 hour
  if (times > 60-1) {
    Blynk.virtualWrite(V3, hour_count / 60);
    BLYNK_LOG("Hours: %04d", hour_count / 60);
    hour_count = 0;
    times = 0;
    }
}
  // 1 second
void sendSecData() {
    Blynk.virtualWrite(V1, sec_count);
    BLYNK_LOG("sec count: %04d", sec_count);
    sec_count = 0;

}
void setup() {
    Serial.begin(9600);
    delay(10);
    pinMode(pin, INPUT);
    Blynk.begin(auth);
    timer.setInterval(60000L, myTimerEvent); 
    timer.setInterval(1000L, sendSecData);
    attachInterrupt(digitalPinToInterrupt(pin),ISR_impulse,FALLING);  
    times = 0;
    sec_count = 0;
    min_count = 0;
    hour_count = 0;

}
void loop() {
    Blynk.run();
    timer.run();
}


Please feel free to comment and address any of my faults in the code. I have not found anything similar on the internet and therefore it may be useful for someone else.

Answering the question of wolph42, this GMC will be used for analysis of background radiation statistics in natural environments and cosmic rays. Therefore it will hardly be subjected to counts greater than 60 cpm. In this way there is no danger of degradation of the electronic components involved.

Thank you,

Cesar

I haven’t a clue about radiation detection… but you are trying to enable and disable a timer by its supposed ID times that you haven’t actually declared first (as a timerID).

You are already using times as another variable, but if it was instead meant for a timerID it would first need to be declared as such…

int times;

times = timer.setInterval(1000, MyFunction);  // example of declaring a timerID for use with enable() disable() restartTimer(), etc.

https://playground.arduino.cc/Code/SimpleTimer

Gunner

I’m a little confused.
I am using

  times = timer.setInterval (60000L, myTimerEvent);

inside void setup. Is this wrong?
Anyway, doesn’t`t work…

Thank you,

Cesar

No, it’s not wrong, but you should not use the same name as the other variable, give it a new name:

is2blynk = timer.setInterval (60000L, myTimerEvent);

It wouldn’t be wrong if you were actually using that command… but you aren’t… see the above quote from your own code posting. You are just simply defining a timer, not assigning it an ID as well, and an ID is required for the fancy timer controls.

And as @ldb stated, and I did earlier, you can’t use the same variable for an ID as you are already using for another purpose.

Thank you Idb and Gunner. It is working now.
Just to finalize, How many times with different names can I use in the same code?

Thanks,

Cesar

You can use as many variables as you can create with different name, the limitation is only your board memory.

hi!

you can also take a look to https://www.uradmonitor.com it is a great project. some years ago i also built the open source version and ported the code to arduino / blynk. the code was not very polished, but it worked for me.

https://www.uradmonitor.com/building-kit1-extra-features/

https://www.uradmonitor.com/kit1-community-edition/

Thank you wanek. I will take a look…

Cesar