//Mereni energie
//(c) Jan Chroust 2013
#include "C:main.h"
#define EEPROM_SDA PIN_C4
#define EEPROM_SCL PIN_C3
//rele v blok sch. REL1 a REL2
#define REL1_IN1 PIN_D6
#define REL1_IN2 PIN_D7
//rele v blok sch. REL5
#define REL2_IN1 PIN_B2
#define REL2_IN2 PIN_B3
//rele v blok sch.REL3
#define REL3_IN1 PIN_A0
#define REL3_IN2 PIN_A1
//rele v blok sch.REL3
#define REL4_IN1 PIN_A2
#define REL4_IN2 PIN_A3
#define NOC PIN_B1 //pro povoleni moznosti nabijet
#use i2c(master, sda=EEPROM_SDA, scl=EEPROM_SCL)
#use rs232(baud=9600,parity=N,xmit=PIN_C7,rcv=PIN_C6,bits=8) //rcv TXD xmit RXD
#include "BQ34Z100.h"
//BAT3 - pro pohyblivý panel - LION1CELLB-1
//BAT2 - pro fixní panel - LION1CELLB-2
//BAT1 - hlavní baterie - LION1CELLB-3
int16 bat1STAV,bat2STAV,bat3STAV; //zbyvajici eneregie akumulátoru v %
signed int16 bat1PROUD,bat2PROUD,bat3PROUD; //proud akumulatorem
int16 bat1NAP,bat2NAP,bat3NAP; //napeti akumulatoru
signed int16 bat1P,bat2P, bat3P; //vykon z nebo do akumulatoru
//pro odeslání
signed int16 rozdil;
char baterka[40];
void batMODE(int d) //nastavi rele do prislusneho modu
{
switch (d) {
case 1: output_high(REL1_IN2); //pro mereni
output_high(REL2_IN1);
output_high(REL3_IN2);
output_high(REL4_IN2);
delay_ms(100);
output_low(REL1_IN1);
output_low(REL1_IN2);
output_low(REL2_IN1);
output_low(REL2_IN2);
output_low(REL3_IN1);
output_low(REL3_IN2);
output_low(REL4_IN1);
output_low(REL4_IN2);
break;
case 2: output_high(REL1_IN2); //dobijeni Hl. clanku z bat3
output_high(REL2_IN1);
output_high(REL3_IN1);
output_high(REL4_IN2);
delay_ms(100);
output_low(REL1_IN2);
output_low(REL2_IN1);
output_low(REL3_IN1);
output_low(REL4_IN2);
break;
case 3: output_high(REL1_IN2); //dobijeni Hl. clanku z bat2
output_high(REL2_IN1);
output_high(REL3_IN2);
output_high(REL4_IN1);
delay_ms(100);
output_low(REL1_IN2);
output_low(REL2_IN1);
output_low(REL3_IN2);
output_low(REL4_IN1);
break;
case 4: output_high(REL1_IN1); //dobijeni Hl. clanku ze sol. clanku
output_high(REL2_IN1);
output_high(REL3_IN2);
output_high(REL4_IN2);
delay_ms(100);
output_low(REL1_IN1);
output_low(REL2_IN1);
output_low(REL3_IN2);
output_low(REL4_IN2);
break;
case 5: output_high(REL1_IN2); //vybijeni bat3 do R
output_high(REL2_IN2);
output_high(REL3_IN1);
output_high(REL4_IN2);
delay_ms(100);
output_low(REL1_IN2);
output_low(REL2_IN2);
output_low(REL3_IN1);
output_low(REL4_IN2);
break;
case 6: output_high(REL1_IN2); //vybijeni bat2 do R
output_high(REL2_IN2);
output_high(REL3_IN2);
output_high(REL4_IN1);
delay_ms(100);
output_low(REL1_IN2);
output_low(REL2_IN2);
output_low(REL3_IN2);
output_low(REL4_IN1);
default:printf("chyba");
break; }
}
void setHUB(int d) //vstupuje 1-8
//hodnota udava jaky port bude pripojen na master I2C
//zde je nastaveno propojeni jen jedne brany, je mozne propojit i vice bran naraz
{
switch (d) {
case 1: d=0x01;
break;
case 2: d=0x02;
break;
case 3: d=0x04;
break;
case 4: d=0x08;
break;
case 5: d=0x10;
break;
case 6: d=0x20;
break;
case 7: d=0x40;
break;
case 8: d=0x80;
break;
default:printf("chyba");
break; }
i2c_start();
I2C_Write(0xE0);
I2C_write(d);
i2c_stop();
}
//nacitani potrebnych informaci z modulu s baterii
void batdata(void)
{
setHUB(1);
bat1PROUD=batPROUD();
bat1STAV=batSTAV();
bat1NAP=batNAP();
setHUB(2);
bat2PROUD=batPROUD();
bat2STAV=batSTAV();
bat2NAP=batNAP();
setHUB(3);
bat3PROUD=batPROUD();
bat3STAV=batSTAV();
bat3NAP=batNAP();
bat1P=(bat1PROUD*(((float)bat1NAP/1000)));
bat2P=(bat2PROUD*(((float)bat2NAP/1000)));
bat3P=(bat3PROUD*(((float)bat3NAP/1000)));
}
void main()
{
batMODE(1);
float vypocet;
setup_adc_ports(NO_ANALOGS|VSS_VDD);
setup_adc(ADC_CLOCK_DIV_2);
setup_spi(SPI_SS_DISABLED);
setup_timer_0(RTCC_INTERNAL|RTCC_DIV_1);
setup_timer_1(T1_DISABLED);
setup_timer_2(T2_DISABLED,0,1);
setup_ccp1(CCP_OFF);
setup_comparator(NC_NC_NC_NC);// This device COMP currently not supported by the PICWizard
batMODE(1);
//printf("STAV1 STAV2 STAV3 VYKON1 VYKON2 VYKON3\r\n");
while(TRUE)
{
batdata();
//nastane pri nedostatku energie v hl. akumulátoru
while(bat1STAV<20)
{
//printf("nedostatek energie\r\n");
if(bat2STAV>10)
{
batMODE(3);
}
else
{
if(bat3STAV>10)
{
batMODE(2);
}
else
{
batMODE(4);
}
}
batdata();
sprintf(baterka, " %3.0Ld %3.0Ld %3.0Ld %5.0Ld %5.0Ld %5.0Ld %5.0Ld", bat1STAV, bat2STAV, bat3STAV, bat1P, bat2P, bat3P, 0);
printf(baterka);
delay_ms(5000);
}
//osetreni proti prebiti clanku
while(bat2STAV>96)
{
//printf("bat2 prebita");
if(bat1STAV>98)
{
batMODE(6); //vybijeni do rezistoru
}
else
{
batMODE(3); //nabijeni hl. akumulatoru
}
batdata();
sprintf(baterka, " %3.0Ld %3.0Ld %3.0Ld %5.0Ld %5.0Ld %5.0Ld %5.0Ld", bat1STAV, bat2STAV, bat3STAV, bat1P, bat2P, bat3P, 0);
printf(baterka);
bat2STAV=bat2STAV-2;
delay_ms(5000);
}
while(bat3STAV>96)
{
//printf("bat3 prebyta\r\n");
if(bat1STAV>98)
{
batMODE(5); //vybijeni do rezistoru
}
else
{
batMODE(2); //vybijeni do hl. akumulatoru
}
batdata();
sprintf(baterka, " %3.0Ld %3.0Ld %3.0Ld %5.0Ld %5.0Ld %5.0Ld %5.0Ld", bat1STAV, bat2STAV, bat3STAV, bat1P, bat2P, bat3P, 0);
printf(baterka);
bat3STAV=bat3STAV-2;
delay_ms(5000);
}
while(input(NOC)==1) //nastane pri zapadu Slunce
{
//printf("noc\r\n");
batdata();
if(bat1STAV<98) //dobiti hl. akumulatoru
{
if(bat2STAV>20)
{
batMODE(3);
}
else
{
if(bat3STAV>20)
{
batMODE(2);
}
else
{
batMODE(1);
}
}
batdata();
}
else //prebitecna energie do rezistoru
{
if(bat2STAV>20)
{
batMODE(6);
}
else
{
if(bat3STAV>20)
{
batMODE(5);
}
else
{
batMODE(1);
}
}
}
batdata();
sprintf(baterka, " %3.0Ld %3.0Ld %3.0Ld %5.0Ld %5.0Ld %5.0Ld %5.0Ld", bat1STAV, bat2STAV, bat3STAV, bat1P, bat2P, bat3P, 0);
//sprintf(baterka, "%Ld %Ld %Ld 0 0 0 0" bat1STAV, bat2STAV, bat3STAV);
printf(baterka);
delay_ms(5000);
}
batMODE(1);
if(bat2P==0) //osetreni deleni nulou
{
rozdil=9999;
}
else
{
vypocet=(((float)bat3P-bat2P)/bat2P)*100; //vypocet rozdilu dodavane enengie dodavane solárnim panelem sledujícím Slunce a fixnim solarnim panelem
rozdil=(signed int)vypocet;
}
//zaslani namerenych udaju na seriovou linku
sprintf(baterka, " %3.0Ld %3.0Ld %3.0Ld %5.0Ld %5.0Ld %5.0Ld %5.0Ld", bat1STAV, bat2STAV, bat3STAV, bat1P, bat2P, bat3P, rozdil);
printf(baterka);
delay_ms (20000);
}
}