Attivazione servomotore con l'orarioGPS

Salve a tutti, premetto che non ho mai usato Arduino, e quindi non ho esperienza , ma sto lavorando a un progetto per una scuola elementare per fotografare lo spostamento apparente del sole nel cielo nel corso di un anno , aprendo l'otturatore di una fotocamera analogica ad esempio alle 12:00, ogni giorno per un anno. Ho comprato un Arduino uno , un modulo gps e un servomotore. Qualcuno riuscirebbe a modificare lo script fornito, per attivare il servomotore usando l'orario estratto dal gps?

Buonasera e benvenuto nella sezione Italiana del forum,

cortesemente, come prima cosa, leggi attentamente il REGOLAMENTO di detta sezione, (... e, per evitare future possibili discussioni/incomprensioni, prestando molta attenzione al punto 15), dopo di che, come da suddetto regolamento (punto 16.7), fai la tua presentazione NELL'APPOSITA DISCUSSIONE spiegando bene quali esperienze hai in elettronica e programmazione, affinché noi possiamo conoscere la tua esperienza ed esprimerci con termini adeguati.

Grazie,

Guglielmo

P.S.: Ti ricordo che, purtroppo, fino a quando non sarà fatta la presentazione nell’apposita discussione, nel rispetto del succitato regolamento nessuno ti risponderà (eventuali risposte o tuoi ulteriori post, verrebbero temporaneamente nascosti), quindi ti consiglio di farla al più presto. :wink:

Benvenuto, Gianluca :slight_smile:

Per cortesia, per prima cosa fai quanto ti è stato chiesto da Guglielmo, moderatore della sezione italiana. Fai la tua presentazione in coda alla discussione:
Presentazioni nuovi iscritti: fatevi conoscere da tutti! (Part 2)

Grazie.
Gianluca

Sul web ho trovato questo progetto, che usa un modulo RTC (Solarigraphy camera - MediaLab _Labs - DEV) . Sarebbe possibile cambiare il progetto per farlo funzionare col GPS? Oppure è piu semplice usare il modulo rtc? Altra cosa, dopo un anno quanto è preciso?

Ti rendi conto che ciò che hai scritto nella presentazione è assolutamente inutile?...

Ma hai letto cosa ti ho scritto nel mio primo post?

... è quello che ci interessa ed è chiaro anche il perché! Quindi, cortesemente, correggi la presentazione con ciò che a tutti noi veramente interessa, NON con tue informazioni personali di nessuna utilità e nessun interesse.

Guglielmo

P.S.: Se avessi dedicato un minimo di tempo a leggere il REGOLAMENTO, a guardare un po' le varie discussioni e a leggere le altre presentazioni ... avremmo evitato tutta questa serie di post.

Tutti hanno fretta, tutti corrono... senza nemmeno sapere per dove! :frowning:
...e in questo campo basta sbagliare una virgola (o un uguale!) per non ottenere il risultato desiderato.

La parte difficile del lavoro è quella meccanica

Come sei messo?

L'ennesima conferma che questi strumenti sono il male assoluto per chi è agli inizi...

Ad ogni modo, hai uno sketch che sia almeno quasi funzionante su cui si può iniziare a ragionare?

Cosa intendi? Se intendi l'hardware,ho un clone Elegoo , il servomotore e il gps.

@gianlucabelgrado: ... ma il REGOLAMENTO continui a NON rispettarlo ...

... fosse anche per una sola riga, come richiesto al punto 7 del REGOLAMENTO, TUTTO il codice va racchiuso tra i tag CODE, per cui, cortesemente edita il tuo post qui sopra (quindi NON scrivendo un nuovo post, ma utilizzando il bottone a forma di piccola matita :pencil2: che si trova in basso del tuo post), seleziona la parte di codice e premi l'icona <code/> nella barra degli strumenti per contrassegnarla come codice. Inoltre, così com'è, non è molto leggibile ... assicurati di averlo correttamente indentato nell'IDE prima di inserirlo (questo lo si fa premendo ctrlT su un PC o cmd T su un Mac, sempre all'interno del IDE).

Grazie,

Guglielmo

P.S.: Ti ricordo che, purtroppo, fino a quando non sarà sistemato il codice come indicato, nel rispetto del regolamento nessuno ti risponderà (eventuali risposte o tuoi ulteriori post, verrebbero temporaneamente nascosti), quindi ti consiglio di farlo al più presto. :wink:

... in tal caso, magari, guarda quanto è indicato al punto 16.1 del suddetto regolamento ... troverai il link ad alcuni .pdf ed ad un ottimo libro da studiare.

Guglielmo

No intendevo la macchina

Come la azioni?
Hai già montato il servo ?
Sai azionario?
Hai provato ad azionario?
Hai la corrente dove vuoi farlo oppure deve andare a pile?

Sono queste le cose che servono, dettagliate bene

Il programma poi è una banalità

Include cosa?
Ho guardato il progetto originario ed è proprio cosi il codice... per la serie chi ben inizia è a metà dell'opera!

Aspettando che metta a posto il codice... c'è anche questa chicca!

// Soft reset
#define RESTART asm("jmp 0x0000")

che equivale al classico e discusso
void(*Riavvia) (void) = 0;
che in un programma ben scritto non deve mai servire. Se serve un vero riavvio, o si usa il watchdog oppure si fa un monostabile (forse basta un condensatore) che tiene basso il Reset per un numero di cicli sufficiente per avere un reset completo del microcontrollore.

Interessante non ci avevamo mai pensato

Comunque quel codice è robaccia marrone molliccia e fetida (ROMAMOFE)
Ne concordiamo

Si fa molto prima a riscriverlo a partire dalle specifiche
A proposito, quali sono?

/*
   Solarigraphy camera control
   David Pello 2019

   It controls the shutter opening of a solarigraphy camera
    using a servo and a RTC DS3231.

   It is designed for Arduino Nano.

*/

#include 
#include 
#include 
#include 
#include 

// Soft reset
#define RESTART asm("jmp 0x0000")

// secuencias
#define TOMA_SOL2
#define TOMA_SOL3

// tiempos
#define HORA_APERTURA_SOL1         16
#define MIN_APERTURA_SOL1          0
#define HORA_CIERRE_SOL1           16
#define MIN_CIERRE_SOL1            1

#define HORA_APERTURA_SOL2         17
#define MIN_APERTURA_SOL2          0
#define HORA_CIERRE_SOL2           17
#define MIN_CIERRE_SOL2            1

#define HORA_APERTURA_SOL3         18
#define MIN_APERTURA_SOL3          0
#define HORA_CIERRE_SOL3           18
#define MIN_CIERRE_SOL3            1

#define HORA_APERTURA_PAISAJE     9
#define MIN_APERTURA_PAISAJE      0
#define HORA_CIERRE_PAISAJE       10
#define MIN_CIERRE_PAISAJE        55

#define ANGULO_APERTURA           30
#define ANGULO_CIERRE             0

#define PIN_ACT_OBTURADOR         3  // Arduino D3
#define PIN_CONFIGURACION_I       6 // D6
#define PIN_CONFIGURACION_O       7 // D7

#define SLEEPTIME                 30


// ESTADOS
#define ESPERA_SOL1               0
#define ABRE_SOL1                 1
#define ESPERA_SOL2               2
#define ABRE_SOL2                 3
#define ESPERA_SOL3               4
#define ABRE_SOL3                 5
#define ESPERA_PAISAJE            6
#define ABRE_PAISAJE              7

// variables

DS3231 Clock;
Servo obturador;
byte anyo;
byte mes;
byte dia;
byte dia_semana;
byte hora;
byte minuto;
bool h12, pm, siglo;
byte estado;
struct rst_info* reset_info;
int init_mode;
byte ADay, AHour, AMinute, ASecond, ABits;
bool ADy, A12h, Apm;


void setup() {
  delay(1);

  // Iniciamos el I2C
  Wire.begin();
  // Aseguramos que estamos en modo de 24h
  Clock.setClockMode(false);

  // Empezar de cero
  siglo = false;

  // LED
  pinMode(LED_BUILTIN, OUTPUT);
  digitalWrite(LED_BUILTIN, LOW);

  // IO
  pinMode(PIN_CONFIGURACION_I, INPUT_PULLUP);
  pinMode(PIN_CONFIGURACION_O, OUTPUT);
  // set to LOW
  digitalWrite(PIN_CONFIGURACION_O, LOW);

  // Y el puerto serie
  Serial.begin(115200);
  Serial.println();
  Serial.println("Iniciando...");

  // Vemos si tenemos que reiniciar o no.
  init_mode = digitalRead(PIN_CONFIGURACION_I);
  Serial.print("Configuración Leida: ");
  Serial.println(init_mode);
  if (init_mode) {
    // parpadeo
    digitalWrite(LED_BUILTIN, HIGH);
    delay(100);
    digitalWrite(LED_BUILTIN, LOW);
    
    Serial.println("Continuando...");
    // Cargamos el modo actual desde la eeprom
    estado = EEPROM.read(0);
    Serial.print("Estado leido: "); Serial.println(estado);
    // Leemos el RTC
    mes = Clock.getMonth(siglo);
    dia_semana = Clock.getDoW();
    dia = Clock.getDate();
    hora = Clock.getHour(h12, pm);
    minuto = Clock.getMinute();

    Serial.println(); Serial.print("---- ");
    Serial.print(mes); Serial.print("/"); Serial.print(dia); Serial.print(" ");
    Serial.print(hora); Serial.print(":"); Serial.println(minuto);

    if (Clock.checkAlarmEnabled(1)) {
      Serial.println("nAlarm 1 enabled");
    }

    Serial.print("Alarm 1: ");
    Clock.getA1Time(ADay, AHour, AMinute, ASecond, ABits, ADy, A12h, Apm);
    Serial.print(ADay, DEC);
    if (ADy) {
      Serial.print(" DoW");
    } else {
      Serial.print(" Date");
    }
    Serial.print(' ');
    Serial.print(AHour, DEC);
    Serial.print(' ');
    Serial.print(AMinute, DEC);
    Serial.print(' ');
    Serial.print(ASecond, DEC);
    Serial.print(' ');
    if (A12h) {
      if (Apm) {
        Serial.print('pm ');
      } else {
        Serial.print('am ');
      }
    }
    Serial.print(' ');
    Serial.println(ABits, BIN);


  } else {
    Serial.println("Iniciando desde cero...");

    // parpadeo largo
    for (int i = 0; i < 20; i++) { digitalWrite(LED_BUILTIN, HIGH); delay(100); digitalWrite(LED_BUILTIN, LOW); delay(100); } // iniciamos estado = ESPERA_SOL1; EEPROM.write(0, estado); // obturador cerrado obturador.attach(PIN_ACT_OBTURADOR); obturador.write(ANGULO_CIERRE); delay(250); obturador.detach(); // Leemos el RTC mes = Clock.getMonth(siglo); dia_semana = Clock.getDoW(); hora = Clock.getHour(h12, pm); minuto = Clock.getMinute(); Serial.println(); Serial.print("---- "); Serial.print(hora); Serial.print(":"); Serial.println(minuto); // Ponemos la alarma (0x8 = 1000b = A4 A3 A2 A1 = horas,minutos,segundos da igual el día) Clock.setA1Time(0, HORA_APERTURA_SOL1, MIN_APERTURA_SOL1, 0, 0x8, false, false, false); // Y la activamos Clock.turnOnAlarm(1); } } void loop() { // reiniciamos el i2c // Wire.begin(); // Comprobamos alarma if (Clock.checkIfAlarm(1)) { Serial.println("Evento de alarma RTC!"); // Dependiendo del estado actual... switch (estado) { case ESPERA_SOL1: // Abrimos obturador estado = ABRE_SOL1; EEPROM.write(0, estado); obturador.attach(PIN_ACT_OBTURADOR); obturador.write(ANGULO_APERTURA); delay(250); obturador.detach(); Serial.println("Abriendo SOL1"); // ponemos la nueva alarma dia_semana = Clock.getDoW(); Clock.setA1Time(0, HORA_CIERRE_SOL1, MIN_CIERRE_SOL1, 0, 0x8, false, false, false); Clock.turnOnAlarm(1); break; case ABRE_SOL1: // Cerramos obturador // cambiamos el estado dependiendo de si hay más aperturas de sol #ifndef TOMA_SOL2 estado = ESPERA_PAISAJE; EEPROM.write(0, estado); EEPROM.commit(); obturador.attach(PIN_ACT_OBTURADOR); obturador.write(ANGULO_CIERRE); delay(250); obturador.detach(); Serial.println("Cerrando SOL1 -> Espera Paisaje");

        // ponemos la nueva alarma
        dia_semana = Clock.getDoW();
        Clock.setA1Time(0, HORA_APERTURA_PAISAJE,
                        MIN_APERTURA_PAISAJE, 0, 0x8, false, false, false);
        Clock.turnOnAlarm(1);
#else
        estado = ESPERA_SOL2;
        EEPROM.write(0, estado);
        obturador.attach(PIN_ACT_OBTURADOR);
        obturador.write(ANGULO_CIERRE);
        delay(250);
        obturador.detach();
        Serial.println("Cerrando SOL1 -> Espera SOL2");

        // ponemos la nueva alarma
        dia_semana = Clock.getDoW();
        Clock.setA1Time(0, HORA_APERTURA_SOL2, MIN_APERTURA_SOL2,
                        0, 0x8, false, false, false);
        Clock.turnOnAlarm(1);
#endif
        break;
      case ESPERA_SOL2:
        // Abrimos obturador
        estado = ABRE_SOL2;
        EEPROM.write(0, estado);
        obturador.attach(PIN_ACT_OBTURADOR);
        obturador.write(ANGULO_APERTURA);
        delay(250);
        obturador.detach();
        Serial.println("Abriendo SOL2");

        // ponemos la nueva alarma
        dia_semana = Clock.getDoW();
        Clock.setA1Time(0, HORA_CIERRE_SOL2, MIN_CIERRE_SOL2,
                        0, 0x8, false, false, false);
        Clock.turnOnAlarm(1);
        break;

      case ABRE_SOL2:
        // Cerramos obturador
        // cambiamos el estado dependiendo de si hay más aperturas de sol
#ifndef TOMA_SOL3
        estado = ESPERA_PAISAJE;
        EEPROM.write(0, estado);
        obturador.attach(PIN_ACT_OBTURADOR);
        obturador.write(ANGULO_CIERRE);
        delay(250);
        obturador.detach();
        Serial.println("Cerrando SOL2... -> Espera paisaje");

        // ponemos la nueva alarma
        dia_semana = Clock.getDoW();
        Clock.setA1Time(0, HORA_APERTURA_PAISAJE,
                        MIN_APERTURA_PAISAJE, 0, 0x0, false, false, false);
        Clock.turnOnAlarm(1);
#else
        estado = ESPERA_SOL3;
        EEPROM.write(0, estado);
        obturador.attach(PIN_ACT_OBTURADOR);
        obturador.write(ANGULO_CIERRE);
        delay(250);
        obturador.detach();
        Serial.println("Cerrando SOL2... -> Espera SOL3");

        // ponemos la nueva alarma
        dia_semana = Clock.getDoW();
        Clock.setA1Time(0, HORA_APERTURA_SOL3, MIN_APERTURA_SOL3,
                        0, 0x8, false, false, false);
        Clock.turnOnAlarm(1);
#endif
        break;

      case ESPERA_SOL3:
        // Abrimos obturador
        estado = ABRE_SOL3;
        EEPROM.write(0, estado);
        obturador.attach(PIN_ACT_OBTURADOR);
        obturador.write(ANGULO_APERTURA);
        delay(250);
        obturador.detach();
        Serial.println("Abriendo SOL3");

        // ponemos la nueva alarma
        dia_semana = Clock.getDoW();
        Clock.setA1Time(0, HORA_CIERRE_SOL3, MIN_CIERRE_SOL3,
                        0, 0x8, false, false, false);
        Clock.turnOnAlarm(1);
        break;

      case ABRE_SOL3:
        // Cerramos obturador
        estado = ESPERA_PAISAJE;
        EEPROM.write(0, estado);
        obturador.attach(PIN_ACT_OBTURADOR);
        obturador.write(ANGULO_CIERRE);
        delay(250);
        obturador.detach();
        Serial.println("Cerrando SOL3... -> Espera Paisaje");

        // ponemos la nueva alarma
        dia_semana = Clock.getDoW();
        Clock.setA1Time(0, HORA_APERTURA_PAISAJE, MIN_APERTURA_PAISAJE,
                        0, 0x8, false, false, false);
        Clock.turnOnAlarm(1);
        break;

      case ESPERA_PAISAJE:
        // Abrimos obturador
        estado = ABRE_PAISAJE;
        EEPROM.write(0, estado);
        obturador.attach(PIN_ACT_OBTURADOR);
        obturador.write(ANGULO_APERTURA);
        delay(250);
        obturador.detach();
        Serial.println("Abriendo Paisaje");

        // ponemos la nueva alarma
        dia_semana = Clock.getDoW();
        Clock.setA1Time(0, HORA_CIERRE_PAISAJE, MIN_CIERRE_PAISAJE,
                        0, 0x8, false, false, false);
        Clock.turnOnAlarm(1);
        break;

      case ABRE_PAISAJE:
        // Cerramos obturador
        estado = ESPERA_SOL1;
        EEPROM.write(0, estado);
        obturador.attach(PIN_ACT_OBTURADOR);
        obturador.write(ANGULO_CIERRE);
        delay(250);
        obturador.detach();
        Serial.println("Cerrando Paisaje -> Espera SOL1");

        // ponemos la nueva alarma
        dia_semana = Clock.getDoW();
        Clock.setA1Time(0, HORA_APERTURA_SOL1, MIN_APERTURA_SOL1,
                        0, 0x8, false, false, false);
        Clock.turnOnAlarm(1);
        break;
    }

    // Apagamos el i2c
    //Wire.end();

  }

  // a dormir (bajo consumo)
  Serial.flush(); // wait for serial
  for (int i = 0 ;  i  <  15 ; i++)
    LowPower.powerDown(SLEEP_2S, ADC_OFF, BOD_OFF);

  RESTART;
}

@gianlucabelgrado: Più sopra ci sono delle risposte che potrebbero sfuggirti, dagli un'occhiata ...

Guglielmo

Ho già fatto qualche prova col servo, funziona. Credo che userò un lungo cavo usb , con una batteria tampone per alimentare Arduino. Poi verrà messo all'esterno,protetto da una scatola impermeabile . Per me il programma mi sta bloccando da oltre anni, infatti avevo abbandonato il progetto proprio per la difficoltà a compilarlo

Infatti mi sfuggono talmente tanto che non le vedo. Riassumendo: IL gps fornisce l'orario a arduino, e controlla il servomotore, muovendolo per un minuto.