Chauffage SOLAIRE THERMIQUE à Aussillon (Tarn)
Sommaire rapide : mise en place
des panneaux - schéma - ballon
- vannes - fonctionnement chauffage
- serpentin poêle - remplissage
solaire - différents type de raccords - cout
total - Automatisation - commandes
circulateurs - programme complet - conclusion.
Début
2014, je tombe sur une annonce de chauffe-eau
solaire par thermosiphon Giordano de 1980 à 100euros (à 10Km
de chez nous). Après installation, je m'aperçois soudain - oh,
miracle ! - que le soleil est capable de chauffer l'eau jusqu'à 80°C
! L’énergie du soleil est énorme !
Dès
lors, je lis des livres (de l'Apper
: "Installer
un chauffage ou un chauffe-eau Solaire", "Installations
solaires thermiques" de Peuser, Remmers, Schnauss, et d'autres livres
comme "La Conception Bioclimatique" éditions Terre
Vivante d'Olivier Oliva et de Samuel Courgey) et consulte les forums ( http://forum.apper-solaire.org/
, http://www.chaleurterre.com/forum/
, https://www.econologie.com/forums/
) sur le web pour me former au solaire thermique.
Bilan :
La meilleure
façon de récupérer la chaleur du soleil pour chauffer une
maison est la maison bioclimatique : isolation extrême (mur terre-paille-chaux
pour éviter l'étanchéité, car la chaux respire contrairement
au ciment/béton), terrain en pente vers le sud, grande baie vitrée
plein sud, gros mur Trombe
(ici)
ou mur capteur derrière la baie vitrée (à quelques mètres)
qui va réguler la température de la maison (notion de "masse
thermique" ou "inertie thermique"), et surtout une casquette
(avancée de toit) bien calculée qui empêche le soleil de
rentrer de fin avril à septembre, quand celui-ci est haut dans le ciel,
afin d'éviter les surchauffes l'été. On voit même
sur cet exemple, à l'ouest (gauche), la maison qui se referme un peu
pour éviter l'entrée du coucher de soleil l'été
:
![]() |
Si
pas possible de construire du neuf et pas possible de faire de grosses modifications
au bâtiment, il reste les panneaux solaires thermiques :
Notre MAISON : près de Mazamet dans le Tarn (Occitanie). Maison de 1913 (rue Blériot à Aussillon), en pierres, 40m² au sol sur 3 étages : cave (non chauffée), rez-de-chaussée (salon/cuisine/WC), étage (1/3 mansardé).
![]() |
Après travaux isolation ouest et toiture :
Historique des travaux d'isolation :
Aout 2011 : changement vieille chaudière gaz (foutue) par chaudière gaz à condensation (A SAVOIR : la condensation ne fonctionne qu'avec une eau de départ en dessous de 55°C, et plus c'est en dessous, plus la condensation se fait et le rendement de la chaudière augmente. L'idéale est donc de la coupler à un plancher chauffant ou à des murs chauffants).
Septembre 2012 : changement des menuiseries de toute la maison par du PVC ou bois (bois beaucoup plus performant) en double vitrage (cout d'env. 5000€).
Septembre 2015 : toiture refaite (nombreuses fuites) et isolée par l'extérieur avec 13cm de polyuréthane (matériel non écologique, car demande beaucoup d’énergie à sa fabrication... En laine de bois il fallait le double d'épaisseur et le prix doublait également : 20 000euros au lieu de 10 000 env.).
Décembre 2015 : isolation des murs extérieurs ouest, est et sud de l'étage, par 13cm de polystyrène (matériel non écologique, car demande beaucoup d’énergie à sa fabrication. Env. 15 000 euros).
Janvier 2016 : j'isole par l'intérieur les derniers murs non encore isolés (surtout au nord, car la présence du trottoir nous interdisait de le faire par l'extérieur) avec des plaques de placo/laine de roche récupérées. J'en profite pour faire des murs chauffants (modèle Pierre Amet, multicouche 16mm).
Maintenant
isolé, on commençait à avoir plus chaud dans la maison,
tout en chauffant beaucoup moins. La chaudière - passée en basse
température grâce aux murs chauffants - consommait peu et lorsqu'on
allumait le poêle le soir pendant seulement 1h, ça chauffait beaucoup
plus vite : on ne devait plus chauffer les murs avant de se chauffer. Puis le
lendemain, il ne faisait pas 13°C, mais 16-17°C.
Isoler
le plafond de la cave ou pas ? (impossible d'isoler les murs, il faut les laisser
respirer, car ils sont enterrés). Entre mai et septembre, la cave rafraichit
la maison, ce qui est très intéressant avec les canicules. Entre
septembre et fin décembre, la cave - à env. 17°C - chauffe
un peu la maison. Mais l'hiver, entre fin décembre et avril, la cave
(à 13-17°C) refroidit plus souvent la maison. Donc l'isolation du
plafond de la cave ne serait intéressant qu'entre fin décembre
et avril.
Les 2 modes de chauffage :
1 - Poêle fonte Jotul F3 : 1 à 2 stères de bois brulé/an (allumé - à feu très vif pour moins polluer - 1h le matin et 1h le soir lors des grands froids).
2 - Chaudière gaz à condensation (4 500KW/an) en basse T°C pour murs chauffants (modèle Pierre Amet, multicouche 16mm), et 4 radiateurs acier (2 dans chaque chambre qu'on chauffe à 15°C, 1 dans cuisine et 1 sèche serviette dans salle de bain)
La chaudière est réglée continuellement à 15°C sauf entre 6-7h et 18-21h à 17°C.
Mise en place des panneaux solaires :
La
maison est petite, nous n'avons pas beaucoup de place : première idée,
mettre les panneaux sur le gazon ?
---> On s'est dit que ce ne serait pas pratique pour passer la tondeuse hélicoïdale entre les panneaux...
Février 2018 :
Pas très esthétique, mais
on ne peut pas tout avoir.
La toiture de la maison (pas très grande) est réservée,
peut-être, aux futurs panneaux photovoltaïques (beaucoup plus légers).
Une
partie des panneaux a été achetée d'occasion (ceux du garage
à gauche, à 100€ pièce, des Roth) et les trois sur
la façade de la maison sont des Tinox LM112 à 350€ pièce.
L'avantage des Tinox est que ce sont des raccords à compression, sans
joint et pratiquement sans fuite (avec le liquide anti-gel, il semble que le
"sans fuite" n'existe pas...). Pour les 4 Roth du garage, les raccords
à joins fuient facilement avec le glycol. Il faut utiliser des joints
PTFE blanc (les joints gaz bleus fuient aussi).
Pour
la fixation sur la façade de la maison, j'ai planté des cornières
galvanisées dans le mur en pierre (le galvanisé coute un bras,
mais ça évite d'avoir des trainées de rouille sur la façade).
La difficulté avec les murs de pierres est de faire les trous là
où on veut les faire. Les pierres derrière décident toujours
par où passera le foret..., c'est à dire entre les pierres. Une
fois le trou fait, on mouille bien au pulvérisateur de jardin (pas au
tuyau d'arrosage quand même..., pour ne pas retrouver de l'eau dans la
maison) et on remplit avec du ciment pâteux (j'utilise un vieux morceau
de gouttière et un bâton de bois pour pousser le ciment). 3 ans
après, ça n'a pas bougé.
Avec
les panneaux horizontaux qui s'emboitent les uns dans les autres, il faut être
très précis dans le parallélisme et l'horizontalité
des supports. J'ai dû ajuster le tout avec des écrous de réhaussement.
(photo ecrous)
Pour
fixer les panneaux du garage, j'ai mis une cornière au dessus et une
cornière en dessous des panneaux (fixée sur la charpente du toit).
Les jambes de maintien sont fixées par des tiges filetées qui
traversent les poutres
de la toiture :
PANNEAUX :
7 panneaux (ou "capteur plan") de 2m² à 85° par rapport
à l'horizontale :
- 3 panneaux Tinox horizontaux LM112 (forme intérieure des tuyau = "échelle"
ou "harpe") de Solaire
Diffusion sur la facade avec des raccords à compression (efficacité
garantie contre les fuites). Le seul problème de ces panneaux est
que lorsqu'il faut démonter celui du milieu, il faut décaler aussi
ceux des côtés. Il y a parfois un peu de buée, mais rien
de grave.
- 4 panneaux Roth (serpentin à l'intérieur). J'en ai acheté 8 pour 800€. Ils avaient l'air en très bon état sur la photo, mais arrivée sur place, à 280Km de chez moi - vers Marseille -, ils étaient très oxydés, sauf un, celui qu'on m'avait montré en photo... Deux ans après, lorsque je les ai branchés, il y en avait 2 qui fuyaient ! Comme ils sont vraiment moches, on a préféré en acheter 3 neufs pour la façade. Ces panneaux, comme les LM112, se démontent facilement en détachant le cadre du devant (notice de l'apper).
Avec
l'oxydation des panneaux Roth et l'isolation un
peu plus faible des panneaux Tinox (au niveau des bouches d'aération
qui diminuent la condensation), le rendement des 2 modèles est assez
semblable. J'ai remarqué que lorsque le soleil monte (à partir
d'avril), l'eau en sortie des Roth devient moins chaude que les Tinox. Mais
entre sept et avril, les 4 panneaux du garage (ouest) sorte une eau 2 à
10°C plus chaude que les 3 panneaux en façade ; je pense que c'est
dû à l'absorption différente de la vitre des panneaux. Aussi,
en fonction des heures de la journée, P6 chauffe davantage, ou alors
P7 (voir plus bas) : c'est à cause du reflet sur le toit de verre de
la petite serre devant ces 2 panneaux.
Isolation
circuit panneaux : bien protéger les manchons
noirs d'isolation du soleil et de la pluie (avec par exemple une chute de bâche
EPDM, de la goutière en zing, etc.). Le blanc est généralement
plus voyant que le noir...
SCHEMA :
J'avais
pris beaucoup de notes durant mes lectures/recherches de 2 ans, donc ça
n'a pas été trop compliqué de faire ce schéma que
j'avais quasi entièrement dans la tête ; le travail est en amont,
pour se former et comprendre les choses :
(Ce
schéma au format photoshop, si vous voulez le réutiliser)
La
liaison ballon-panneaux solaires est en cuivre de 22mm, brasée (PAS d'étain
sur le circuit solaire qui peut monter à 150°C !) . J'ai respecté
l'égalité des distances en faisant la boucle
de tickelman (l'eau prend toujours le chemin le plus court. Il faut que
les distances depuis la station solaire soient les même pour chaque panneau,
sinon, le panneau dont le chemin est plus court fonctionnera plus que les autres).
Bien réfléchir aux phénomènes
de dilatation : en évitant de brancher un panneau (qui connait des changements
de température de -10°C à +150°C) directement après
plusieurs mètres de ligne droite. Mettre un coude juste avant, il pliera
légèrement et encaissera les dilatations.
Afin de limiter les pertes de charge
et moins fatiguer le circulateur, il faut éviter les coudes secs à
90°C. Prendre plutôt des coudes larges ou 2 coudes de 45° montés
ensemble. De même, les liaisons rapides en inox créaient de la
perte de charge (mais elles sont tellement pratiques...).
BALLON :
Merci aux voisins qui m'ont aidé à le rentrer... (200Kg)
Commandée
en Allemagne, 800 litres, 2 serpentins acier et un serpentin "hygiénique"
en inox pour l'eau sanitaire (en jaune, au milieu sur le schéma ci-dessus).
Ne jamais le déplacer à l'horizontale
ou le coucher (à cause du poids des serpentins à l'intérieur,
qui pourraient les plier et casser les soudures). Le ballon de 800L est à
la cave et c'est le plus gros que je puisse rentrer dans la maison (j'ai dû
"démonter" la fenêtre et son cadre...). Avec 7 panneaux,
il me fallait normalement 1500L de réserve pour ne pas être en
surchauffe l'été ; c'est pour cela que j'ai mis les panneaux très
à la verticale (85° / horizontale). Pour l'hiver, avoir plus de réserve
ne servirait à rien : en mars, lorsque j'ai vidé la cuve dans
les radiateurs (jusqu'à température haut de cuve = 26°C),
il faut env. 5h de super soleil (ciel non voilé) pour remonter la cuve
à 50°C (que je revide aussitôt à 26°C pour être
sûr de redémarrer rapidement le chauffage par le solaire le lendemain).
Je n'ai pas vraiment d'excédant de chaleur et ma cuve de 800L suffit.
Par contre, en octobre, comme le soleil commence à être bas, s'il
y a un grand soleil et qu'il ne fait pas froid, je ne consomme pas les calories
solaires, donc ma cuve monte jusqu'à 75°C (j'ai amélioré
le programme en "cassant" le rendement à cette période.
Et si le ballon dépasse les 75°C, j'envoie l'eau chaude dans les
panneaux la nuit pour refroidir le système). Si j'avais eu 1500L, je
n'aurais pas eu ces problèmes de surchauffe. Les maisons bioclimatiques
ont souvent le même problème. Si la maison est bien conçue,
ce n'est pas l'été qu'elle a des surchauffes (le soleil ne rentre
pas), mais plutôt en octobre.
Isolation du ballon : Je conseille fortement de la faire avant tout
branchement de tuyau (si vous la faites à la fin, c'est vraiment plus
compliqué au niveau des raccords). Il vaut mieux aussi limiter les entrées-sorties
au niveau du ballon pour limiter les pertes des chaleurs (si j'avais su, j'aurais
enlevé V5 et V6 pour ne garder que V4, vu qu'avec les vannes V8-V7, je
mixte et régle à la température que je veux).
Afin d'économiser, je n'ai pas acheté l'isolant du constructeur
du ballon. J'ai isoler en 2 couches de laine de verre (récup), au total
30cm d'isolant, recouvert d'un film étirable en plastique pour éviter
d'avoir la poussière de laine de verre dans la pièce.
Même très bien isolé, le ballon génère de
la chaleur en été : pour nous, ça fait monter d'env. 2-3°C
la partie de la cave où il est.
L'été (cave à 22°C), lorsque j'ai le haut du ballon
à 75°C, 24h après, il est à env. 70°C (sans consommation
de chaleur et sans apport). Si le haut de la cuve est à 55°C, je
perds moins de 2°C/24h (et à 28°C haut cuve, je perds env. 1°C/24h,
sans prélévement/apport). Plus le ballon est très chaud,
plus il perd vite sa chaleur. On voit là qu'une réserve énorme
d'eau très chaude ne sert à rien puisqu'on ne pourra pas la garder
très longtemps. S'il n'y a pas de soleil, un système solaire ne
fonctionne jamais très longtemps...
On peut coudre les morceaux d'isolant à
l'aide d'une ficelle et d'une grosse aiguille.
Je conseille d'isoler AVANT de faire les branchements de plomberie.
J'ai aussi posé le ballon sur des plaques de polystyrène extrudé récupérées (enfermées dans un sac plastique) avec par dessus une plaque de plastique (panneau publicitaire) ; rien qui ne pourrit. Et je m'arrange pour avoir le minimum au sol afin de faciliter le ménage.
Raccords sur le serpentin d'eau sanitaire
en inox : j'ai utilisé du multicouche
qui est censé résister jusque 95°C (la température
maxi autorisée pour le ballon est de 90°C).
Les manchons bleus isolent, mais servent surtout
à évacuer l'eau d'éventuelles fuites vers l'extérieur
de l'isolation du ballon (sans enlever l'isolant, je peux vérifier qu'il
n'y a pas de fuite, puisque l'eau descendra dans ces manchons bleus).
Pour éviter la légionellose, il faut avoir, de temps en
temps, une température supérieure à 55°C.
On peut voir le purgeur (gris, à placer dans tous les points hauts) qui
permet d'évacuer l'air qui serait dans le ballon (et qui fait aussi rentrer
l'air si on vide le ballon...). On remarque aussi les raccords diélectriques
(plastique avec bague de cuivre) qui isolent électriquement le ballon
du réseau d'eau de ville (mais le multicouche le fait déjà).
Sur le ballon, il est fortement conseillé de mettre des vannes partout pour pouvoir modifier ou démonter le circuit sans vider le ballon (sauf sur les serpentins qu'on peut vider facilement) :
Côté raccords circuit chauffage |
Côté raccords circuit solaire |
Mon
ballon n'est pas recouvert d'émail à l'intérieur. Ce n'est
pas nécessaire, car l'eau qu'il contient est de l'eau du circuit chauffage
radiateur, donc de "l'eau morte" qui perd son oxygène avec
le temps (il faut donc éviter de le vider ou de vider le circuit de chauffage
trop souvent). D'après ce que j'ai lu, les revêtements émaillés
ne sont d'ailleurs pas formidables : il y a toujours un endroit moins bien émaillé
qui finit par s'oxyder. Les problèmes d'oxydation des ballons surviennent
surtout avec l'eau sanitaire venant de la ville qui contient de l'oxygène.
Dans mon ballon, cette eau passe uniquement dans le "serpentin sanitaire"
en inox.
Composition des raccords pour la protection du ballon :
- circuit solaire : serpentins acier du ballon + raccord acier brut ou fer noir (PAS d'acier galvanisé avec glycol) + raccord diélectrique 3/4" + raccord laiton + tuyau cuivre 22mm
- circuit chauffage : ballon acier + raccord acier galvanisé + raccord diélectrique 3/4" + raccord laiton + tuyau cuivre 22mm + radiateurs (une vieille partie en acier, du multicouche dans les murs chauffants, quelques très petites longueurs en PER BAO)
- circuit EauChaudeSanitaire : serpentin inox + coude inox + raccord diélectrique 3/4" + raccord laiton + multicouche + tuyau cuivre 14mm (à l'arrivée d'eau de ville, je mets un petit filtre avec des aimants autour pour être sûr qu'il n'y ait pas de particules d'acier qui aillent dans le ballon inox)
- doigts de gant en inox et bouchons en inox ou acier galva.
Si vous achetez un ballon entièrement en inox, il faut prendre de l'inox austénique (21% de chrome et 7% de Nickel) et faire attention qu'aucune particule d'acier ne rentre dans le ballon (mettre des filtres aux l'entrées). Le ballon 100% inox n'est pas forcément la solution idéale et sans oxydation...
Sur le site de l'apper-solaire, il y a une excellente fiche sur les problèmes de corrosion galvanique : ici ou ici.
Normalement,
sur mon ballon, il n'y a pas besoin d'anode magnésium, mais j'en ai quand
même mis une pour apporter un peu de minéraux à mon eau.
J'ai d'ailleurs lu qu'il ne fallait pas remplir son ballon avec de l'eau
de pluie très peu minéralisée.
![]() |
Il existe des systèmes électroniques d' "anode hydride" ou anode à courant permanent (ou imposé, AEP) type Correx. C'est une électrode en titane qui est entré dans le ballon et qui émet un courant pour contrer le courant d'électrolyse d'oxydation. Pour vérifier l'état d'une anode magnésium : on débranche le fil de l'anode en y incérant un ampèremetre : l'anode est bonne si le courant > 0,3mA (en général, c'est à 0,8mA) entre le fil de l'anode et la terre. Une anode a une durée de vie de 10 ans. |
Normalement
il faut mettre le ballon sur la prise de terre, mais j'ai lu que cela pouvait
augmenter l'oxydation du ballon (en créant un courant qui va à
la terre...).
Les prises de température sur le ballon : il n'y en a que trois possibles et je regrette de ne pas avoir mis une ligne de 6-7 capteurs DS18B20 collés sur la tôle du ballon afin d'avoir plus de précision : |
LES DIFFERENTES VANNES :
(Ce
schéma au format photoshop, si vous voulez le réutiliser)
V1 : j'ai dû l'ajouter à
cause d'un effet thermosiphon qui se mettait en marche, dans le sens normal
du circulateur C1 : lorsque la cuve était bien chaude et que dehors il
faisait assez froid, l'eau du ballon remonté naturellement. Les panneaux
solaires sont en effet 4 à 5m plus haut que la cuve...
Dans la station solaire, il y a un clapet anti-thermosiphon au niveau du thermomètre
rouge, mais celui-ci a déconné au bout d'un mois d'utilisation,
donc je l'ai doublé avec celui en haut à gauche du ballon, appelé
"Clapet anti-retour" sur le schéma (comme quoi les clapets
c'est bien, mais rien de plus fiable qu'une vanne...). A savoir aussi, les clapets
à battant ne sont pas très hermétiques, préférez
des clapets à ressort.
Si comme pour moi, votre ballon est plus bas que les panneaux, l'idéal
est de mettre des vannes partout pour bloquer tout phénomène de
thermosiphon...
V2 : permet d'envoyer les calories de l'eau solaire au bon niveau dans le ballon (favorise la stratification). Si l'eau retour solaire est plus chaude que la sonde en milieu de cuve, alors je ferme V2 pour faire passer l'eau par le serpentin du haut. Sinon, j'ouvre V2 et l'eau prendra le chemin le plus court.
V3 : commandé directement
par V1 (si V1 s'ouvre, V3 se ferme, et inversement). Plusieurs fonctions : 1-
Si la température dans les panneaux est plus petite que -10°C, elle
s'ouvre (V1 étant fermée), on met alors en route le circulateur
C1 pour faire circuler dans le vide. C'est une protection de plus si le liquide
anti-gel est défaillant (l'étape suivant est d'envoyer l'eau chaude
du ballon dans les panneaux).
2- Lorsque les panneaux commencent à chauffer dans la journée,
je mets en route C1, mais sans faire rentrer l'eau dans le ballon tout de suite
(V1 fermée, V3 ouverte). Ce n'est que lorsque l'eau dans les tuyaux est
bien chaude que j'ouvre V1 pour fermer V3, afin de faire rentrer l'eau chaude
dans le ballon (ce n'est pas compliqué à faire, mais globalement,
ce n'est pas indispensable ; le plus important est d'avoir du soleil...).
V4, V5, V6 : je prends ou bien je place, l'eau à la température souhaitée. Ces vannes permettent de respecter la stratification du ballon et d'éviter les remous dans le ballon (pour les flux entrant et sortant). En effet, si j'envoie une eau à 60°C en V6 alors que le haut du ballon est à 40°C, ce flux d'eau va créer beaucoup de remous en montant jusqu'en haut du ballon. Alors que si j'envoie cette eau de 60°C directement en V4, je n'aurais pas de remous et je ne créerais pas d'eau tiède.
V8 et V7 : forment une vanne de mélange 3 voies qui permet de maintenir une température de chauffage de 39°C max, lorsque c'est possible (voir aussi plus bas le chapitre chauffage).
V9 : fermée la plupart du temps, sauf quand C3 est en route.
V10 et V11 : s'ouvre lorsque la chaudière au gaz se met en route pour chauffer la maison (je ferme alors V4, V5, V6, V7, V8, V9).
V12 : vanne 3 voies qui permet le choix
entre :
- Eau chaude sanitaire 100% par ballon solaire : si la température en
haut du ballon solaire est supérieure à 43°C, je ne passe
plus par la chaudière et j'éteins la chaudière au gaz (par
un relais dans la prise).
- Eau chaude sanitaire venant du ballon solaire avec un complément de
la chaudière au gaz pour être chauffée à au moins
55°C (pour tuer la légionellose).
Toutes les vannes motorisées
sont en 12V (23€ pièce)
: facilite l'installation, la commande, la sécurité. Inconvénient
: elle font un peu de bruit (mais cela me permet de savoir ce qu'il se passe
à l'oreille... elles ont toutes un bruit particulier, et un petit nom
que je ne vous dirai pas)
FONCTIONNEMENT DU CHAUFFAGE MAISON :
Je
veux avoir chaud dans la maison seulement lorsque c'est l'énergie solaire
--> donc pas question de chauffer le ballon avec la chaudière au gaz
(même si j'ai prévu cette possibilité avec un bouton dans
mon programme Arduino).
J'utilise 2 thermostats : un pour la chaudière gaz (réglé
à 18°C jour et 16°C nuit) et le deuxième pour le ballon
solaire (réglé à 24°C jour et 19°C nuit). On voit
donc que le ballon déclenche avant la chaudière.
L'idée est d'évacuer la chaleur du ballon le plus souvent
possible pour permettre au circulateur solaire de démarrer même
par temps peu ensoleillé (intérieur panneaux = 35°C env.).
Exemple : si j'ai le ballon à 45°C, il faut que l'eau dans les panneaux
solaires soit à plus de 48°C pour démarrer la circulation
solaire. Si j'ai le ballon à 25°C, il faut que l'eau des panneaux
soit à 28°C pour démarrer la circulation --> donc le système
démarre plus vite et je récupère plus de calories solaires.
A savoir aussi, le transfert des calories de l'eau qui circulent dans les serpentins
du ballon est plus efficace lorsqu'il y a une grosse différence de chaleur
(ex.: eau à 55°C venant des panneaux avec un ballon à 30°C).
La maison est en pierre avec, principalement, une isolation extérieure,
donc surchauffer la maison n'est pas perdu, cela chauffe les murs qui stockent
la chaleur.
Tout l'hiver, j'ai le bouton "mode 0" enclenché (radiateurs
sur chaudière gaz ou sur ballon solaire), et lorsque le haut du ballon
dépasse les 28°C, je bloque la chaudière gaz et son circulateur
(grâce à un relais en série), je place mes vannes correctement
et j'active le circulateur chauffage solaire.
Gestion de la vanne 3 voies chauffage (V7-V8) :
Le mieux est de regarder dans le programme.
En gros, j'alimente mes 2 vannes (qui forment la 3 voies) par des impulsions
plus ou moins longues.
Au démarrage, si la température de retour est < 18°C, la
température de départ vers les radiateurs est fixée à
25°C pendant env. 3mn (j'ai vu que la chaudière au gaz fait comme
ça. Je suppose que c'est pour éviter les chocs thermiques). Après,
lorsque le retour est plus grand que 18°C, la température de départ
vise 39°C. Au moment de faire cette partie du programme, j'ai essayé
de la faire en PID,
beaucoup trop compliqué pour moi, et je me suis aperçu qu'on pouvait
faire beaucoup plus simple.
A savoir aussi : j'ai fixé un fusible thermique réarmable de 40°C
sur le tuyau de départ qui coupe le circulateur chauffage (donc C2 ;
avec un branchement en série sur l'alim 220V). Si jamais mon programme
déconne ou qu'un relais reste collé, le circulateur s'éteindra.
Ca m'a sauvé une fois, lors de la fabrication du programme. Ce jour-là,
je me suis d'ailleurs rendu compte que même en arrêtant le circulateur
C2, l'eau chaude continuée à monter dans les étages par
thermosiphon... Il faut donc bien fermer systématiquement les vannes
qui font le lien avec le ballon. Il est conseillé aussi de mettre la
vanne 3 voies sur la partie chaude (ce que je n'ai pas fait
au début), de manière à bien bloquer l'eau qui monterait
par thermosiphon.
A l'usage, on a tendance à utiliser la télécommande/sonde solaire comme un bouton poussoir. C'est-à-dire que lorsqu'on voit que le lendemain il va y avoir du soleil, on met le chauffage solaire en route pour envoyer l'eau chaude dans les radiateurs afin de vider au maximum les calories du ballon solaire. Une fois sous 26°C, le chauffage solaire s'arrête (et la nuit aussi, pour éviter de faire du bruit). Le lendemain, comme la température du ballon est basse, le circulateur solaire démarrera plus vite et on récupérera plus tôt les calories solaires.
CIRCUIT POELE, serpentin :
J'en
parle, mais sachez tout de suite que cela ne marche pas ! J'ai
mis 10 mètres de tuyau de cuivre de 12mm de diamètre contre le
tube de sortie des fumées du poêle (en le collant fortement). Mais
essayer de récupérer des calories avec la chaleur des fumées,
et même, en se rapprochant le plus possible du poêle, ne produit
pas beaucoup d'eau chaude... Une meilleure solution serait le bouilleur, installé
dans la chambre de combustion du poêle !
Dans mon programme Arduino, comme le serpentin chauffe
très peu, je suis obligé d'arrêter le circulateur C3 toutes
les minutes, le temps que l'eau chauffe suffisamment... (et même : je
circule 30s, j'attends 3mn, je circule 30s, j'attends 3mn, etc. en fonction
de la vivacité du feu)
En moyenne, sur une chauffe (3-4 buches), je gagne 1°C sur le ballon
de 800L avec un départ à 15°C (retour à 25°C)
; et 0,5°C avec un départ à 23°C (retour à 32°C).
Plus le ballon est froid, plus le rendement monte légèrement.
Lorsque le bas du ballon est à plus de 35°C, le rendement tombe énormément.
Le delta devient même parfois négatif, donc il vaut mieux arrêter
d'utiliser le serpentin du poêle plutôt que de refroidir l'eau du
ballon...
Un jour, le circulateur n'a pas démarré (malgré le 220V
à ses bornes), ça a chauffé très fort, le multicouche
a fondu (il y a 2m de cuivre près du poêle, puis après du
multicouche qui tient à 95°C), fuite, j'ai vidé le circuit
rapidement sans danger (grâce aux robinets prévus à cet
effet), puis j'ai laissé tombé cette partie du système.
Je la laisse quand même dans mon programme Arduino, si ça peut
aider quelqu'un. Puis peut-être que je la réutiliserai lorsque
j'aurai un poêle bouilleur.
VASES D'EXPANSION :
Pour
le vase d'expansion du chauffage, le gros rouge de 150L, il est dimensionné
pour le cas où j'eusse installé 1500L de réserve. Avec
mon ballon de 800L, un vase d'expansion de 80L aurait suffi. Je règle
le circuit chauffage à 2 bars.
Pour
le branchement du vase d'expansion solaire, on l'éloigne fortement avec
un long tuyau (du 12mm, ca refroidit plus vite qu'un gros tuyau), ce qui le
protègera des surchauffes (jusqu'à 95°C !). Le circuit solaire
est à 2-3 bars.
Toujours
monter les circulateurs avec l'axe à l'HORIZONTALE et
en point bas (où il y a toujours de l'eau à pousser). Sur le circuit
solaire, il faut les mettre sur la partie la moins chaude (donc en pousser vers
les panneaux).
Au
dessus du vase d'expansion solaire, on voit les vannes V7 et V8 qui forment
la vanne 3 voies du chauffage, et son circulateur C2.
C3 et V9 sont pour le serpentin du poêle.
Sur
la station solaire, le gros cylindre de laiton à gauche de C1, c'est
un dégazeur qui récupère en continu l'air contenue
dans l'eau ; il faut le purger de temps en temps.
En
dessous de C1, il y a :
Un
débitmètre (avec robinets de remplissage/vidage du circuit
solaire) |
Juste en dessous, un autre débitmètre qu'utilise l'automate Arduino (jamais aucun problème, même lors de passage d'eau à 100°C) : |
REMPLISSAGE du circuit solaire :
NE
JAMAIS REMPLIR LES CAPTEURS LORSQU'ILS SONT CHAUDS (les chocs thermiques
pourraient casser les soudures). Le faire en soirée (en jours très
gris, on n'est pas à l'abri que le soleil apparaisse au moment du remplissage...).
Protocole : je ferme la vanne bleue (les thermomètres
sont aussi des vannes) afin de faire passer l'eau par le bas du ballon en premier
(et de chasser l'air des serpentins) ; V1 et V2 étant ouvertes. Au bout
d'un moment, lorsque les serpentins solaires sont remplis, j'ouvre la vanne/thermomètre
bleue, l'eau va monter dans les panneaux solaires.
J'utilise une pompe de camping car 12V (Shurflo), cela me permet de monter à 2-3 bars. Le vase d'expansion solaire est chargé à 2 bars (vide). |
Mon circuit solaire fait 55L (pour des tubes
de 22mm compter 0,314L /m + 2L par panneau) en théorie et 45L en pratique
(j'ai vidé en mettant dans des bidons de 20L).
J'ai utilisé un mélange concentré (MB444E),
donc à diluer avec de l'eau (c'est un peu moins cher 85euros/20L) plutôt
que du mélange déjà prêt (67euros/20L, donc 134€
pour 40L).
Il faut utiliser du glycol dit "alimentaire" : Mono Propylène
Glycol (MPG) = non toxique ; moins en tout cas.
(glycol "standard" dans les voitures :
Mono Ethylène Glycol (MEG) = toxique )
Le fluide anti-gel caramélise/durci au dessus de 180°C.
Rechargement : comme c'est souvent plus facile de mettre de l'eau du réseau de la ville (qui vous donne la pression) plutôt que de l'anti-gel avec une pompe, je conseille de mettre trop d'anti-gel au début. Au moins, si vous avez des fuites, vous n'aurez qu'à ajouter un peu d'eau.
Bien
penser à mettre des petits robinets purgeurs (à pointeau ou avec
joint EPDM) afin de chasser l'air lors du remplissage (donc aux points hauts)
et aussi vider le circuit correctement lors du vidage (donc aux points bas).
Les petits sont plus facile à isoler correctement.
Différents types de RACCORDS :
- Filasse (chanvre) : jusqu'à 140°C , mais pas bon avec glycol (suinte) et pas pour fortes pressions. Il y a plein de vidéos sur le web qui vous expliqueront comment faire : abimer le filetage avec une pince ou une lame de scie à métaux pour que la filasse ne glisse pas au serrage. Bien tendre la filasse et mettre la pâte (argile) à la fin (si vous la mettez au debut, vous augmentez les risques de glissement au serrage). Lorsque vous voyez que la filasse est repoussée par le vissage, il vaut mieux refaire le raccord.
- Téflon PTFE : jusqu'à 260°C. Pour que cela fonctionne bien, il faut en mettre beaucoup (jusqu'à ce qu'on ne distingue plus le filetage) et le tendre fortement. Il existe du téflon très épais (ça va plus vite à poser, on ne fait pas 36 000 tours). Convient bien avec le circuit solaire au glycol.
- Colles : (Loctite 577-542-266, GEB, Tangit, etc.) jusqu'à 225°C. Le problème des colles est qu'au moindre mouvement (choc, resserrage d'un raccord à côté, dilatation), ça casse et ça fuit...
--> Donc pour le circuit solaire, qui à cause de l'antigel crée beaucoup de fuites, utilisez plutôt du téflon PTFE (et mettre du frein filet sur les filetages pour ne pas qu'ils se desserrent avec les dilatations).
Différents types de JOINTS
: voir ici
ou ici
Réseau eau potable
|
EPDM |
Spécial gaz. On me les avait conseillés pour le circuit solaire, mais ils finissent par fuir légèrement (le glycol les attaque). |
Pour le circuit solaire avec glycol
(les autres joints fuient). |
EVITER LES RACCORDS A JOINT le plus possible. J'en ai actuellement 2 sur le circuit chauffage qui fuient légèrement, à un endroit où je dois vider tous les radiateurs pour réparer... (c'est un branchement juste avant une vanne..., pas de chance). Préférez des raccords olive ou les soudures brasées.
Pour le circuit solaire
: qui est soumis à de grosses différences de température
(de -5°C à 150°C...), les raccords vissés (olive, à
joints, etc.) ont tendance à se dévisser à la longue :
il faut mettre du frein filet ou colle (loctite, GEB, etc. résistant
à 200°C minimum) sur les 2 filetages. Pour démonter, si c'est
trop collé, chauffer le raccord au chalumeau. Evitez autant que possible
les raccords sur le circuit solaire et soudez à la brasure autodécapante
de cuivre (à faire dans un endroit aéré). Si vous
n'avez pas de chalumeau assez puissant, vous
pouvez utiliser 2 petits chalumeaux ensemble.
J'ai beaucoup de petites fuites qui réapparaissent avec les grosses chaleurs
notamment sur les raccords olive (pas trop ceux des panneaux Tinox LM...).
EFFET THERMOSIPHON :
Lorsque
c'est possible, l'idéal est d'avoir les panneaux au sol (facile
à installer, à réparer, à couvrir en cas de surchauffe)
et le ballon un peu au dessus.
Moi j'ai dû faire l'inverse et cela m'a causé beaucoup de problèmes
de thermosiphon. Grâce aux multiples sondes de température, je
me suis aperçu que je n'arrive pas à récupérer toute
la chaleur qui est au niveau haut des panneaux solaires. Souvent, j'ai env.
47°C en haut des panneaux et sur le conduit de retour chaud qui va vers
le ballon, je n'ai que 41°C. (voir
sur cet exemple)
En hiver, lorsque la cuve n'est pas très
chaude (30°C), un jour de très beau soleil, il faut parfois que je
maintienne un débit d'au moins 20L/mn pour réussir à descendre
les calories (ce qui augmente la consommation du circulateur). Plus j'ai la
cuve froide et les panneaux très chauds, plus l'effet thermosiphon se
fait et plus j'ai du mal à descendre l'eau chaude des panneaux vers le
ballon.
J'ai aussi eu de gros problèmes de thermosiphon avec le chauffage de
la maison : lorsque le ballon était très chaud (au dessus de 60°C),
à l'ouverture du circuit qui envoi l'eau chaude vers les radiateurs,
l'eau montait extrêmement vite (bien plus vite que le circulateur) et
mon système se mettait en sécurité (éteignant circulateur
C2, fermant v7, v8 et v4,v5,v6). J'ai corrigé en déplaçant
la vanne 8 sur la partie chaude (départ), avant elle était sur
le retour (partie froide).
DIVERSES NOTES :
La consommation
des circulateurs (15W par circulateur) est assez négligeable. Consommation
des circulateurs du 11/10/2018 au 22/02/2019 = 31KW (6KW/mois = 1€/mois)
Pour augmenter de 1°C un litre d'eau, il faut 1000 calories = 1,16 Wh
COUT TOTAL :
PANNEAUX |
4 panneaux solaires Roth d'occasion + frais pour aller les chercher | 450 |
3 panneaux solaires TINOX LM112 (à 350€ pièce sur solaire-diffusion) + frais de port | 1200 |
|
Visserie inox | 80 |
|
Cornières galvanisées pour fixer les panneaux sur façade maison et toit garage (12m en 40/40mm) | 500 |
|
7 raccords olive 18mm panneaux solaire-diffusion | 30 |
|
Sous
total = |
2260 |
|
CIRCULATEURS |
Station solaire (avec circulateur WILO 25/6-3p) neuve, leboncoin | 145 |
Circulateur pour circuit chauffage Grundfos UPS 25-60 180, occasion | 60 |
|
Circulateur Salmson pour serpentin autour du conduit poêle | 30 |
|
Sous
total = |
235 |
|
BALLON |
Ballon TWL hygiénique (5,8m², 29,1L), 2 serpentins acier (2,8m²+1,9m²), 800 L + frais de port | 1560 |
Anode magnésium en 3/4" | 22 |
|
Sous
total = |
1582 |
|
VASES |
Vase expansion pour circuit solaire 35L | 70 |
Vase d'expansion de 150L, pour stock chauffage (calculé pour 1500L) | 187 |
|
Vase d'expansion sanitaire 11L | 42 |
|
Sous
total = |
299 |
|
VANNES |
10 vannes 2 voies motorisées DN25 (23euros pièce) | 230 |
3 vannes 2 voies motorisées DN15 (15euros pièce) | 45 |
|
10 vannes classique 3/4" pour ballon, neuve | 50 |
|
Sous
total = |
325 |
|
TUYAUX
CUIVRE |
couronne de 20 mètres de cuivre recuit en 22mm pour liaison solaire, acheté d'occasion | 80 |
10 mètres de cuivre en 22mm pour liaison solaire | 65 |
|
10 mètres de cuivre de 22mm de récupération | 0 |
|
10 mètres de cuivre en 12mm pour serpentin autour conduit du poele | 36 |
|
10 mètres de cuivre de 18mm de récupération | 0 |
|
Sous
total = |
181 |
|
RACCORDS |
65 raccords divers en 22mm (coudes, T, prolongateurs), occasion | 27 |
Divers raccords cuivre, laiton, galva, inox, 2 purgeurs+vannes solaire, étain, téflon, joints, baguette | 600 |
|
Liquide solaire | 85 |
|
Sous
total = |
712 |
|
ARDUINO |
2 cartes Arduino Mega (à 8€ pièce, une de rechange), shields écran, ethernet, relais, 20 capteurs | 50 |
Sous
total = |
50 |
|
TOTAL
SOLAIRE = |
5644€ |
|
MURS
CHAUFFANTS |
300m de multicouche en 16mm (pour radiateurs mur chauffant ; compter 70m par mur de 5m de lar | 230 |
10 sacs de platre | 80 |
|
Placo hydrofuge, sacs de joint, tasseaux bas de gamme, etc. | 350 |
|
TOTAL
MURS CHAUFFANTS (env.
200€ / mur) = |
660
€ |
Au niveau du temps, c'est surtout de se former qui m'en a pris beaucoup (lectures, forums, etc.). Compter 1 semaine pour la plomberie ? Pour la partie programmation à l'Arduino, si vous êtes comme moi débutant, ça prend plusieurs mois. Mais maintenant, je fais toutes sortes d'applications (porte automatique poulailler, mangeoire, suiveur solaire, etc.) beaucoup plus rapidement.
AUTOMATISATION avec carte ARDUINO :
J'ai mis beaucoup de notes dans le programme
(voir plus bas) qui vous aideront à mieux comprendre.
Grâce à l'Arduino, je peux visualiser le fonctionnement de l'installation solaire de 3 manières :
- Le moniteur série du logiciel Arduino (il faut mettre un cable USB entre la carte Arduino et le PC) :
- Un afficheur dans le salon (c'est celui qu'on utilise le plus, très pratique de l'avoir à un endroit où l'on passe souvent):
- sur chaque ordinateur branché à la box ethernet, en tapant l'adresse 192.168.1.111 :
(A la période de l'impression d'écran,
il fait 0°C la nuit et 18°C le jour)
Théoriquement, je pourrais aussi donner l'accès
depuis internet, mais avec la livebox d'orange, ça ne marche pas (un
jour, si je change... ).
Je
n'ai pas fait de doigts de gant pour mettre les capteurs de température,
je les ai fixés avec du fil de cuivre, comme ci-dessous. Une fois le
tuyau bien isolé, la précision/réactivité me suffit,
même au niveau des panneaux solaires. Sur le schéma ci-dessus,
les températures sur les panneaux solaires ( "P6(cadre)" )
sont juste des capteurs vissés sur le cadre du panneau (sans isolation),
mais contrairement à ce qu'on pourrait croire, cela fonctionne assez
bien pour voir le panneau qui chauffe le plus. Le P6 et P7 sont toujours un
peu plus chaud, car il y a une serre avec un toit en verre qui reflète
le soleil.
|
Schéma de montage des capteurs de température sur le Arduino. Le DS18B20 permet d'avoir jusqu'à 128 petits capteurs en réseau avec 3 fils ! : |
Commande des vannes 12V (bleues, fermées/ouvertes par inversion de polarité) avec le Arduino :
|
Branchement de la sonde de lumière qui me sert surtout pour le contrôle de l'arrosage goutte à goutte des jardinières de la rue :
|
Le schéma de branchement de la sonde K
avec son convertisseur qui mesure les températures du poêle
(jusqu'à 1500°C !) . Puis, à droite, le schéma
du RTC, horloge de l'arduino. |
Valeurs des résistances à mettre pour les diodes témoins : |
Ci-dessus, les boutons du panneau :
1 - ON/OFF du système général
2 - permet de choisir entre : "Chaudière gaz chauffe radiateurs" - "0" (position neutre, c'est l'arduino qui choisi) - "Chaudière gaz chauffe le ballon"
3 - bouton activation du "goutte à goutte" des jardinières de la rue (système géré par le Arduino en fonction de l'ensoleillement)
4 - bouton "sèche-serviette de la salle de bain", ce qui alimente en priorité le sèche-serviette (même l'été). C'est juste une vanne mise en parallèle sur le robinet d'équilibrage qui fait que l'eau chaude passe plus facilement par le sèche-serviette et donc moins sur le reste du réseau de chauffage.
En haut : la carte
Arduino méga avec une carte ethernet par dessus.
Au milieu : la carte à relais de commande des vannes (on peut aussi utiliser des L293D, voir Terran sur forum) A gauche : les boutons dont je parle ci-dessus.
|
COMMANDES DES CIRCULATEURS
J'ai
fait un boitier très pratique qui me permet de mettre chaque circulateur
en marche forcée, en arrêt forcé
ou en mode automatique (mode contrôlé par l'Arduino).
En cas de problème, je peux ainsi éteindre ou allumer le circulateur
facilement. Il y a aussi des voyants 220v qui m'indique si le circulateur tourne.
![]() A gauche, on voit le radiateur du variateur que je vais démonter plus tard. |
Voici le schéma (pour un circulateur)
:
Côté Arduino, j'utilise un transistor
BC548 qui commande un petit relais 5V.
Pour le circulateur solaire "C1", il y a en plus
un variateur (ou "Dimmer", avec radiateur) comme celui-ci
, que je vais finalement abandonner. La variation de vitesse apporte peu d'avantage
(même si cela permet d'accélèrer régulièrement
le circulateur pour éviter l'effet laminaire) et le variateur me faisait
légèrement vibrer le circulateur en vitesse lente. En général,
tous les circulateurs sont sur la plus faible vitesse (pour avoir une faible
consommation). D'après mes observations, lorsque j'augmente la vitesse
de C1, je perds beaucoup en efficacité (le transfert de chaleur dans
le ballon et dans les panneaux se fait moins bien et le delta diminue beaucoup).
Le circulateur C1 est aussi protégé par le programme Arduino grâce
au capteur de débit : si le circulateur est allumé et que le débit
est nul, au bout de 5mn, le programme coupe le circulateur (et une petite alarme
retentit dans la maison).
Pour chaque circulateur, il y a un voyant (éteint ou allumé), un fusible (1A) et pour C2 et C3 un fusible thermique pour le cas où le circulateur chauffe parcequ'il ne peut pas circuler à cause d'une vanne fermée (fusible th fixé avec un fil de cuivre contre le corps du circulateur):
Fusible thermique autoréarmable
qui coupe le circuit électrique au dessus de 60°C. Il devrait y en avoir obligatoirement dans tous les moteurs vendus dans le commerce pour les sauver d'une surchauffe. |
|
![]() |
|
![]() |
LE PROGRAMME COMPLET :
Je
vous conseille de l'ouvrir dans le logiciel Arduino de votre PC, ce sera plus
lisible (il fait 40 pages, 2400 lignes). Il y a une carte mémoire sur
la carte ethernet de l'Arduino, que je n'utilise pas encore. Cela va permettre
de réaliser un "datalogger" qui mémorisera toute l'activité
du système (donc mémoriser la météo, l'ensoleillement,
l'énergie produite, etc.).
// Programme de gestion installation solaire thermique (eau chaude pour chauffage maison + eau chaude sanitaire) // Matthieu MONCEAUX, fevrier 2018 // Explications ici : http://mmonceaux.free.fr/solaire_thermique/ // // Je vous conseille d'avancer pas à pas votre projet, car il y a beaucoup de possibilités de problèmes entre périphériques (ethernet, // capteurs, etc.). Commencez très simple et ajouter petit à petit d'autres périphériques (en enregistrant sous un nouveau nom de // fichier à chaque fois, pour pouvoir revenir à l'état stable) // // Eviter les "while" car il y a des risques de blocage en restant dans la boucle, préférer les "if" // // if (10 < difference_temperature < 20) --> NE FONCTIONNE PAS // PREFERER : if (10 < difference_temperature and difference_temperature < 20) // // NE PAS FAIRE DES "delay" > 7s A CAUSE DU WATCHDOG (reset automatique en cas de plantage après 8s d'inactivité) // // Toujours essayer de réduire l'utilisation de la mémoire en mettant des variables appropriées (c'est mieux de le faire dès le début, // plutot que de devoir tout refaire à la fin car plus assez de mémoire...) // // ATTENTION, alimentation idéale de la carte ARDUINO = 6 à 7v (avec 12v, ça chauffe très fort) // // Utiliser "Serial.print(F("Hello World")) " plutot que Serial.print("Hello World") permet d'économiser un peu de mémoire // // ******************** // corrigé : thermo couple bloquer à cause de l'écran LCD -> conflit avec sonde K du poele (utilise 4,5,6) "Data Out Port SPI sur 4-5-6" // ******************** #include <SPI.h> // reseau communication SPI (ethernet, carte memoire SD, ) #include <Wire.h> // pour réseau I²C (horloge DS1307, capteur humiditee, etc.) #include <OneWire.h> // reseau capteur temperature DS18B20 #include "max6675.h" // si " " = inclure fichier local au projet : librairie du MAX6675 pour la sonde K du poele, max 1000°C #include <avr/wdt.h> // fonction WATCHDOG = reset du arduino s'il plante //#include <MemoryFree.h> -> permet de voir la memoire disponible avec la commande Serial.print("freeMemory()reports"); Serial.println(freeMemory()); // 8k sur arduino Mega et 2K sur UNO // Pour la sonde humidité (simple affichage, non indispensable dans le prog), j'ai eu de gros problèmes de conflit avec la carte Ethernet // (qui ne fonctionnait plus) et l'affichage en I2C. J'ai résolu ces problèmes en changeant de bibliothèque // Ne pas utiliser : "Adafruit_HTU21DF.h" et "HTU21D.h" #include "SparkFunHTU21D.h" // cette bibliothèque m'a résolu les problèmes //// Declaration capteur humidté HTU21 . ATTENTION : alimentation en 3,3V prise sur carte arduino HTU21D myHumidity; unsigned char humidite_cave; //float ? float temperature_cave; //float ? //// Declaration des variables, pour organiser la memoire de l'Arduino boolean arrosee = false; unsigned char dernier_arrosage = 0; const unsigned char broche_buzzer_cave = 29 ; // Broche d29 = alarme (buzzer) Surchauffe ballon const unsigned char broche_buzzer_poele = 28 ; // Broche d30 = alarme (buzzer) Surchauffe poele const unsigned char broche_ldr = 15 ; // Broche de mesure capteur lumiere LDR A15 // si 700< <800 --> nuageux. // nuit = 15 // Nuit de pleine lune = 0,5 lux // Rue de nuit bien éclairée = 20 à 70 luxl // Local de vie = 100 à 200 lux // Appartement bien éclairé = 200 à 400 lux // Local de travail = 200 à 3 000 lux // Stade de nuit = 150 à 1 500 lux // Extérieur par ciel couvert = 500 à 25 000 lux // Extérieur en plein soleil = 50 000 à 100 000 lux boolean ete; boolean alarm1; // probleme circulateur panneaux solaire qui ne tourne pas alors qu'allumé boolean alarm2; // surchauffe ballon boolean alarm3; // surchauffe poele boolean alarm4; // erreur lecture des températures boolean alarm5; // gel dans les panneaux solaires unsigned char mois_demarrage, jour_demarrage, heure_demarrage, minute_demarrage; //// SOLAIRE const unsigned char consigne_solaire = 2; // C1 démarre si (température du panneau 2 > température bas ballon + consigne_solaire) const char consigne_demarrage_circu_antigel = -7; // C1 démarre si température panneau 3 < consigne_demarrage_circu_antigel unsigned int cycle_demarrage_solaire = 0; boolean etatC1; boolean etatC2; boolean mode_gel = 0; int delta_panneaux_ballon_milieu; float delta_chd_frd_station; float delta_stratification; boolean serpentin_haut = 1; boolean solaire_chauffe_ballon = 0; float wh = 0; // puissance, débitmètre float ballon_temp_moy; // somme des T°C ballon divisée par 3, donne la température totale du ballon sans stratification unsigned int broche_sonde_pt100 = A11; // sonde pt100 qui se trouve dans le panneau n°2 unsigned int valeur_sonde_pt100; // valeur brut affichee sur l'arduino unsigned int valeur_sonde_pt100_corrigee; unsigned int valeur_sonde_pt100_precedente = 260; // valeur à env. 10°C pour éviter une alarme au reset de l'arduino unsigned int valeur_sonde_pt100_precedente1 = 260; // valeur à env. 10°C pour éviter une alarme au reset de l'arduino unsigned int temperature_sonde_pt100 = 0; // valeur calculee en °C boolean v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12; //// EAU CHAUDE const unsigned char consigne_eau_chaude = 44; // valeur T°C haut du ballon en dessous de laquelle on démarre la chaudiere gaz pour // complémenter l'eau chaude sanitaire. //// POELE const unsigned char thermoDO = 34; // Data Out Port SPI sur 4-5-6, thermocouple SERPENTIN Peole ---> mais conflit avec shield LCD+boutons const unsigned char thermoCS = 35; //Chip Select, thermocouple SERPENTIN Peole const unsigned char thermoCLK = 33; //Clock, thermocouple SERPENTIN Peole MAX6675 thermocouple(thermoCLK, thermoCS, thermoDO); // Déclaration des pins utilisées pour thermocouple serpentin poele (communication SPI) float delta_poele; boolean c3_tourne = 0; // circulateur C3 allumer = 1 , éteint = 0 unsigned long duree_allumage_c3 = 250000; /// CHAUFFAGE const unsigned char heure_seche_serviette_matin = 7; const unsigned char heure_seche_serviette_soir = 21; boolean chauffer_sechoir = false; const unsigned char broche_gaz_on_off = 25 ; // relais d'allumage chaudiere const unsigned char broche_gaz_circulateur = 27 ; // relais pour bloquer le circulateur chaudiere boolean relais_gaz; // lit l'etat du relais on/off chaudière gaz unsigned char temperature_eau_visee_de_chauffe = 39; // VOIR DANS LA PARTIE CHAUFFAGE : on la change au démarrage du cycle de chauffe pour // éviter les chocs thermiques dans les murs chauffants. boolean demarrage_seche_serviette; unsigned int ldr; // capteur de lumiere, au sud unsigned char mode = 0; // mode0=BallonSolaire ou Gaz sur Radiateurs, mode1=Gaz sur radiateurs, mode2=Gaz sur BallonSolaire, mode3=Poele, // mode4=BallonSolaire sur Radiateurs. unsigned char etat_bouton_gaz_precedent = 5; // on oblige à relire l'intérieur des "if" des boutons int j; // pour poele boolean eau_par_gaz = 1; // = 1 si l'eau passe par la chaudiere au gaz, sinon = 0 unsigned int eau_par_gaz_compteur = 0; boolean thermostat_chauffage_solaire; unsigned int cycle_chauffage = 0; boolean circulateur_C2_en_pause = 0; float delta_chauffage; float consigne_delta_chauffage; float temperature_precedente; float gain_temperature_chauffage; int difference_consigne; unsigned int temps_ouverture_vanne_v8v7; int position_v8; int position_v8_degre; boolean mode_degommage = 0; // mode qui débloque les circulateurs 1 fois par jour const unsigned char broche_vanne_goute_a_goutte = 39 ; //// Commandes Circulateurs C1 et C3 const unsigned char broche_relais_C1 = 22 ; const unsigned char broche_relais_C2 = 23 ; const unsigned char broche_relais_C3 = 24 ; unsigned char AC_LOAD_c1 = 17; // PWM = Output to Opto Triac pin unsigned char dimming_c1 = 25; // 0=OFF ou entre 25(rapide) et 55(lent) //// LECTURE DES BOUTONS/INTERRUPTEURS int lecture_bouton_gaz; // entrée analogique A14 int lecture_bouton_goutte_a_goutte; // entrée analogique A13 int lecture_bouton_4; // entrée analogique A12 boolean bouton_gaz = 0; // etat du bouton "gaz" boolean bouton_goutte_a_goutte = 0; // etat du bouton "goutte à goutte" boolean bouton_4; // état du "bouton 4" = seche serviette de la salle de bain (a chauffer meme en été) //// DEBITMETRE volatile unsigned long firstPulseTime; volatile unsigned long lastPulseTime; volatile unsigned long numPulses; unsigned long currentMilis; unsigned long lastMilis = 0; float F; float debit; unsigned char temps = 2000 ;// durée de la mesure en ms //// CAPTEURS TEMPERATURE DS18B20 (temp = -55 à 125°C, 128 capteurs max sur le réseau, alim=3v à 5,5v)(PT1000 = -50°C à 450°C) // Prendre du cable blindé et éviter les cablages en étoile, cela crée des problèmes de lecture // si ça ne fonctionne pas, essayer de changer la résistance (entre +5V et data) de 4,7KOhms (mettre par ex 2,2KO) // bien récupérer les adresses des capteurs un à un avant de les brancher en réseau // pour trouver facilement un capteur défaillant, faire plusieurs réseaux, plutot qu'un seul const byte BROCHE_ONEWIRE_toit = 31; //broche du réseau de capteur DS18B20 const byte BROCHE_ONEWIRE_ballon = 30; //broche du réseau de capteur DS18B20 float temperature[29]; // nombre de float = 29 capteurs de température int i; const byte SENSOR_ADDRESS_0[] = {0x28, 0xFF, 0xF1, 0x01, 0x8B, 0x16, 0x03, 0xAB};// = en haut du serpentin solaire bas const byte SENSOR_ADDRESS_1[] = {0x28, 0xFF, 0x06, 0x52, 0xA3, 0x16, 0x03, 0xBD};// = corps panneau 3 const byte SENSOR_ADDRESS_2[] = {0x28, 0xFF, 0x61, 0x95, 0x71, 0x17, 0x03, 0xD0};// = tuyau après panneau 1 et 2 const byte SENSOR_ADDRESS_3[] = {0x28, 0xFF, 0x8F, 0x2F, 0xA2, 0x16, 0x04, 0x98};// = corps panneau 2 const byte SENSOR_ADDRESS_4[] = {0x28, 0xFF, 0x80, 0xA9, 0xA2, 0x16, 0x05, 0x79};// = tuyau après panneau 1 const byte SENSOR_ADDRESS_5[] = {0x28, 0xFF, 0x61, 0x01, 0x71, 0x14, 0x04, 0xE9};// = corps panneau 1 const byte SENSOR_ADDRESS_6[] = {0x28, 0xFF, 0x3C, 0xC9, 0x70, 0x14, 0x04, 0x1E};// = tuyau panneau 4, 5, 6 et 7 const byte SENSOR_ADDRESS_7[] = {0x28, 0xFF, 0x05, 0x14, 0x71, 0x14, 0x04, 0x5E};// = corps panneau 4 const byte SENSOR_ADDRESS_8[] = {0x28, 0xFF, 0x5F, 0xC8, 0x70, 0x14, 0x04, 0xCE};// = corps panneau 5 const byte SENSOR_ADDRESS_9[] = {0x28, 0xFF, 0x69, 0x51, 0xA3, 0x16, 0x05, 0x96};// = corps panneau 6 const byte SENSOR_ADDRESS_10[] = {0x28, 0xFF, 0x66, 0x14, 0x71, 0x14, 0x04, 0x01};// = tuyau panneau 6 et 7 const byte SENSOR_ADDRESS_11[] = {0x28, 0xFF, 0x28, 0x70, 0x71, 0x14, 0x04, 0xD4};// = corps panneau 7 const byte SENSOR_ADDRESS_12[] = {0x28, 0xFF, 0x46, 0xC9, 0x6C, 0x14, 0x03, 0xBC};// = eau froide rue const byte SENSOR_ADDRESS_13[] = {0x28, 0xFF, 0x5E, 0x88, 0x71, 0x14, 0x04, 0x48};// = départ bidon récup eau douche const byte SENSOR_ADDRESS_14[] = {0x28, 0xFF, 0xB0, 0x13, 0x71, 0x14, 0x04, 0x45};// const byte SENSOR_ADDRESS_15[] = {0x28, 0xFF, 0x91, 0x02, 0x71, 0x14, 0x04, 0xC7};// const byte SENSOR_ADDRESS_16[] = {0x28, 0xFF, 0x4E, 0x02, 0x71, 0x14, 0x04, 0xF6};// = retour Chd panneaux facade const byte SENSOR_ADDRESS_17[] = {0x28, 0xFF, 0x79, 0x13, 0x71, 0x14, 0x04, 0x94};// = retour Chd panneaux garage const byte SENSOR_ADDRESS_18[] = {0x28, 0xFF, 0x30, 0x02, 0x71, 0x14, 0x04, 0x39};// = station arrivée chaud solaire const byte SENSOR_ADDRESS_19[] = {0x28, 0xFF, 0xC6, 0xFB, 0x70, 0x14, 0x04, 0x4A};// = station depart froid solaire const byte SENSOR_ADDRESS_20[] = {0x28, 0xFF, 0x24, 0x14, 0x71, 0x14, 0x04, 0x6B};// = C2 retour mur chauffant const byte SENSOR_ADDRESS_21[] = {0x28, 0xFF, 0x1F, 0x8A, 0x71, 0x14, 0x04, 0x6B};// = puits //const byte SENSOR_ADDRESS_21[] = {0x28, 0xFF, 0x60, 0x84, 0x71, 0x17, 0x03, 0xAA}; // ? const byte SENSOR_ADDRESS_22[] = {0x28, 0xFF, 0x27, 0x80, 0x2D, 0x04, 0x00, 0x87};// = Salle Bain Etage const byte SENSOR_ADDRESS_23[] = {0x28, 0xFF, 0x4C, 0xE1, 0x70, 0x14, 0x04, 0x1F};// = Milieu ballon const byte SENSOR_ADDRESS_24[] = {0x28, 0xFF, 0x4B, 0x02, 0x71, 0x14, 0x04, 0x24};// = Haut ballon const byte SENSOR_ADDRESS_25[] = {0x28, 0xFF, 0x1A, 0x95, 0x71, 0x17, 0x03, 0xCD};// = Bas ballon const byte SENSOR_ADDRESS_26[] = {0x28, 0xFF, 0x9E, 0xC4, 0x71, 0x17, 0x03, 0x4E};// = arrivé/départ vannes de startification (et vers mur chauffant) const byte SENSOR_ADDRESS_27[] = {0x28, 0xFF, 0xE4, 0x4D, 0x71, 0x17, 0x03, 0xD4};// = Salon (avec résistance de 33K, sinon, ne fonctionne pas) const byte SENSOR_ADDRESS_28[] = {0x28, 0xFF, 0x60, 0x84, 0x71, 0x17, 0x03, 0xAA};// = depart chauffage solaire OneWire ds(BROCHE_ONEWIRE_toit); // Création de l'objet OneWire pour manipuler le bus 1-Wire, pour capteur température en réseau OneWire ds2(BROCHE_ONEWIRE_ballon); // Création de l'objet OneWire pour manipuler le bus 1-Wire, pour capteur température en réseau ///// HORLOGE avec DS3231, en I2C (broche SDA-20 et SCL-21 de arduino Mega) à l'adresse 0x68 // Mon horloge a tendance à perdre 1 à 2 mn par mois. Prenez-en une bonne... #include <DS1307new.h> int I2C_DS3232 = 0xD0 >> 1; byte DS3232control = 0b00011100, DS3232status = 0b11001000 , DS3232aging , DS3232Msb , DS3232Lsb; uint16_t startAddr = 0x0000; // Adresse de démarrage Start dans NV-RAM uint16_t lastAddr; // Nelle addresse des stockage NV-RAM uint16_t TimeIsSet = 0xaa55; // Prévient qu'il n'y a pas de remise à l'heure #define DDS_LOAD 12 //FQ_UD // DDS/Arduino Connections, SCL= broche SCL21 (pour Mega) ou pin A5, SD= broche SDA20 (pour Mega) ou pin A4 #define DDS_CLOCK 3 #define DDS_DATA 2 // int Select; unsigned char Heure; unsigned char Minute; unsigned char Seconde; unsigned char Jour; unsigned char Mois; unsigned int Annee; ///// HORLOGE avec DS3231 //// DECLARATION ETHERNET Connecteur ICSP obligatoire; broche D4(lecteurSD), D10(ethernet), D11,D12,D13, // Sur arduino Mega : garder broche 50 à 53 libres pour carte ethernet //#include <SPI.h> // déjà en debut de programme #include <Ethernet.h> //MAC addr of Ethernet Shield byte mac[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }; //Linksys Router default IP address is 192.168.1.1 byte ip[] = { 192, 168, 1, 111 }; // P1 --> { 10, 1, 1, 5 }; EthernetServer server(80); // port 80 is default for HTTP. Can use 8080 or 8081 also //EthernetServer server = EthernetServer(80); // DECLARATION carte mémoire SD utilise broche D4 #include <SD.h> // pour carte SD File monFichier; //// DECLARATION LCD 20*4 HD44780 sur l'adresse 0x27 du I2C (broche SDA-20 et SCL-21 de arduino Mega) #include <LiquidCrystal_I2C.h> // Set the pins on the I2C chip used for LCD connections: // addr, en,rw,rs,d4,d5,d6,d7,bl,blpol LiquidCrystal_I2C lcd(0x27, 2, 1, 0, 4, 5, 6, 7, 3, POSITIVE); // Set the LCD I2C address MOST use address 0x27, a FEW use 0x3F //*** LiquidCrystal_I2C lcd(0x20, 2, 1, 0, 4, 5, 6, 7, 3, POSITIVE); // pour le 2eme afficheur, souder les 3 bornes de config adresse //-------------------------------- Fin Déclarations des variables --------------------------------------------------- //-------------------------------- Fin Déclarations des variables --------------------------------------------------- //// Fonction DEMARRER PRISE DE MESURE capteur température DS18B20. void startTemperatureMeasure(const byte addr[]) { // addr[] : Adresse du module 1-Wire détecté ds.reset(); // Reset le bus 1-Wire et sélectionne le capteur ds.select(addr); // selection de l'adresse ds.write(0x44, 1); } // commande 0x44 = Lance une prise de mesure et attend la fin de la mesure */ //// Fonction RECUPERATION VALEUR DE MESURE capteur température DS18B20. float readTemperatureMeasure(const byte addr[]) { byte data[9]; // data[] : Données lues depuis le scratchpad addr[] : Adresse du module 1-Wire détecté ds.reset();// Reset le bus 1-Wire, sélectionne le capteur et envoie une demande de lecture du scratchpad ds.select(addr); ds.write(0xBE); for (byte i = 0; i < 9; i++) { data[i] = ds.read(); // Lecture du scratchpad } return ((data[1] << 8) | data[0]) * 0.0625; } // Calcul de la température en degré Celsius //// Fonction DEMARRER PRISE DE MESURE capteur température DS18B20. void startTemperatureMeasure2(const byte addr[]) { // addr[] : Adresse du module 1-Wire détecté ds2.reset(); // Reset le bus 1-Wire et sélectionne le capteur ds2.select(addr); // selection de l'adresse ds2.write(0x44, 1); } // commande 0x44 = Lance une prise de mesure et attend la fin de la mesure */ //// Fonction RECUPERATION VALEUR DE MESURE capteur température DS18B20. float readTemperatureMeasure2(const byte addr[]) { byte data[9]; // data[] : Données lues depuis le scratchpad addr[] : Adresse du module 1-Wire détecté ds2.reset();// Reset le bus 1-Wire, sélectionne le capteur et envoie une demande de lecture du scratchpad ds2.select(addr); ds2.write(0xBE); for (byte i = 0; i < 9; i++) { data[i] = ds2.read(); // Lecture du scratchpad } return ((data[1] << 8) | data[0]) * 0.0625; } // Calcul de la température en degré Celsius //// FIN Fonction RECUPERATION VALEUR DE MESURE capteur température DS18B20. //// Fonction ERREUR_LECTURE_ETEINDRE_CIRCULATEURS, seulement pour chauffage Circulateur C2 //// Eteint les circulateurs pour ne pas qu'ils chauffent s'il y a une erreur (large) de lecture des capteurs de température void erreur_lecture_eteindre_circulateurs() { etatC1 = digitalRead(broche_relais_C1); etatC2 = digitalRead(broche_relais_C2); if (temperature[25] < 5 and (etatC1 == 1 or etatC2 == 1)) //--> probleme, éteindre C1 et C2, + buzzer { digitalWrite(broche_relais_C2, LOW); // ne jamais eteindre C1 pour eviter les surchauffes solaires. Le poele se passe de sonde DS18B20 // ALARM : 1 bips= prob px solaire, 2 = surchauff ballon/murs chauffants, 3 = surchauff poele, 4 = prob temperature, 5 = gele Panneaux alarm4 = true; for (j = 0; j <= 3; j++) { tone(broche_buzzer_cave, 700, 200); //(pin, frequency, duration) delay(250); noTone(broche_buzzer_cave); } } else { alarm4 = false; } } //// FIN Fonction erreur_lecture_eteindre_circulateurs //// Fonction SOLAIRE_ANTI-GEL //// Faire tourner l'eau à haute vitesse pour éviter le gel dans les panneaux void solaire_anti_gel() { if (mode_gel == 0 and temperature[1] <= consigne_demarrage_circu_antigel) // consigne_demarrage_circu_antigel = -10 env. { mode_gel = 1; digitalWrite(32, LOW); // fermer V1 et ouvrir V3 pour circuler en dehors du ballon digitalWrite(broche_relais_C1, HIGH); // allumer circulateur } if (mode_gel == 1 and temperature[2] < consigne_demarrage_circu_antigel - 5 and temperature[2] != -0.06) { // si T°C -5°C en dessous de la consigne antigel : sonner l'alarm et circuler avec eau du ballon digitalWrite(32, HIGH); // fermer V3 et ouvrir V1 pour faire rentrer l'eau dans la ballon et réchauffer l'eau des panneaux digitalWrite(broche_relais_C1, HIGH); // allumer circulateur // ALARM : 1 bips= prob px solaire, 2 = surchauff ballon/murs chauffants, 3 = surchauff poele, 4 = prob temperature, 5 = gele Panneaux alarm5 = true; for (i = 0; i < 5; i++) { tone(broche_buzzer_cave, 800, 250); //(pin, frequency, duration) delay(150); noTone(broche_buzzer_cave); tone(broche_buzzer_poele, 800, 250); delay(150); noTone(broche_buzzer_poele); } } else { alarm5 = false; } if (mode_gel == 1 and temperature[2] > consigne_demarrage_circu_antigel) { mode_gel = 0; digitalWrite(broche_relais_C1, LOW); // éteindre circulateur digitalWrite(32, LOW); // ouvrir V3 et fermer V1 pour ne pas faire rentrer l'eau dans le ballon } } //// FIN Fonction solaire_antigel /* //// Fonction POELE : mesure et démarrage circulateur poele // Finalement, comme le serpentin chauffe tres peu, je suis obligé d'arreter le circulateur serpentin 1mn, // le temps que l'eau chauffe suffisamment, puis de le rallumer juste 30s, le temps de renouveler l'eau du serpentin. // J'ai essayé de ralentir le circulateur et limiter au maximum le débit, mais cela ne chauffait pas encore assez. // Puis j'ai l'impression qu'avec une circulation extrement lente en continu, on n'arrive plus à extraire les calories, // on a un régime laminaire. // Amélioration : prendre la température en direct dans le serpentin et démarrer le circulateur serpentin poele quand eau assez chaude ? // --> oblige à avoir deux sondes (une "poele démarré" et une "eau" entre 13 et 70°C), n'apporte pas bcp plus de calorie. // Cela restera toujours un serpentin sur les fumées... Mais on peut améliorer en mettant une tole autour du serpentin // En moyenne, sur une chauffe (3-4 buches), je gagne 1°C sur le ballon de 800L avec un départ à 15°C (retour à 25°C), // et 0,5°C avec un départ à 23°C (retour à 32°C)... // Le problème est qu'il faut vider le circuit de tuyau à 13°C (dans la cave) avant d'avoir enfin le retour à 30°C... // Lorsque le bas du ballon est à plus de 35°C, le rendement tombe énormément, le delta devient négatif, voir = 1, donc il vaut mieux // arrêter d'utiliser le serpentin... // 28/2/18: le circulateur n'a pas démarré (malgré le 220V à ses bornes), ça chauffait très fort, le multicouche a fondu, fuite, // j'ai vidé le circuit rapidement sans danger void poele() { Serial.println(" "); Serial.print(F("POELE = ")); Serial.print(thermocouple.readCelsius()); delta_poele = temperature[26] - temperature[25]; Serial.print(F(" C3=")); Serial.print(c3_tourne); Serial.print(F(" Retour_T26=")); Serial.print(temperature[26], 2); Serial.print(F(" D_T26-T25=")); Serial.print(delta_poele); Serial.print(F(" Duree_Allum=")); Serial.print(duree_allumage_c3); Serial.print(F(" ")); // VITESSE CIRCULATEUR=3. Bien pour ballon à 30°C, mais PROBLEME : si ballon est à 40°C ? retour négatif ? if (temperature[24] <= 35) // si haut du ballon solaire >= 35°C { if (thermocouple.readCelsius() >= 180) { duree_allumage_c3 = 120000 ; // 120000ms=120s/60=2min } if (thermocouple.readCelsius() < 180 and thermocouple.readCelsius() >= 160) { duree_allumage_c3 = 150000 ; } if (thermocouple.readCelsius() < 160 and thermocouple.readCelsius() >= 120) { duree_allumage_c3 = 250000 ; } if (thermocouple.readCelsius() < 120 and thermocouple.readCelsius() >= 60) { duree_allumage_c3 = 350000 ; } } else // temperature[24]> 35°C { if (thermocouple.readCelsius() >= 180) { duree_allumage_c3 = 250000 ; // 120000ms=120s/60=2min } if (thermocouple.readCelsius() < 180 and thermocouple.readCelsius() >= 160) { duree_allumage_c3 = 350000 ; } if (thermocouple.readCelsius() < 160 and thermocouple.readCelsius() >= 120) { duree_allumage_c3 = 400000 ; } if (thermocouple.readCelsius() < 120 and thermocouple.readCelsius() >= 60) { duree_allumage_c3 = 999999999 ; // le retour devient négatif --> ne plus faire tourner le circulateur } } if (thermocouple.readCelsius() >= 70) // garder une valeur d'hystérésis, pour éviter que les vannes basculent sans arret durant // une prise de décision et une variation de la sonde. { mode = 3; // mode0=BallonSolaire ou Gaz sur Radiateurs, mode1=Gaz sur radiateurs, mode2=Gaz sur BallonSolaire, mode3=Poele, // mode4=BallonSolaire sur Radiateurs. digitalWrite(broche_relais_C2, LOW); // éteindre circulateur chauffage solaire s'il était en marche. digitalWrite(45, HIGH); // alim vanne 7 et vanne 8 digitalWrite(46, HIGH); // FERMER Vanne 7 si chaudière en marche digitalWrite(47, HIGH); // FERMER vanne 8 pour poele, et aussi si chaudière en marche digitalWrite(36, LOW); //ouvrir vanne9 static unsigned long previousMillis2 = 0; // Temps de la précédente mesure et actuel, LAISSER LE "static" unsigned long currentMillis2 = millis(); // millis() est une fonction qui donne le temps du Arduino depuis son démarrage if ((currentMillis2 - previousMillis2) >= duree_allumage_c3) // 120000-30000 = TEMPS ENTRE CHAQUE DEMARRAGE CIRCULATEUR { // il faut 60s au poele pour chauffer l'eau de 13°C à 45°C --> REDUIRE un peu le tps car si l'eau d'entrée est à 30°C... // à ballon haut=25,7, après 5 buches, ballon = 25,8°C ! previousMillis2 = currentMillis2; digitalWrite(broche_relais_C3, HIGH); // allumer circulteur C3. Il y a une diode en parallèle positionnée sous le poele. c3_tourne = 1; digitalWrite(broche_buzzer_poele, HIGH); // faire un petit bruit dans le buzzer pour signaler la mise en marche digitalWrite(broche_buzzer_cave, HIGH); // faire un petit bruit dans le buzzer pour signaler la mise en marche delay(100); digitalWrite(broche_buzzer_poele, LOW); digitalWrite(broche_buzzer_cave, LOW); } if (c3_tourne == 1 and (currentMillis2 - 15000 >= previousMillis2)) // éteint circulateur x millisecondes apres { // il faut 30 secondes au circulateur pour vider le serpentin (vitesse 1 et robinet grand ouvert) // 15 secondes en vitesse 2, qui évite l'effet laminère et thermosiphon // 15 secondes en vitesse 3, qui évite l'effet laminère et thermosiphon c3_tourne = 0; digitalWrite(broche_relais_C3, LOW); // éteindre circulteur C3 digitalWrite(broche_buzzer_poele, HIGH); // faire un petit bruit dans le buzzer pour signaler la mise à l'arret digitalWrite(broche_buzzer_cave, HIGH); // faire un petit bruit dans le buzzer pour signaler la mise à l'arret delay(200); digitalWrite(broche_buzzer_poele, LOW); digitalWrite(broche_buzzer_cave, LOW); } //**** A REMETTRE SI CIRCULATEUR NE BLOQUE PAS AU DEMARRAGE : stratification(); // envoi l'eau à la bonne hauteur dans le ballon. } if (thermocouple.readCelsius() < 60 and mode == 3) // Le "and mode==3" permet d'éviter le retour dans ce "if" par la suite { static unsigned long previousMillis4 = 0; // Temps de la précédente mesure et actuel, LAISSER LE "static" unsigned long currentMillis4 = millis(); // millis() est une fonction qui donne le temps du Arduino depuis son démarrage if (currentMillis4 - previousMillis4 >= 300000) // lit la suite seulement toutes les x millisecondes { // délais de x millisecondes sans bloquer le programme et pour éviter les variations du capteur previousMillis4 = currentMillis4; digitalWrite(broche_relais_C3, LOW); // éteindre circulteur C3 digitalWrite(42, LOW); // Vanne 10, ouverte pour laisser la chaudiere gaz digitalWrite(37, LOW); // Vanne 11, ouverte pour laisser la chaudiere gaz digitalWrite(48, HIGH); // Fermer Vanne 4 digitalWrite(49, HIGH); // Fermer Vanne 5 digitalWrite(38, HIGH); // Fermer Vanne 6 digitalWrite(36, HIGH); // Fermer Vanne 9 digitalWrite(45, HIGH); // Alim des doubles vannes 7-8 digitalWrite(46, HIGH); // vanne 7 fermee digitalWrite(47, HIGH); // Vanne 8 fermee //digitalWrite(broche_gaz_circulateur, LOW); // activer la circulation de la chaudière (un relais branché en série sur le circulateur) c3_tourne = 0; mode = 0; // mode=0 signifie qu'on rend la main à une autre fonction, comme les interrupteurs, qui sélectionnent un autre mode } } } //// Fin Fonction POELE */ //// Fonction DEBITMETRE void isr() { unsigned long now = micros(); // now = number of microseconds since the Arduino board began running the current program if (numPulses == 1) { firstPulseTime = now; } else { lastPulseTime = now; } ++numPulses; } //// Fin fonction DEBITMETRE //// Fonction CIRCULATEUR solaire, variateur void zero_crosss_int_c1() // function to be fired at the zero crossing to dim the light { int dimtime_c1 = (100 * dimming_c1); // For 60Hz =>65 delayMicroseconds(dimtime_c1); // Off cycle digitalWrite(AC_LOAD_c1, HIGH); // triac firing delayMicroseconds(10); // triac On propogation delay (for 60Hz use 8.33) digitalWrite(AC_LOAD_c1, LOW); // triac Off } //// Fin fonction CIRCULATEUR solaire, variateur //// Fonction DEGOMMAGE_CIRCULATEURS // Allumer tous les circulateurs, à fond, 10 secondes pour les débloquer, de préférence le matin à 8h (fonction anti-gel) // pas la peine d'ouvrir les vannes, en 10 secondes les circulateurs n'ont pas le temps de chauffer void degommage_circulateurs_vannes() { if (Heure == 8 and Minute == 30 and Seconde < 15) { mode_degommage = 1; digitalWrite(broche_relais_C1, HIGH); // allumer circulateur digitalWrite(broche_relais_C2, HIGH); // allumer circulateur digitalWrite(broche_relais_C3, HIGH); // allumer circulateur } else if (mode_degommage == 1) { mode_degommage = 0; digitalWrite(broche_relais_C1, LOW); // éteindre circulateur digitalWrite(broche_relais_C2, LOW); // éteindre circulateur digitalWrite(broche_relais_C3, LOW); // éteindre circulateur } } //// fin Fonction DEGOMMAGE_CIRCULATEURS //// Fonction STRATIFICATION : envoi/prend l'eau au bon endroit dans le ballon en fonction du capteur de T°C n°26 positionné en sortie void stratification() { static unsigned long previousMillis = 0; // Temps de la précédente mesure et actuel, LAISSER LE "static" unsigned long currentMillis = millis(); // millis() est une fonction qui donne le temps du Arduino depuis son démarrage if (currentMillis - previousMillis >= 10000) // lit la suite seulement toutes les 10 secondes pour ne pas bouger sans arret les vannes { // délais de 5 secondes sans bloquer le programme previousMillis = currentMillis; if (temperature[26] > temperature[24]) // // Si T26 > T21 --> ouvrir V4-48, fermer V5-49, V6-38 { digitalWrite(48, LOW); // toujours ouvrir avant de fermer, pour ne pas bloquer le circulateur digitalWrite(49, HIGH); digitalWrite(38, HIGH); Serial.print(F(" Vers Haut Ballon ")); } if (temperature[26] <= temperature[24] and temperature[26] > temperature[23]) { digitalWrite(49, LOW); // toujours ouvrir avant de fermer, pour ne pas bloquer le circulateur digitalWrite(48, HIGH); digitalWrite(38, HIGH); Serial.print(F(" Vers Milieu Ballon ")); } if (temperature[26] <= temperature[23]) // "-0.06" = capteur déconnecté or (temperature[26] == -0.06) { digitalWrite(38, LOW); // toujours ouvrir avant de fermer, pour ne pas bloquer le circulateur digitalWrite(48, HIGH); digitalWrite(49, HIGH); Serial.print(F(" Vers Bas Ballon ")); } } } //// Fin STRATIFICATION //// Fonction ALARM surchauffe BALLON (buzzer entre la masse et D29) const int broche_buzzer_cave = 29 ; void alarm_ballon() { // ALARM : 1 bips= prob px solaire, 2 = surchauff ballon/murs chauffants, 3 = surchauff poele, 4 = prob temperature, 5 = gele Panneaux if (temperature[25] > 80) // si température haut ballon > 85°C { Serial.print(F(" ALARM SURCHAUFFE BALLON")); Serial.print(temperature[25]); Serial.print(F(" ")); alarm2 = true; for (j = 0; j <= 1; j++) { tone(broche_buzzer_cave, 500, 250); //(pin, frequency, duration) delay(130); noTone(broche_buzzer_cave); tone(broche_buzzer_poele, 500, 250); //(pin, frequency, duration) delay(130); noTone(broche_buzzer_poele); } } else { alarm2 = false; } } //// Fin Fonction ALARM BALLON /* //// Fonction TEST ALARM void test_alarm() if () // si bouton test alarmes enfoncé { alarm1 = true; // probleme circulateur panneaux solaire qui ne tourne pas alors qu'allumé for (i = 0; i < 5; i++) { tone(broche_buzzer_cave, 800, 250); //(pin, frequency, duration) delay(150); noTone(broche_buzzer_cave); tone(broche_buzzer_poele, 800, 250); delay(150); noTone(broche_buzzer_poele); } delay(4000); //wdt_disable(); wdt_enable(WDTO_8S); si delay > 5 secondes alarm1 = false; // probleme circulateur panneaux solaire qui ne tourne pas alors qu'allumé alarm2 = true; // surchauffe ballon for (j = 0; j <= 1; j++) { tone(broche_buzzer_cave, 500, 250); //(pin, frequency, duration) delay(130); noTone(broche_buzzer_cave); tone(broche_buzzer_poele, 500, 250); //(pin, frequency, duration) delay(130); noTone(broche_buzzer_poele); } wdt_disable(); //wdt_enable(WDTO_8S); ON ETEINT LE WATCHDOG POUR EVITER UN RESET delay(4000); wdt_enable(WDTO_8S); // on rallume le watchdog alarm2 = false; // surchauffe ballon alarm3 = true; // surchauffe poele for (j = 0; j < 3; j++) { tone(broche_buzzer_cave, 500, 250); //(pin, frequency, duration) delay(130); noTone(broche_buzzer_cave); tone(broche_buzzer_poele, 500, 250); //(pin, frequency, duration) delay(130); noTone(broche_buzzer_poele); } delay(4000); alarm3 = false; // surchauffe poele alarm4 = true; // erreur lecture des températures for (j = 0; j <= 3; j++) { tone(broche_buzzer_cave, 700, 200); //(pin, frequency, duration) delay(250); noTone(broche_buzzer_cave); } delay(4000); alarm4 = false; // erreur lecture des températures alarm5 = true; // gel dans les panneaux solaires for (i = 0; i < 5; i++) { tone(broche_buzzer_cave, 800, 250); //(pin, frequency, duration) delay(150); noTone(broche_buzzer_cave); tone(broche_buzzer_poele, 800, 250); delay(150); noTone(broche_buzzer_poele); } delay(4000); alarm5 = false; // gel dans les panneaux solaires } //// Fin Fonction TEST ALARM */ /* //// Fonction POSITION DES VANNES PAR DEFAUT : lorsque relais OFF (si arret carte arduino). /// Finalement, je n'utilise plus cette fonction : je positionne les fils des vannes en fonction de ce que je veux. void PositionVannesParDefaut() { digitalWrite(38, LOW); // Vanne 6, stratification basse : ouverte par défaut digitalWrite(39, LOW); // Vanne goutte à goutte rue : fermée par défaut ! digitalWrite(40, LOW); // Vanne 3 voies, +12v sur rouge = l'eau du ballon va à la chaudiere par défaut digitalWrite(41, LOW); // Vanne 41 : ballon récupération eau douche : ouverte par défaut digitalWrite(42, LOW); // Vanne 10, ouverte pour laisser la chaudiere gaz par défaut digitalWrite(37, LOW); // Vanne 11, ouverte pour laisser la chaudiere gaz par défaut digitalWrite(44, LOW); // Vanne 13 : Radiateur Salle de Bain fermé par défaut (pour laisser l'eau circuler dans les autres radiateurs) digitalWrite(45, LOW); // ALIM Vanne7-8 : Chauffage, derriere Circulateur C2 : digitalWrite(46, LOW); // Vanne 7 : ouverte digitalWrite(47, LOW); // Vanne 8 : derriere Circulateur C2 : ouverte par défaut digitalWrite(36, LOW); // Vanne 9, derriere circulateur poele C3 (ouvert par défaut) digitalWrite(48, LOW); // Vanne 4, stratification haute : ouverte par défaut digitalWrite(49, LOW); // Vanne 5, stratification milieu : ouverte par défaut digitalWrite(32, LOW); // Vanne 3 et vanne 1, fonction anti-gel et thermosiphon : v3 ouverte par défaut, v1 fermée digitalWrite(26, LOW); // Vanne 2, circuit solaire plus court : fermée par défaut (l'eau passe dans les 2 serpentins) } //// Fin Fonction POSITION DES VANNES PAR DEFAUT */ //// Fonction LECTURE DES BOUTONS/INTERRUPTEURS : GAZ, goutte à goutte, et bouton 4 void lecture_boutons() { lecture_bouton_gaz = analogRead(14); // lecture de la valeur analogique en A14 if (80 < lecture_bouton_gaz and lecture_bouton_gaz < 700) { bouton_gaz = 1; } if (lecture_bouton_gaz < 70) { bouton_gaz = 2; } if (lecture_bouton_gaz > 701) { bouton_gaz = 0; } lecture_bouton_goutte_a_goutte = analogRead(13); // lecture de la valeur analogique en A13 if (lecture_bouton_goutte_a_goutte > 800) { bouton_goutte_a_goutte = 0; } if (lecture_bouton_goutte_a_goutte < 100) { bouton_goutte_a_goutte = 1; } lecture_bouton_4 = analogRead(12); // lecture de la valeur analogique en A12 if (lecture_bouton_4 > 800) { bouton_4 = 0; } if (lecture_bouton_4 < 100) { bouton_4 = 1; } } //// Fin Fonction LECTURE DES BOUTONS/INTERRUPTEURS //// Fonction EAU CHAUDE SANITAIRE void eau_chaude_sanitaire() { if (temperature[24] >= consigne_eau_chaude + 1) // si T°C haut ballon > consigne+1 (env.43°C +1)--> ne pas passer sur chaudiere gaz { digitalWrite(40, HIGH); // vanne n°12 (3voies) vers réseau maison, sans passer par chaudiere digitalWrite(broche_gaz_on_off, HIGH); // on peut éteindre définitivement la chaudiere qui ne sert plus eau_par_gaz = 0; eau_par_gaz_compteur = 0; } else if (temperature[24] < consigne_eau_chaude) // si T°C haut ballon < consigne-1 (env.43°C)--> passer sur chaudiere gaz { digitalWrite(broche_gaz_on_off, LOW); // allumer chaudiere if (eau_par_gaz_compteur == 30) // basculer la vanne au 30eme tour (env. 30secondes), le temps que la chaudière chauffe son eau { digitalWrite(40, LOW); // vanne n°12 (3voies) vers la chaudiere eau_par_gaz = 1; } if (eau_par_gaz_compteur < 30) { eau_par_gaz_compteur = eau_par_gaz_compteur + 1; // on incremente le compteur, le temps d'arriver à 30s et que la chaudière ait chauffé son eau } } } //// Fin Fonction EAU CHAUDE SANITAIRE /* //// Fonction RECUPERATION EAU DOUCHE // Bidon de 20L directement branché sur l'évacuation de la douche et qui se vide par une vanne motorisée (+ trop plein). // On fait passer dedans l'eau froide venant de la rue à l'intérieur d'un serpentin de PER diam. 12mm. // En Hiver : l'eau arrive à 8°C et sort à 15°C du bidon (qui est à 30°C). Donc l'échangeur en PER est très mauvais... // Finalement : je n'utilise plus ce système, mon évacuation n'était pas assez grosse et elle a fini par se boucher. void recup_eau_douche() { if (ete == false) // si entre octobre et mai { if ((Heure == 11 and Minute == 00) or (Heure == 16 and Minute == 0) ) // vider bidon à 11h et 16h { digitalWrite(41, LOW); // ouvrir vanne du bidon pour le vider } else { digitalWrite(41, HIGH); // fermer vanne du bidon récup eau douche } } else { digitalWrite(41, LOW); // ouvrir vanne du bidon récup eau douche si pas l'hiver (pas nécessaire de chauffer la cave et eau de ville pas tres froide) } } //// Fin RECUPERATION EAU DOUCHE */ //// Fonction GOUTTE à GOUTTE // Gere l'arrosage dans les jardinieres dehors // Ayant eu des problemes avec les détecteurs d'humidité (s'oxyde en terre ; utiliser branche de lunettes en titane ?), // j'ai préféré utiliser un capteur de lumiere et un capteur de température extérieur (celui du panneau 4) // le système fonctionne maintenant assez bien, même si j'ai mis du micro à goutte goutte (tuyau de 4mm) qui entraine // des difficultés à régler les débits. Je conseille plutot des tuyaux de 16mm (moins de problèmes si différences // de longeur importantes). Eviter aussi les différences de hauteur des bacs... : car celui du haut videra ses tuyaux dans ceux du bas. void goutte_a_goutte() { if (bouton_goutte_a_goutte == 1) // si bouton goutte à goutte = ON { pinMode (broche_ldr, INPUT); ldr = analogRead(broche_ldr); // plus la valeur est petite, moins il y a de soleil RTC.getTime(); Heure = RTC.hour; Minute = RTC.minute; if (Minute != 0) { arrosee = false; } wdt_disable(); if (arrosee == false and Heure == 10 and Minute == 0 and ldr > 700 and temperature[7] > 20) { digitalWrite(broche_vanne_goute_a_goutte, HIGH); // ouvrir arrosage delay(15000); // arroser 10s : NE PAS FAIRE DES "delay" > 7s A CAUSE DU WATCHDOG (reset automatique en cas de plantage) digitalWrite(broche_vanne_goute_a_goutte, LOW); // fermer arrosage arrosee = true; dernier_arrosage = 10; } if (arrosee == false and Heure == 12 and Minute == 0 and ldr > 850 and temperature[7] > 25) // température du cadre panneau 4 { digitalWrite(broche_vanne_goute_a_goutte, HIGH); // ouvrir arrosage delay(15000); // arroser 10s : NE PAS FAIRE DES "delay" > 7s A CAUSE DU WATCHDOG (reset automatique en cas de plantage) digitalWrite(broche_vanne_goute_a_goutte, LOW); // fermer arrosage arrosee = true; dernier_arrosage = 12; } if (arrosee == false and Heure == 14 and Minute == 0 and ldr > 850 and temperature[7] > 30) { digitalWrite(broche_vanne_goute_a_goutte, HIGH); // ouvrir arrosage delay(15000); // arroser 10s : NE PAS FAIRE DES "delay" > 7s A CAUSE DU WATCHDOG (reset automatique en cas de plantage) digitalWrite(broche_vanne_goute_a_goutte, LOW); // fermer arrosage arrosee = true; dernier_arrosage = 14; } if (arrosee == false and (Heure == 16) and Minute == 0 and ldr > 880 and temperature[7] > 35) { digitalWrite(broche_vanne_goute_a_goutte, HIGH); // ouvrir arrosage delay(15000); // arroser 10s : NE PAS FAIRE DES "delay" > 7s A CAUSE DU WATCHDOG (reset automatique en cas de plantage) digitalWrite(broche_vanne_goute_a_goutte, LOW); // fermer arrosage arrosee = true; dernier_arrosage = 16; } if (arrosee == false and Heure == 18 and Minute == 0 and ldr > 750 and temperature[7] > 35) { digitalWrite(broche_vanne_goute_a_goutte, HIGH); // ouvrir arrosage delay(15000); // arroser 10s : NE PAS FAIRE DES "delay" > 7s A CAUSE DU WATCHDOG (reset automatique en cas de plantage) digitalWrite(broche_vanne_goute_a_goutte, LOW); // fermer arrosage arrosee = true; dernier_arrosage = 18; } if (arrosee == false and Heure == 20 and Minute == 0 and ldr > 680 and temperature[7] > 30) { digitalWrite(broche_vanne_goute_a_goutte, HIGH); // ouvrir arrosage delay(15000); // arroser 10s : NE PAS FAIRE DES "delay" > 7s A CAUSE DU WATCHDOG (reset automatique en cas de plantage) digitalWrite(broche_vanne_goute_a_goutte, LOW); // fermer arrosage arrosee = true; dernier_arrosage = 20; } wdt_enable(WDTO_8S); digitalWrite(broche_vanne_goute_a_goutte, LOW); // fermer arrosage } else { digitalWrite(broche_vanne_goute_a_goutte, LOW); // fermer arrosage } } //// Fin fonction GOUTTE à GOUTTE /* fonction pour eviter les problemes du watchdog: void delaySeconds (int seconds) {// Function that feeds the puppy for (int i = 0; i <= seconds * 10; i ++) { delay (100); ESP.wdtFeed (); } } Example of use: delaySeconds (30); // delay 30 seconds ou alors : wdt_disable(); wdt_enable(WDTO_8S); */ //-------------------------------- SETUP ------------------------------------------- //-------------------------------- SETUP ------------------------------------------- //-------------------------------- SETUP ------------------------------------------- void setup() { for (i = 22; i < 33; i++) // ATTENTION : 33,34,35 utilisées pour sonde K du Poele { pinMode(i, OUTPUT); } for (i = 36; i < 54; i++) { // ATTENTION : 33,34,35 utilisées pour sonde K du Poele pinMode(i, OUTPUT); // definition des ports relais en sortie } // PositionVannesParDefaut(); // Positionne les vannes par défaut, toutes sur LOW. digitalWrite(42, LOW); // Vanne 10, ouverte pour laisser la chaudiere gaz digitalWrite(37, LOW); // Vanne 11, ouverte pour laisser la chaudiere gaz digitalWrite(48, HIGH); // Fermer Vanne 4 digitalWrite(49, HIGH); // Fermer Vanne 5 digitalWrite(38, HIGH); // Fermer Vanne 6 digitalWrite(36, HIGH); // Fermer Vanne 9 digitalWrite(45, HIGH); // Alim des doubles vannes 7-8 digitalWrite(46, HIGH); // vanne 7 fermee digitalWrite(47, HIGH); // Vanne 8 fermee digitalWrite(broche_gaz_circulateur, LOW); // autoriser la circulation de la chaudière (un relais branché en série sur le circulateur de la chaudière) pinMode(broche_sonde_pt100, INPUT); // sonde pt100 dans panneau n°2 et branchée sur un petit ampli puis sur arduino, mesure très instable pinMode(broche_ldr, INPUT); // sonde lumiere sur panneaux solaires //// Initialisation commandes Circulateur C1,C2,C3 pinMode(broche_relais_C1, OUTPUT); pinMode(broche_relais_C2, OUTPUT); pinMode(broche_relais_C3, OUTPUT); digitalWrite(broche_relais_C1, LOW); // éteindre circulteur C1 digitalWrite(broche_relais_C2, LOW); // éteindre circulteur C2 digitalWrite(broche_relais_C3, LOW); // éteindre circulteur C3 pinMode(AC_LOAD_c1, OUTPUT);// Set AC Load pin as output attachInterrupt(4, zero_crosss_int_c1, RISING); // prépare les interruptions : sur Arduino MEGA: interruption n°4 = broche 19 /* Pin | Interrrupt # | Arduino Platform --------------------------------------- 2 | 0 | All -But it is INT1 on the Leonardo 3 | 1 | All -But it is INT0 on the Leonardo 18 | 5 | Arduino Mega Only 19 | 4 | Arduino Mega Only 20 | 3 | Arduino Mega Only 21 | 2 | Arduino Mega Only 0 | 0 | Leonardo 1 | 3 | Leonardo 7 | 4 | Leonardo The Arduino Due has no standard interrupt pins as an iterrupt can be attached to almosty any pin.*/ //// Fin Initialisation commandes Circulateur C1,C2,C3 attachInterrupt(5, isr, CHANGE); // interruption n°5 pour DEBITMETRE, broche 18 pinMode(43, INPUT); // définir D43 comme une entrée, entrée de l'état du thermostat chauffage //digitalWrite(43, HIGH); //on active la résistance de pull-up en mettant la broche à l'état haut (mais cela reste toujours une entrée) pinMode(broche_buzzer_cave, OUTPUT); // si vous oubliez cette ligne, vous allez avoir des bruits parasites dans vos buzzers pinMode(broche_buzzer_poele, OUTPUT); // si vous oubliez cette ligne, vous allez avoir des bruits parasites dans vos buzzers digitalWrite(broche_buzzer_cave, LOW); // couper vraiment le son digitalWrite(broche_buzzer_poele, LOW); // couper vraiment le son // digitalWrite(broche_buzzer_cave, HIGH); //on active la résistance de pull-up en mettant la broche à l'état haut (mais cela reste toujours une entrée) // digitalWrite(broche_buzzer_poele, HIGH); //on active la résistance de pull-up en mettant la broche à l'état haut (mais cela reste toujours une entrée) Serial.begin(9600); // Initialisation du port série //// INITIALISATION HORLOGE DS3231 RTC.setRAM(0, (uint8_t *)&startAddr, sizeof(uint16_t));// Entree startAddr in NV-RAM address 0x08 TimeIsSet = 0xffff; RTC.setRAM(54, (uint8_t *)&TimeIsSet, sizeof(uint16_t)); RTC.ctrl = 0x00; // 0x00=disable SQW pin, 0x10=1Hz, 0x11=4096Hz, 0x12=8192Hz, 0x13=32768Hz RTC.setCTRL(); //// Fin INITIALISATION HORLOGE DS3231 //// Enregistrement heure et date démarrage de l'arduino RTC.getTime(); Heure = RTC.hour; Minute = RTC.minute; Seconde = RTC.second; Jour = RTC.day; Mois = RTC.month; Annee = RTC.year; mois_demarrage = Mois; jour_demarrage = Jour; heure_demarrage = Heure; minute_demarrage = Minute; //// ECRAN LCD 20*4 lcd.begin(20, 4); // initialize the lcd for 20 chars 4 lines, turn on backlight //// FIN ECRAN LCD 20*4 //// Initialisation ETHERNET // NE PAS UTILISER LES BROCHES 50 à 53 pour autre chose (sur carte arduino Mega) pinMode(10, OUTPUT); // canbus and ethernet SPI CS. digitalWrite(10, HIGH); pinMode(53, OUTPUT); digitalWrite(53, HIGH); // ET NE PAS UTILISER la broche 53, pour que le port SPI fonctionne Ethernet.begin(mac, ip); //Démarrer la connexion Ethernet et le serveur (version DHCP) server.begin(); //// FIN Initialisation Ethernet // Initialisation carte SD // SD.begin(4); //début de la communication avec la carte sur le pin 4 ou 10? //// FIN Initialisation carte SD myHumidity.begin(); // capteur d'humidité HTU 21D en I2C wdt_enable(WDTO_8S); // Initialisation du WatchDog : reset de la carte en cas de plantage } //--------------------------------- LOOP ------------------------------------------- //--------------------------------- LOOP ------------------------------------------- void loop() { startTemperatureMeasure(SENSOR_ADDRESS_1); startTemperatureMeasure(SENSOR_ADDRESS_2); startTemperatureMeasure(SENSOR_ADDRESS_3); startTemperatureMeasure(SENSOR_ADDRESS_4); startTemperatureMeasure(SENSOR_ADDRESS_5); startTemperatureMeasure(SENSOR_ADDRESS_6); startTemperatureMeasure(SENSOR_ADDRESS_7); startTemperatureMeasure(SENSOR_ADDRESS_8); startTemperatureMeasure(SENSOR_ADDRESS_9); startTemperatureMeasure(SENSOR_ADDRESS_10); startTemperatureMeasure(SENSOR_ADDRESS_11); startTemperatureMeasure(SENSOR_ADDRESS_16); startTemperatureMeasure(SENSOR_ADDRESS_17); startTemperatureMeasure2(SENSOR_ADDRESS_0); startTemperatureMeasure2(SENSOR_ADDRESS_12); startTemperatureMeasure2(SENSOR_ADDRESS_13); startTemperatureMeasure2(SENSOR_ADDRESS_14); startTemperatureMeasure2(SENSOR_ADDRESS_15); startTemperatureMeasure2(SENSOR_ADDRESS_18); startTemperatureMeasure2(SENSOR_ADDRESS_19); startTemperatureMeasure2(SENSOR_ADDRESS_20); startTemperatureMeasure2(SENSOR_ADDRESS_21); // sonde puits startTemperatureMeasure2(SENSOR_ADDRESS_22); // salle de bain startTemperatureMeasure2(SENSOR_ADDRESS_23); startTemperatureMeasure2(SENSOR_ADDRESS_24); // ballon haut startTemperatureMeasure2(SENSOR_ADDRESS_25); startTemperatureMeasure2(SENSOR_ADDRESS_26); startTemperatureMeasure2(SENSOR_ADDRESS_27); // rez de chaussée startTemperatureMeasure2(SENSOR_ADDRESS_28); wdt_reset(); // Reset du watchDog (et de la carte arduino), si plantage // calcul ETE ou HIVER if (Mois > 6 and Mois < 9) { ete = true; } else { ete = false; } lecture_boutons(); // lecture des états des boutons solaire_anti_gel(); // active circulateur et alarm si on risque le gel dans les panneaux alarm_ballon(); // met en route une alarm si ballon solaire de 800L > 80°C //poele(); // met en route le circulateur serpentin poele si sonde K > 60°C // ALARM Poele : permet de savoir si le poele chauffe trop, surtout lorsqu'on est pas dans la pièce du poele if (thermocouple.readCelsius() >= 250) // si T°C poele > 250°C --> démarrer alarm { // ALARM : 1 bips= prob px solaire, 2 = surchauff ballon/murs chauffants, 3 = surchauff poele, 4 = prob temperature, 5 = gele Panneaux Serial.print(F(" POELE SURCHAUFFE=")); Serial.print(thermocouple.readCelsius()); Serial.print(F(" ")); alarm3 = true; for (j = 0; j < 3; j++) { tone(broche_buzzer_cave, 500, 250); //(pin, frequency, duration) delay(130); noTone(broche_buzzer_cave); tone(broche_buzzer_poele, 500, 250); //(pin, frequency, duration) delay(130); noTone(broche_buzzer_poele); } } else { alarm3 = false; // Fin ALARM } eau_chaude_sanitaire(); // si l'eau du ballon solaire de 800L < 43°C --> on complete la chauffe de l'eau sanitaire avec la chaudiere au gaz erreur_lecture_eteindre_circulateurs(); // eteint les circulateurs si erreur dans les sondes température DS18B20 // ****** recup_eau_douche(); // gére le petit bidon de récup eau évacuation douche, abandonné car efficacité faible goutte_a_goutte(); // gére l'arrosage goutte à goutte si bouton goutte à goutte enclenché degommage_circulateurs_vannes(); // debloque les vannes une fois par jour 15 secondes humidite_cave = myHumidity.readHumidity(); temperature_cave = myHumidity.readTemperature(); Serial.println(""); Serial.print(F("Etag= ")); Serial.print(temperature[22], 2); Serial.print(F(" RdC= ")); Serial.print(temperature[27], 2); Serial.print(F(" Cav= ")); Serial.print(temperature_cave, 2); Serial.print(F(" (Hum=")); Serial.print(humidite_cave, 1); Serial.print(F("%)")); Serial.print(F(" Puits= ")); Serial.print(temperature[21], 2); // DEBUT HORLOGE Serial.println(F(" ")); Serial.println(" "); Serial.print(F("Last Start: ")); Serial.print(jour_demarrage); Serial.print(F("/")); Serial.print(mois_demarrage); Serial.print(F(", ")); Serial.print(heure_demarrage); Serial.print(F(":")); if (minute_demarrage < 10) { Serial.print(F("0")); } Serial.print(minute_demarrage); Serial.println(" "); RTC.getTime(); Heure = RTC.hour; Minute = RTC.minute; Seconde = RTC.second; Jour = RTC.day; Mois = RTC.month; Annee = RTC.year; Serial.print(Heure); Serial.print( ":"); if (Minute < 10) { Serial.print(F("0")); } Serial.print( Minute ); Serial.print( ":" ); if (Seconde < 10) { Serial.print("0"); } Serial.print(Seconde); Serial.print(F(", ")); Serial.print(Jour); Serial.print(F("/")); Serial.print(Mois); Serial.print(F("/")); Serial.print(Annee); Serial.print(F(" ")); /* if (ete == true) { Serial.print(F("ete"); } else { Serial.print(F("hiver"); } */ // Fin HORLOGE // Affichage LDR ldr = analogRead(broche_ldr); // plus la valeur est petite, moins il y a de soleil Serial.print(F(" LDR = ")); //Serial.print(F("Hello World")) Serial.print(ldr); // Début DEBITMETRE /* G3/4" OD25.4mm Débit: 1 ~ 30L/min Impulsion de débit: F (Hz) = (6.6xQ) Q = L/min Max. Courant De Fonctionnement: 15mA (DC5 V) Min. Tension De Fonctionnement: DC 5 V liquide Température: 80°C précision: +-2% ~ 5% cable Connection: Rouge: Positif + ; Noir: Négative- ; jaune: signal D'impulsion. */ attachInterrupt(5, isr, CHANGE); // enable the interrupt delay (1000); //Attendre 1 seconde. Apparemment, lorsque j'utilise millis(), je perds des impulsions. detachInterrupt(5); F = ((1000000.0 * (float)(numPulses - 2)) / (float)(lastPulseTime - firstPulseTime) / 2); numPulses = 0; attachInterrupt(5, isr, CHANGE); // enable the interrupt debit = ((F) / 6.6) ; //debit = ((F) / 6.6) * 60; // doc débimetre : Impulsion de débit: F (Hz) = (6.6xQ) Q = L/min = F/6.6 if (debit > 50) { debit = 0; // si over flow ou si le débitmetre ne bouge plus } // Serial.print(F); Serial.print(F(" Hz "); // Calcul de la puissance thermique: P(KW)=m(m3/h) * cp * dT * 1.16 (avec cp=1 pour l'eau). Un capteur solaire fourni jusqu'à 2000W (1KW/m2) wh = (debit * 60) * 1.0 * (temperature[18] - temperature[19]) * 1.16; // wh = flow() * 1.0 * (tempIn - tempOut) * 1.16; //Garder sur 11 lignes, permet de remonter avec une lecture facile (synchronisée) Serial.print(F(" Deb = ")); Serial.print(debit); Serial.print(F(" L/mn ")); Serial.print(F(" CycSol=")); Serial.print(cycle_demarrage_solaire); Serial.print(F(" Delta_P2-BalBas=")); Serial.print(delta_panneaux_ballon_milieu); Serial.print(F("(")); Serial.print(consigne_solaire); Serial.print(F(")")); Serial.print(F(" ChaufBal=")); Serial.print(solaire_chauffe_ballon); Serial.print(F(" SerpHaut=")); Serial.print(serpentin_haut); Serial.print(F("|")); Serial.print(temperature[0], 2); Serial.print(F(" P=")); Serial.print(wh, 0); Serial.print(F(" W")); Serial.println(" "); Serial.print(F("RetourChd = ")); Serial.print(temperature[18], 2); Serial.print(F(" DepFrd = ")); Serial.print(temperature[19], 2); delta_chd_frd_station = (temperature[18] - temperature[19]); // calcul du delta Chaud Froid au niveau de la station Serial.print(F(" (D = ")); Serial.print(delta_chd_frd_station); Serial.println(") "); Serial.print(F("P1 = ")); Serial.print(temperature[1], 2); Serial.print(F(" (T2 = ")); Serial.print(temperature[2], 2); Serial.print(F(") ")); Serial.print(F("P2 = ")); Serial.print(temperature[3], 2); Serial.print(F(" (dedans=")); Serial.print(temperature_sonde_pt100); Serial.print(F(";")); Serial.print(valeur_sonde_pt100); Serial.print(F(") ")); Serial.print(F("(T4 = ")); Serial.print(temperature[4], 2); Serial.print(F(") ")); Serial.print(F("P3 = ")); Serial.print(temperature[5], 2); Serial.println(" "); Serial.print(F("P4 = ")); Serial.print(temperature[7], 2); Serial.print(F(" (T6 = ")); Serial.print(temperature[6], 2); Serial.print(F(") ")); Serial.print(F(" P5 = ")); Serial.print(temperature[8], 2); Serial.println(" "); Serial.print(F("P6 = ")); Serial.print(temperature[9], 2); Serial.print(F(" (T10 = ")); Serial.print(temperature[10], 2); Serial.print(F(") ")); Serial.print(F(" P7 = ")); Serial.print(temperature[11], 2); Serial.println(""); Serial.print(F(" Ret Garg = ")); Serial.print(temperature[17], 2); Serial.print(F(" ")); Serial.print(F("Ret Facad = ")); Serial.print(temperature[16], 2); Serial.print(F(" Moy = ")); Serial.print((temperature[16] + temperature[17]) / 2); Serial.println(" "); Serial.print(F("BalHT = ")); Serial.print(temperature[24], 2); Serial.print(F(" BalMIL = ")); Serial.print(temperature[23], 2); Serial.print(F(" BalBAS = ")); Serial.print(temperature[25], 2); delta_stratification = (temperature[24] - temperature[25]); // calcul du delta de stratification Serial.print(F(" (D=")); Serial.print(delta_stratification); Serial.print(F(") TempTt = ")); ballon_temp_moy = (temperature[24] + temperature[23] + temperature[25]) / 3; Serial.print(ballon_temp_moy); Serial.println(" "); relais_gaz = digitalRead(broche_gaz_on_off); if (eau_par_gaz == 1) { Serial.print(F("EAU GAZ(rel=")); Serial.print(relais_gaz); Serial.print(F(")")); } else { Serial.print(F("EAU SOL(rel=")); Serial.print(relais_gaz); Serial.print(F(")")); } Serial.print(F(" EauFrdRue=")); Serial.print(temperature[12], 2); if (bouton_4 == 1) { Serial.print(F(" Sech Sal Bain ON (a ")); Serial.print(heure_seche_serviette_matin); Serial.print(F("h et a ")); Serial.print(heure_seche_serviette_soir); Serial.print(F("h = ")); Serial.print(chauffer_sechoir); Serial.print(F(")")); } Serial.println(""); Serial.print(F("MODE=")); Serial.print(mode); switch (mode) { // mode0=BallonSolaire ou Gaz sur Radiateurs, mode1=Gaz sur radiateurs, mode2=Gaz sur BallonSolaire, // mode3=Poele, mode4=BallonSolaire sur Radiateurs. case 0: Serial.print(F(" (BAL/GAZ->RAD)")); break; case 1: Serial.print(F(" (GAZ->RAD)")); break; case 2: Serial.print(F(" (GAZ->BAL)")); break; case 3: Serial.print(F(" (POEL->Bal)")); break; case 4: Serial.print(F(" (BAL->RAD)")); break; } Serial.print(F(" Bt_gaz=")); Serial.print(bouton_gaz); Serial.print(F("|")); Serial.print(lecture_bouton_gaz); Serial.print(F(" Bt_g_a_g=")); Serial.print(bouton_goutte_a_goutte); Serial.print(F(" Bt_Sech_Serv=")); Serial.print(bouton_4); Serial.println(" "); // GESTION DES BOUTONS // GAZ sur RADIATEUR : seulement si le ballon solaire < 28°C avec thermostat_chauffage_solaire == 0 if (bouton_gaz == 1 and mode != 3) // mettre la chaudiere gaz sur les radiateurs de la maison { mode = 1; // mode0=BallonSolaire ou Gaz sur Radiateurs, mode1=Gaz sur radiateurs, mode2=Gaz sur BallonSolaire, // mode3=Poele, mode4=BallonSolaire sur Radiateurs. digitalWrite(broche_relais_C2, LOW); // arreter circulateur C2 du chauffage solaire // au cas où... digitalWrite(42, LOW); // Vanne 10, ouverte pour laisser la chaudiere gaz digitalWrite(37, LOW); // Vanne 11, ouverte pour laisser la chaudiere gaz digitalWrite(48, HIGH); // Fermer Vanne 4 digitalWrite(49, HIGH); // Fermer Vanne 5 digitalWrite(38, HIGH); // Fermer Vanne 6 digitalWrite(36, HIGH); // Fermer Vanne 9 digitalWrite(45, HIGH); // Alim des doubles vannes 7-8 digitalWrite(46, HIGH); // vanne 7 fermee digitalWrite(47, HIGH); // Vanne 8 fermee digitalWrite(broche_gaz_on_off, LOW); // allumer la chaudiere digitalWrite(broche_gaz_circulateur, LOW); // activer la circulation de la chaudière // (un relais branché en série sur le circulateur de la chaudière) cycle_chauffage = 0; // variable du chauffage par le ballon solaire etat_bouton_gaz_precedent = 1; } // GAZ sur BALLON if (bouton_gaz == 2 and mode != 3) // mettre la chaudiere gaz sur le chauffage du ballon { mode = 2; // mode0=BallonSolaire ou Gaz sur Radiateurs, mode1=Gaz sur radiateurs, mode2=Gaz sur BallonSolaire, mode3=Poele, // mode4=BallonSolaire sur Radiateurs. digitalWrite(broche_relais_C2, LOW); // arreter circulateur C2, au cas où... digitalWrite(42, LOW); // Vanne 10, ouverte digitalWrite(37, HIGH); // Vanne 11, fermée digitalWrite(36, HIGH); // Fermer Vanne 9 digitalWrite(45, HIGH); // Alim des doubles vannes 7-8 digitalWrite(46, HIGH); // Vanne v7 fermée digitalWrite(47, LOW); // Vanne 8 ouverte digitalWrite(broche_gaz_on_off, LOW); // allumer la chaudiere // delay (20000); //attendre que la chaudiere s'allume, mais ne pas faire des delais > 7s à cause du watchdog // digitalWrite(broche_gaz_manuel,HIGH); // appui bref sur MANUEL pour chauffer le ballon // delay (2000); // digitalWrite(broche_gaz_manuel,LOW); // appui bref sur MANUEL pour chauffer le ballon digitalWrite(broche_gaz_circulateur, LOW); // activer la circulation de la chaudière // (un relais branché en série sur le circulateur de la chaudière) stratification(); // envoi l'eau à la bonne hauteur dans le ballon cycle_chauffage = 0; // variable du chauffage par le ballon solaire etat_bouton_gaz_precedent = 2; } // Retour à etat 0 if (bouton_gaz == 0 and mode != 3 and etat_bouton_gaz_precedent != 0) { // on laisse faire le chauffage solaire et son mode 4, qu'il quitte de temps à autre // if (eau_par_gaz == 0 and ete == true){digitalWrite(broche_gaz_on_off,HIGH);} // Eteindre la chaudiere digitalWrite(broche_relais_C2, LOW); // arreter circulateur C2 digitalWrite(42, LOW); // Vanne 10, ouverte pour laisser la chaudiere gaz digitalWrite(37, LOW); // Vanne 11, ouverte pour laisser la chaudiere gaz digitalWrite(48, HIGH); // Fermer Vanne 4 digitalWrite(49, HIGH); // Fermer Vanne 5 digitalWrite(38, HIGH); // Fermer Vanne 6 digitalWrite(36, HIGH); // Fermer Vanne 9 digitalWrite(45, HIGH); // Alim des doubles vannes 7-8 digitalWrite(46, HIGH); // vanne 7 fermee digitalWrite(47, HIGH); // Vanne 8 fermee position_v8 = 0; // 0 = fermee digitalWrite(broche_gaz_circulateur, LOW); // autoriser la circulation de la chaudière // (un relais branché en série sur le circulateur de la chaudière) cycle_chauffage = 0; mode = 0; etat_bouton_gaz_precedent = 0; } //---------------------------------------------- SOLAIRE ------------------------------------------------ //// SONDE PT100 dans le panneau solaire, que je n'utilise finalement pas dans le fonctionnement du programme (juste en affichage), //// car ce système est très imprécis (variation en fonction de la longueur du cable, de l'alim, etc.) valeur_sonde_pt100 = analogRead(broche_sonde_pt100); // lecture port de la sonde PT100 // Comme l'ampli n'est pas très proche de la sonde, j'avais des écarts de temperature jusqu'à +/-5°C, donc je fais une moyenne // avec les valeurs precedentes pour stabiliser : valeur_sonde_pt100_corrigee = (valeur_sonde_pt100 + valeur_sonde_pt100_precedente + valeur_sonde_pt100_precedente1) / 3; valeur_sonde_pt100_precedente1 = valeur_sonde_pt100_precedente; valeur_sonde_pt100_precedente = valeur_sonde_pt100; temperature_sonde_pt100 = 1.27 * valeur_sonde_pt100_corrigee - 290 ; // conversion en °C de la valeur ; voir ci-dessous : // 1.27 * valeur_sonde_pt100_corrigee - 320 /* Formule à recalculer en fonction de votre capteur (évitez d'ajouter une longueur de cable au pt100, sinon instabilité). Fonction : Y (temperature) = Pente (ou coef directionnel) * X (résistance) + b Après avoir fait quelques relevés de température / valeur donnée par le arduino (ou résistance), on prend deux points extrêmes du graphique (en X la résistance, en Y la température) : P1 (arduino 240 , Température de 10°C) ou P1(257,3) P2 (arduino 370 , Température de 260°C) ou P2(318,80) P=1.26 b=-320 (ça c'est qd j'ai allongé le cable de la PT100...) --> on calcule la pente (ou "coefficient directionel") P = y / x = (260-10)/(370-240) = 1,923 De là, on en déduit "b" : 10 (Y) = 1,923 (P) * 240 (X) + b --> b = 10-1,923*240 = -451.538 Voir aussi site : http://edu.mrpigg.ca/termo.html A savoir aussi, dès que l'alimentation des circuits (arduino et ampli) varie, la valeur de PT100 varie... donc ce n'est pas un capteur prècis ! */ // finalement, je n'utilise pas la pt100, car trop instable // Notons qu'augmenter la vitesse du circulateur solaire est intéressant pour récupérer davantage d'énergie seulement lorsqu'il // y a beaucoup d'énergie, et que donc souvent, on en a déjà trop... // Donc je laisse le circulteur en vitesse 1, pour récupérer le maximum de calorie l'hiver, tout en en perdant lorsqu'il // y a beaucoup beaucoup de soleil et de chaleur (à ce moment là, il faudrait circuler plus vite pour déplacer toutes les // calories vers le ballon) delta_panneaux_ballon_milieu = temperature[2] - (temperature[23] + temperature[25]) / 2 ; //-- rendement maxi ------ si pas été et température bas ballon < 70 ; VERSION RENDEMENT OPTIMAL ------- if (Mois != 7 and Mois != 8 and Mois != 9 and temperature[25] < 70) { // hiver : Garder un delta solaire (panneau - bas cuve) élevé, mais pas forcément le plus élevé possible, car les panneaux // perdent en rendement à haute température. // Démarrer le circulateur rapidement (panneau déjà bien chaud) // Eviter les circulations trop lente(<5L/mn), car on entre en régime laminaire ("dans ce cas, tout se passe comme si une couche de // fluide adhérait à l'intérieur du tube et seul le centre du tube est utilisé par le courant de fluide") // Préférer allumer C1, éteindre C1 le temps que cela chauffe, rallumer, éteindre, etc. A chaque allumage du circulateur, cela créera // des remous qui amélioreront le rendement. // Utiliser V3 en bypass le temps que l'eau qui arrive sur le ballon soit chaude if (delta_panneaux_ballon_milieu > consigne_solaire and ldr > 700 and temperature[25] > 5) // si (T°C dans panneau 2 - T°C ballon bas) > consigne (env. 8) // le temperature[25]>5 permet d'éviter le démarrage du circulateur à chaque reset (T°C=0 ou -0,06) de l'arduino ou // lorsqu'il y a un problème de lecture des températures { digitalWrite(broche_relais_C1, HIGH); // allumer circulateur cycle_demarrage_solaire = cycle_demarrage_solaire + 1; if (temperature[18] > (temperature[23] + temperature[25]) / 2) // si T°C Chd station > T°C bas cuve { digitalWrite(32, HIGH); // HIGH = fermer V3 et ouvrir V1 pour faire rentrer l'eau dans le ballon solaire_chauffe_ballon = 1; static unsigned long previousMillis10 = 0; // Temps de la précédente mesure et actuel, LAISSER LE "static" unsigned long currentMillis10 = millis(); // millis() est une fonction qui donne le temps du Arduino depuis son démarrage if (currentMillis10 - previousMillis10 >= 30000) // lit la suite seulement toutes les 30s pour ne pas bouger sans arret les vannes { if (temperature[18] < temperature[23]) { previousMillis10 = currentMillis10; digitalWrite(26, HIGH); //ouvrir vanne 2 pour passer l'eau seulement dans le serpentin du bas serpentin_haut = 0; } else if (temperature[18] >= temperature[23]) { digitalWrite(26, LOW); //fermer vanne 2 pour passer l'eau dans les deux serpentins serpentin_haut = 1; } } if (debit <= 0 and cycle_demarrage_solaire > 100) // si C1 tourne depuis plus de 5mn et pas de débit --> erreur { digitalWrite(broche_relais_C1, LOW); // éteindre C1, mais relais peut-être défectueux (collé ?) // ALARM : 1 bips= prob px solaire, 2 = surchauff ballon/murs chauffants, 3 = surchauff poele, 4 = prob temperature, 5 = gele Panneaux Serial.print(F("ALARM ERREUR DEBIT C1=0")); alarm1 = true; for (i = 0; i < 5; i++) { tone(broche_buzzer_cave, 800, 250); //(pin, frequency, duration) delay(500); noTone(broche_buzzer_cave); tone(broche_buzzer_poele, 800, 250); delay(500); noTone(broche_buzzer_poele); } } else { alarm1 = false; } } else { digitalWrite(32, LOW); // LOW = ouvrir v3, ne pas faire rentrer l'eau solaire_chauffe_ballon = 0; } // delta_chd_frd_station = (temperature[18] - temperature[19]); // calcul du delta Chaud Froid au niveau de la station ; déjà calculé plus haut } else { static unsigned long previousMillis5 = 0; // Temps de la précédente mesure et actuel, LAISSER LE "static" unsigned long currentMillis5 = millis(); // millis() est une fonction qui donne le temps du Arduino depuis son démarrage if (currentMillis5 - previousMillis5 >= 30000) // lit la suite seulement toutes les 30 secondes pour ne pas bouger sans arret les vannes { // vider les dernière calorie dans le circuit previousMillis5 = currentMillis5; digitalWrite(broche_relais_C1, LOW); // éteindre circulateur digitalWrite(32, LOW); // LOW = ne pas faire rentrer l'eau dans la cuve et fermer vanne anti-thermosiphon V1 digitalWrite(26, LOW); // fermer vanne 2 pour éviter thermosiphon de remonter vers panneaux cycle_demarrage_solaire = 0; solaire_chauffe_ballon = 0; } } } //-- été pas surchauffe --------- si été, baisser la température de la cuve et moins chauffer la maison ------------------ // ne plus utiliser la vanne bypass V3 pour l'économiser et baisser légèrement l'efficacité // J'ajoute +10 à la consigne solaire --> il faut qu'il y ait 3+10°C d'écart entre panneau et bas milieu de cuve pour démarrer le Circu1 if ((Mois == 7 or Mois == 8 or Mois == 9) and temperature[25] < 60) { if (delta_panneaux_ballon_milieu > consigne_solaire + 10 and ldr > 700 and temperature[25] > 5) // si (T°C dans panneau 2 - T°C ballon bas) > consigne (env. 3) // temperature[25]>5 permet d'éviter le démarrage du circulateur à chaque reset (T°C=0 ou -0,06) de l'arduino ou lorsqu'il y a // un problème de lecture des températures. { cycle_demarrage_solaire = cycle_demarrage_solaire + 1; digitalWrite(32, HIGH); // HIGH = fermer V3 et ouvrir V1 pour faire rentrer l'eau dans le ballon static unsigned long previousMillis10 = 0; // Temps de la précédente mesure et actuel, LAISSER LE "static" unsigned long currentMillis10 = millis(); // millis() est une fonction qui donne le temps du Arduino depuis son démarrage if (currentMillis10 - previousMillis10 >= 60000) // lit la suite seulement toutes les 60s pour ne pas bouger sans arret les vannes { if (temperature[18] < temperature[23]) { previousMillis10 = currentMillis10; digitalWrite(26, HIGH); //ouvrir vanne 2 pour passer l'eau seulement dans le serpentin du bas serpentin_haut = 0; } else { digitalWrite(26, LOW); //fermer vanne 2 pour passer l'eau dans les deux serpentins serpentin_haut = 1; } } digitalWrite(broche_relais_C1, HIGH); // allumer circulateur solaire_chauffe_ballon = 1; if (debit <= 0 and cycle_demarrage_solaire > 100) // si C1 tourne depuis plus de 5mn et pas de débit --> erreur { digitalWrite(broche_relais_C1, LOW); // éteindre C1, mais relais peut-être défectueux (collé ?) // ALARM : 1 bips= prob px solaire, 2 = surchauff ballon/murs chauffants, 3 = surchauff poele, 4 = prob temperature, 5 = gele Panneaux Serial.print(F("ALARM ERREUR DEBIT C1=0")); alarm1 = true; for (i = 0; i < 5; i++) { tone(broche_buzzer_cave, 800, 250); //(pin, frequency, duration) delay(500); noTone(broche_buzzer_cave); tone(broche_buzzer_poele, 800, 250); delay(500); noTone(broche_buzzer_poele); } } else { alarm1 = false; } } else { static unsigned long previousMillis5 = 0; // Temps de la précédente mesure et actuel, LAISSER LE "static" unsigned long currentMillis5 = millis(); // millis() est une fonction qui donne le temps du Arduino depuis son démarrage if (currentMillis5 - previousMillis5 >= 120000) // lit la suite seulement toutes les 120 secondes pour ne pas bouger sans arret les vannes { previousMillis5 = currentMillis5; digitalWrite(broche_relais_C1, LOW); // éteindre circulateur digitalWrite(32, LOW); // LOW = ne pas faire rentrer l'eau dans le ballon et fermer vanne anti-thermosiphon digitalWrite(26, LOW); // fermer vanne 2 pour éviter thermosiphon cycle_demarrage_solaire = 0; } } } //-- été + surchauffe ------ si été et 60°C <= Ballon Bas < 70°C => allumer circu 1 qu'à 120°C ------------------------------------- if ((Mois == 7 or Mois == 8 or Mois == 9) and temperature[25] >= 60 and temperature[25] < 70) // bas ballon { // SURCHAUFFE --> casser le rendement des capteurs en les faisant fonctionner à haute T° // Garder la vitesse la plus lente pour chercher à monter le delta, garder les panneaux tres chauds (+ de °C, mais - de kWh, car - de débit) // Demarrer circulateur lorsque panneaux >= 120°C // l'eau glycolee peut tenir à 150°C env. à 2 bar, avant d'entrer en stagnation ("gazéification") // et le glycol s'abime fortement au dessus de 170°C env. if (temperature[2] >= 120) // si T°C dans panneau 2 > 120°C { cycle_demarrage_solaire = cycle_demarrage_solaire + 1; digitalWrite(26, LOW); // fermer vanne 2 pour passer l'eau dans les deux serpentins digitalWrite(32, HIGH); // fermer V3 et ouvrir V1 pour faire rentrer l'eau dans le ballon et la refroidir serpentin_haut = 1; digitalWrite(broche_relais_C1, HIGH); // allumer circulateur solaire_chauffe_ballon = 1; if (debit <= 0 and cycle_demarrage_solaire > 100) // si C1 tourne depuis plus de 5mn et pas de débit --> erreur { digitalWrite(broche_relais_C1, LOW); // éteindre C1, mais relais peut-être défectueux (collé ?) // ALARM : 1 bips= prob px solaire, 2 = surchauff ballon/murs chauffants, 3 = surchauff poele, 4 = prob temperature, 5 = gele Panneaux Serial.print(F("ALARM ERREUR DEBIT C1=0")); alarm1 = true; for (i = 0; i < 5; i++) { tone(broche_buzzer_cave, 800, 250); //(pin, frequency, duration) delay(500); noTone(broche_buzzer_cave); tone(broche_buzzer_poele, 800, 250); delay(500); noTone(broche_buzzer_poele); } } else { alarm1 = false; } } else { static unsigned long previousMillis8 = 0; // Temps de la précédente mesure et actuel, LAISSER LE "static" unsigned long currentMillis8 = millis(); // millis() est une fonction qui donne le temps du Arduino depuis son démarrage if (currentMillis8 - previousMillis8 >= 120000) // lit la suite seulement toutes les 120 secondes pour ne pas bouger sans arret les vannes { previousMillis8 = currentMillis8; // digitalWrite(32, HIGH); // ouvrir V1 pour laisser l'eau remonter par thermosiphon dans les panneaux digitalWrite(broche_relais_C1, LOW); // éteindre circulateur solaire solaire_chauffe_ballon = 0; cycle_demarrage_solaire = 0; } } } //-- surchauffe 2 = décharge ---------- si Ballon Bas > 70°C => allumer le circulateur à 120°C et DECHARGE LA NUIT ----------- if (temperature[25] >= 70) // bas ballon, je n'utilise pas la temp BallonHaut pour avoir plus de fiabilité et n'avoir que temp // BallonBas qui est utile au programme { // SURCHAUFFE --> refroidir la nuit et casser le rendement des capteurs en les faisant fonctionner à haute T° // Garder la vitesse la plus lente pour chercher à monter le delta, garder les panneaux tres chauds (plus de °C, mais moins de kWh, car moins de débit) // Demarrer circulateur lorsque panneaux >= 120°C // l'eau glycolee peut tenir à 150°C env. à 2 bar, avant d'entrer en stagnation ("gazéification") // et le glycol s'abime fortement au dessus de 170°C env. if (ldr < 100 or Heure >= 22 or Heure <= 7) // si nuit, alors décharger le ballon dans les panneaux { static unsigned long previousMillis9 = 0; // Temps de la précédente mesure et actuel, LAISSER LE "static" unsigned long currentMillis9 = millis(); // millis() est une fonction qui donne le temps du Arduino depuis son démarrage if (currentMillis9 - previousMillis9 >= 120000) // lit la suite seulement toutes les 120 secondes pour ne pas bouger sans arret les vannes { previousMillis9 = currentMillis9; // REFROIDIR LA NUIT cycle_demarrage_solaire = cycle_demarrage_solaire + 1; digitalWrite(26, LOW); // fermer vanne 2 pour passer l'eau dans les deux serpentins serpentin_haut = 1; digitalWrite(32, HIGH); // fermer V3 et ouvrir V1 pour faire rentrer l'eau dans le ballon et le refroidir digitalWrite(broche_relais_C1, HIGH); // allumer circulateur solaire_chauffe_ballon = 1; } } else if (temperature[2] >= 120) // si T°C dans panneau 2 > 120°C { cycle_demarrage_solaire = cycle_demarrage_solaire + 1; digitalWrite(26, LOW); // fermer vanne 2 pour passer l'eau dans les deux serpentins digitalWrite(32, HIGH); // fermer V3 et ouvrir V1 pour faire rentrer l'eau dans le ballon et la refroidir serpentin_haut = 1; digitalWrite(broche_relais_C1, HIGH); // allumer circulateur solaire_chauffe_ballon = 1; if (debit <= 0 and cycle_demarrage_solaire > 100) // si C1 tourne depuis plus de 5mn et pas de débit --> erreur { digitalWrite(broche_relais_C1, LOW); // éteindre C1, mais relais peut-être défectueux (collé ?) // ALARM : 1 bips= prob px solaire, 2 = surchauff ballon/murs chauffants, 3 = surchauff poele, 4 = prob temperature, 5 = gele Panneaux Serial.print(F("ALARM ERREUR DEBIT C1=0")); alarm1 = true; for (i = 0; i < 5; i++) { tone(broche_buzzer_cave, 800, 250); //(pin, frequency, duration) delay(500); noTone(broche_buzzer_cave); tone(broche_buzzer_poele, 800, 250); delay(500); noTone(broche_buzzer_poele); } } else { alarm1 = false; } } else { static unsigned long previousMillis8 = 0; // Temps de la précédente mesure et actuel, LAISSER LE "static" unsigned long currentMillis8 = millis(); // millis() est une fonction qui donne le temps du Arduino depuis son démarrage if (currentMillis8 - previousMillis8 >= 120000) // lit la suite seulement toutes les 120 secondes pour ne pas bouger sans arret les vannes { previousMillis8 = currentMillis8; // digitalWrite(32, HIGH); // ouvrir V1 pour laisser l'eau remonter par thermosiphon dans les panneaux digitalWrite(broche_relais_C1, LOW); // éteindre circulateur solaire solaire_chauffe_ballon = 0; cycle_demarrage_solaire = 0; } } } // fin décharge dans panneaux //---------------------------------------------- CHAUFFAGE ------------------------------------------------ // Je veux avoir chaud seulement lorsque c'est l'énergie solaire --> donc pas question de chauffer le ballon avec la chaudière au gaz. // J'utilise 2 thermostats : un pour la chaudière gaz et le deuxième pour le ballon solaire. // La chaudière au gaz ne s'allume que lorsque la température de la maison descend sous 16-17°C // (c'est une chaudière qui fait aussi l'eau chaude sanitaire, donc tjrs chaude). // Le thermostat du circulateur du ballon solaire est lui règlé sur 18-22°C, il déclenche en priorité. // L'idée est d'évacuer la chaleur du ballon le plus souvent possible pour permettre au circulateur solaire de // démarrer même par temps peu ensoleillé le lendemain matin (intérieur panneaux = 35°C env.). // Exemple : si j'ai le ballon à 45°C, il faut que l'eau des panneaux soit à plus de 45°C pour démarrer la circulation. // Si j'ai le ballon à 25°C, il faut que l'eau des panneaux soit à plus de 30°C pour démarrer la circulation --> donc je récupére plus de calories // La maison est en pierre avec isolation extérieure, donc surchauffer la maison n'est pas perdu, cela chauffe les murs qui stockent. // Tout l'hiver, j'ai le bouton "mode 0" (gaz sur radiateur ou ballon solaire sur radiateur), mais lorsque le haut du ballon > 30°C, // je bloque le circulateur de la chaudière gaz avec un relais en série (+ placement des vannes), pour activer // le circulateur du chauffage solaire. thermostat_chauffage_solaire = digitalRead(43); // lecture thermostat télécommande chauffage Serial.print(F("CHAUF Therm = ")); Serial.print(thermostat_chauffage_solaire); Serial.print(F(" CycleChauff = ")); Serial.print(cycle_chauffage); Serial.print(F(" C2Pause = ")); Serial.print(circulateur_C2_en_pause); Serial.print(F(" Aller_T28 = ")); Serial.print(temperature[28], 2); Serial.print(F(" Retour_T20 = ")); Serial.print(temperature[20], 2); Serial.print(F(" d(depart-retour)=")); Serial.print(delta_chauffage); Serial.print(F(" ")); Serial.print(gain_temperature_chauffage); static unsigned long previousMillis7 = 0; // Temps de la précédente mesure et actuel, LAISSER LE "static" unsigned long currentMillis7 = millis(); // millis() est une fonction qui donne le temps du Arduino depuis son démarrage if (circulateur_C2_en_pause == 1 and (currentMillis7 - previousMillis7) >= 1800000) // lit la suite seulement toutes les 30mn=1800000ms { previousMillis7 = currentMillis7; circulateur_C2_en_pause = 0; // 30mn après, on peut redémarer le circulateur c2 } if (bouton_4 == 1 and ((Heure == heure_seche_serviette_matin and Minute < 15) or (Heure == heure_seche_serviette_soir and Minute < 15)) ) // 9h et 21h, ne chauffer que le séche serviette salle de bain. { chauffer_sechoir = true; // 7h et 22h digitalWrite(44, HIGH); // ouvrir bypass sèche serviette et l'eau prendra le parcours le plus court en alimentant que le sèche serviette } else { chauffer_sechoir = false; digitalWrite(44, LOW); // fermer vanne séchoir salle de bain bas et retrouver le robiner d'équilibrage } // BOUCLE PRINCIPALE // J'empêche le chauffage de fonctionner la nuit pour éviter le bruit des vannes if (Heure >= 8 and Heure <= 23 and circulateur_C2_en_pause == 0 and (thermostat_chauffage_solaire == 1 or chauffer_sechoir == true) and temperature[24] >= 28 and temperature[28] < 43 and temperature[28] > 0 and (mode == 0 or mode == 4) and mode != 1 and mode != 2 and mode != 3) // si ballon froid (T21), aucun intérêt d'envoyer l'eau dans les radiateurs. // Temperature[28]>0 pour ne pas démarrer si les capteurs temperature déconnent. { delta_chauffage = temperature[28] - temperature[20]; // Temp de départ - Temp de retour du circuit chauffage mode = 4; // // mode0=BallonSolaire ou Gaz sur Radiateurs, mode1=Gaz sur radiateurs, mode2=Gaz sur BallonSolaire, mode3=Poele, // mode4=BallonSolaire sur Radiateurs. digitalWrite(broche_gaz_circulateur, HIGH); // couper la circulation de la chaudière (un relais branché en série sur le circulateur) digitalWrite(42, HIGH); // Vanne 10, fermée digitalWrite(37, LOW); // Vanne 11, ouverte digitalWrite(36, HIGH); // Fermer Vanne 9 if (cycle_chauffage == 0) { digitalWrite(45, HIGH); // Alim des doubles vannes 7-8 digitalWrite(46, LOW); // Vanne v7 ouverte digitalWrite(47, HIGH); // Vanne v8 fermee wdt_disable(); //wdt_enable(WDTO_8S); ON ETEINT LE WATCHDOG POUR EVITER UN RESET delay(6000);// le temps que les vannes se ferment wdt_enable(WDTO_8S); // ON RALLUME LE WATCHDOG position_v8 = 0; // 0 = v8 fermee } // Si l'on vient de démarrer la chauffe, alors envoyer de l'eau à 25°C maxi pour éviter les chocs thermiques dans les murs chauffants if (cycle_chauffage < 150 and temperature[20] <= 18) // 150 et si le retour n'est pas déjà à plus de 20°C { temperature_eau_visee_de_chauffe = 25; // temperature de démarrage pour éviter les chocs thermiques } else { temperature_eau_visee_de_chauffe = 39; // après 150 cycle = 38-39 MAXIMUM ! Murs chauffants ! } // gestion vanne 3 voies chauffage (qui sont en fait 2 vannes) static unsigned long previousMillis3 = 0; // Temps de la precedente mesure et actuel, LAISSER LE "static" unsigned long currentMillis3 = millis(); // millis() est une fonction qui donne le temps du Arduino depuis son démarrage if (cycle_chauffage == 0 or (currentMillis3 - previousMillis3) >= 10000) // lit la suite seulement toutes les 10 secondes pour ne pas bouger sans arret les vannes { previousMillis3 = currentMillis3; digitalWrite(48, LOW); // ouvrir V4, toujours ouvrir avant de fermer, pour ne pas bloquer le circulateur digitalWrite(49, HIGH); // fermer V5 digitalWrite(38, HIGH); // fermer V6 difference_consigne = temperature_eau_visee_de_chauffe - temperature[28]; // température[28]= température de départ chauffage gain_temperature_chauffage = temperature[28] - temperature_precedente; // si gain_temperature_chauffage>0--> T°C départ monte. Si gain_temperature_chauffage<0--> T°C depart descend if (difference_consigne >= 20) { temps_ouverture_vanne_v8v7 = 600; //800 } if (10 < difference_consigne and difference_consigne < 20) { temps_ouverture_vanne_v8v7 = 300; //500 } if (5 <= difference_consigne and difference_consigne <= 10) { temps_ouverture_vanne_v8v7 = 100; //200 } if (2 <= difference_consigne and difference_consigne < 5) { temps_ouverture_vanne_v8v7 = 70; //100 } if (1 <= difference_consigne and difference_consigne < 2) { temps_ouverture_vanne_v8v7 = 30; //50 } Serial.print(F(" ")); Serial.print(temps_ouverture_vanne_v8v7); Serial.print(F(" ")); Serial.print(difference_consigne); Serial.print(F(" ")); if (temperature[28] < temperature_eau_visee_de_chauffe and gain_temperature_chauffage <= 0.25 and difference_consigne > 2 and position_v8 < 2600) // si petit ecart /à la consigne, arrêter de bouger { digitalWrite(45, HIGH); // Alim des doubles vannes 7-8 digitalWrite(46, HIGH); // fermer un peu V7 digitalWrite(47, LOW); // ouvrir un peu V8 wdt_disable(); //wdt_enable(WDTO_8S); ON ETEINT LE WATCHDOG POUR EVITER UN RESET delay(temps_ouverture_vanne_v8v7); wdt_enable(WDTO_8S); // on rallume le watchdog digitalWrite(45, LOW); // couper Alim des doubles vannes 7-8 position_v8 = position_v8 + temps_ouverture_vanne_v8v7; // 0 = fermee 2000 = ouverte au maxi Serial.print(F("OUVRE")); Serial.print(F(" (Posi V8=")); Serial.print(position_v8); Serial.print(F(")")); } // si T°C continue de monter --> arreter d'ouvrir (avec la variable gain_temperature_chauffage) if (temperature[28] > temperature_eau_visee_de_chauffe and gain_temperature_chauffage > 0) { digitalWrite(45, HIGH); // Alim des doubles vannes 7-8 digitalWrite(46, LOW); // ouvrir un peu V7 digitalWrite(47, HIGH); // fermer un peu V8 wdt_disable(); //wdt_enable(WDTO_8S); ON ETEINT LE WATCHDOG POUR EVITER UN RESET delay(temps_ouverture_vanne_v8v7); wdt_enable(WDTO_8S); // on rallume le watchdog digitalWrite(45, LOW); // couper Alim des doubles vannes 7-8 position_v8 = position_v8 - temps_ouverture_vanne_v8v7; // 0 = fermee 2600 = ouverte au maxi Serial.print(F("FERME")); Serial.print(F(" (V8=")); Serial.print(position_v8); Serial.print(F(")")); } if (temperature[28] > temperature_eau_visee_de_chauffe + 2 or temperature[28] <= 0) // securite si sonde temperature deconne (-0.06) { digitalWrite(45, HIGH); // Alim des doubles vannes 7-8 digitalWrite(46, LOW); // ouvrir V7 digitalWrite(47, HIGH); // fermer V8 digitalWrite(48, HIGH); // fermer V4 temps_ouverture_vanne_v8v7 = 1500; wdt_disable(); //wdt_enable(WDTO_8S); ON ETEINT LE WATCHDOG POUR EVITER UN RESET delay(temps_ouverture_vanne_v8v7); wdt_enable(WDTO_8S); // on rallume le watchdog digitalWrite(45, LOW); // couper Alim des doubles vannes 7-8 if (position_v8 < 800) { position_v8 = 0; } else { position_v8 = position_v8 - temps_ouverture_vanne_v8v7; // 0 = fermee 2600 = ouverte au maxi } Serial.print(F("FERME FORT")); Serial.print(F(" (V8=")); Serial.print(position_v8); Serial.print(F(")")); } temperature_precedente = temperature[28]; } // transforme la valeur de la position_v8 de 0 à 2600 vers 0 à 90° position_v8_degre = map(position_v8, 0, 2000, 0, 90); cycle_chauffage = cycle_chauffage + 1; digitalWrite(broche_relais_C2, HIGH); // demarrer circulateur C2 // si ballon très chaud, décharger dans l'inertie des murs et démarrer plus rapidement la récupération des calories solaires if (temperature[24] > 50) { consigne_delta_chauffage = 1.5; // le delta chauffage est la différence entre la temperature de depart et la temperature de retour } else { consigne_delta_chauffage = 3; } if (cycle_chauffage > 160 and delta_chauffage < consigne_delta_chauffage) { // si delta_chauffage très bas, la chaleur n'est plus diffusée dans les murs, faire une pause pour économiser l'électricité du circulateur // Garder un delta haut pour ne pas trop mélanger le ballon : en dessous de 4, on envoie beaucoup d'eau chaude en bas du ballon. // Mais aussi : lorsqu'on ne circule plus, la chaleur dans les radiateurs est seulement en haut et la diffusion se dégrade... circulateur_C2_en_pause = 1; // attendre mini 60mn que la chaleur se diffuse dans les murs avant de refaire tourner le circulateur digitalWrite(broche_relais_C2, LOW); // arreter circulateur C2 digitalWrite(42, LOW); // Vanne 10, ouverte pour laisser la chaudiere gaz digitalWrite(37, LOW); // Vanne 11, ouverte pour laisser la chaudiere gaz digitalWrite(48, HIGH); // Fermer Vanne 4 digitalWrite(49, HIGH); // Fermer Vanne 5 digitalWrite(38, HIGH); // Fermer Vanne 6 digitalWrite(36, HIGH); // Fermer Vanne 9 digitalWrite(45, HIGH); // Alim des doubles vannes 7-8 digitalWrite(46, HIGH); // vanne 7 fermee digitalWrite(47, HIGH); // Vanne 8 fermee position_v8 = 0; // 0 = fermee digitalWrite(broche_gaz_circulateur, LOW); // autoriser circulation de la chaudière (un relais branché en série sur le circulateur chaudière) mode = 0; cycle_chauffage = 0; } } else if (mode == 4 and (thermostat_chauffage_solaire == 0 or temperature[24] < 27) and chauffer_sechoir == false ) { // sortir du mode chauffage si thermostat == 0 digitalWrite(broche_relais_C2, LOW); // arreter circulateur C2 digitalWrite(42, LOW); // Vanne 10, ouverte pour laisser la chaudiere gaz digitalWrite(37, LOW); // Vanne 11, ouverte pour laisser la chaudiere gaz digitalWrite(48, HIGH); // Fermer Vanne 4 digitalWrite(49, HIGH); // Fermer Vanne 5 digitalWrite(38, HIGH); // Fermer Vanne 6 digitalWrite(36, HIGH); // Fermer Vanne 9 digitalWrite(45, HIGH); // Alim des doubles vannes 7-8 digitalWrite(46, HIGH); // vanne 7 fermee digitalWrite(47, HIGH); // Vanne 8 fermee position_v8 = 0; // 0 = fermee digitalWrite(broche_gaz_circulateur, LOW); // autoriser circulation de la chaudière (un relais branché en série sur le circulateur chaudière) mode = 0; cycle_chauffage = 0; } // PROTECTION des murs chauffants : garder cette partie du programme le plus facilement actif, donc hors d'autres boucles if (temperature[28] >= 43) // il y a aussi un fusible thermique de 40°C fixer sur tuyau départ qui coupe c2 (branchement série) { digitalWrite(broche_relais_C2, LOW); // arreter circulateur C2 du chauffage solaire digitalWrite(42, LOW); // Vanne 10, ouverte pour laisser la chaudiere gaz digitalWrite(37, LOW); // Vanne 11, ouverte pour laisser la chaudiere gaz digitalWrite(48, HIGH); // Fermer Vanne 4 pour éviter que l'eau monte par thermosiphon dans les radiateurs digitalWrite(49, HIGH); // Fermer Vanne 5 pour éviter que l'eau monte par thermosiphon dans les radiateurs digitalWrite(38, HIGH); // Fermer Vanne 6 pour éviter que l'eau monte par thermosiphon dans les radiateurs digitalWrite(36, HIGH); // Fermer Vanne 9 digitalWrite(45, HIGH); // Alim des doubles vannes 7-8 digitalWrite(46, HIGH); // vanne 7 fermee : pour éviter que l'eau monte par thermosiphon dans les radiateurs (si bas ballon>50°C) digitalWrite(47, HIGH); // Vanne 8 fermee position_v8 = 0; // 0 = fermee digitalWrite(broche_gaz_circulateur, LOW); // autoriser la circulation de la chaudière (un relais branché en série sur le circulateur) mode = 0; cycle_chauffage = 0; Serial.print(F(" SURCHAUFFE ")); /* // ALARM : 1 bips= prob px solaire, 2 = surchauff ballon/murs chauffants, 3 = surchauff poele, 4 = prob temperature, 5 = gele Panneaux for (i = 0; i < 2; i++) { tone(broche_buzzer_cave, 500, 250); delay(130); noTone(broche_buzzer_cave); tone(broche_buzzer_poele, 500, 250); // (pin, frequency, duration) delay(130); noTone(broche_buzzer_poele); } */ } //---------------------------------------------- FIN CHAUFFAGE ------------------------------------------------ //-------------- AFFICHEUR -------------------- // mode , heure/mois, temperature : haut ballon, interieur panneau/bas ballon, poele, ou toutes (reset pour revenir à zéro) if ((Heure == 8 or Heure == 9 or Heure == 10 or Heure == 11 or Heure == 12 or Heure == 13 or Heure == 14 or Heure == 15 or Heure == 16 or Heure == 17 or Heure == 18 or Heure == 19 or Heure == 20 or Heure == 21) and Minute == 0 and Seconde < 5) { lcd.begin(20, 4); // initialize the lcd for 20 chars 4 lines, turn on backlight } //// HORLOGE ET ECRAN LCD avec DS3231 (conservation de la librairie DS1307) site: http://f5mna.free.fr lcd.setCursor( 0, 0 ); if (Jour < 10) { lcd.print ("0"); } lcd.print(Jour ); lcd.print("/"); if (Mois < 10) { lcd.print ("0"); } lcd.print(Mois); lcd.print (" "); if (Heure < 10) { lcd.print ("0"); } lcd.print (Heure); lcd.print( ":"); if (Minute < 10) { lcd.print ("0"); } lcd.print( Minute ); lcd.print( ":" ); /* if (Seconde < 10) { lcd.print ("0"); }*/ lcd.print( Seconde ); lcd.print(" MOD="); lcd.print(mode); //---------- lcd.setCursor( 0, 1 ); if (temperature[2] < 100) { lcd.print("Pan="); lcd.print(temperature[2], 0); } else { lcd.print("Pa="); lcd.print(temperature[2], 0); } lcd.print(" Rt="); lcd.print(temperature[18], 0); lcd.print(" C"); lcd.print(cycle_demarrage_solaire); if (cycle_demarrage_solaire < 10) { lcd.print(" "); } else if (cycle_demarrage_solaire < 1000 and cycle_demarrage_solaire > 9) { lcd.print(" "); } else if (cycle_demarrage_solaire > 999) { lcd.print(""); } if ((Mois == 7 or Mois == 8 or Mois == 9) and temperature[25] >= 60 and temperature[25] < 70) { lcd.print("S"); } else if (temperature[25] >= 70) { lcd.print("D"); } else { lcd.print(" "); } //---------- lcd.setCursor( 0, 2 ); lcd.print("Bal="); lcd.print(temperature[24], 0); lcd.print(" T="); lcd.print(ballon_temp_moy, 0); lcd.print(" Poel="); lcd.print(thermocouple.readCelsius(), 0); if (thermocouple.readCelsius() < 100) { lcd.print(" "); } //---------- lcd.setCursor( 0, 3 ); lcd.print("DepChauf="); lcd.print(temperature[28], 1); lcd.print(" C"); lcd.print(cycle_chauffage); if (cycle_chauffage < 10) { lcd.print(" "); } else if (cycle_chauffage < 1000 and cycle_chauffage > 9) { lcd.print(" "); } else if (cycle_chauffage > 999) { lcd.print(""); } /* BOUTON POUR REGLAGE HORLOGE // RAZ valeur de la touche sensorValue = analogRead(sensorPin); // lecture de la touche val_key = int(sensorValue / 100); // valeur entière de la touche / 10 if (val_key < 10) { // Bouton(); } */ //// FIN HORLOGE ET ECRAN LCD avec DS3231 //// ETHERNET // en utilisant "client.print(F(" j'ai gagné 5700 octets de RAM dynamique... J'avais 95% de libre et j'ai 25% de libre... // Inconveniant : ça ralenti un peu l'affichage // EthernetClient client = server.available();// Ecouter les clients entrants if (client) { // Une requète HTTP terminée par une ligne vide boolean currentLineIsBlank = true; while (client.connected()) { //Serial.println("new client"); // Serial.print(F("adresse IP: "); // Serial.println(Ethernet.localIP()); if (client.available()) { // Envoyer un header de reponse standard http //client.print(F("HTTP/1.1 200 OK")); //C'est OK //client.print(F("Content-Type: text/html")); //client.print(F("<html><head>")); //---- debut de la page HTML --- //client.print(F("<meta content=\"utf-8\">")); //client.print(F("<META HTTP-EQUIV=\"Content-Type\" CONTENT=\"text/html; charset=iso-8859-1\">")); //client.print(F("<META HTTP-EQUIV=\"Content-Language\" CONTENT=\"fr-FX\">")); client.println(F("<html><head><title>Solaire Aussillon</title></head><body>")); client.println(F("<META HTTP-EQUIV=\"Refresh\" CONTENT=\"2\"><font face=\"Calibri\">")); // METTRE un "\" devant " pour éviter problemes // METTRE un "\" devant " pour éviter problemes client.print("<div style=\"width:700px;height:695px;background-image:url('http://mmonceaux.free.fr/solaire_thermique/ plan_solaire_matthieu_monceaux_31.jpg');position:relative;top:0;left:0\">"); // RECOLLER cette ligne à celle du dessus //masquage si poele froid if (thermocouple.readCelsius() < 40) { client.print("<div style=\"position:absolute;left:563px;top:595px\">"); client.print("<img src=\"http://mmonceaux.free.fr/solaire_thermique/solaire_masque_poele.jpg\">"); client.print("</div>"); } client.print(Heure); client.print(F(":")); if (Minute < 10) { client.print(F("0")); } client.print( Minute ); client.print(F(":" )); if (Seconde < 10) { client.print(F("0")); } client.print(Seconde); client.print(F(", ")); client.print(Jour); client.print(F("/")); client.print(Mois); client.print(F("/")); client.print(Annee); client.print(F("   <BR>     Luminosité = ")); client.print(ldr); client.print(F(" Lux")); // ajouter \ avant ", sinon probleme client.print(F("<div style=\"background:white;font-size:11px;position:absolute;left:365px;top:285px;\">")); client.print(debit); client.print(F(" L/mn ")); if (cycle_demarrage_solaire > 0) { client.print(F("  CycSol = <mark>")); client.print(cycle_demarrage_solaire); client.print(F("</mark> <BR>   Delta_P2-BalBas = ")); client.print(delta_panneaux_ballon_milieu); client.print(F("(seuil=")); client.print(consigne_solaire); client.print(F(")")); client.print(F("<BR>ChaufBal=")); client.print(solaire_chauffe_ballon); client.print(F("   SerpHaut=")); client.print(serpentin_haut); } client.print(F("</div>")); if (etatC1 == 1) { client.print(F("<div style=\";position:absolute;left:346px;top:195px;\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/solaire_thermique_pompe_animee_06.gif\" height=\"30\" width=\"30\">")); client.print(F("</div>")); } client.print(F("<div style=\"background:white;font-size:14px;text-align:center;position:absolute;left:438px;top:129px;\">")); client.print(F("P = ")); client.print(wh, 0); client.print(F(" Watts")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:11px;text-align:center;position:absolute;left:178px;top:546px;\">")); client.print(temperature[0], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:12px;text-align:center;position:absolute;left:365px;top:128px;\">")); client.print(temperature[19], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:12px;text-align:center;position:absolute;left:265px;top:147px;\">")); client.print(temperature[18], 1); client.print((char)176); client.print(F("C")); client.print(F("<BR>(D=")); client.print(delta_chd_frd_station); client.print(F(")")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:12px;text-align:center;position:absolute;left:324px;top:38px;padding:2px;\">")); client.print(F("P1(cadre)<BR>")); client.print(temperature[1], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:14px;text-align:center;position:absolute;left:398px;top:8px;\">")); client.print(F("<mark>")); client.print(temperature[2], 1); if ((Mois == 7 or Mois == 8 or Mois == 9) and temperature[25] >= 60 and temperature[25] < 70) { client.print(F("°C </mark>(dém 120°C)")); } else if (temperature[25] >= 70) { client.print(F("°C </mark>(décharg nuit)")); } else { client.print(F("°C</mark>")); } client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:12px;text-align:center;position:absolute;left:431px;top:38px;padding:2px;\">")); client.print(F("P2(cadre)<BR>")); client.print(temperature[3], 1); client.print(F("°C (Dedans=")); client.print(temperature_sonde_pt100); client.print(F(")")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:12px;text-align:center;position:absolute;left:532px;top:8px;\">")); client.print(temperature[4], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:12px;text-align:center;position:absolute;left:592px;top:38px;padding:2px;\">")); client.print(F("P3(cadre)<BR>")); client.print(temperature[5], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"font-size:12px;text-align:center;position:absolute;left:252px;top:45px;\">")); client.print(temperature[16], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"font-size:12px;text-align:center;position:absolute;left:217px;top:60px;\">")); client.print(temperature[17], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:12px;text-align:center;position:absolute;left:45px;top:108px;padding:2px;\">")); client.print(F("P4(cadre)<BR>")); client.print(temperature[7], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:10px;text-align:center;position:absolute;left:120px;top:99px;\">")); client.print(temperature[6], 0); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:12px;text-align:center;position:absolute;left:175px;top:108px;padding:2px;\">")); client.print(F("P5(cadre)<BR>")); client.print(temperature[8], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:12px;text-align:center;position:absolute;left:45px;top:209px;padding:2px;\">")); client.print(F("P6(cadre)<BR>")); client.print(temperature[9], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:10px;text-align:center;position:absolute;left:120px;top:213px;\">")); client.print(temperature[10], 0); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:12px;text-align:center;position:absolute;left:175px;top:209px;padding:2px;\">")); client.print(F("P7(cadre)<BR>")); client.print(temperature[11], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:9px;text-align:center;position:absolute;left:278px;top:98px;\">")); client.print((temperature[16] + temperature[17]) / 2, 0); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:13px;text-align:center;position:absolute;left:216px;top:443px;padding:1px;\">")); client.print(temperature[24], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:13px;text-align:center;position:absolute;left:216px;top:495px;padding:1px;\">")); client.print(temperature[23], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:13px;text-align:center;position:absolute;left:216px;top:584px;padding:1px;\">")); client.print(temperature[25], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"background:white;font-size:12px;text-align:center;position:absolute;left:210px;top:625px;\"><mark>Totale = ")); client.print(ballon_temp_moy, 1); client.print((char)176); client.print(F("</mark><BR>Delta Strat = ")); client.print(delta_stratification); client.print(F("</div>")); // CHAUFFAGE if (cycle_chauffage > 0) { client.print(F("<div style=\"font-size:11px;position:absolute;left:397px;top:622px;\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/solaire_thermique_pompe_animee_06.gif\" height=\"25\" width=\"25\">")); client.print(F("<BR>Thermostat = ")); client.print(thermostat_chauffage_solaire); client.print(F("   CycleChauff = ")); client.print(cycle_chauffage); client.print(F("<BR>Pause = ")); client.print(circulateur_C2_en_pause); client.print(F(" Delta = ")); client.print(delta_chauffage); client.print(F("  Gain = ")); client.print(gain_temperature_chauffage); client.print(F("<BR>")); client.print(F("</div>")); //v7 client.print(F("<div style=\"position:absolute;left:389px;top:597px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_verticale.jpg\">")); client.print(F("</div>")); client.print(F("<div style=\"position:absolute;left:381px;top:606px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_horizon.jpg\">")); client.print(F("</div>")); //v8 client.print(F("<div style=\"position:absolute;left:345px;top:573px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_horizon.jpg\">")); client.print(F("</div>")); client.print(F("<div style=\"position:absolute;left:353px;top:564px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_verticale.jpg\">")); client.print(F("</div>")); // position_v8 | position_v8_degre client.print(F("<div style=\"font-size:10px;position:absolute;left:322px;top:638px\"><CENTER><mark>V8=")); client.print(position_v8); client.print(F("|")); client.print(position_v8_degre); client.print((char)176); client.print(F("</mark><BR>")); client.print(F("(90")); client.print((char)176); client.print(F("=ouvert max)</CENTER></div>")); } else { if (v7 == 0) { client.print(F("<div style=\"position:absolute;left:389px;top:597px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_verticale.jpg\">")); client.print(F("</div>")); } else { client.print(F("<div style=\"position:absolute;left:379px;top:606px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_horizon.jpg\">")); client.print(F("</div>")); } if (v8 == 0) { client.print(F("<div style=\"position:absolute;left:345px;top:573px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_horizon.jpg\">")); client.print(F("</div>")); } else { client.print(F("<div style=\"position:absolute;left:353px;top:564px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_verticale.jpg\">")); client.print(F("</div>")); } client.print(F("<div style=\"font-size:11px;position:absolute;left:397px;top:635px;\">")); client.print(F("<BR>Thermostat = ")); client.print(thermostat_chauffage_solaire); client.print(F("<BR>Pause = ")); client.print(circulateur_C2_en_pause); client.print(F("</div>")); } client.print(F("<div style=\"font-size:11px;text-align:center;position:absolute;left:350px;top:488px;;\">")); client.print(temperature[28], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"font-size:11px;text-align:center;position:absolute;left:449px;top:618px;;\">")); client.print(temperature[20], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"font-size:11px;text-align:center;position:absolute;left:312px;top:567px;;\">")); client.print(temperature[26], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"font-size:11px;text-align:center;position:absolute;left:535px;top:560px;;\">")); client.print(thermocouple.readCelsius(), 1); client.print((char)176); client.print(F("C")); // poele client.print(F("</div>")); client.print(F("<div style=\"font-size:12px;position:absolute;left:462px;top:346px;\">")); if (eau_par_gaz == 1) { client.print(F("EAU sanitaire par GAZ ")); client.print(F(" (")); client.print(consigne_eau_chaude); client.print(F(")")); } else { client.print(F("EAU sanitaire par <mark>SOLEIL</mark>")); client.print(F(" (")); client.print(consigne_eau_chaude); client.print(F(") ")); } client.print(F("</div>")); client.print(F("<div style=\"font-size:12px;position:absolute;left:590px;top:275px;\">")); client.print(temperature[12], 1); client.print((char)176); client.print(F("C")); // tempéarature arrivee eau rue client.print(F("</div>")); // chaudière ON / OFF client.print(F("<div style=\"color:#ff0000;font-size:14px;position:absolute;left:398px;top:391px;\"><B>")); if (relais_gaz == 0) // chaudière allumée { client.print(F("ON")); } else { client.print(F("OFF")); } client.print(F("</B></div>")); client.print(F("<div style=\"font-size:12px;text-align:center;position:absolute;left:530px;top:135px;\">")); client.print(F("<mark>MODE = ")); client.print(mode); switch (mode) { // mode0=BallonSolaire ou Gaz sur Radiateurs, mode1=Gaz sur radiateurs, mode2=Gaz sur BallonSolaire, mode3=Poele, // mode4=BallonSolaire sur Radiateurs. case 0: client.print(F("</mark><BR>BALLON/GAZ sur RADIATEURS")); break; case 1: client.print(F("</mark><BR>GAZ sur RADIATEURS")); break; case 2: client.print(F("</mark><BR>GAZ sur BALLON")); break; case 3: client.print(F("</mark><BR>POELE sur BALLON")); break; case 4: client.print(F("</mark><BR>BALLON sur RADIATEURS")); break; } // ALARMES if (alarm1 == true) { client.print(F("<mark><BR>ALARME = Circu_1 NE TOURNE PAS</mark>")); } if (alarm2 == true) { client.print(F("<mark><BR>ALARME = SURCHAUFFE BALLON</mark>")); } if (alarm3 == true) { client.print(F("<mark><BR>ALARME = SURCHAUFFE POELE</mark>")); } if (alarm4 == true) { client.print(F("<mark><BR>ALARME = ERREUR LECTURE Températures</mark>")); } if (alarm5 == true) { client.print(F("<mark><BR>ALARME = GEL dans les panneaux solaires</mark>")); } /// bouton TEST alarm : client.print(F("<button onclick="TestAlarm();">TEST ALARM</button>")); client.print(F("</div>")); // temperature maison client.print(F("<div style=\"font-size:13px;position:absolute;left:54px;top:366px;\">")); client.print(temperature[22], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"font-size:13px;position:absolute;left:61px;top:405px;\">")); client.print(temperature[27], 1); client.print((char)176); client.print(F("C")); client.print(F("</div>")); client.print(F("<div style=\"text-align:center;background:white;font-size:13px;position:absolute;left:33px;top:442px;padding:1px\">")); client.print(temperature_cave, 1); client.print((char)176); client.print(F("C  ")); client.print(humidite_cave); client.print(F("% <BR> Puits = ")); client.print(temperature[21]); client.print(F("</div>")); //client.print(F(" (Mur= "); client.print(temperature[26]);client.print(F(") "); // Impression des barres sur les vannes v2 = digitalRead(26); v3 = digitalRead(32); v4 = digitalRead(48); v5 = digitalRead(49); v6 = digitalRead(38); v7 = digitalRead(46); v8 = digitalRead(47); v9 = digitalRead(36); v10 = digitalRead(42); v11 = digitalRead(37); v12 = digitalRead(40); if (v2 == 1) { client.print(F("<div style=\"position:absolute;left:183px;top:517px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_verticale.jpg\">")); client.print(F("</div>")); } else { client.print(F("<div style=\"position:absolute;left:175px;top:526px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_horizon.jpg\">")); client.print(F("</div>")); } if (v3 == 0) { client.print(F("<div style=\"position:absolute;left:160px;top:569px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_verticale.jpg\">")); client.print(F("</div>")); client.print(F("<div style=\"position:absolute;left:184px;top:609px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_verticale.jpg\">")); client.print(F("</div>")); } else { client.print(F("<div style=\"position:absolute;left:151px;top:578px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_horizon.jpg\">")); client.print(F("</div>")); client.print(F("<div style=\"position:absolute;left:174px;top:619px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_horizon.jpg\">")); client.print(F("</div>")); } if (v4 == 0) { client.print(F("<div style=\"position:absolute;left:318px;top:424px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_horizon.jpg\">")); client.print(F("</div>")); } else { client.print(F("<div style=\"position:absolute;left:328px;top:414px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_verticale.jpg\">")); client.print(F("</div>")); } if (v5 == 0) { client.print(F("<div style=\"position:absolute;left:318px;top:476px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_horizon.jpg\">")); client.print(F("</div>")); } else { client.print(F("<div style=\"position:absolute;left:328px;top:467px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_verticale.jpg\">")); client.print(F("</div>")); } if (v6 == 0) { client.print(F("<div style=\"position:absolute;left:318px;top:541px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_horizon.jpg\">")); client.print(F("</div>")); } else { client.print(F("<div style=\"position:absolute;left:328px;top:531px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_verticale.jpg\">")); client.print(F("</div>")); } if (v9 == 1) { client.print(F("<div style=\"position:absolute;left:388px;top:496px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_verticale.jpg\">")); client.print(F("</div>")); } else { client.print(F("<div style=\"position:absolute;left:378px;top:506px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_horizon.jpg\">")); client.print(F("</div>")); } if (v10 == 0) { client.print(F("<div style=\"position:absolute;left:456px;top:471px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_horizon.jpg\">")); client.print(F("</div>")); } else { client.print(F("<div style=\"position:absolute;left:466px;top:461px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_verticale.jpg\">")); client.print(F("</div>")); } if (v11 == 0) { client.print(F("<div style=\"position:absolute;left:486px;top:471px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_horizon.jpg\">")); client.print(F("</div>")); } else { client.print(F("<div style=\"position:absolute;left:496px;top:461px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_verticale.jpg\">")); client.print(F("</div>")); } if (v12 == 0) { client.print(F("<div style=\"position:absolute;left:385px;top:350px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_verticale.jpg\">")); client.print(F("</div>")); client.print(F("<div style=\"position:absolute;left:406px;top:330px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_verticale.jpg\">")); client.print(F("</div>")); } else { client.print(F("<div style=\"position:absolute;left:375px;top:359px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_horizon.jpg\">")); client.print(F("</div>")); client.print(F("<div style=\"position:absolute;left:397px;top:339px\">")); client.print(F("<img src=\"http://mmonceaux.free.fr/solaire_thermique/plan_solaire_matthieu_monceaux_barre_horizon.jpg\">")); client.print(F("</div>")); } client.print(F("</div>")); // de l'image de fond if (bouton_goutte_a_goutte == 1) { client.print(F("<BR>Arrosage jardinière ON (10h / 700Lux, 12 / 750, 14 / 850, 16 / 880, 18 / 750, 20 / 700, dernier = ")); client.print(dernier_arrosage); client.print(F(")<BR>")); } if (bouton_4 == 1) { client.print(F("Séchoir Salle de Bain ON (à ")); client.print(heure_seche_serviette_matin); client.print(F("h et à ")); client.print(heure_seche_serviette_soir); client.print(F("h = ")); client.print(chauffer_sechoir); client.print(F(")")); } client.print(F("Bouton_gaz = ")); client.print(bouton_gaz); client.print(F(" | ")); client.print(lecture_bouton_gaz); client.print(F("   Bouton_g_a_g = ")); client.print(bouton_goutte_a_goutte); client.print(F("   Bouton_seche_serviette = ")); client.print(bouton_4); client.print(F("    Last Start: ")); client.print(jour_demarrage); client.print(F("/")); client.print(mois_demarrage); client.print(F(", ")); client.print(heure_demarrage); client.print(F(":")); if (minute_demarrage < 10) { client.print(F("0")); } client.print(minute_demarrage); client.print(F("<BR>")); /*client.print(F("POELE   =   ")); client.print(thermocouple.readCelsius()); delta_poele = temperature[26] - temperature[25]; client.print(F("   C3 = ")); client.print(c3_tourne); client.print(F("   D_T26 - T25 = ")); client.print(delta_poele); client.print(F("   Duree_Allum = ")); client.print(duree_allumage_c3);*/ client.print(F("<BR>ALARMES : 1 bips = surchauffe Panneaux   2 bips = surchauffe Ballon / Murs chauffants<BR>3 bips = surchauffe Poêle   4 bips = erreur température   5 bips = gèle Panneaux")); // RECOLLER cette ligne à celle du dessus //client.println(F("<BR><h4 style = \"color: red\">Bienvenue sur le SOLAIRE arduino d'AUSSILLON !</h4>")); client.print(F("</font>")); client.print(F("</body></html>")); // break; } } } delay(1); // Laisser au navigateur web le temps de recevoir les données client.stop(); // Refermer la connexion: //// FIN ETHERNET // enregistrement carte SD : Panneaux (PT100, si surchauffe qui entraine mauvaise lecture des DS18B20),P watts,alarm,chauffage, // eau gaz/solaire, conso KW maison // Enegistrement des températures ( -0.06 = erreur ) temperature[1] = readTemperatureMeasure(SENSOR_ADDRESS_1); temperature[2] = readTemperatureMeasure(SENSOR_ADDRESS_2); temperature[3] = readTemperatureMeasure(SENSOR_ADDRESS_3); temperature[4] = readTemperatureMeasure(SENSOR_ADDRESS_4); temperature[5] = readTemperatureMeasure(SENSOR_ADDRESS_5); temperature[6] = readTemperatureMeasure(SENSOR_ADDRESS_6); temperature[7] = readTemperatureMeasure(SENSOR_ADDRESS_7); temperature[8] = readTemperatureMeasure(SENSOR_ADDRESS_8); temperature[9] = readTemperatureMeasure(SENSOR_ADDRESS_9); temperature[10] = readTemperatureMeasure(SENSOR_ADDRESS_10); temperature[11] = readTemperatureMeasure(SENSOR_ADDRESS_11); temperature[16] = readTemperatureMeasure(SENSOR_ADDRESS_16);// retour chaud panneaux facade temperature[17] = readTemperatureMeasure(SENSOR_ADDRESS_17);// retour chaud panneaux garage temperature[0] = readTemperatureMeasure2(SENSOR_ADDRESS_0); temperature[12] = readTemperatureMeasure2(SENSOR_ADDRESS_12); temperature[13] = readTemperatureMeasure2(SENSOR_ADDRESS_13); temperature[14] = readTemperatureMeasure2(SENSOR_ADDRESS_14); temperature[15] = readTemperatureMeasure2(SENSOR_ADDRESS_15); temperature[18] = readTemperatureMeasure2(SENSOR_ADDRESS_18); temperature[19] = readTemperatureMeasure2(SENSOR_ADDRESS_19); temperature[20] = readTemperatureMeasure2(SENSOR_ADDRESS_20); temperature[21] = readTemperatureMeasure2(SENSOR_ADDRESS_21); // puits temperature[22] = readTemperatureMeasure2(SENSOR_ADDRESS_22); //salle de bain temperature[23] = readTemperatureMeasure2(SENSOR_ADDRESS_23); temperature[24] = readTemperatureMeasure2(SENSOR_ADDRESS_24); // haut ballon temperature[25] = readTemperatureMeasure2(SENSOR_ADDRESS_25); // SI = -0.06 --> erreur temperature[26] = readTemperatureMeasure2(SENSOR_ADDRESS_26); temperature[27] = readTemperatureMeasure2(SENSOR_ADDRESS_27); // Rez de Chaussée temperature[28] = readTemperatureMeasure2(SENSOR_ADDRESS_28); // Serial.print(F("freeMemory() reports ")); Serial.println( freeMemory() ); // 8k sur arduino Mega et 2K sur UNO } |
ZIP de ce programme : avec les librairies associées et des petits programmes complémentaires (comme le réglage de l'heure depuis le PC, les essais des relais, la recherche des adresses des DS18B20, etc.) : solaire_thermique_arduino_mmonceaux.free.fr.zip (4,8Mo)
Bilan bien
sûr très positif, surtout pour l'écologie et tout ce que
j'ai appris en faisant cette installation.
En plus de se chauffer gratuitement et écologiquement à volonté
lorsqu'il y a du soleil, cette installation a permis de réduire de
60% à 70% notre consommation de gaz : de 4500KW/an avant (en chauffant
peu) à 2000KW/an aujourd'hui (en chauffant davantage si soleil), soit
250€ de gagné par an. Vu que cela nous a couté 5650€,
on remboursera l'investissement dans 20ans. A court terme, le bilan financier
n'est pas fameux. Vu son très faible prix, on aurait donc pu se contenter
de continuer à bruler le gaz que les générations n'auront
pas... Mais faut-il réfléchir de manière financière
? N'est-ce pas ce mode de pensée "financier" que nous a inculqué
l'usage de l'argent, qui cause la perte de tant de vies sur Terre (disparition
d'espèces végétales, animales, humaines, etc. causées
par la destruction de l'environnement, le réchauffement climatique,
etc.) ?
Cette installation va éviter
le rejet d'environ 650Kg de CO2 par an (le calcul ici
ou ici.
Mais il faudrait aussi prendre en compte ce que j'ai acheté pour faire
cette installation solaire..., pas évident). C'est env. 5000Km/an en
voiture d'économisé.
Le gaz n'étant pas une énergie renouvelable, en consommer moins,
c'est en laisser aux générations futures (et c'est pareils pour
toutes les autres énergies - même dites "renouvelables"
- qui reposent souvent en grande partie sur une grosse consommation de pétrole
: la meilleure énergie est celle que l'on ne consomme pas
!).
Courbes des consommations totales de la maison : ici
Merci bien-sûr aux créateurs, administrateurs et participants
bénévoles de l'APPER
, à ceux qui prennent le temps departager leurs expériences
et aux contributeurs des forums.
Aller plus loin :
Site de l'Apper : http://www.apper-solaire.org/
Forum de l'Apper : http://forum.apper-solaire.org/
Solari-home, solaire thermique & économie d'énergie : http://solari-home.wifeo.com/economie-dlectricit.php
Des présentations sur des systèmes solaires : http://slideplayer.fr/search/solaire/
Connaitre le nombre d'heures d'ensoleillement dans votre région : http://www.linternaute.com/voyage/climat/mazamet/ville-81163
ARDUINO :
http://www.mon-club-elec.fr
Mesure de puissance thermique & data logging
: http://domoenergytics.com/domo.energy/Puissance-thermique-data-logging
MattMonc, (page commencée en janv 2018)