コード例 #1
0
ファイル: Main.cpp プロジェクト: hal7df/further-suggestions
	void TeleopPeriodic() {
		if(m_driver->GetRawButton(BUTTON_LB)) {
			// PYRAMID
			m_PIDController->SetSetpoint(PLATE_PYRAMID_THREE_POINT);
			m_PIDController->Enable();
		} else if(m_driver->GetRawButton(BUTTON_RB)) {
			// FEEDER
			m_PIDController->SetSetpoint(PLATE_FEEDER_THREE_POINT);
			m_PIDController->Enable();
		} else if(m_driver->GetRawAxis(TRIGGERS) > 0.5) {
			m_PIDController->SetSetpoint(PLATE_TEN_POINT_CLIMB);
			m_PIDController->Enable();
		} else {
			// MANUAL CONTROL
			m_PIDController->Disable();
			
			m_plate1->Set(-deadband(m_driver->GetRawAxis(LEFT_Y)));
			m_plate2->Set(-deadband(m_driver->GetRawAxis(LEFT_Y)));
		}
		
		// ----- PRINT -----
		SmartDashboard::PutNumber("Plate Position: ", m_plateSensor->GetVoltage());
		SmartDashboard::PutNumber("PID GET: ", m_plateSensor->PIDGet());
		
	} // TeleopPeriodic()
コード例 #2
0
task main()
{
    float leftFront, leftBack, rightFront, rightBack; // motors

    /***** BEGIN Mecanum Arcade Drive Test *****/
    init();
    StartTask(gyro_calibrate, 8);
    StartTask(displaySmartDiags, 255);
    if (bCompetitionMode) {waitForStart();}

    while (true)
    {
        /***** Proportional Motor Control *****/
        getJoystickSettings(joystick); //get all joystick statuses

        mecanum_arcade(deadband(k_deadband,joystick.joy1_y1),
		       deadband(k_deadband,joystick.joy1_x1),
        	       deadband(k_deadband,joystick.joy1_x2),
        	       leftFront, rightFront, leftBack, rightBack);

        motor[Lf] = leftFront;
        motor[Rf] = rightFront;
        motor[Lb] = leftBack;
        motor[Rb] = rightBack;

        nxtDisplayCenteredBigTextLine(6, "%.2f", gyro_getheading());
        nxtDisplayCenteredTextLine(5, "%.2f", gyro_getrotspeed());

        if(joy1Btn(4) == 1) { gyro_reset(); }
        while(nNxtButtonPressed == kEnterButton) { gyro_reset(); }
    }
}
コード例 #3
0
void setDrive()         // reads Joystick, calculates drive motor values and sends values to motors - used in driver control 
{ 
    int driveJoystickY = deadband(vexRT[Ch3], DRIVE_DEADBAND_THRESHOLD);    // read from the left josytick Y-axis (channel 3) and deadband value 
    int driveJoystickX = deadband(vexRT[Ch4], DRIVE_DEADBAND_THRESHOLD);    // read from the left josytick X-axis (channel 4) and deadband value 
    int rightMotorValue = driveJoystickY - driveJoystickX;                                // arcade drive left side value 
    int leftMotorValue = driveJoystickY + driveJoystickX;                                     // arcade drive right side value 
    setDriveMotors(rightMotorValue, leftMotorValue);    // send the calculated motor values to the drive sides 
} 
コード例 #4
0
/**
 * update attitude
 *
 * @param 
 * 		void
 *
 * @return
 *		void
 *
 */
void attitudeUpdate(){

	float yrpAttitude[3];
	float pryRate[3];
	float xyzAcc[3];
	float xComponent[3];
	float yComponent[3];
	float zComponent[3];
	float xyzMagnet[3];
#if CHECK_ATTITUDE_UPDATE_LOOP_TIME
	struct timeval tv_c;
	static struct timeval tv_l;
	unsigned long timeDiff=0;
	
	gettimeofday(&tv_c,NULL);
	timeDiff=GET_USEC_TIMEDIFF(tv_c,tv_l);
	_DEBUG(DEBUG_NORMAL,"attitude update duration=%ld us\n",timeDiff);
	UPDATE_LAST_TIME(tv_c,tv_l);
#endif	
			
	getYawPitchRollInfo(yrpAttitude, pryRate, xyzAcc, xComponent, yComponent, zComponent,xyzMagnet); 

	setYaw(yrpAttitude[0]);
	setRoll(yrpAttitude[1]);
	setPitch(yrpAttitude[2]);
	setYawGyro(-pryRate[2]);
	setPitchGyro(pryRate[0]);
	setRollGyro(-pryRate[1]);
	setXAcc(xyzAcc[0]);
	setYAcc(xyzAcc[1]);
	setZAcc(xyzAcc[2]);
	setXGravity(zComponent[0]);
	setYGravity(zComponent[1]);
	setZGravity(zComponent[2]);
	setVerticalAcceleration(deadband((getXAcc() * zComponent[0] + getYAcc() * zComponent[1]
		+ getZAcc() * zComponent[2] - 1.f) * 100.f,3.f) );
	setXAcceleration(deadband((getXAcc() * xComponent[0] + getYAcc() * xComponent[1]
		+ getZAcc() * xComponent[2]) * 100.f,3.f) );
	setYAcceleration(deadband((getXAcc() * yComponent[0] + getYAcc() * yComponent[1]
		+ getZAcc() * yComponent[2]) * 100.f,3.f) );

	_DEBUG(DEBUG_ATTITUDE,
			"(%s-%d) ATT: Roll=%3.3f Pitch=%3.3f Yaw=%3.3f\n", __func__,
			__LINE__, getRoll(), getPitch(), getYaw());
	_DEBUG(DEBUG_GYRO,
			"(%s-%d) GYRO: Roll=%3.3f Pitch=%3.3f Yaw=%3.3f\n",
			__func__, __LINE__, getRollGyro(), getPitchGyro(),
			getYawGyro());
	_DEBUG(DEBUG_ACC, "(%s-%d) ACC: x=%3.3f y=%3.3f z=%3.3f\n",
			__func__, __LINE__, getXAcc(), getYAcc(), getZAcc());
	
}
コード例 #5
0
task main()
{
    float leftFront, leftBack, rightFront, rightBack; // motors
    float y, x, c;
    tPSP controller;

    /***** BEGIN Mecanum Field Oriented Drive Test *****/
    init();
    wait10Msec(100);
    StartTask(readSensors, 8);
    StartTask(displaySmartDiags, 255);
    //if (bCompetitionMode) {waitForStart();}

    while (true)
    {
				nxtDisplayCenteredTextLine(3, "%i", gyro_getheading());
        /***** Proportional Motor Control *****/
        PSPV4readButtons(PSPNXV4, controller);

			  //scale to -1 to 1
        y = (deadband(k_deadband,-controller.joystickLeft_y))/100; //strafe
        x = (deadband(k_deadband,controller.joystickLeft_x))/100; //forward/rev
        c = (deadband(k_deadband,controller.joystickRight_x))/100; //spin

        nxtDisplayTextLine(4, "%i", controller.joypadRight);
        nxtDisplayTextLine(4, "%i", controller.joypadLeft);

        if ((y == 0) && (x == 0))
        {
        	x += controller.joypadRight; //strafe
        	x -= controller.joypadLeft; //strafe
	        y += controller.joypadUp; //forward/rev
	        y -= controller.joypadDown; //forward/rev
        }

        nxtDisplayTextLine(5, "%i", y);

        mecanum_arcadeFOD(y, x, c, gyro_getheading(),
        leftFront, rightFront, leftBack, rightBack);

        motor[Lf] = leftFront*100;
        motor[Rf] = rightFront*100;
        motor[Lb] = leftBack*100;
        motor[Rb] = rightBack*100;

        if(controller.circleBtn == 1) { gyro_reset(); }
        while(nNxtButtonPressed == kEnterButton) { gyro_reset(); }
        wait1Msec(5);
    }
}
コード例 #6
0
//Called to run the robot.
task usercontrol()
{
	startTask (Drive_control);
	startTask (catapult);
	startTask (liftPlatform);

	while (true)
	{
		driveSpeed = deadband(vexRT[Ch3]);
		turnCoef = deadband(vexRT[Ch1]);

		wait1Msec(dt);
	}
}
コード例 #7
0
ファイル: HoodTest.c プロジェクト: jl2550/Aluminati
task main()
{
	waitForStart();   // wait for start of tele-op phase
	//initializeRobot();
	while (true)
	{
		getJoystickSettings(joystick);

		drive(deadband(joystick.joy1_x1), deadband(joystick.joy1_y1), deadband(joystick.joy1_x2)); // normal drive

		liftTalons(joy1Btn(4));
		dropTalons(joy1Btn(1));
	}
}
コード例 #8
0
void Turn(int power, long distance)
{
writeDebugStreamLine("new *****");
//writeDebugStreamLine("value: %d", SensorValue[Gyro]);
//int zero = initialize() + 59;//59 is added to perfectly 0 it.
long sum = 0;
//writeDebugStreamLine("delta: %d", SensorValue[Gyro] - zero);// begining delta is 59 +-1 often
//writeDebugStreamLine("zero: %d", zero);
//writeDebugStreamLine("value: %d", SensorValue[Gyro]);
//nMotorEncoder[motorB] = 0;
motor[motorD] = power;
motor[motorE] = -1 * power;
while( abs(sum) < abs(distance))// +-8400 is 90 degrees
{
   //writeDebugStreamLine("%d", SensorValue[Gyro] - zero);
   sum = sum + deadband(HTGYROreadRot(HTGYRO), 5);
   wait1Msec(10);// update interval
   writeDebugStreamLine("sum: %d", sum);
   writeDebugStreamLine("Gyro:   %4d", HTGYROreadRot(HTGYRO));
   nxtDisplayTextLine(4, "Gyro:   %4d", HTGYROreadRot(HTGYRO));
}
//writeDebugStreamLine("sum: %d", sum);
motor[motorD] = 0;
motor[motorE] = 0;
wait10Msec(1); // just to let the encoders reset when the robot is still
nMotorEncoder[motorE] = 0;
nMotorEncoder[motorD] = 0;
}
コード例 #9
0
// Called repeatedly when this Command is scheduled to run
void DriveBot::Execute() {
	Joystick* stick = Robot::oi->getGamePad();
	
	if(Robot::mover->speedSwitch->Get()){

			Robot::mover->rightMotor0->Set(deadband(stick->GetThrottle()*-0.75,.01));
			Robot::mover->rightMotor1->Set(deadband(stick->GetThrottle()*-0.75,.01));

			Robot::mover->leftMotor2->Set(deadband(stick->GetY()*0.75,.01));
			Robot::mover->leftMotor3->Set(deadband(stick->GetY()*0.75,.01));
	}else{
			Robot::mover->rightMotor0->Set(stick->GetThrottle()*-0.25);
			Robot::mover->rightMotor1->Set(stick->GetThrottle()*-0.25);

			Robot::mover->leftMotor2->Set(stick->GetY()*0.25);
			Robot::mover->leftMotor3->Set(stick->GetY()*0.25);
	}
}
コード例 #10
0
void Chassis::DriveWithJoysticks(){
	float left = deadband(Robot::oi->getleftJoy()->GetY(),0.05);

	/*if (photonOn) {
		photonCannon->Set(Relay::kForward);
	} else {
		photonCannon->Set(Relay::kReverse);
	}
	*/
	if (Robot::pneumaticSub->GetGShiftSolenoid()->Get()){
		rightMotor1->ConfigNeutralMode(CANSpeedController::NeutralMode::kNeutralMode_Brake);
		rightMotor2->ConfigNeutralMode(CANSpeedController::NeutralMode::kNeutralMode_Brake);
		float right = deadband(-1*Robot::oi->getGamepad()->GetThrottle(),0.05);
		leftMotor1->Set(left);
		leftMotor2->Set(left);
		if (right>0) {
			if (climbLS->Get()) {
				rightMotor1->Set(right*0.7);
				rightMotor2->Set(right*0.7);
			} else {
				rightMotor1->Set(0);
				rightMotor2->Set(0);
			}
		} else {
			rightMotor1->Set(right);
			rightMotor2->Set(right);
		}
	} else {
		rightMotor1->ConfigNeutralMode(CANSpeedController::NeutralMode::kNeutralMode_Coast);
		rightMotor2->ConfigNeutralMode(CANSpeedController::NeutralMode::kNeutralMode_Coast);
		float right = deadband(Robot::oi->getrightJoy()->GetY(),0.05);
		if (Robot::oi->getrightJoy()->GetRawButton(1) && Robot::oi->getleftJoy()->GetRawButton(1)){
			left  = left * -0.5;
			right = right * -0.5;
			driveMotors->TankDrive(right,left);
		} else {
			driveMotors->TankDrive(left,right);
		}
	}
}
コード例 #11
0
ファイル: RoverBot.c プロジェクト: Noah0H/Pre-Season-2013
//
// main() is where program execution begins
//
task main()
{
  waitForStart();   // wait for start of tele-op phase

  while (true)	// infinite loop
  {
  	// Read the latest joystick data from the field/driverstation
  	getJoystickSettings(joystick);

  	// Read the left and right joystick y axis
  	int left = joystick.joy1_y1;
  	int right = joystick.joy1_y2;

  	// Apply deadband function
  	left = deadband(left, DRIVE_JOYSTICK_DB);
  	right = deadband(right, DRIVE_JOYSTICK_DB);

  	// Drive with the joysticks
  	motor[leftDrive] = left;
  	motor[rightDrive] = right;
  }
}
コード例 #12
0
void TankDrive::RevArcadeDrive(Joystick* stick)
{
	float xAxis = deadband(-1*stick->GetX(), .2,0);
	float yAxis = deadband(stick->GetY(), .2,0);
	float zAxis = deadband(stick->GetZ(), .3,0);

	float left=0;
	float right=0;

	if(!zAxis==0)
	{
		left=zAxis;
		right=-1*zAxis;
	}

	else if(!xAxis==0)
	{
		if(xAxis<0)
		{
			left=(fabs(yAxis)-fabs(xAxis))*(yAxis/fabs(yAxis));
			right=yAxis;
		}
		if(xAxis>0)
		{
			right=(fabs(yAxis)-fabs(xAxis))*(yAxis/fabs(yAxis));
			left=yAxis;
		}
	}
	else if(!yAxis==0)
	{
		left=yAxis;
		right=yAxis;
	}
	leftTarget=left*maxTicks;
	rightTarget=right*maxTicks;
}
コード例 #13
0
// Task for the driver controlled portion of the competition.
task usercontrol()
{
	startTask(Pid1);
	startTask(Pid2);
	startTask(Drive_control);


	while (true)
	{
		// Drive control
		driveSpeed = deadband(vexRT[Ch3]);
		turnCoef = deadband(vexRT[Ch1]);

		/* if (vexRT(Btn7L) == 1) {
			if (victory == 0) {
				startTask(victoryDance);
				victory = 1;
			}
		} else {
			victory = 0;
		} */

		sleep(20);



		// Intake control
		upperSpeed = 0;
		lowerSpeed = 0;
		gateSpeed = 0;
		if (vexRT[Btn6U] == 1) {  // run both intake motors up when button 6 up pressed
			lowerSpeed = 127;
			if (launcherSpeed == maxLauncherSpeed) {
				upperSpeed = 127;
			}
		} else if (vexRT[Btn6D] == 1){ // both intake motors up when button 6D pressed
			lowerSpeed = -127;
			upperSpeed = -127;
		}
		if (vexRT[Btn8UXmtr2] == 1){
			gateSpeed = 127;
		}
		if (vexRT[Btn8DXmtr2] == 1){
			gateSpeed = -127;
		}

		motor[gate] = gateSpeed;

		// Individual intake control
		if (vexRT[Btn5U] == 1) {
			upperSpeed = 127;  // upper intake runs up
		} else if (vexRT[Btn5D] == 1) {
			lowerSpeed = 127;  // lower intake runs up
		}
		motor[intakeLower] = lowerSpeed;
		motor[intakeUpper] = upperSpeed;
		motor[cuteIntake] = lowerSpeed;

		// Launcher
		if (vexRT[Btn6UXmtr2] == 1 && launcherSpeed < maxLauncherSpeed) {
			launcherSpeed++; // add 1 to the launcher speed
		} else if (launcherSpeed > 0 && vexRT[Btn6UXmtr2] == 0) {
			launcherSpeed--; // subtract 1 to launcher speed
		}
		//motor[leftLauncher] = launcherSpeed;
		//motor[rightLauncher] = launcherSpeed;
		// now done by pid loops
	}
}
コード例 #14
0
static void stabilizerAltHoldUpdate(void)
{
  // Get altitude hold commands from pilot
  commanderGetAltHold(&altHold, &setAltHold, &altHoldChange);

  // Get barometer height estimates
  //TODO do the smoothing within getData
  ms5611GetData(&pressure, &temperature, &aslRaw);
  asl = asl * aslAlpha + aslRaw * (1 - aslAlpha);
  aslLong = aslLong * aslAlphaLong + aslRaw * (1 - aslAlphaLong);
  // Estimate vertical speed based on successive barometer readings. This is ugly :)
  vSpeedASL = deadband(asl - aslLong, vSpeedASLDeadband);

  // Estimate vertical speed based on Acc - fused with baro to reduce drift
  vSpeed = constrain(vSpeed, -vSpeedLimit, vSpeedLimit);
  vSpeed = vSpeed * vBiasAlpha + vSpeedASL * (1.f - vBiasAlpha);
  vSpeedAcc = vSpeed;

  // Reset Integral gain of PID controller if being charged
  if (!pmIsDischarging())
  {
    altHoldPID.integ = 0.0;
  }

  // Altitude hold mode just activated, set target altitude as current altitude. Reuse previous integral term as a starting point
  if (setAltHold)
  {
    // Set to current altitude
    altHoldTarget = asl;

    // Cache last integral term for reuse after pid init
    const float pre_integral = altHoldPID.integ;

    // Reset PID controller
    pidInit(&altHoldPID, asl, altHoldKp, altHoldKi, altHoldKd,
            ALTHOLD_UPDATE_DT);
    // TODO set low and high limits depending on voltage
    // TODO for now just use previous I value and manually set limits for whole voltage range
    //                    pidSetIntegralLimit(&altHoldPID, 12345);
    //                    pidSetIntegralLimitLow(&altHoldPID, 12345);              /

    altHoldPID.integ = pre_integral;

    // Reset altHoldPID
    altHoldPIDVal = pidUpdate(&altHoldPID, asl, false);
  }

  // In altitude hold mode
  if (altHold)
  {
    // Update target altitude from joy controller input
    altHoldTarget += altHoldChange / altHoldChange_SENS;
    pidSetDesired(&altHoldPID, altHoldTarget);

    // Compute error (current - target), limit the error
    altHoldErr = constrain(deadband(asl - altHoldTarget, errDeadband),
                           -altHoldErrMax, altHoldErrMax);
    pidSetError(&altHoldPID, -altHoldErr);

    // Get control from PID controller, dont update the error (done above)
    // Smooth it and include barometer vspeed
    // TODO same as smoothing the error??
    altHoldPIDVal = (pidAlpha) * altHoldPIDVal + (1.f - pidAlpha) * ((vSpeedAcc * vSpeedAccFac) +
                    (vSpeedASL * vSpeedASLFac) + pidUpdate(&altHoldPID, asl, false));

    // compute new thrust
    actuatorThrust =  max(altHoldMinThrust, min(altHoldMaxThrust,
                          limitThrust( altHoldBaseThrust + (int32_t)(altHoldPIDVal*pidAslFac))));

    // i part should compensate for voltage drop

  }
  else
  {
    altHoldTarget = 0.0;
    altHoldErr = 0.0;
    altHoldPIDVal = 0.0;
  }
}
コード例 #15
0
float SpektrumRX::getThrottle(void){
	return deadband(reference_command[0], 0.2);
}
コード例 #16
0
float SpektrumRX::getRoll(void){
	return deadband(reference_command[1], 0.05);
}
コード例 #17
0
float SpektrumRX::getPitch(void){
	return deadband(reference_command[2], 0.05);
}
コード例 #18
0
float SpektrumRX::getYaw(void){
	return deadband(reference_command[3], 0.05);
}
コード例 #19
0
static void stabilizerTask(void* param) {
	uint32_t attitudeCounter = 0;
	uint32_t altHoldCounter = 0;
	uint32_t lastWakeTime;

	vTaskSetApplicationTaskTag(0, (void*) TASK_STABILIZER_ID_NBR);

	//Wait for the system to be fully started to start stabilization loop
	systemWaitStart();

	lastWakeTime = xTaskGetTickCount();

	while (1) {
		vTaskDelayUntil(&lastWakeTime, F2T(IMU_UPDATE_FREQ)); // 500Hz

		// Magnetometer not yet used more then for logging.
		imu9Read(&gyro, &acc, &mag);

		if (imu6IsCalibrated()) {
			commanderGetRPY(&eulerRollDesired, &eulerPitchDesired, &eulerYawDesired);
			commanderGetRPYType(&rollType, &pitchType, &yawType);

			// 250HZ
			if (++attitudeCounter >= ATTITUDE_UPDATE_RATE_DIVIDER) {
				sensfusion6UpdateQ(gyro.x, gyro.y, gyro.z, acc.x, acc.y, acc.z, FUSION_UPDATE_DT);
				sensfusion6GetEulerRPY(&eulerRollActual, &eulerPitchActual, &eulerYawActual);

				accWZ = sensfusion6GetAccZWithoutGravity(acc.x, acc.y, acc.z);
				accMAG = (acc.x * acc.x) + (acc.y * acc.y) + (acc.z * acc.z);
				// Estimate speed from acc (drifts)
				vSpeed += deadband(accWZ, vAccDeadband) * FUSION_UPDATE_DT;

				controllerCorrectAttitudePID(eulerRollActual, eulerPitchActual, eulerYawActual,
						eulerRollDesired, eulerPitchDesired, -eulerYawDesired, &rollRateDesired,
						&pitchRateDesired, &yawRateDesired);
				attitudeCounter = 0;
			}

			// 100HZ
			if (imuHasBarometer() && (++altHoldCounter >= ALTHOLD_UPDATE_RATE_DIVIDER)) {
				stabilizerAltHoldUpdate();
				altHoldCounter = 0;
			}

			if (rollType == RATE) {
				rollRateDesired = eulerRollDesired;
			}
			if (pitchType == RATE) {
				pitchRateDesired = eulerPitchDesired;
			}
			if (yawType == RATE) {
				yawRateDesired = -eulerYawDesired;
			}

			// TODO: Investigate possibility to subtract gyro drift.
			controllerCorrectRatePID(gyro.x, -gyro.y, gyro.z, rollRateDesired, pitchRateDesired,
					yawRateDesired);

			controllerGetActuatorOutput(&actuatorRoll, &actuatorPitch, &actuatorYaw);

			if (!altHold || !imuHasBarometer()) {
				// Use thrust from controller if not in altitude hold mode
				commanderGetThrust(&actuatorThrust);
			} else {
				// Added so thrust can be set to 0 while in altitude hold mode after disconnect
				commanderWatchdog();
			}

			if (actuatorThrust > 0) {
#if defined(TUNE_ROLL)
				distributePower(actuatorThrust, actuatorRoll, 0, 0);
#elif defined(TUNE_PITCH)
				distributePower(actuatorThrust, 0, actuatorPitch, 0);
#elif defined(TUNE_YAW)
				distributePower(actuatorThrust, 0, 0, -actuatorYaw);
#else
				distributePower(actuatorThrust, actuatorRoll, actuatorPitch, -actuatorYaw);
#endif
			} else {
				distributePower(0, 0, 0, 0);
				controllerResetAllPID();
			}
		}
	}
}
コード例 #20
0
ファイル: TELEOP.c プロジェクト: jl2550/Aluminati
task main()
{
	waitForStart();   // wait for start of tele-op phase
	// initializeRobot();
	while (true)
	{
		getJoystickSettings(joystick); // update joystick input

		drive(deadband(joystick.joy1_x1), deadband(joystick.joy1_y1), deadband(joystick.joy1_x2)); // normal drive
		manualLiftSlide(deadband(joystick.joy2_y1), deadband(joystick.joy2_y2));

		if (joy1Btn(4) == 1) {
			liftTalons();
		}
		if (joy1Btn(1) == 1) {
			dropTalons();
		}

		if (joy2Btn(3) == 1)
			liftHood();

		if (joy2Btn(2) == 1)
			dropHood();

		if (joy2Btn(6) == 1)
			openGate();

		if (joy2Btn(5) == 1)
			closeGate();

		//if (joy2Btn(8))
		//{
		//	while (joy2Btn(8)) // Wait while pressed
		//	{
		//		getJoystickSettings(joystick);
		//	}
		//	if (brushToggle)
		//		brushToggle = false;
		//	else
		//		brushToggle = true;
		//}

		//if (brushToggle)
		//	motor[Brush] = 90;
		//else
		//	motor[Brush] = 0;

		if (joy1Btn(5))
			motor[Brush] = 75;

		if (joy1Btn(6))
			motor[Brush] = 0;

		if (joy2Btn(1))
			motor[Shooter] = -90;
		else
			motor[Shooter] = 0;
		// ball shooting
		//if (ServoValue[])
	}
}
コード例 #21
0
static void stabilizerAltHoldUpdate() {
	// Get the time
	float altitudeError = 0;
	static float altitudeError_i = 0;
	float instAcceleration = 0;
	float deltaVertSpeed = 0;
	static uint32_t timeStart = 0;
	static uint32_t timeCurrent = 0;


	// Get altitude hold commands from pilot
	commanderGetAltHold(&altHold, &setAltHold, &altHoldChange);

	// Get barometer height estimates
	//TODO do the smoothing within getData
	ms5611GetData(&pressure, &temperature, &aslRaw);

	// Compute the altitude
	altitudeError = aslRaw - estimatedAltitude;
	altitudeError_i = fmin(50.0, fmax(-50.0, altitudeError_i + altitudeError));

	instAcceleration = deadband(accWZ, vAccDeadband) * 9.80665 + altitudeError_i * altEstKi;

	deltaVertSpeed = instAcceleration * ALTHOLD_UPDATE_DT + (altEstKp1 * ALTHOLD_UPDATE_DT) * altitudeError;
    estimatedAltitude += (vSpeedComp * 2.0 + deltaVertSpeed) * (ALTHOLD_UPDATE_DT / 2) + (altEstKp2 * ALTHOLD_UPDATE_DT) * altitudeError;
    vSpeedComp += deltaVertSpeed;

	aslLong = estimatedAltitude;		// Override aslLong

	// Estimate vertical speed based on Acc - fused with baro to reduce drift
	vSpeedComp = constrain(vSpeedComp, -vSpeedLimit, vSpeedLimit);

	// Reset Integral gain of PID controller if being charged
	if (!pmIsDischarging()) {
		altHoldPID.integ = 0.0;
	}

	// Altitude hold mode just activated, set target altitude as current altitude. Reuse previous integral term as a starting point
	if (setAltHold) {
		// Set to current altitude
		altHoldTarget = estimatedAltitude;

		// Set the start time
		timeStart = xTaskGetTickCount();
		timeCurrent = 0;

		// Reset PID controller
		pidInit(&altHoldPID, estimatedAltitude, altHoldKp, altHoldKi, altHoldKd, ALTHOLD_UPDATE_DT);

		// Cache last integral term for reuse after pid init
		// const float pre_integral = hoverPID.integ;

		// Reset the PID controller for the hover controller. We want zero vertical velocity
		pidInit(&hoverPID, 0, hoverKp, hoverKi, hoverKd, ALTHOLD_UPDATE_DT);
		pidSetIntegralLimit(&hoverPID, 3);
		// TODO set low and high limits depending on voltage
		// TODO for now just use previous I value and manually set limits for whole voltage range
		//                    pidSetIntegralLimit(&altHoldPID, 12345);
		//                    pidSetIntegralLimitLow(&altHoldPID, 12345);              /


		// hoverPID.integ = pre_integral;
	}

	// In altitude hold mode
	if (altHold) {
		// Get current time
		timeCurrent = xTaskGetTickCount();

		// Update target altitude from joy controller input
		altHoldTarget += altHoldChange / altHoldChange_SENS;
		pidSetDesired(&altHoldPID, altHoldTarget);

		// Compute error (current - target), limit the error
		altHoldErr = constrain(deadband(estimatedAltitude - altHoldTarget, errDeadband), -altHoldErrMax, altHoldErrMax);
		pidSetError(&altHoldPID, -altHoldErr);

		// Get control from PID controller, dont update the error (done above)
		float altHoldPIDVal = pidUpdate(&altHoldPID, estimatedAltitude, false);

		// Get the PID value for the hover
		float hoverPIDVal = pidUpdate(&hoverPID, vSpeedComp, true);

		float thrustValFloat;

		// Use different weights depending on time into altHold mode
		if (timeCurrent > 150) {
			// Compute the mixture between the alt hold and the hover PID
			thrustValFloat = 0.5*hoverPIDVal + 0.5*altHoldPIDVal;
		} else {
			// Compute the mixture between the alt hold and the hover PID
			thrustValFloat = 0.1*hoverPIDVal + 0.9*altHoldPIDVal;
		}
		// float thrustVal = 0.5*hoverPIDVal + 0.5*altHoldPIDVal;
		uint32_t thrustVal = altHoldBaseThrust + (int32_t)(thrustValFloat*pidAslFac);

		// compute new thrust
		actuatorThrust = max(altHoldMinThrust, min(altHoldMaxThrust, limitThrust( thrustVal )));

		// i part should compensate for voltage drop
	} else {
		altHoldTarget = 0.0;
		altHoldErr = 0.0;
	}
}
コード例 #22
0
/*Control Layout:
Controller 1:
Left Joystick x/y - Strafe and forward for robot
Right Joystick x - Turn
Button 1: Goal Latch Closed
Button 3: Goal Latch Open
Button 4: Gyro Reset
Button 8: Slo-Mo
Controller 2:
Button 1: Blower
Button 2: Intake
Button 3: Ball storage
Button 4: Kickstand
Button 5: Intake slow (lift release)
Button 6: Intake backwards
Button 7: Touch sensor
Timers:
T1:Gyro
T2:Measure RPM
T3:Blower
T4:Global
*/
task main()
{
  float leftFront, leftBack, rightFront, rightBack; // motors
  float y, x, c;
  bool touchsensorenabled = false;
  bool blowerenabled = false;
  bool kickstandenabled = false;
  bool storageclosed = false;
  bool intakeenabled = false;
  bool estop = false;
  bool intakestartup = false;
  long intakelastchecked = -10000;
  int joy1Btn3last = 0;
  int joy1Btn2last = 0;
  int joy1Btn1last = 0;
  //Operator
  int joy2Btn1last = 0;
  int joy2Btn2last = 0;
  int joy2Btn3last = 0;
  int joy2Btn4last = 0;
  int power = 100; //power for drive motors
  /***** BEGIN Mecanum Field Oriented Drive Test *****/
  init();
  StartTask(readSensors);
  StartTask(displaySmartDiags);
  if (bCompetitionMode) {waitForStart();}
  ClearTimer(T4);
  tele_log_init();
  while (true)
  {
    /***** Proportional Motor Control *****/
    getJoystickSettings(joystick); //get all joystick statuses
    if (joy1Btn(8))
    {
      power = 25;
    }
    else { power = 100; }
    //Drive Code
    if ((deadband(k_deadband,joystick.joy1_y1) == 0 &&
      deadband(k_deadband,joystick.joy1_x1) == 0 &&
    deadband(k_deadband,joystick.joy1_x2) == 0)) {
      motor[Lf] = 0;
      motor[Rf] = 0;
      motor[Lb] = 0;
      motor[Rb] = 0;
    }
    else {
      //scale to -1 to 1
      y = ((deadband(k_deadband,joystick.joy1_y1)+1)/128); //strafe
      x = ((deadband(k_deadband,joystick.joy1_x1)+1)/128); //forward/rev
      c = ((deadband(k_deadband,joystick.joy1_x2)+1)/128); //spin

      mecanum_arcadeFOD(y, x, c, gyro_getheading(),
      leftFront, rightFront, leftBack, rightBack);

      motor[Lf] = leftFront*power;
      motor[Rf] = rightFront*power;
      motor[Lb] = leftBack*power;
      motor[Rb] = rightBack*power;
    }
    //Gyro Reset Code
    if(joy1Btn(4) == 1) { gyro_reset(); }
  if(joystick.joy1_TopHat == 0) {
		gyro_reset();
	}
	//90 Deg
	if(joystick.joy1_TopHat == 2) {
		gyro_reset();
		gyro_set(90);
	}
	//180 Deg
	if(joystick.joy1_TopHat == 4) {
		gyro_reset();
		gyro_set(180);
	}
	//270 Deg
	if(joystick.joy1_TopHat == 6) {
		gyro_reset();
		gyro_set(270);
	}
    if(nNxtButtonPressed == kEnterButton) { gyro_reset(); }
    if (joy1Btn(7) == 1){
      servo[GoalRetainer] = 255;
    }
    //Goal Latch Open
    if(joy1Btn(3)== 1 && joy1Btn3last != 1){
      servo[GoalRetainer] = 130;
    }
    //Goal Latch Closed
    if(joy1Btn(1)== 1 && joy1Btn1last != 1){
      servo[GoalRetainer] = 5;
    }

    //Blower Toggle
    if(joy2Btn(1)== 1 && joy2Btn1last != 1){
      if (blowerenabled){
        motor[BlowerA] = 1;
        motor[BlowerB] = 1;
        motor[BlowerC] = 1;
        //Start timer for 1 sec, then set motors to 0
        ClearTimer(T3);
        blowerenabled = false;
        log_write("BL","OFF");
      }
      else{
        ClearTimer(T2);
        nMotorEncoder[BlowerB] = 0;
        motor[BlowerA] = 100;
        motor[BlowerB] = 100;
        motor[BlowerC] = 100;
        blowerenabled = true;
        log_write("BL","ON");
      }
    }
    //If 5 seconds since blower shutdown-brake motors
    if (time1[T3] > 5000 && !blowerenabled){
      motor[BlowerA] = 0;
      motor[BlowerB] = 0;
      motor[BlowerC] = 0;
    }
    //Intake Forwards, back, slow forward
    if (joy2Btn(2) && joy2Btn2last != 1){
      if (intakeenabled){
        intakeenabled = false;
        log_write("IN","OFF");
      }
      else{
        intakelastchecked = -10000;
        nMotorEncoder[Rf] = 4000;
        intakeenabled = true;
        intakestartup = true;
        log_write("IN","ON");
      }
    }
    int nIntakeHealthyVal = 400;

    if (joy2Btn(5) == 1){
      motor[Intake] = 25;
    }
    else if (joy2Btn(6) == 1){
      motor[Intake] = -100;
    }
    else if (joy2Btn(7) == 1){
      motor[Intake] = 100;
    }
    else if (joy2Btn(8) == 1){
      motor[Intake] = -50;
    }
    else if (!intakeenabled){
      motor[Intake] = 0;
    }
    else if (intakeenabled && time1[T4] > intakelastchecked+500){
      if (abs(nMotorEncoder[Rf]) > nIntakeHealthyVal || intakestartup){
        motor[Intake] = 100;
        intakestartup = false;
      }
      else {
        motor[Intake] = -100;
      }
      nMotorEncoder[Rf] = 0;
      intakelastchecked = time1[T4];
    }
    //Storage Toggle
    if(joy2Btn(3)== 1 && joy2Btn3last != 1){
      if (storageclosed){
        servo[BallStorage] = 80;
        storageclosed = false;
      }
      else{
        servo[BallStorage] = 140;
        storageclosed = true;
      }
    }
    //Kickstand Toggle
    if(joy2Btn(4)== 1 && joy2Btn4last != 1){
      if (kickstandenabled){
        servo[Kickstand] = 155;
        kickstandenabled = false;
      }
      else{
        servo[Kickstand] = 31;
        kickstandenabled = true;
      }
    }

    //Touch Sensor Toggle
    if(joy1Btn(2)== 1 && joy1Btn2last != 1){
      if (touchsensorenabled){
        servo[TouchSensor] = 65;
        touchsensorenabled = false;
      }
      else{
        servo[TouchSensor] = 190;
        touchsensorenabled = true;
      }
    }

    //E Stop for blower
    if (!estop && time1[T4] > 117000 && blowerenabled){
      motor[BlowerA] = 1;
      motor[BlowerB] = 1;
      motor[BlowerC] = 1;
      //Start timer for 1 sec, then set motors to 0
      ClearTimer(T3);
      blowerenabled = false;
      estop = true;
    }
    else if (time1[T4] >117000){
      log_stop();
    }

    //VOLTAGE
    if (time100[T2] >= 20) {
      float v = (float)externalBatteryAvg / (float)1000;
      string sv = "";
      StringFormat(sv, "%1.2f", v);
      log_write("V", sv);

      if (blowerenabled) {
        float dEncoderCount = nMotorEncoder[BlowerB];
        float dTime = time1[T2];
        float rpm = (4439 * (dEncoderCount))/(dTime);
        string s = "";
        StringFormat(s,"RPM: %1.2f",rpm);
        nxtDisplayTextLine(5, s);
        log_write("BL",s);
        nMotorEncoder[BlowerB] = 0;
      }

      //Clear for next calculation
      ClearTimer(T2);
    }
    //Winch
    if (deadband(k_deadband,joystick.joy2_y2) == 0){
      servo[TubeWinch] = 127;
    }
    else{
      servo[TubeWinch] = (deadband(k_deadband,joystick.joy2_y2))+127;
    }
    joy1Btn1last = joy1Btn(1);
    joy1Btn2last = joy1Btn(2);
    joy1Btn3last = joy1Btn(3);
    joy2Btn1last = joy2Btn(1);
    joy2Btn2last = joy2Btn(2);
    joy2Btn3last = joy2Btn(3);
    joy2Btn4last = joy2Btn(4);
    //DO NOT REMOVE THIS WAIT, See issue #11
    nxtDisplayTextLine(4, "%i", gyro_getheading());
    wait1Msec(5);
  }
}