Fabrication industrielle
Internet des objets industriel | Matériaux industriels | Entretien et réparation d'équipement | Programmation industrielle |
home  MfgRobots >> Fabrication industrielle >  >> Manufacturing Technology >> Processus de fabrication

Chargeur intelligent pour piles rechargeables NiMH 9V V1

Composants et fournitures

Arduino UNO
× 1
SparkFun I2C DAC Breakout - MCP4725
× 1
Régulateur linéaire avec sortie réglable
× 1
Texas Instruments à usage général Dual Op-Amp
× 1
Résistance 6.8k ohm
× 2
Résistance 3.3k ohm
× 1
Résistance 5.1k ohm
× 1
Résistance 1k ohm
× 1
Résistance 10 ohm
× 1
Relais (générique)
× 1
Résistance 20k ohm
× 1
SparkFun Breadboard Alimentation 5V/3.3V
× 1
Alimentation 17V
× 1
MODULE SÉRIE LCD 1602 YwRobot I2C
× 1

À propos de ce projet

J'ai cherché un chargeur intelligent capable de charger une batterie NiMH 9V en quelques heures et je n'en ai pas trouvé. De plus, tous les chargeurs que j'ai trouvés étaient vraiment "idiots". Courant de charge inconnu et aucune fonction pour terminer la charge une fois la batterie complètement chargée. Problème avec de tels chargeurs qui peuvent surcharger la batterie et réduire considérablement la durée de vie. J'ai donc décidé de créer un chargeur "intelligent".

La première version que j'ai l'intention de garder simple, elle permet des choses de base comme la charge avec un courant constant, la fin de charge automatique une fois la batterie complètement chargée, la charge d'entretien, la mesure de la charge transférée à la batterie.

Dans la prochaine version, j'ajouterai quelques fonctionnalités utiles supplémentaires telles que la décharge, la mesure de la capacité et le cycle.

Avertissement :Charger la batterie avec un courant élevé peut provoquer une explosion ou un incendie de la batterie. Veuillez ne pas laisser le chargeur sans surveillance. N'essayez pas non plus de charger la batterie qui n'est pas destinée à être chargée comme alcaline. Ce chargeur n'a été testé qu'avec des batteries NiMH (et vous l'utilisez toujours à vos risques et périls et je n'ai absolument aucune responsabilité en cas de dommages causés par des bugs de conception ou de code). Le chagrin des autres types de batteries nécessitera une modification du code.

Théorie

Quelques faits utiles à retenir qui aideront à comprendre les paramètres nécessaires du chargeur.

C - courant égal à la capacité nominale de la batterie

Lorsqu'elle est chargée au taux C, la tension d'une seule cellule peut atteindre 1,6 V. Cette tension peut être plus élevée pour les vieilles batteries.

La tension nominale d'une seule cellule est de 1,2 V, mais une cellule complètement chargée a une tension en circuit ouvert jusqu'à 1,5 V.

Un taux de charge d'entretien inférieur à 0,025 C (C/40) est recommandé une fois la batterie complètement chargée.

Il existe généralement deux options pour charger la batterie NiMH :

1. Charge rapide. Courant de charge 0.5C-1C. L'état de charge doit être surveillé et terminé par dV/dt (taux de changement de tension) ou dT/dt (taux de changement de température)

2. Charge lente. Courant de charge 0,1C. Temps de charge 14-16 heures. Fin de charge par minuterie. Terminaison de charge dT/dt impossible pour les courants faibles. La terminaison dV/dt peut ne pas être fiable pour des courants inférieurs à 0,5 C selon la littérature.

Paramètres de base du circuit de charge

La batterie 9V a généralement 7 ventes connectées en série, mais dans certains cas, elle peut avoir 6 ou 8 cellules. Le régulateur de tension doit être capable de fournir une tension de charge d'au moins 8 * 1,6 =12,8 V. Tension de chute du régulateur LM317 jusqu'à 2 V, la tension d'alimentation doit donc être d'environ 15 V (cela ne tient pas compte de la chute de tension sur la résistance de détection de courant).

Pour un courant de charge maximal de 200 mA et une résistance de détection de courant de 10 ohms, la chute supplémentaire de la résistance de détection de courant est de 2 V, une tension d'alimentation de 17 V est donc nécessaire.

Une cellule complètement déchargée peut avoir une tension très faible, voire négative. La tension minimale du régulateur devrait idéalement être de 0, mais avec le LM317, elle peut être aussi basse que 1,2 V.

Circuit

Explications des circuits

L'idée de base est de mesurer le courant de charge et d'ajuster la tension du régulateur jusqu'à ce que le courant souhaité soit atteint. Courant mesuré en mesurant la chute de tension sur la résistance de détection de courant R5. I=V/R.

SparkFun I2C DAC Breakout - MCP4725 - Convertisseur numérique-analogique 12 bits utilisé pour contrôler la tension. La came de tension de sortie peut être configurée via I2C entre 0 et 5V. Parce que nous devons pouvoir ajuster la tension dans une plage plus large, de 0 à 15V, l'amplificateur opérationnel LM358 utilisé pour amplifier la tension de sortie du DAC. Amplification de l'amplificateur opérationnel réglée par les résistances R4 et R3. Gain=1+R4/R3=1+6800/3300=3.06 donc tension de sortie de l'amplificateur opérationnel d'environ 0 à 15V.

Le courant de sortie maximum du LM358 est de 50mA, donc le régulateur de tension réglable LM317 est utilisé pour contrôler un courant plus élevé. Sortie de l'amplificateur opérationnel connectée à la borne ADJ du LM317. Le LM317 maintiendra 1,2 V entre les bornes ADJ et OUT, de sorte que la tension réelle sur la batterie peut être configurée entre 1,2 et 16,2 V. Le LM317 a besoin d'un courant minimum de 3,5 mA pour maintenir la régulation. Donc résistance 1kOhm R6 servant à assurer la régulation si batterie non branchée. Condensateur C1 utilisé pour filtrer la tension de sortie et améliorer la stabilité du LM317.

Tension mesurée en deux points différents.

1. Résistance R5 connectée à la broche A2 d'Arduino. Tension sur la résistance mesurée et que le courant de charge calculé comme Icharge=V/R

2. La tension sur la batterie peut aller jusqu'à 16,2 V, donc le diviseur résistif R1, R2 utilisé pour amener la tension en dessous de 5 V, autorisé par Arduino. Sortie du diviseur connecté à la broche A0 d'Arduino. Pour R1=5.1k Ohm et R2=20kOhm Vout=Vin/(20000+5100)*5100=0.2 Donc la tension de la batterie divisée par 5.

Relais utilisé pour déconnecter la batterie du circuit de charge. Vous pouvez voir sur le relais photo que j'ai utilisé, mais généralement tout relais avec contrôle 5V peut être utilisé. Il est plus sûr de connecter la batterie aux contacts normalement ouverts du relais.

J'ai utilisé le MODULE YwRobot I2C SERIAL LCD 1602 pour afficher l'état du chargeur, mais tout autre module LCD contrôlé par I2C peut être utilisé. Il semble que le module LCD YwRobot ne soit pas pris en charge par la bibliothèque LiquidCrystal_I2C standard, j'ai donc utilisé la nouvelle bibliothèque LiquidCrystal. Si vous utilisez un module LCD différent, vous devrez modifier cette ligne :

LiquidCrystal_I2C lcd (0x27, 2, 1, 0, 4, 5, 6, 7, 3, POSITIF); // met l'adresse LCD à 0x27 pour un affichage de 16 caractères et 2 lignes 

Pour alimenter le convertisseur numérique-analogique et l'écran LCD, j'ai utilisé l'alimentation SparkFun Breadboard 5V/3.3V. Il est probablement possible d'utiliser 5V à partir de la carte Arduino.

Vous devrez également fournir 17 V au circuit de charge. Si vous n'avez pas d'alimentation, vous pouvez utiliser un convertisseur CC/CC réglable comme celui-ci

http://www.ebay.com/itm/DC-DC-Adjustable-Step-up-boost-Power-Converter-Module-XL6009-Replace-LM2577-/310717070508

Fonctionnalité

Je ne voulais pas beaucoup de fils, donc il n'y a pas de boutons pour configurer la charge. Courant de chagrin configuré uniquement dans le code. Vous devez définir le courant de charge souhaité dans charger.ino

//****************************** Paramètres de charge ************* ******************************* //************************ ******************************************************** *******************float target_current_mA=30 ; //Courant de charge mAfloat battery_nominal_capacity_mA=170 ; //Capacité nominale de la batterie mAfloat max_time_for_trickle_charge=6 ; //Temps de charge d'entretien maximum en minutes//****************************************** *******************************************************/ /****************************************************** ************************************** 

target_current_mA - courant de charge constant

max_time_for_trickle_charge - nombre maximum de minutes pour la charge d'entretien, peut être configuré jusqu'à 600 (10h)

battery_nominal_capacity_mA - capacité de la batterie utilisée pour calculer le courant d'entretien

En général, le courant de charge peut atteindre la capacité nominale. Pour une batterie d'une capacité nominale de 170 mAh, le courant de charge maximal est de 170 mA. Courant de charge minimum généralement C/10 - 17mA pour une batterie de 170mAh.

Après la mise sous tension, le chargeur vérifiera si la batterie est connectée. Si la batterie est connectée, la batterie sera chargée avec un courant constant configuré jusqu'à ce qu'elle soit complètement chargée. Charge terminée en détectant un dV/dt négatif pendant 5 minutes. Une fois la charge terminée, le chargeur passera en charge d'entretien avec le courant C/40. Le chargeur se déconnectera de la batterie une fois le temps de charge d'entretien maximum écoulé.

1 - dV/dt

2 - temps de charge en minutes

1 - Temps de charge

2 - Charge transférée sur batterie

Informations supplémentaires sur les batteries NiMH :

1. http://data.energizer.com/PDFs/nickelmetalhydride_appman.pdf

2. http://batteryuniversity.com/learn/article/ Charging_nickel_metal_hydride

Code

  • charger.ino
  • main.ino
  • hw.ino
  • lcd.ino
  • calculs.ino
  • Nouvelle bibliothèque LiquidCrystal utilisée pour ce projet
charger.inoArduino
Fichier principal
//Ceci pour charger la batterie 9V NiMH //La batterie peut avoir 6,7 ou 8 cellules 1,25V//Cela fait une tension nominale entre 7,5 et 10V#include #include #include  #include #include LiquidCrystal_I2C lcd (0x27, 2, 1, 0, 4, 5, 6, 7, 3, POSITIF); // définissez l'adresse LCD sur 0x27 pour un affichage de 16 caractères et 2 lignes//Défenitions matérielles#define MCP4725_ADDR 0x60 //Adresse DAC#define DAC_REF_VOLTAGE 5.0#define CHARGE_RELAY_PIN 2#define DISCONNECT_CHARGE_RELAY HIGH#define CONNECT_CHARGE_RELAY LOW#define CURSESISTIN_Sdefine CURRENT_SENSING_SESISTOR 10.2 //OHm#define BATTERY_VOLTAGE_PIN A0#define R1 5090 //Résistance côté bas du diviseur de détection de tension#define R2 19910//Résistance côté haut du diviseur de détection de tension#define ADC_REF_VOLTAGE 4.89 //Tension d'alimentation réelle Arduino ou tension AREF pour une bonne Conversion ADC en tension#define R3 3300.0#define R4 6800.0#define AMP_GAIN (1+R4/R3)//Diverses définitions//#define MINIMUM_VOLTAGE 8.1 //Tension minimale après régulateur#define BATTERY_GOOD_VOLTAGE_THRESHOLD 7.0#define MAXIMIM_ALLOWED_CUR courant de la batterie mA (coupure dure)#define MAXIMUM_BATTERY_VOLTAGE 15.0 //Tension maximale autorisée de la batterie V (coupure dure)#define VOLTAGE_STEP 0,001 //Pas pour la tension régulation#define POINTS_FOR_AVERAGING 100 //Combien de points pris pour la moyenne#define MEASURE2MEASURE_US 5000 //Temps entre les mesures en microsecondes (doit être supérieur à 200 à cause de deux lectures analogiques)#define VOLTAGE_LOG_TIME_MIN 30.0 //Temps en minutes pour économiser la tension pour dV /dT cutoff#define MINUTES_TO_LOG 5#define TRICKLE_CURRENT_RATIO 40//Charger states#define INITIALIZATION 0#define NO_BATTERY 5#define BATTERY_CONNECTED 10#define BATTERY_VOLTAGE_LOW 15#define CURRENT_RAMP_UP 20#define CURRENT_RAMP_UP 20#define COWNURGING 30 37#define UNEXPECTED_CURRENT_FALL 40#define UNABLE_TO_REACH_CURRENT 60#define FULLY_CHARGED 70#define CURRENT_TOO_HIGH 80#define REGULATION_FAILED 90#define OVERCURRENT 100#define OVERVOLTAGE 101#define FINAL_STATE_SENSING_FOR_tension 200///INGUNsignedRA_reading,[POINTRA_indéterminé] //Pour faire la moyenne sur un int non signé voltage_sum,current_sum ;//Somme de la moyennef loatregulator_voltage_code,resistor_voltage,csr_voltage_code,regulator_voltage,current_mA,battery_voltage;//Measurmentsfloat tmp_resistor_voltage,tmp_current_mA,tmp_regulator_voltage,tmp_battery_voltage;int i,j,unlast_second_state;tmp_current_mA,tmp_regulator_voltage,tmp_battery_signage;int i,j,unlast_second_state;;String msg,eoc_line1,eoc_line2;unsigned char sec_index,min_index;//long long int loading_started;float sec_log[60],min_log[MINUTES_TO_LOG],last_blf;float trickle_current_mA;int total_minutes_average=0;elapsedTimeatMillis ChargingTime=TrickleChar 0;float last_dac_voltage=0;//Messagesconst char msg_battery_detected[] PROGMEM ="Batterie détectée";const char msg_no_battery[] PROGMEM ="Pas de batterie";const char msg_battery_ok[] PROGMEM ="Batterie ok"_low_voltage[ PROGMEM ="Tension batterie trop faible";const char msg_voltage_too_low_short[] PROGMEM ="V Batterie faible";const char msg_ramp_up[] PROGM EM ="Ramp up";const char msg_charge[] PROGMEM ="Charge";const char msg_space[] PROGMEM =" ";const char msg_ramp_down[] PROGMEM ="Ramp down";const char msg_tricle_charge[] PROGMEM =" Charge d'entretien ";const char msg_no_current[] PROGMEM ="Pas de courant";const char msg_current_unreachable[] PROGMEM ="Je ne suis pas joignable";const char msg_current_unreachable_long[] PROGMEM ="Impossible d'atteindre le courant désiré";const char msg_completed[] PROGMEM ="Impossible d'atteindre le courant désiré";const char msg_completed[] PROGMEM =" ";const char msg_charge[] PROGMEM ="Charge";const char msg_high_current[] PROGMEM ="Courant élevé";const char msg_regulation_fault[] PROGMEM ="Défaut de régulation";const char msg_overcurrent[] PROGMEM ="Courant trop élevé" ; const char msg_overvoltage[] PROGMEM ="Tension trop élevée";const char msg_trickle_completed[] PROGMEM ="Trickle terminé";//**************************** **** Paramètres de charge *******************************************//* ******************************************************** **************************************float target_current_mA=30 ; //Courant de charge mAfloat battery_nominal_capacity_mA=170 ; //Capacité nominale de la batterie mAfloat max_time_for_trickle_charge=6 ; //Temps de charge d'entretien maximum en minutes//****************************************** *******************************************************/ /****************************************************** ******************************************** struct mytime { heures de caractère non signées ; minutes de caractères non signées ; unsigned int total_minutes;} elapsed_time;void setup() { pinMode(CHARGE_RELAY_PIN, OUTPUT); déconnecter_charge_circuit(); //Déconnectez le chargeur de la batterie Wire.begin();//I2C dac_write_voltage(0);//Assurez-vous que le courant le plus bas possible Serial.begin(115200); last_second=second(); lcd_last_second=second(); log_last_second=second(); Timer1.initialize(MEASURE2MEASURE_US); // Sera utilisé pour mesurer la tension et le courant de la batterie (microsecondes) Timer1.attachInterrupt(read_hw); // attache read_hw() en tant qu'interruption de dépassement de temporisateur a average_index=0 ; index_sec=0 ; index_min=0 ; charger_state=0;//État initial de la machine d'état want_dac_voltage=0;//Make shure tension minimum out last_blf=1.0; trickle_current_mA=battery_nominal_capacity_mA/TRICKLE_CURRENT_RATIO ; //ChargingTimeMillis=0; //LCD lcd.begin(16,2); LCD rétro-éclairage(); lcd.clear(); update_lcd(F("Power up..."),empty_string); delay(1000);}float log_battery_voltage(){ //Enregistrer une seule fois par seconde si (log_last_second==second()) return last_blf; else log_last_second=second(); sec_log[sec_index]=tension_batterie ; if (sec_index<59) { sec_index++ ; } else {//Si une minute enregistrée //Calculer la moyenne par minute if (min_index>=MINUTES_TO_LOG) min_index=0; index_sec=0 ; float sum_v=0; pour (i=0;i<60;i++){ sum_v+=sec_log[i] ; } float min_average=sum_v/60.0; for(i=1;i 
main.inoArduino
boucle vide() { String msg1; switch(charger_state){ case INITIALIZATION://Initial state unlock_charge_circuit();//Make shure relais déconnecté dac_write_voltage(0);//Assurez-vous que le courant le plus bas possible défini want_dac_voltage=0;//Make Shure délai de sortie de tension minimum (100); read_status(); if (battery_voltage>0.1) { charger_state=BATTERY_CONNECTED;//Batterie détectée update_lcd(M2S(msg_battery_detected),empty_string); Serial.println(M2S(msg_battery_detected)); retard (2000); } else {//Pas de batterie Serial.println(M2S(msg_no_battery)); update_lcd(M2S(msg_no_battery),construct_status_string()); charger_state=NO_BATTERY ; // Délai de détection de la batterie (1000 ); } Pause; case NO_BATTERY://No battery read_status(); if (battery_voltage>0.1) { charger_state=BATTERY_CONNECTED;//Batterie détectée Serial.println(M2S(msg_battery_detected)); update_lcd(M2S(msg_battery_detected),construct_status_string()); retard(1500); } else{ // Si aucune batterie ne reste dans cet état update_lcd(M2S(msg_no_battery),construct_status_string()); retard (1100); } Pause; case BATTERY_CONNECTED://Batterie connectée dac_write_voltage(0) ;//Assurez-vous que le courant le plus bas possible est défini want_dac_voltage=0 ; retard (100); read_status(); if (battery_voltage>BATTERY_GOOD_VOLTAGE_THRESHOLD){ charger_state=CURRENT_RAMP_UP;//Démarrer la montée en charge du courant de charge //snprintf(welcome, sizeof(welcome),"Firmware:V%d.%d%d",ver,ver2,ver3) ; update_lcd(M2S(msg_battery_ok),construct_status_string()); Serial.println(M2S(msg_battery_ok)); retard (2000); Wanted_dac_voltage=get_approximated_dac_voltage(battery_voltage);//Définir la tension du régulateur nécessaire //Serial.println(get_approximated_dac_voltage(battery_voltage)); connect_charge_circuit(); retard (200); } else { charger_state=BATTERY_VOLTAGE_LOW;//Tension de la batterie trop faible Serial.println(M2S(msg_voltage_too_low)); update_lcd(M2S(msg_voltage_too_low_short),construct_status_string()); retard(1000); } Pause; case BATTERY_VOLTAGE_LOW://Tension de la batterie trop faible update_lcd(M2S(msg_voltage_too_low_short),construct_status_string()); Serial.println(M2S(msg_voltage_too_low)); charger_state=FINAL_STATE;//Pause d'arrêt ; case CURRENT_RAMP_UP:///Current rampup //if (current_mA<1.0) charger_state=40;//Current est tombé de manière inattendue read_status(); update_lcd(M2S(msg_ramp_up),construct_status_string()); retard (50); if (current_mAMAXIMUM_BATTERY_VOLTAGE) charger_state=OVERVOLTAGE;//Surtension if (abs(current_mA-target_current_mA)>0.2){//Si courant dévié 0.01) want_dac_voltage=wanted_dac_voltage-VOLTAGE_STEP; else charger_state=CURRENT_TOO_HIGH;//Courant trop élevé, impossible de baisser } } if (abs(current_mA-target_current_mA)>5){//Échec de la régulation, différence trop élevée charger_state=REGULATION_FAILED;//Erreur de régulation, différence trop élevée } dac_write_voltage (wanted_dac_voltage); if (total_minutes_averagetrickle_current_mA) { if (wanted_dac_voltage>VOLTAGE_STEP) { want_dac_voltage=wanted_dac_voltage-VOLTAGE_STEP ; dac_write_voltage(wanted_dac_voltage); } else charger_state=CURRENT_TOO_HIGH;//Impossible de réduire le courant au taux d'entretien } else { charger_state=TRICKLE;//Charging TrickleChargingTimeMillis=0; Serial.println(M2S(msg_trickle_charge)); } Pause; cas TRICKLE://Délai de charge (200); read_status(); if (current_mA<0.2) charger_state=UNEXPECTED_CURRENT_FALL;//Le courant est tombé de manière inattendue si (battery_voltage>MAXIMUM_BATTERY_VOLTAGE ) charger_state=OVERVOLTAGE;//Surtension if (abs(current_mA-trickle_current_mA)>0.2){//Si courant (dévié) 0.01) want_dac_voltage=wanted_dac_voltage-VOLTAGE_STEP; else charger_state=CURRENT_TOO_HIGH;//Courant trop élevé, impossible de baisser } } if (abs(current_mA-trickle_current_mA)>5){//Échec de la régulation, différence trop élevée charger_state=REGULATION_FAILED;//Erreur de régulation, différence trop élevée } dac_write_voltage (wanted_dac_voltage); //if (total_minutes_averagemax_time_for_trickle_charge) {//Charge d'entretien maximale autorisée update_lcd(eoc_line1,eoc_line2) ; charger_state=END_OF_TRICKLE ;//Arrêter déconnecter_charge_circuit(); //Déconnecter le chargeur de la batterie } break; cas END_OF_TRICKLE :si ((second()%8)<4) update_lcd(M2S(msg_trickle_completed),construct_status_string()); sinon update_lcd(eoc_line1,eoc_line2) ; Pause; case UNEXPECTED_CURRENT_FALL://Le courant est tombé de manière inattendue Serial.println(F("Le courant est tombé de manière inattendue")); déconnecter_charge_circuit(); voulu_dac_voltage=0; update_lcd(M2S(msg_no_current),construct_status_string()); charger_state=FINAL_STATE;//Délai d'arrêt (1000); Pause; case UNABLE_TO_REACH_CURRENT://Impossible d'atteindre le Serial.println actuel souhaité (M2S(msg_current_unreachable_long)); déconnecter_charge_circuit(); voulu_dac_voltage=0; dac_write_voltage(wanted_dac_voltage); retard(1000); update_lcd(M2S(msg_current_unreachable),construct_status_string()); charger_state=FINAL_STATE;//Pause d'arrêt ; case FULLY_CHARGED://Complètement chargé elapsed_time=mills2time(ChargingTimeMillis); int charge_mAh; charge_mAh=calculate_charge(ChargingTimeMillis); msg =String(M2S(msg_completed)+M2S(msg_space)+construct_time_string(elapsed_time)); msg1=String(M2S(msg_charge)+M2S(msg_space)+String(charge_mAh)+String("mAh")); eoc_line1=msg; eoc_line2=msg1; update_lcd(msg,msg1) ; Serial.println(msg); //disconnect_charge_circuit(); //voulait_dac_voltage=0; //dac_write_voltage(wanted_dac_voltage); retard (3000); charger_state=CURRENT_RAMP_DOWN;//Pause d'arrêt ; case CURRENT_TOO_HIGH://Current too high Serial.println(F("Impossible d'abaisser le courant vers la cible")); déconnecter_charge_circuit(); voulu_dac_voltage=0; dac_write_voltage(0) ; update_lcd(M2S(msg_high_current),construct_status_string()); retard(1000); charger_state=FINAL_STATE;//Pause d'arrêt ; case REGULATION_FAILED://La régulation a échoué Serial.println(M2S(msg_regulation_fault)); déconnecter_charge_circuit(); voulu_dac_voltage=0; dac_write_voltage(0) ; update_lcd(M2S(msg_regulation_fault),construct_status_string()); retard(1000); charger_state=FINAL_STATE;//Pause d'arrêt ; case OVERCURRENT://Overcurrent disconnect_ Charging_circuit(); Serial.println(M2S(msg_overcurrent)); voulu_dac_voltage=0; dac_write_voltage(wanted_dac_voltage); update_lcd(M2S(msg_overcurrent),construct_status_string()); retard(1000); charger_state=FINAL_STATE;//Pause d'arrêt ; case OVERVOLTAGE://Overvoltage disconnect_ Charging_circuit(); Serial.println(M2S(msg_overvoltage)); voulu_dac_voltage=0; dac_write_voltage(wanted_dac_voltage); update_lcd(M2S(msg_overvoltage),construct_status_string()); retard(1000); charger_state=FINAL_STATE;//Pause d'arrêt ; case FINAL_STATE://Délai d'arrêt (10000); Pause; par défaut :want_dac_voltage=0 ; charger_state=0; } //Série.println(current_mA); //Serial.print("Current="); //Serial.print(current_mA); //Série.println("mA"); //Serial.print("Tension DAC"); //Serial.println(dac_voltage); //Serial.print("Tension DAC recherchée"); //Serial.println(wanted_dac_voltage); //Serial.print(current_mA); //Série.print(" "); //Serial.print(dac_voltage); //Série.print(" "); read_status(); if (last_second!=second()){ Serial.print(current_mA); Serial.print(","); //Serial.print(resistor_voltage); //Série.print(","); //Serial.print(dac_voltage); //Série.print(","); //Serial.print(regulator_voltage); //Série.print(","); Serial.println(battery_voltage); last_second=second(); }}
hw.inoArduino
float get_approximated_dac_voltage(float vbat){ //float offset_voltage=1,2/R3*(R3+R4) ; float offset_voltage=1,2 ; float adc_voltage=(vbat-offset_voltage)/AMP_GAIN-0.5 ; si (adc_voltage<0) adc_voltage=0 ; return adc_voltage;}int voltage_to_code(float voltage){ int code=4095.0/DAC_REF_VOLTAGE*voltage; code de retour;}void dac_write(int code){ Wire.beginTransmission(MCP4725_ADDR); Wire.write(64); // cmd pour mettre à jour le DAC Wire.write(code>> 4); // les 8 bits les plus significatifs... Wire.write((code &15) <<4); // les 4 bits les moins significatifs... Wire.endTransmission();}void read_status(){ voltage_sum=0; somme_courante=0 ; pour (i=0;i=POINTS_FOR_AVERAGE) index_moyenne=0 ; if(tmp_battery_voltage>MAXIMUM_BATTERY_VOLTAGE) { déconnecter_circuit_charge (); //Déconnecter le chargeur de la batterie charger_state=OVERVOLTAGE; } if (tmp_current_mA>MAXIMIM_ALLOWED_CURRENT ){ disconnect_ Charging_circuit(); //Déconnecter le chargeur de la batterie charger_state=OVERCURRENT; }} void disconnect_charge_circuit(){ digitalWrite(CHARGE_RELAY_PIN,DISCONNECT_CHARGE_RELAY); //Déconnectez le chargeur de la batterie}void connect_charge_circuit(){ digitalWrite(CHARGE_RELAY_PIN,CONNECT_CHARGE_RELAY); //Connecter le chargeur à la batterie}//sec_index=0;//min_index=0;
lcd.inoArduino
void update_lcd(String first_line,String second_line){ //Serial.print("update_lcd "); //Série.print(lcd_last_string2) ; //Série.print(" "); //Serial.println(second_line); if (lcd_last_string1!=first_line){ lcd.clear(); lcd.setCursor(0,0); lcd.print(première_ligne); lcd_last_string1=first_line; lcd.setCursor(0,1) ; lcd.print(second_line); lcd_last_string2=second_line ; } if(lcd_last_second!=second()){ if (lcd_last_string2!=second_line){ lcd.setCursor(0,1) ; lcd.print(second_line); lcd_last_string2=second_line ; } } lcd_last_second=second();}String construct_status_string(void){ String v,i; if (battery_voltage<10) v=String(battery_voltage, 2); else v=String(battery_voltage, 1); if (current_mA<10) i=String(current_mA, 2); sinon i=String(current_mA, 1); //Série.println(v); mon temps s'est écoulé ; Chaîne msg,msg_time; //Serial.print(charge_démarré); //Série.print(" "); //Serial.println(String(millis()-charge_started)); switch(charger_state){ case CHARGING:elapsed=mills2time(ChargingTimeMillis); Pause; cas TRICKLE :écoulé=mills2time(TrickleChargingTimeMillis); Pause; } if (charger_state==CHARGING || charger_state==TRICKLE){ if (elapsed.total_minutes<10) msg_time=String(elapsed.total_minutes)+" " ; else if (elapsed.total_minutes<100) msg_time=String(elapsed.total_minutes)+" "; else msg_time=String(elapsed.total_minutes); } switch(charger_state){ case CHARGING:msg=v+String(F("V "))+i+String(F("mA"))+" "+msg_time; Pause; case TRICKLE:msg=v+String(F("V "))+i+String(F("mA"))+" "+msg_time; Pause; default:msg=v+String(F("V "))+i+String(F("mA")); } msg.replace("-","");//Remove minus sign return msg;}String construct_time_string(mytime timeinfo){ String mystring=String(timeinfo.hours,DEC)+String(F(":"))+String(timeinfo.minutes,DEC); //return String(timeinfo.hours,DEC)+String(F(":"))+String(timeinfo.minutes,DEC); return mystring;}
calculations.inoArduino
float best_linear_fit(float y[MINUTES_TO_LOG]){ float sx =0.0, sy =0.0, sxx =0.0, sxy =0.0; //int n =y.size(); for (i =0; i  
New LiquidCrystal library used for this projectArduino
Aucun aperçu (téléchargement uniquement).

Schémas

charger_AgK96zxw2T.zip

Processus de fabrication

  1. Alarme de soif d'usine
  2. Horloge de mots italienne
  3. Seulement trois broches pour un clavier 4x3
  4. Compteur kWh Sigfox
  5. Moniteur de température Bluetooth
  6. Serrure à commande gestuelle
  7. Le compagnon IC
  8. Une entrée analogique isolée pour Arduino
  9. Mesurez votre temps de réaction