My team and I built the fly wheel design where there are two wheels and the sides of the wheels are parallel to the initial path of the ball.
We are having problems with consistency based on a number of factors, but one of them is the amount of charge our battery has at any given time. I attempted to write a program that based the programmed motor power off of the revolutions per second of the flywheel using optical shaft encoders.
clearTimer(T1);
int t = T1; //time variable
int shooterPower = 80; //power of shooters
int averageSpeed = 0; //average of the encoder readings between the two shooters to account for variation
int RPS_IDEAL = 20; //ideal revolutions per second we want the shooters to go at
int SPEED_TOLERANCE = 5; //tolerance on the ideal RPS
SensorValue[shaftRight] = 0; //setting encoders to 0 at beginning
SensorValue[shaftLeft] = 0;
motor[leftLaunch] = shooterPower; //initial acceleration
motor[rightLaunch] = shooterPower;
while(true)
{
wait1Msec(100); //to keep track of time elapsed for time variable
averageSpeed = (SensorValue[shaftRight] + SensorValue[shaftLeft])/2; //average of the encoder readings between the
//two shooters to account for variation
if (((averageSpeed/t) < (RPS_IDEAL - SPEED_TOLERANCE)) && (t != 0)) //if it's below the speed tolerance, more power
{
shooterPower = shooterPower + 5;
}
else if(((averageSpeed/t) > (RPS_IDEAL + SPEED_TOLERANCE)) && (t != 0)) //if above, less power
{
shooterPower = shooterPower - 5;
}
motor[leftLaunch] = shooterPower;
motor[rightLaunch] = shooterPower;
if((((averageSpeed/t) < (RPS_IDEAL + SPEED_TOLERANCE))&& (t != 0)) && (((averageSpeed/t) > (RPS_IDEAL - SPEED_TOLERANCE)))&& (t != 0))
{ //once it's moving at an appropriate speed, feed the balls into shooter
motor[intake] = 90;
}
else {
motor[intake] = 0; //if not moving at appropriate speed, don't feed balls into shooter
}
}
The program isn’t working, even after experimenting with the tolerance and ideal RPS. I keep getting a “divide by zero” error with “91” in parentheses. The only variable I divide by is time, and time should never be zero in the program. In the if-statements where something is divided by time, I even added an additional condition, “t != 0,” but I still get the same error.
Can T1 be used this way? Initially, I had it to where a variable, t, was increased by .1 every 100 milliseconds. But that had the same problem, and a team mate suggested I use the internal timer.
Does anyone know what the problem may be?
Also, I’m sure this isn’t the most efficient program to accomplish my goal, so suggestions on the structure of the program are also welcome.
I think that it is because “enconder / t” comes before “if t != 0” in the if statement it will divide by 0 before it reaches the “if t != 0”. Try moving it to the front or just put a 1 millisecond wait after you start the timer and before the program enters the while loop.
But it’s an “and” condition, meaning both conditions would have to be true for it to execute the code inside the if-statement. That’s what the ‘&&’ means.
And I already have a wait before it reaches those if-statements. The “wait1Msec(100).”
Thanks for the ideas though.
EDIT: I realize now what you meant the order of the conditions. Thanks
I’ve been thinking that an optical shaft encoder would be a good measure for consistent firing, because ultimately what’s important is the speed of the flywheel. But I thought the shaft encoders could only read up to ~ 1100 rpm. At 20 rps aren’t you already exceeding that?
Also, why average the 2 sides? Won’t that just impart some curve left or right? It seems like you’d just want to get left and right side equal?
Ideally, yes, I’d like for the left and right side to be equal, but I’m assuming that will never be the case due to variables beyond my control, so I take the average of the two instead.
Also, the shaft encoders only measure the degrees of rotation, not rpm. I’m unsure as to the limits of it. I had planned on experimenting with it. 20 rps would be 1200 rpm, so yeah, that would exceed 1100 rpm. Not sure what to do about that. But 20 rps was really just an initial guess. I’m unsure of what rps we actually need and I was planning on figuring that out through testing.
Thank you so much! Now I know why t = 0 in the program.
But since it’s an AND condition, wouldn’t both of the conditions have to be true regardless of which one is first? That’s what I don’t understand. edit: I understand now, thank you.
And I did not know that’s how T1 worked, thank you. Will it always just divide by the number of seconds counted? Should I do away with it and go back to my original approach of “wait1Msec(100) then t = t + .1”? I should add that I still had the divide by zero error with that approach, but I don’t think I even had the “t != 0” condition, or at least I didn’t have it first.
Also, is there anything specific you see that tells you the code might not work regardless?