I have written a code for dual axis sun tracking based on time..
I am interfacing an lcd with the pic 16f877a.
I have stumbled on a problem.
The problem I find here is that if I write it as int am1
I get output as 1.0 (I want the output to show 1.8). Here 1.8 is the step angle of the motor.
If I write it as double am1
I get an error saying operator not applicable to this operands.
If I write it as long am1
it does not rotate properly, i.e it turns 1.8 degrees and then 3.6* in the opposite direction (Considering Step Angle is 1.8*)
I've got another problem also.
I have put 2 while
loops in the beginning, while(count2>13)
and while(count2<13)
, if certain conditions are not satisfied.
Now after the while loops it should go to the infinite loop but after the first 2 for
loops in the infinite loop it seems to start from the beginning, i.e. the while
loop
Just see what is the problem.
I noticed something:
If I remove the 2nd while
loop, i.e. while(count2<13)
the program seems to work properly and vice versa. If 1st while
loop is removed and 2nd kept it works properly.
Now, I don't know what's causing the previous problem to occur.
int i;
int j;
int k;
int m;
int l;
int ch;
int count=0; //Keep track of days
int count1=0; //Reference position of motor
int count2=13+2; //Equator count value+(days passed since equator/7)
int count3=0;
int count4=0; //Direction of N-S motor 0=clockwise 1=anticlockwise
int count5=0;
int count6=0;
int count7=0;
int count8=13; //Count at equator
int am1=0.0;
int am2=0.0;
char txt1[6];
//LCD Module Connection Initialization
sbit LCD_RS at RC2_bit;
sbit LCD_EN at RC3_bit;
sbit LCD_D7 at RC7_bit;
sbit LCD_D6 at RC6_bit;
sbit LCD_D5 at RC5_bit;
sbit LCD_D4 at RC4_bit;
//End of LCD Module Connection
//Intialization of LCD Pin Direction
sbit LCD_RS_Direction at TRISC2_bit;
sbit LCD_EN_Direction at TRISC3_bit;
sbit LCD_D7_Direction at TRISC7_bit;
sbit LCD_D6_Direction at TRISC6_bit;
sbit LCD_D5_Direction at TRISC5_bit;
sbit LCD_D4_Direction at TRISC4_bit;
//End of LCD Pin Direction
void main()
{
//Intialization of Ports
TRISB=0X00; //Initialize Port B as output
PORTB=0X00; //Assign Value 0 to port B
TRISD=0X00; //Initialize Port D as output
PORTD=0X00; //Assign Value 0 to port D
//End of Initialization
Lcd_Init(); //Initailize LCD Module
Lcd_Cmd(_LCD_CLEAR); //Clear Display
Lcd_Cmd(_LCD_CURSOR_OFF); //Cursor Off
while(count2>13){ //If Earth greater than 0* of the Equator
PORTD=0X04; //Move stepper motor by a step
delay_ms(500); //Short delay
count8++; //Increment value to increment motor value by 1
if(count8==count2){ //Check if motor value = Equinox value
PORTD=0X00; //Pass no current to motor
count1=1; //Reference position value set
delay_ms(500); //Short delay
break;
}
PORTD=0X02; //Move stepper motor by a step
delay_ms(500); //Short delay
count8++; //Increment value to increment motor value by 1
if(count8==count2){ //Check if motor value = Equinox value
PORTD=0X00; //Pass no current to motor
count1=2; //Reference position value set
delay_ms(500); //Short delay
break;
}
PORTD=0X08; //Move stepper motor by a step
delay_ms(500); //Short delay
count8++; //Increment value to increment motor value by 1
if(count8==count2){ //Check if motor value = Equinox value
PORTD=0X00; //Pass no current to motor
count1=3; //Reference position value set
delay_ms(500); //Short delay
break;
}
PORTD=0X01; //Move stepper motor by a step
delay_ms(500); //Short delay
count8++; //Increment value to increment motor value by 1
if(count8==count2){ //Check if motor value = Equinox value
PORTD=0X00; //Pass no current to motor
count1=0; //Reference position value set
delay_ms(500); //Short delay
break;
}
}
while(count2<13){ //If Earth lesser than 0* of the Equator
PORTD=0X08;
delay_ms(500);
count8--;
if(count8==count2){
PORTD=0X00;
count1=1;
delay_ms(500);
break;
}
PORTD=0X02;
delay_ms(500);
count8--;
if(count8==count2){
PORTD=0X00;
count1=2;
delay_ms(500);
break;
}
PORTD=0X04;
delay_ms(500);
count8--;
if(count8==count2){
PORTD=0X00;
count1=3;
delay_ms(500);
break;
}
PORTD=0X01;
delay_ms(500);
count8--;
if(count8==count2){
PORTD=0X00;
count1=0;
delay_ms(500);
break;
}
}
for(;;) //Infinite Loop
{
for(i=0;i<1;i++) //Rotating from east to west by 1.8 every 7 minutes
{
PORTB=0X04; //Move stepper motor by a step
delay_ms(500); //Delay
PORTB=0X00; //Pass no current to motor
Lcd_Out(1,1,"Angle M1:");
am1=am1+1.8;
Lcd_Chr(1,10,48+am1); //Output value of am1 on LCD
Lcd_Chr_CP('.'); //To display value "."
ch=am1*10;
ch=ch%10;
Lcd_Chr(1,10,48+ch);
PORTB=0X02; //Move stepper motor by a step
delay_ms(500); //Delay
PORTB=0X00; //Pass no current to motor
am1=am1+1.8;
PORTB=0X08; //Move stepper motor by a step
delay_ms(500); //Delay
PORTB=0X00; //Pass no current to motor
am1=am1+1.8;
PORTB=0X01; //Move stepper motor by a step
delay_ms(500); //Delay
PORTB=0X00; //Pass no current to motor
am1=am1+1.8;
}
for(j=0;j<1;j++) //Rotating from west to east
{
PORTB=0X08; //Move stepper motor by a step
delay_ms(500); //Delay
am1=am1-1.8;
PORTB=0X02; //Move stepper motor by a step
delay_ms(500); //Delay
am1=am1-1.8;
PORTB=0X04; //Move stepper motor by a step
delay_ms(500); //Delay
am1=am1-1.8;
PORTB=0X01; //Move stepper motor by a step
delay_ms(500); //Delay
am1=am1-1.8;
count++;
}
if(count==2){ //For 7 days ((365/94)=3.80) --> (1.8*3.80 = 6.84 = 7 days)
if(count4==0){ //Reference that motor moving in clockwise direction
switch(count1){ //Reference position the motor stopped
case 0:
{
if (count2==26){ //One end of Equinox = 23.5* --> For 47 degrees ((47/1.8) = 26.11) =26 steps
count4=1; //Reference that motor should move in anti-clockwise direction
break;
}
PORTD=0X04; //Move stepper motor by a step
count=0; //Reset 7 day counter to 0
count1=1; //Reference position value set
delay_ms(500); //delay
count2=count2++; //Increment Equinox Step by 1
}
break;
case 1:
{
if (count2==26){ //One end of Equinox = 23.5*
count4=1; //Reference that motor should move in anti-clockwise direction
break;
}
PORTD=0X02; //Move stepper motor by a step
count1=2; //Reference position value set
count=0; //Reset 7 day counter to 0
delay_ms(500); //delay
count2=count2++; //Increment Equinox Step by 1
}
break;
case 2:
{
if (count2==26){ //One end of Equinox = 23.5*
count4=1; //Reference that motor should move in anti-clockwise direction
break;
}
PORTD=0X08; //Move stepper motor by a step
count1=3; //Reference position value set
count=0; //Reset 7 day counter to 0
delay_ms(500); //delay
count2=count2++; //Increment Equinox Step by 1
break;
}
case 3:
{
if (count2==26){ //One end of Equinox = 23.5*
count4=1; //Reference that motor should move in anti-clockwise direction
break;
}
PORTD=0X01; //Move stepper motor by a step
count1=0; //Reference position value set
count=0; //Reset 7 day counter to 0
delay_ms(500); //delay
count2=count2++; //Increment Equinox Step by 1
break;
}
}
}
if(count4==1){ //Reference that motor should move in anti-clockwise direction
switch(count5){
case 0:
{
if (count2==0){ //One end of Equinox = 23.5*
count4=0; //Reference that motor should move in clockwise direction
break;
}
switch(count1){ //Reference position of the motor
case 0:
{
count6=1;
break;
}
case 1:
{
count6=4;
break;
}
case 2:
{
count6=3;
break;
}
case 3:
{
count6=2;
break;
}
}
}
}
switch(count6){
case 1:
{
if (count2==0){ //One end of Equinox = 0.0*
count4=0; //Reference that motor should move in clockwise direction
break;
}
PORTD=0X08; //Move stepper motor by a step
count=0; //Reset 7 day counter to 0
count1=3; //Reference position value set
delay_ms(500); //delay
count2=count2-1; //Decrement Equinox Step by 1
break;
}
case 2:
{
if (count2==0){ //One end of Equinox = 0.0*
count4=0; //Reference that motor should move in clockwise direction
break;
}
PORTD=0X02; //Move stepper motor by a step
count1=2; //Reference position value set
count=0; //Reset 7 day counter to 0
delay_ms(500); //delay
count2=count2-1; //Decrement Equinox Step by 1
break;
}
case 3:
{
if (count2==0){ //One end of Equinox = 0.0*
count4=0; //Reference that motor should move in clockwise direction
break;
}
PORTD=0X04; //Move stepper motor by a step
count1=1; //Reference position value set
count=0; //Reset 7 day counter to 0
delay_ms(500); //delay
count2=count2-1; //Decrement Equinox Step by 1
break;
}
case 4:
{
if (count2==0){ //One end of Equinox = 0.0*
count4=0; //Reference that motor should move in clockwise direction
break;
}
PORTD=0X01; //Move stepper motor by a step
count1=0; //Reference position value set
count=0; //Reset 7 day counter to 0
delay_ms(500); //delay
count2=count2-1; //Decrement Equinox Step by 1
break;
}
}
}
if (count2==0){ //One end of Equinox = 0.0*
count4=0; //Reference that motor should move in clockwise direction
}
}
else
{
for (l=0;l<2;l++){ //Delay for the rest of the 12 hours
delay_ms(431);
}
}
}
}
am1
andam2
are of typeint
. These variables are holding integer values. So by assigning float values, they will be casted to integers. So if you for example useam1 = 1.8;
the actual value ofam1
will be 1.