Close

Otáčení solárního panelu za sluncem

Úvodní stránka Fórum Vaše projekty Arduino Otáčení solárního panelu za sluncem

  • Toto téma obsahuje celkem 23 odpovědí. Do diskuze (4 diskutující) se naposledy zapojil uživatel posjirka a poslední změna proběhla před 7 roky a 5 měsíci.
Aktuálně je na stránce zobrazeno 24 příspěvků - 1. až 24. (celkem z 24)
  • Autor
    Příspěvky
  • #11852
    marvik.jiri
    Účastník

    Dobrý den a ahoj.
    Jsem další začátečník a již mě nebaví hrát si jen s ledkami a tak jsem se rozhodl vytvořit něco složitějšího a praktického. Chtěl bych vytvořit jednoduchý držák na solární panel k bazenu, který se natáčí od východu k západu dle intenzity světla (otáčení za sluncem).
    Nejprve bych měl popsat konstrukci a až pak fungování programu.
    Konstrukčně dva pevně umístěné fotorezistory (1x východ a 1x západ). Další dva jsou na otočném rámu se solárním panelem oddělené přepážkou. Ta funguje jako stínítko. Jakmile slunce popojde jeden fotorezistor přejde do stínu a zvýší se rozdíl odporu mezi nima = sepne se relé pro napájení motoru a solár se pootočí dokud se hodnoty mezi fotorezistory +- nesrovnají a opět motor vypne. Otáčení panelu bude řešeno přes 2x rele spínající stykače, které spínají nebo prohazují napětí na stejnosměrný motor (pravděpodobně z automobilového stěrače).

    Programově bych chtěl na dva digitální piny desky UNO připojit fotorezistory (východní, západní = postačí signál 1:0). Tato hodnota by vyplývala z rozdílu těchto dvou hodnot. Program určí zda je ráno a slunce vychází nebo večer a zapadá. Dle toho otočí solar na výchozí pozici.
    Dále na anologových pinech budou nalojeny další dva fotorezistory, které budou určovat přesnou pozici slunce a díky nim bude solár natáčen po krocích.
    Další dva analogové piny budou teplotní čidla. Jedno by mělo plnit podmínku zda je na sluníčku více jak cca 25°C tak se uvede program v činnost. A drohé bude hlídat teplotu vody. Pokud bude voda ohřátá na cca 28°C tak bude program fungovat reverzně a to znamená, že naopak bude vyhledávat stín, aby nedocházelo k dalšímu ohřevu.

    Myslím si, že jako začátečník si vymýšlím dost 🙂

    Arduiňáci chtěl bych Vás poprosit o pomoc při programování. Nechci aby za mě někdo psal celý program i když bych se nebránil, ale neumím ještě používat funkce „když a nebo“ a takové ty podmínky.
    Moc mi pomůžou i kusé části programu, které seskládám a nějak polepím.

    Celý hotový program i třebu s konstrukcí a zapojením celého zařízení sem následně rád poskytnu.

    Zatím děkuji za nápady a veškerou snahu.
    Jirka

    #11853
    Vojtěch Vosáhlo
    Účastník

    Máte to super vymyšlené a to je hodně důležité u jakéhokoliv projektu. Zaprvé máte už nějak navržené schéma? Většinou je lepší nejdříve dořešit hardware a pak až software. Taky by mě zajímalo pár věcí ohledně vašich rozhodnutí. Psal jste o teplotních čidlech. Proč byste rád použil analogová? Nic proti nim nemám ale nevím jak to bude s přesností při použití ADC (analogově digitální převodník) u arduina. Nevím jestli bude tak jednoduché zjistit rozdíl mezi 25 a 28 stupni (u některých je rozdíl třeba 10mV na stupeň celsia), pak by možná bylo lepší něco digitálního nebo použít externí napěťovou referenci (externí „zdroj“ napětí s minimálním šumem se kterým se potom porovnává napětí na analogových pinech). Bohužel nemluvím z vlastních zkušeností tak mě tu snad opraví někdo kdo analogy používá pokud melu nesmysly.

    Fotorezistory můžete taky použít jen 2 místo 4. Panel by mohl při spuštění programu „proskenovat“ oblohu a zjistit kde slunce je a podle toho určit jestli je ráno nebo večer. Možná máte jiný důvod pro používání i těch pevně přichycených fotorezistorů ale já ho nevidím.

    Určitě bych počítal s použitím limitových spínačů které vypnou motory když se panel otočí na určitou koncovou pozici. Ušetří vám to hodně starostí a zabere jen 2 piny.

    Co se týče kódu, řešil bych to teprv až budete mít opravdu vymyšlený hardware. Pokud to ale chcete přesně tak jak jste napsal tak můžem začít makat na prográmku 🙂

    Mimo to vítejte, super že se to tu tak rozrůstá

    Vojta

    #11856
    marvik.jiri
    Účastník

    Dobrý den Vojto,
    děkuji za reakci a první připomínky a také za přijetí.
    Hardwarově to vymyšlené mám. Mechanika je brnkačka 🙂
    Již se projevuje má neznalost a málo zkušeností. V žádném případě netrvám na analogovém vstupu. Chtěl bych použít teplotní čidla například DS18B20. Jsou vodotěsná takže bych s jedním mohl měřit i teplotu vody.

    Samozřejmě před namontováním a zkušebním provoze program musím doladit na parapetu a výpisem na sériovou linku a s externím teploměrem vedle. Naměřené hodnoty pak zapsat do programu, tak aby fungoval dle představ a ne třeba o pár stupňů celsia jinak. Takjisto zkalibrovat světelné podmínky při použití fotodporů.

    Použití 4 fotorezistorů s nichž jsou dva pevné jsem volil z toho důvodu, že by program hned věděl kde zhruba je a jakým směrem má natočit solární panel aby našel slunce. Fungovalo by to na principu rozdílu hodnot na fotorezistorech a zvolení směru natočení k tomu, který snímá větší intenzitu světla. Dále by fungovalo ovládání již jen podle těch dvou pohyblivých na panelu. Samozřejmě by vůbec nevadilo aplikovat pouze dva fotorezistory a napsat program jak uvádíte Vy. Funkce je naprosto stejná a funkční.
    Vlastně máte pravdu. Slunce vychází pořád na stejné straně a tak by program věděl jakým směrem se má točit po zapnutí 😀
    Zapomněl jsem uvést, že bych zařízení na noc nevypínal. Bylo by v provozu non-stop přes sezónu. Ideálně v programu dát podmínku při snížení intenzity světla zastavit program a pokračovat až ráno začne svítat znovu jej obnovit a natočit na východní stranu.

    Použití koncových spínačů mám v plánu jen jsem nechtěl v prvním příspěvku rozepisovat.
    Vlastně tam budou na každé straně dva. Ideálně jeden pro impuls pro Arduino a druhý jako bezpečnostní, který odstaví napájení motoru kdyby motor nezastavil.

    Jirka

    #11857
    Vojtěch Vosáhlo
    Účastník

    Já osobně bych u takového projektu volil DS18B20, dají se najít i v hezkých vodotěsných obalech a nikdy s nimy nebyl problém. Pojďme tedy na takovou reprezentaci programu slovy:

    
    
    //definice pinů a proměnných
    
    smyčka{
    
     pokud (cas = den){
       pokud(chceme ohrivat){
         //třeba 10, chce to nějaký prostor, testovat jestli se = 0 by nemělo význam
         dokud (rozdil fotorezistoru < 10){
           otacejMotor(strana = x); //Otáčej motor na stranu kde je na fotor. víc světla
         }
       }nebo pokud(nechceme ohrivat){
         otacejMotor(strana = x); //Otáčej motor tak aby na pannel svítilo co nejmíň světla - nebo nastav panel na jednu z konečných pozic
       }  
     }pokud (cas = noc); // Nedelej nic
    }
    

    Je to super zjednodušené ale pomůže to pro představu. Osobně bych začal „kódit“ trochu od prostředka. Pojďme zkusit třeba zrealizovat funkci co přečte rozdíl mezi fotorezistory.

    
    int rozdilRezistoru(){
      int R1 = analogRead(pinR1); //Přečtu napětí na prvním fotorezistoru
      int R2 = analogRead(pinR2); //Přečtu napětí na druhém fotorezistoru
      int rozdil = R1 - R2; //Rozdíl napětí
      return rozdil; //Vrátím rozdíl napětí jako hodnotu
    }
    

    Tahle funkce vám jednoduše vrátí rozdíl mezi senzory. Ale pozor, není to hodnota napětí. analogRead(); totiž vrací hodnoty 0-1023 (10bit) které jsou vlastně namapované na referenci. Tzn. s referencí 5V znamená hodnota 0 0V a 1023 5V. Je to zatím srozumitelné? Můžete začít stavět základní strukturu programu podle toho co jsem napsal výše a pak přidávat funkce které vám ulehčí práci.

    Ptejte se na vše co vám přijde na mysl. Taky si kdyžtak řekněte pokud popisuju něco co jsou pro vás už banálnosti, opravdu nevím jak jste na tom 🙂

    #11859
    marvik.jiri
    Účastník

    No… když to řeknu úsměvně tak jsem panic 🙂
    S arduinem jsem začal cca před 2-mi měsíci a dostanu se k pc abych měl čas programovat jen po večerech a to jen někdy. Zatím jsem si hrál převážně s led. Dělal jsem synovi světelnou semafor pro auta s přechodem pro chodce. Ono se toho na Unu moc nedá udělat, když je k dispozici jen nějakých 18pinů. Toto bylo na 10 pinů. Dále jsem zkoušel infra přijímač s výpisem kódu z dálkového ovladače přes sériovou linku a následně jsem se snažil doprogramovat záměnu kódu a vyslání vysílačem jiný. Jednoduše řečeno pokud arduino přijme určitý kod (třeba ze starého ovladače od videorekorderu tak vyšle jiný kod, který přepne na televizi třeba kanál nebo zesílí zvuk. Má to být něco jako univerzální ovladač. Bohužel jsem to nedodělal. Dokážu pouze ovládat ledky na pinech dálkovým ovladačem.Ztroskotal jsem na zkušenostech. Použil jsem jiné programy, které jsem se snažil zkompilovat do jednoho.
    Můj poslední výtvor je plně funkční mechanická přístrojová deska z auta kterou ovládá arduino a mám ji ke hře Euro Truck Simulátor. Zde jsem použil kód os Silase, kterou následně ještě někdo upravil a vytvořil plugin přímo pro hru. Zde jsem částečně upravil a částečně doprogramoval kód. Jelikož jsem použil místo Megy Uno a navíc místo led displeje 1602 připojenou přes ISP převodník (snad to píši správně).

    Vyhledávám podobné aplikace tomu čeho chci dosáhnout a snažím si je předělat nebo doprogramovat. Takže zkušeností jen málo… 🙁

    #11861
    marvik.jiri
    Účastník

    Zkusil jsem udělat nástřel struktury programu.

    int rozdilRezistoru(){
    int R1 = analogRead(pinR1); //Přečtu napětí na prvním fotorezistoru
    int R2 = analogRead(pinR2); //Přečtu napětí na druhém fotorezistoru
    int rozdil = R1 – R2; //Rozdíl napětí
    return rozdil; //Vrátím rozdíl napětí jako hodnotu

    void setup() {
    pinMode(11, OUTPUT); //nastav pin 11 jako vystup = motor doprava – solar natáčí k východu
    pinMode(12, OUTPUT); //nastav pin 12 jako vystup = motor doleva – solar natáčí k západu
    pinMode(10, INPUT); //nastav pin 10 jako vstup = koncový spínač východ
    pinMode(9, INPUT); //nastav pin 9 jako vstup = koncový spínač západ
    pinMode(8, OUTPUT); //nastav pin 8 jako vstup = rele zapínání filtrace a transformátoru po motor solárního panelu
    }

    pokud na teplotním snímači ovzduší je hodnota menší než 25 = zastav program

    pokud na teplotním snímači ovzduší je hodnota větší než 25 = pokračuj dále // například 25°C
    digitalWrite (8,HIGH) // zapne filtraci a napájení transformátoru (půjde zapínat i samostatně přes vypínač)
    pokud (hodnota světla menší na „pinR1“ než 10 = nedělej nic //hodnota je informativní
    pokud (hodnota světla větší na „pinR1“ než 10 = otáčej motor doprava až na koncový spínač K1 digitalWrite (11,true) //číslo pinu je informativní
    pokud sepnuto pinK1 = digitalWrite(11,LOW); //na pinu 11 vypni proud = motor se zastavý
    pokud na pinu R2 bude větší hodnota než na R1 = digitalWrite (12,true) – /* tady vycházím z toho že pin R1 je více na východ a R2 na západní stranu
    je nutné určit rozsah (od – do) jalové hodnoty mezi R1 a R2, aby nedocházelo k tomu, že se bude chtít natáčet každých pár minut o milimetry.
    Ještě k tomu snímámí hodnot z fotorezistorů by se měla dát určitá časová prodleva – třeba 30s z důvodu kdy půjde mrak a zastíní jeden z nich
    */
    pokud sepnuto pinK2 digitalWrite(12,LOW); //na pinu 12 vypni proud = motor se zastavý
    pokud na teplotním snímači vody je více jak 28°C = digitalWrite (12,true) až na koncový spínač K2 /* bude se snažit odstínit panel ze sluníčka
    Ono by to chtělo zase nějak zprůměrovat a k večeru přetočit na východní stranu aby později večer a při západu na panel nesvítilo sluníčko, ale to
    by se teď asi nemuselo řešit. To by se dalo až úplně nakonec v horším případě vynechat zcela. Tohle měli řešit ty další dva pevné fotorezistory*/
    Pokud na teplotním snímači ovzduší menší teplota než na sníémači vody zastav filtraci digitalWrite (8, LOW)

    #11862
    Vojtěch Vosáhlo
    Účastník

    Tak jo, máte to hezky nastrukturované, vzal jsem to a trochu poupravil. Nejdůležitější jsou asi ty proměnné, pokud je budete používat místo pevného definování pinů tak můžete pak cokoliv jednoduše měnit. Definice pinu by tedy teď měla vypadat třeba takto: int pinR1 = 11;

    Pak jsem vzal kód který jste si jen tak předepsal a hodil ho do reálně funkčího kódu.

    Opět se ptejte na vše co vás napadne.

    
    //Definice pinu
    int pinR1 = ...; //pin s fotorezistorem 1
    int pinR2 = ...; //pin s fotorezistorem 2
    int pinRZ = ...; //pin s fotorezistorem na zapade
    int pinRV = ...; //pin s fotorezistorem na vychode
    int pinMotorP = ...; //pin s rele spoustejici motor doprava
    int pinMotorL = ...; //pin s rele spojstejici motor doleva
    int pinKoncakV = .. ; //pin s koncovym spinacem na vychode
    int pinKoncakZ = ...; //pin s koncovym spinacem na zapade
    int pinTrafo = ...; //pin s rele pr zapnuti trafa a napajeni motoru
    
    //Definice hodnot pouzivanych programem
    int maxTeplotaVzduchu = ...;
    int minTeplotaVzduchu = ...;
    int maxTeplotaVody = ...;
    int minTeplotaVody = ...;
    int maxRozdilSvetla = ...;
    boolean ohrivej = ...; //promena skryvajici 1 nebo 0 bude urcovat jestli chceme ohrivat nebo ne
    
    void setup() {
      //nastav piny pro ovladani motoru na vystupy
      pinMode(pinMotorP, OUTPUT);
      pinMode(pinMotorL, OUTPUT);
    
      //nastav piny fotorezistoru jako vstupy
      pinMode(pinR1, INPUT);
      pinMode(pinR2, INPUT);
      pinMode(pinRZ, INPUT);
      pinMode(pinRV, INPUT);
      
      //nastav piny s koncovymi spinaci jako vstupy
      pinMode(pinKoncakV, INPUT);
      pinMode(pinKoncakZ, INPUT);
    
      //nastav pin pro ovladani trafa jako vystup
      pinMode(pinTrafo, OUTPUT);
    }
    
    void loop(){
    
      //urcete si podminky kdy chcete aby se ohrivalo a kdy ne, podle toho se pak bude spoustet program dole
      if(neco a neco je splneno){ //treba pokud (teplotaVzduchu > teplotaVzduchuMin && teplotaVody < maxTeplotaVody)
        ohrivej = true;  
      }else{
        ohrivej = false;  
      }
    
      
      if(ohrivej){ //spust program pouze pokud chceme ohrivat
        
        digitalWrite (pinTrafo,HIGH); // zapni filtraci a napájení transformátoru (půjde zapínat i samostatně přes vypínač)
        
        while(digitalRead(pinKoncakV) == 0){ //otacej motorem na pravo dokud se nesepne koncak
          digitalWrite(pinMotorP, HIGH);
        }
    
        digitalWrite(pinMotorP, LOW); //potom co se sepne koncak se smycka rozpadne a motor se vypne
        
        if(abs(rozdilRezistoru) > maxRozdilSvetla){ //pokud je rozdil svetla mezi rezistory (absolutni hodnota, chceme znat jen rozdil, ne ne kterem je vic a na kterem mene) vetsi nez maxRozdil svetla pokracuj dale
          //kod pro pohybovani panelem dokud se rozdil mezi rezistory nezmensi
        }
    
        
      }
    }
    
    int rozdilRezistoru(){
      int R1 = analogRead(pinR1); //Přečtu napětí na prvním fotorezistoru
      int R2 = analogRead(pinR2); //Přečtu napětí na druhém fotorezistoru
      int rozdil = R1 – R2; //Rozdíl napětí
      return rozdil; //Vrátím rozdíl napětí jako hodnotu
    }
    
    #11863
    posjirka
    Účastník

    přidám svoji troškou do mlýna:
    Pro definici čísel pinu použivejte spíš #define
    #define pinR1 1
    na konci se nepíše středník. ROzdíl je v tom, že nezabíráte místo v paměti, ale při kompilaci program nahradí tyto zástupné „pinR1“ za hodnotu „1“.

    Co se týká těch 2 fotorezistorů, tak princip je trochu jiný než tu popisujete. Funguje to tak, že dáte 2 fotorezistory vedle sebe (východ a západ) a oddělíte je přepážkou. Potud to máte správně 🙂 Funkce je ale taková, že se panel snaží vyrovnat intenzitu světla na obou fotorezistorech na stejnou hodnotu. To co je ve stínu říka, že se má panel otočit na druhou stranu. Nemusíš právě skenovat celou oblohu, jen stačí najít nejasnější stranu a snažit se pohybem panelu vyrovnat hodnoty světla na obou stranách.

    tady máš takový jednoduchý příklad:

    Arduino Solar Tracker, Get More From Your Solar Panels

    #11880
    marvik.jiri
    Účastník

    Konečně jsem po několika hodinách něco spáchal. Je to zatím jen nadefinování, natočení do výchozí pozice a zapnutí filtrace-transformátoru. Můžete mi potvrdit, zda by to takto mohlo fungovat nebo dělám hlouposti.

    //Definice pinu
    int pinR1 = A0; //pin s fotorezistorem 1
    int pinR2 = A1; //pin s fotorezistorem 2
    int pinRZ = A2; //pin s fotorezistorem na zapade
    int pinRV = A3; //pin s fotorezistorem na vychode
    int pinMotorP = …; //pin s rele spoustejici motor doprava
    int pinMotorL = …; //pin s rele spojstejici motor doleva
    int pinKoncakV = .. ; //pin s koncovym spinacem na vychode
    int pinKoncakZ = …; //pin s koncovym spinacem na zapade
    int pinTrafo = …; //pin s rele pro zapnuti trafa napajeni motoru
    int pinFiltr = …; //pin s rele pro zapnuti filtrace
    int pinTepVzd = A4; //pin na čidlo teploty vzduchu
    int pinTepVod = A5; //pin na čidlo teploty vody
    //int pinTlacFiltr = …; // pro ruční zapnutí/vypnutí filtrace !!! – zatím nepoužito

    //Definice hodnot pouzivanych programem
    int maxTeplotaVzduchu = …;
    int minTeplotaVzduchu = …;
    int maxTeplotaVody = …;
    int minTeplotaVody = …;
    int maxRozdilSvetla = …; //30
    int minSvetloRV = …; // čeká na minimální hodnotu pro zapnutí filtrace
    int minSvetloRZ = …; //pokud bude nižší tak program vypne a čeká do svítání na R1
    // vložit rozdíl mezi pevnými fotorezistory pro otočení solaru do stínu při dosažení určité teloty vody
    int RozdilSvetla = …; // pokud bude voda teplejší jak … tak se bude solar otáčet na stranu k nižší hodnotě světla a odstiňovat další ohřev
    boolean nasleduj = …; //promena skryvajici 1 nebo 0 bude urcovat jestli chceme ohrivat nebo ne
    boolean stin = …; //promena skryvajici 1 nebo 0 bude urcovat jestli chceme odstinit ohrev nebo ne

    //pro seriovou linku
    int pinR1_value = A0; //pin s fotorezistorem 1
    int pinR2_value = A1; //pin s fotorezistorem 2
    int pinRZ_value = A2; //pin s fotorezistorem na zapade
    int pinRV_value = A3; //pin s fotorezistorem na vychode

    void setup()
    {
    //nastav piny pro ovladani motoru na vystupy
    pinMode(pinMotorP, OUTPUT);
    pinMode(pinMotorL, OUTPUT);
    //nastav piny fotorezistoru jako vstupy
    pinMode(pinR1, INPUT);
    pinMode(pinR2, INPUT);
    pinMode(pinRZ, INPUT);
    pinMode(pinRV, INPUT);
    //nastav piny teplotních čidel jako vstupy
    pinMode(pinTepVod, INPUT);
    pinMode(pinTepVzd, INPUT);
    //nastav piny s koncovymi spinaci jako vstupy
    pinMode(pinKoncakV, INPUT);
    pinMode(pinKoncakZ, INPUT);
    //nastav pin pro ovladani trafa a filtrace jako vystup
    pinMode(pinTrafo, OUTPUT);
    pinMode(pinFiltr, OUTPUT);
    //nastav pin tlačítka pro ruční zapnutí filtrace
    //pinMode(pinTlacFiltr, INPUT); zatím nepoužito
    {
    Serial.begin(9600);
    Serial.println(„Pripojeno“);
    }
    }

    void loop()
    {
    Serial.println(„R1“);
    pinR1_value = analogRead(pinR1); //čte hodnoty fotorezistoru R1
    Serial.println(pinR1_value); //zobrazí hodnoty R1 na seriove lince
    Serial.println(„R2“);
    pinR2_value = analogRead(pinR2); //čte hodnoty fotorezistoru R2
    Serial.println(pinR2_value); //zobrazí hodnoty R1 na seriove lince
    Serial.println(„RZ“);
    pinRZ_value = analogRead(pinRZ); //čte hodnoty fotorezistoru RZ
    Serial.println(pinRZ_value); //zobrazí hodnoty R1 na seriove lince
    Serial.println(„RV“);
    pinRV_value = analogRead(pinRV); //čte hodnoty fotorezistoru RV
    Serial.println(pinRV_value); //zobrazí hodnoty R1 na seriove lince
    Serial.println(„konec“);
    delay(1000); //wait
    }
    {
    // Po rozednění natočení na východ
    // po rozednění se se solární panel natočí k východu, když hodnota na R1 vzroste nad určitou hodnotu
    if(minSvetloRV > 120) digitalWrite (pinMotorP = HIGH);
    while(digitalRead(pinKoncakV) == 0){ //otacej motorem na pravo dokud se nesepne koncak
    digitalWrite(pinMotorP, LOW);
    while(digitalRead(pinKoncakV) == 1){ //zastav otaceni motorem na pravo – je sepnut koncak
    digitalWrite(pinMotorP, LOW);
    }
    }
    }
    {
    // FILTRACE ZAP-VYP
    // po rozednění se sepne filtrace, když hodnota na RV vzroste nad určitou hodnotu zapne se filtrace
    if(minSvetloR1 > 120) digitalWrite (pinFiltr = HIGH);
    // po schování slunce za horizont se filtrace vypne, když hodnota na RZ klesne pod určitou hodnotu
    if(minSvetloR2 < 140) digitalWrite (pinFiltr = LOW); // musí být větší hodnota, aby se to nevyplo hned po zapnuti
    }
    {
    // Transformátor ZAP-VYP
    // po rozednění se sepne trafo, když hodnota na R1 vzroste nad určitou hodnotu, která je vyšší než hodnota filtrace
    if(minSvetloR1 > 80) digitalWrite (pinTrafo = HIGH);
    // po schování slunce za horizont se trafo vypne, když hodnota na R2 klesne pod určitou hodnotu, která je vyšší než hodnota filtrace
    if(minSvetloR2 < 95) digitalWrite (pinTrafo = LOW);
    }

    #11882
    marvik.jiri
    Účastník

    Tady mám asi nesmysl.
    if(minSvetloRV > 120) digitalWrite (pinMotorP = HIGH);
    Nemělo by tam být spíše:
    if(minSvetloRV < pinRV_value) digitalWrite (pinMotorP = HIGH);
    nebo
    if(120 > pinRV_value) digitalWrite (pinMotorP = HIGH);

    #11883
    marvik.jiri
    Účastník

    Mám čistě hypotetickou otázku 🙂
    Za předpokladu, že jeden den bude příznivé počasí a hodnoty budou splněny (25°C, světelné podnínky) třeba v 9hodin a další dny bude počasí ještě hezčí a podmínky se splní již v 6hodin. Nebo snažší příklad. Začátek léta kdy nejsou potřebné podmínky časně z rána a průběh léta, kdy jsou splněny o poznání dříve.
    Dá se do programu zadat výpočet pro výchozí hodnoty pomocí potenciometru?
    Jako příklad uvedu:
    Fotorezistor udává hodnoty od 12 (ostré světlo) po cca 700 (tma)

    původní data
    int maxRozdilSvetla = 50 ;
    int minSvetloRV = 150 ; // minimální hodnotu pro zapnutí filtrace
    int minSvetloRZ = 150; //pokud bude nižší tak program vypne a čeká do svítání na RV

    nová data s použitím potenciometru pro úpravu výchozích hodnot
    Teď nevím jaký rozsah bude mít 10KOhmový potenciometr, ale například 2000… což je daleko více než fotorezistor ve tmě (cca 3x) a musím připojit na digitál jelikož analog již nemám volný.

    definice pinu
    int pinPot = 2 ; //pin s potenciometrem 10K
    int pinPot_value = 2;
    int maxRozdilSvetla = 50+(digitalRead(pinPot)/3) ; // výchozí hodnota nastavená na zhoršené podmínky + hodnota z potenciometru / 3
    int minSvetloRV = 150+(digitalRead(pinPot)/3) ; //minimální hodnotu pro zapnutí filtrace
    int minSvetloRZ = 150+(digitalRead(pinPot)/3) ; //pokud bude nižší tak program vypne a čeká do svítání na RV

    #11886
    Vojtěch Vosáhlo
    Účastník
    1.
    Jak psal jirka, pro definici pinů používejte #define, tady jsem vás špatně navedl na proměnné. Definice vypadá třeba takto: #define pinR1 A0
    
    2.
    Proč nastavujete hodnoty pinRx_value na nějaký z analogových pinů? Není to potřeba, stačí je inicializovat jako prázdnou proměnnou: int pinRx_value;
    Data se do nich zapisují až pomocí analogRead()
    
    3. 
    V setupu máte na konci navíc 2 závorky, proč? Měl jste s tím nějaký úmysl?
    Jde o tento kousek kódu:
    

    {
    Serial.begin(9600);
    Serial.println(„Pripojeno“);
    }
    `
    4.
    Po void loop() máte spoustu závorek. To mají být funkce (smyčky)? Pokud ano chybí jim jméno a typ. Musí se definovat takto:
    typ nazev(odatecne promenne){}
    Typ: Void – nic nevrací
    Název proměnné – int, boolean, … – funkce vrací hodnotu typu této proměnné

    5. DigitalWrite u filtrace ZAP-VYP máte špatně, ne digitalWrite(pinFiltr = HIGH) ale digitalWrite(pinFiltr, HIGH)

    6.
    Proměnné minNeco a maxNeco byly zamýšlené pro určení těch hranic. Podmínku byste tedy zapisoval třeba takto:
    If(namrenaHodnota > R1min) neco sepni;
    Namerena hodnota může být třeba z analogRead(); pokud tato hodnota stoupne nad hodnotu R1min která je pevně definovaná třeba na 120 tak můžete něco spustit.

    #11887
    Vojtěch Vosáhlo
    Účastník

    A teď k poslední otázce. Problém je že otáčenoím poťákem ničeho nedocílíte. Digitální piny umí číst jen hodnotu 0 nebo 1 a to vše závisí na tom jestli je překročena určitá napěťová hranice. Nedostanete tedy nic víc než 1 nebo 0.

    #11890
    posjirka
    Účastník

    potenciometr jde řešit i na digitálním pinu, ale není to nic přesnýho.
    Funguje to na principu:
    Dig.out dej do log. 0 – vybije se kondenzátor
    přepni na dig.in a čekej než se přepne do log.1
    tento čas je roven velikosti natoční potenciometru.

    http://gcbasic.sourceforge.net/help/output/html/images/potb1.JPG

    je třeba při psaní kodu používat párové značky CODE jinak se kod zapisuje nesprávně.

    Doporučoval bych udělat si přehled použitých čidel, akutatoru a ovl. obvod + nějákou rezervu. Pak si teprve hrát s programem. Bude se ti lépe bádat když už budeš mít vše po ruce a nebudeš mít těžkou hlavu kde jsi co nevyřešil.

    #11891
    posjirka
    Účastník

    podle popisu bych viděl použité vstupy výstupy takto (příloha)
    jestli souhlasí tak těm pinům můžeme dát rovnou pozici na Arduinu.
    Koukám že tam máš navíc Trafo a filtraci jako digi výstupy (opraveno).
    Takže by ti to na UNO mohlo vyjít včetně 5 rezerv (4xdigi, 1xanalog) a to jsem tam ještě přihodil LCD 🙂

    Sktrukturu programu máš vcelku správně. na začátku s všechno načti (světlo, nastavení, teploty,..) pak vyhodnoť a nakonci zareaguj.

    Vypadne ti z toho, že si jen všechno načteš a postupně pomocí podmínek ožiuješ jednotlivé výstupy …

    #11905
    MiK
    Účastník

    Skoro by stálo za úvahu, podívat se na celý problém z trochu jiného pohledu.

    Jestli jde jen o to, aby se panel natáčel pořád za Sluncem, tak ho přece stačí přidělat na krokový motor, který bude mít svou osu sklopenou na 50° nad severní horizont (osa bude mířit na Polárku).

    A ten motor se pak už bude pomalu krokovat tak, aby se otočil přesně o 1 otáčku za 24 hodin.
    Odpadnou všechny čidla (zůstanou jen 2 bezpečnostní koncáky, aby se panel nepřetočil kolem dokola).

    V principu to tedy bude jakási paralaktická vidlicová montáž, jaká se používá v Astronomii.

    Takže by to vypadalo nějak takhle:
    http://home.zcu.cz/~smid/stroje/bobik.jpg

    Akorát místo dalekohledu by tam byl solární panel
    A myslím, že by mohla odpadnout i ta možnost natáčení panelu nahoru a dolu (deklinace). Prostě by se napevno nastavila nějaká „průměrná letní“ deklinace.

    #11917
    marvik.jiri
    Účastník

    Děkuji všem za Vaše příspěvky a trpělivost se mnou.
    Jako začátečníkovi mi uniká docela dost věcí a musím říci, že ne všemu co mi radíte rozumím nebo rozumím tím správným způsobem.
    „posjirka“ psal, že na digitálním pinu lze snímat jen I/O a v dalším příspěvku na obrázku zapojení čidel dáte snímače teploty „DS18B20“ na digitální piny. Vždyť z nich potřebuji získat hodnoty dle teploty vzduchu a vody…

    Pane Vosáhlo děkuji za výtky k chybám. Vše co Vám je divná a dotazujete se na to, jsou skutečně mé chyby a opravím je dle rad.

    Zkusím ještě jednou jednoduše popsat co od programu a snímačů chci:
    4x fotorezistor (http://www.the-diy-life.com/arduino-solar-tracker/)
    2x teplotní čidlo (https://www.tweaking4all.com/hardware/arduino/arduino-ds18b20-temperature-sensor/)
    1) po rozednění (pevný fotoodpor východ) splní min intenzitu světla = solar se natočí na východ na koncový spínač – (pevný fotoodpor východ + teplota vzduchu) splní druhou vyšší hodnotu = zapne se filtrace – dále se otáčení řídí dle rozdílu hodnot na 2x fotoodporu, který je přidělám na rámu solárního panelu. Např. R1 východní a R2 západní. – měřená hodnota na R1 je vyšší než na R2 = solar stojí => měřená hodnota na R1 je nižší než na R2 = sepne se rele a solar se pootočí k západu dokud hodnota na R1 nebude vyšší než na R2 – celé se to opakuje až na koncový spínač na západě – následně při poklesu hodnoty na pevném západním fotoodporu se program zastaví taktéž.

    Dále je v programu podmínka, nadřazená fotoodporům R1 a R2 a čidlu vzduchu. Jedná se o snímač teploty vody.
    Pokud je program v provozu (zapnuta filtrace a natáčení dle R1 a R2, ale bude překročena teplota vody (např.28°C) budou se vyhodnocovat data z pevného východního a pevného západního fotoodporu – určí se menší hodnota a k té se solar natočí až na koncový spínač tak, aby na solar dále nesvítilo sluníčko, ale schovával se do stínu.

    Snad jsem to popsal pochopitelně 🙂

    #11920
    Vojtěch Vosáhlo
    Účastník

    Pane si prosím nechte, na to ještě věk nemám 😉 a odpovím trošku za jirku, snad to nebude vadit
    DS18B20 jsou totiž digitální senzory – jednoduše řečeno vysílají jedničky a nuly s určitou časovou prodlevou (běží na protokolu onewire). Arduino si vlastně měří časy po které je pin na 1 a nebo na 0 a podle toho sestaví bity, z nich pak stvoří data. O tohle všechno se stará jedna knihovna která udělá vše za vás a vrátí vám teplotu. Proto se pro tyto čidla používají digitální piny.

    Zkuste na ten kód kouknout, něco poupravit a ozvěte se.

    #11921
    marvik.jiri
    Účastník

    Díky za vysvětlení.

    Asi se v tom začínám plácat… Mám to opravené správně?

    Asi ještě přidám na A4 ten potenciometr pro změnu výchozích hodnot.

    //Definice pinu
    #define pinR1 A0 //pin s fotorezistorem 1
    #define pinR2 A1 //pin s fotorezistorem 2
    #define pinRZ A2 //pin s fotorezistorem na zapade
    #define pinRV A3 //pin s fotorezistorem na vychode
    #define pinTepVzd 3 //pin na čidlo teploty vzduchu
    #define pinTepVod 4 //pin na čidlo teploty vody
    #define pinKoncakV 5 //pin s koncovym spinacem na vychode
    #define pinKoncakZ 6 //pin s koncovym spinacem na zapade
    #define pinMotorP 7 //pin s rele spoustejici motor doprava
    #define pinMotorL 8 //pin s rele spojstejici motor doleva
    #define pinTrafo 9 //pin s rele pro zapnuti trafa napajeni motoru
    #define pinFiltr 10 //pin s rele pro zapnuti filtrace
    #define pinTlacFiltr 11 // pro ruční zapnutí/vypnutí filtrace

    //Definice hodnot pouzivanych programem
    int minTeplotaVzduchu = 25; //°C
    int maxTeplotaVody = 28; //°C
    int maxRozdilSvetla = 20; //20 = zatím odhad

    // sem ještě dát zda je vyšší hodnota na R1 než // svítání
    int minSvetloRV = 150; // čeká na minimální hodnotu pro zapnutí filtrace
    int minSvetloRZ = 180; //pokud bude nižší tak program vypne a čeká do svítání na R1
    // vložit rozdíl mezi pevnými fotorezistory pro otočení solaru do stínu při dosažení určité teloty vody
    int RozdilSvetla = …; // pokud bude voda teplejší jak … tak se bude solar otáčet na stranu k nižší hodnotě světla a odstiňovat další ohřev
    boolean nasleduj = …; //promena skryvajici 1 nebo 0 bude urcovat jestli chceme ohrivat nebo ne
    boolean stin = …; //promena skryvajici 1 nebo 0 bude urcovat jestli chceme odstinit ohrev nebo ne
    //pro seriovou linku
    int pinR1_value; //pin s fotorezistorem 1
    int pinR2_value; //pin s fotorezistorem 2
    int pinRZ_value; //pin s fotorezistorem na zapade
    int pinRV_value; //pin s fotorezistorem na vychode

    void setup()
    {
    //nastav piny pro ovladani motoru na vystupy
    pinMode(pinMotorP, OUTPUT);
    pinMode(pinMotorL, OUTPUT);
    //nastav piny fotorezistoru jako vstupy
    pinMode(pinR1, INPUT);
    pinMode(pinR2, INPUT);
    pinMode(pinRZ, INPUT);
    pinMode(pinRV, INPUT);
    //nastav piny teplotních čidel jako vstupy
    pinMode(pinTepVod, INPUT);
    pinMode(pinTepVzd, INPUT);
    //nastav piny s koncovymi spinaci jako vstupy
    pinMode(pinKoncakV, INPUT);
    pinMode(pinKoncakZ, INPUT);
    //nastav pin pro ovladani trafa a filtrace jako vystup
    pinMode(pinTrafo, OUTPUT);
    pinMode(pinFiltr, OUTPUT);
    pinMode(pinTlacFiltr, INPUT);
    //nastav pin tlačítka pro ruční zapnutí filtrace
    //pinMode(pinTlacFiltr, INPUT); zatím nepoužito
    }
    {
    Serial.begin(9600);
    Serial.println(„Spojeno“);
    }

    void loop()
    {
    Serial.println(„R1“);
    pinR1_value = analogRead(pinR1); //čte hodnoty fotorezistoru R1
    Serial.println(pinR1_value); //zobrazí hodnoty R1 na seriove lince
    Serial.println(„R2“);
    pinR2_value = analogRead(pinR2); //čte hodnoty fotorezistoru R2
    Serial.println(pinR2_value); //zobrazí hodnoty R1 na seriove lince
    Serial.println(„RZ“);
    pinRZ_value = analogRead(pinRZ); //čte hodnoty fotorezistoru RZ
    Serial.println(pinRZ_value); //zobrazí hodnoty R1 na seriove lince
    Serial.println(„RV“);
    pinRV_value = analogRead(pinRV); //čte hodnoty fotorezistoru RV
    Serial.println(pinRV_value); //zobrazí hodnoty R1 na seriove lince
    Serial.println(„konec“);
    delay(1000); //wait
    }
    {
    // Po rozednění natočení na východ

    // po rozednění se se solární panel natočí k východu, když hodnota na R1 vzroste nad určitou hodnotu
    if(minSvetloRV > 120) digitalWrite (pinMotorP, HIGH);
    while(digitalRead(pinKoncakV) == 0){ //otacej motorem na pravo dokud se nesepne koncak
    digitalWrite(pinMotorP, LOW);
    while(digitalRead(pinKoncakV) == 1) //zastav otaceni motorem na pravo – je sepnut koncak
    digitalWrite(pinMotorP, LOW); }
    }
    {
    // FILTRACE ZAP-VYP
    // po rozednění se sepne filtrace, když hodnota na RV vzroste nad určitou hodnotu zapne se filtrace
    if(minSvetloR1 > 120) digitalWrite (pinFiltr, HIGH);
    // po schování slunce za horizont se filtrace vypne, když hodnota na RZ klesne pod určitou hodnotu
    if(minSvetloR2 < 140) digitalWrite (pinFiltr, LOW); // musí být větší hodnota, aby se to nevyplo hned po zapnuti
    }
    {
    // Transformátor ZAP-VYP

    // po rozednění se sepne trafo, když hodnota na R1 vzroste nad určitou hodnotu, která je vyšší než hodnota filtrace
    if(minSvetloR1 > 80) digitalWrite (pinTrafo, HIGH);
    // po schování slunce za horizont se trafo vypne, když hodnota na R2 klesne pod určitou hodnotu, která je vyšší než hodnota filtrace
    if(minSvetloR2 < 95) digitalWrite (pinTrafo, LOW);
    }

    #11922
    posjirka
    Účastník

    DS18B20 je digitální čídlo se sběrnicí 1-wire. Tzn. že si veškerou komunikaci posílá přes 1 digitální pin. čte z čidla ovšem aktuální teplotu (-55 … +125 st.C) i když přes digitální pin.

    4 fotorezistory jsou podle mě zbytečné když nebudeš panel ještě naklánět. právě se dávají 2 fotorezistory oddělené vertikální přepážkou a někdy se polepují třeba alobalem aby brali i světlo z druhé strany. Právě pro měření min. intenzity světla.

    napsal jsem ti jednoduchý algoritmus jak by to mohlo celé fungovat, i když už dost velkou část máš …

    používej prosím párové značky CODE. zachová se ti i formátování kodu a bude přehlednější. Formátováním teď myslím odstazením např. závorek…

    #11925
    posjirka
    Účastník

    asi tě nechám v dobrých rukou ch Vojtěcha, a´t na tebe nesypeme rady ze 2 stran. Kdyby byl problém ozvi se …

    #11926
    Vojtěch Vosáhlo
    Účastník

    No nevím jestli v nejlepších rukou, k takovým funkčním diagramům mám ještě kousek cesty. Mimo to kde je kreslíš? Nějaký osvědčený soft by se hodil.

    Každopádně vložte sem prosím kód jak psal jirka. Použijte možnost textu code. Takhle se to opravdu velmi těžko čte. Nebo to vložte třeba na pastebin a pak pošlete odkaz, je to jedno. Člověk se v tom akorát nemůže vyznat…

    #11927
    marvik.jiri
    Účastník

    Tak nějak by to mělo skutečně fungovat. Jen bych upravil to natočení o vteřinu, ale rád bych na konkrétní snímané hodnoty. Čtení by mohlo být delší i třeba 5minut. Jen narážím na problem s mrakem, který zrovna zakryje jeden fotorezistor nebo proletí pták, list. Cokoli co může na chvilku zastínit jeden ze dvou fotorezistorů. Proto si myslím, že by bylo lepší snímat po čase (třeba 1-5minut) kontinuálně hodnoty z rezistorů a při spuštění motoru je sledovat dokud se nevyrovnají a poté natáčení vypnout a opět čekat několik minut.

    Fotorezistory 2 pohyblivé s panelem a 2pevné.
    pohyblivé na sledování slunce
    pevné na spuštění programu při svítání a následně při nahřátí vody k určení polohy slunce = dopoledne – FRvýchod má vyšší hodnotu světla =>solar se schová na západní stranu / odpoledne – FRzápad má vyšší hodnotu světla => solar se natočí na koncový spínač východu

    #11931
    posjirka
    Účastník

    to vojtech: používám diagram designer.je až primitivně funkční:
    https://www.zive.cz/clanky/diagram-designer-rychla-tvorba-diagramu-zdarma/sc-3-a-167191/default.aspx

    to marvik: z těch pevných fotoodporů mám trochu osypky. startovat proces při východu slunce je velmi nešťastné. nezapomeň, že i krátkodobý výpadek napájení (špička) ti může resetovat procesor. Ten pak „ztratí nit“ a musí se něják znovu chytit. jinak ti může spinkat do dalšího rána. proto se mi to řešení moc nelíbí. Rozhodně schavaluju koncáky jako vymezení max. polohy otáčení panelu. Nastavení na nejlepší hodnoty samozřejmě jde.

    Zatím bych se vykašlal na „solární chlazení“ při překročení 28 st.C.

    V příloze máš upravený algoritmus. je to už trochu hybrid a nejsme z něj moc nadšený. Radši bych celý proces regulace řešil „real time“ bez zpoždění. No pro začátek by ti toale mohlo vcelku vyhovovat…

Aktuálně je na stránce zobrazeno 24 příspěvků - 1. až 24. (celkem z 24)
  • Pro reakci na toto téma se musíte přihlásit.