How do I restart a cycle after 30sec.?

Dear all,

I'm working on photoduino (Google Code Archive - Long-term storage for Google Code Project Hosting.) open source camera controller for my DSLR camera.

Unfortunatly I'm not a programmer guy but only a photographer.

Looking to firmware code (Google Code Archive - Long-term storage for Google Code Project Hosting.) I'm interested in changing those parts (I think):

runmode_barrier.pde:
if (barrierMode_shootingMode == SHOOTINGMODE_PREBULB) {

camera_autofocusBegin(barrierMode_autofocusTime);
camera_shutterBegin(barrierMode_shutterLagTime);
laser_turnOn();
sensor_waitFor(PINS_SENSOR_BARRIER, SENSOR_MODE_LOWER, barrierMode_sensorLimit, 0);
laser_turnOff();

if(!cancelFlag) {
if (barrierMode_useFlash1) flash_shoot(barrierMode_preFlash1Time, PINS_FLASH1);
if (barrierMode_useFlash2) flash_shoot(barrierMode_preFlash2Time, PINS_FLASH2);
}

devices_manager.pde:
boolean sensor_waitFor(byte pin, byte mode, unsigned int limitValue, unsigned int limitTime){

unsigned long time = millis();
unsigned int sensorValue = sensor_read(pin);
boolean result = false;

for(; !result && !cancelFlag && (millis()<time+limitTime || limitTime==0); sensorValue = sensor_read(pin)) {
if (mode==SENSOR_MODE_HIGHER && sensorValue>=limitValue) result = true;
if (mode==SENSOR_MODE_LOWER && sensorValue<=limitValue) result = true;
}
if(cancelFlag) result = true;
return result;
}

In this mode the camera shutter stay open until sensor_WaitFor becomes FALSE (i think). But this mean that shutter can stay open for minutes or hour until something broke the barrier.

I would like to limit this to 30sec. after that time if nothing broke the barrier,close the shutter and than restart the cycle without activating the flash (flash_shoot). How do I modify the code to achieve this?

Could you please help me?

Kind regards,
Gianpaolo.

It looks to me that in the line:

sensor_waitFor(PINS_SENSOR_BARRIER, SENSOR_MODE_LOWER, barrierMode_sensorLimit, 0);

you can replace the value 0 by the maximum time in milliseconds that you want it to wait. However, there is a small bug in the code. The line:

for(; !result && !cancelFlag && (millis()<time+limitTime || limitTime==0); sensorValue = sensor_read(pin)) {

should be replaced by:

for(; !result && !cancelFlag && (millis() - time < limitTime || limitTime==0); sensorValue = sensor_read(pin)) {

Dear dc42, thank you so much for looking at the code.

I think that if I replace the value 0 to the maximum time in milliseconds that I want to wait, after 30sec. I will also activate the flash (flash_shoot) because the program continue is run and reaches the line:

laser_turnOff();

if(!cancelFlag) {
if (barrierMode_useFlash1) flash_shoot(barrierMode_preFlash1Time, PINS_FLASH1);
if (barrierMode_useFlash2) flash_shoot(barrierMode_preFlash2Time, PINS_FLASH2);
}

So after 30sec. the sensor stop to wait, but it will also activate the flash (and that's not fine to me).

Am I wrong?

Regards,
Gianpaolo.

I'm thinking about please don't blame me if I'm wrong... but

What about something like this:

while(sensor_waitFor(PINS_SENSOR_BARRIER, SENSOR_MODE_LOWER, barrierMode_sensorLimit, 0)) {
I don't know how to code that but

  • after 30sec.
    camera_shutterEnd(barrierMode_preCloseTime);
    camera_autofocusEnd();
    camera_autofocusBegin(barrierMode_autofocusTime);
    camera_shutterBegin(barrierMode_shutterLagTime);
    }

No?

I think you're right about the flash going off it if times out. To fix that, try the following change [WARNING: untested code!]:

for(; !result && !cancelFlag && (millis()<time+limitTime || limitTime==0); sensorValue = sensor_read(pin)) {

to:

for(; !result && !cancelFlag; sensorValue = sensor_read(pin)) {
if (limitTime != 0 && (millis() - time) >= limitTime) {
cancelFlag = true;
}

Dear dc42 thank you so much. I will try it for sure.

Please, what about something like that, just to be curious after 8 hours of studying (LOL):

unsigned long now = millis();
unsigned long recycleTime = 30000;

while(sensor_waitFor(PINS_SENSOR_BARRIER, SENSOR_MODE_LOWER, barrierMode_sensorLimit, 0)) {

if ((millis()-now)>=recycleTime) {
camera_shutterEnd(barrierMode_preCloseTime);
camera_autofocusEnd();
camera_autofocusBegin(barrierMode_autofocusTime);
camera_shutterBegin(barrierMode_shutterLagTime);
}
}

What do you think? I'm not sure about cancelFlag... it sounds to me that if true it stop all the cycles...

Regards,
Gianpaolo.

I think your solution is nearly right, if what you are trying to do is reset the autofocus and shutter every 30 minutes. How about:

unsigned long recycleTime = 30000;

while(!sensor_waitFor(PINS_SENSOR_BARRIER, SENSOR_MODE_LOWER, barrierMode_sensorLimit, recycleTime)) {
      camera_shutterEnd(barrierMode_preCloseTime);
      camera_autofocusEnd();
      camera_autofocusBegin(barrierMode_autofocusTime);
      camera_shutterBegin(barrierMode_shutterLagTime);
}

The reason I think this should work is that sensor_waitFor() returns true if the sensor was activated or the cancel flag was set, and false if it timed out.

I would like to reset autofocus (not important, I will work only in manual mode), shutter etc. after 30sec. if nothing broke the sensor...

But if something broke the sensor, I would like to activate the flash and going on with normal procedure... The reason I would like to do that is about digital camera noise etc.

What I do not understand is cancelFlag...

cancelFlag is not set in any of the code you posted, so it is presumably set somewhere else in the code, perhaps in an interrupt service routine.

Dear dc42, lookig at the code, photoduino.pde cancelFlag is defined as below:

// Variables used on interrupt mode
volatile boolean cancelFlag = false; // Flag used to abort interrupt mode

So cancelFlag seems to be used for interrupting the procedure and then restart the for cycle in runmode_barrier.pde.

After your latest code, do I need to modify also this or not?

for(; !result && !cancelFlag && (millis()<time+limitTime || limitTime==0); sensorValue = sensor_read(pin)) {

should be replaced by:

for(; !result && !cancelFlag && (millis() - time < limitTime || limitTime==0); sensorValue = sensor_read(pin)) {

GS88:
After your latest code, do I need to modify also this or not?

for(; !result && !cancelFlag && (millis()<time+limitTime || limitTime==0); sensorValue = sensor_read(pin)) {

should be replaced by:

for(; !result && !cancelFlag && (millis() - time < limitTime || limitTime==0); sensorValue = sensor_read(pin)) {

Yes - although the bug that it fixes only comes into play if you leave the system on for more than about 50 days.

Great! Thank you so much :slight_smile: