#include <Servo.h> Servo esc1; Servo esc2; Servo esc3; Servo esc4; #define SRC_NEUTRAL 1504 #define SRC_MAX 2004 #define SRC_MIN 988 #define TRC_NEUTRAL 1504 #define TRC_MAX 1992 #define TRC_MIN 1004 #define SRC_INTERVAL 50 #define TRC_INTERVAL 30 uint16_t unSteeringMin = SRC_MIN; uint16_t unSteeringMax = SRC_MAX; uint16_t unSteeringCenter = SRC_NEUTRAL; uint16_t unThrottleMin = TRC_MIN; uint16_t unThrottleMax = TRC_MAX; uint16_t unThrottleCenter = TRC_NEUTRAL; #define pos_min 39 #define pos_max 140 #define PPM_SPEED_1 5 #define PPM_SPEED_2 6 #define PPM_SPEED_3 9 #define PPM_SPEED_4 10 #define THROTTLE_IN_PIN 2 #define STEERING_IN_PIN 3 #define THROTTLE_FLAG 1 #define STEERING_FLAG 2 volatile uint8_t bUpdateFlagsShared; volatile uint16_t unThrottleInShared; volatile uint16_t unSteeringInShared; uint32_t ulThrottleStart; uint32_t ulSteeringStart; uint8_t gThrottle = 0; uint8_t gGear = 1; uint8_t gOldGear = 1; #define DIRECTION_STOP 0 #define DIRECTION_FORWARD 1 #define DIRECTION_REVERSE 2 #define DIRECTION_ROTATE_RIGHT 3 #define DIRECTION_ROTATE_LEFT 4 uint8_t gThrottleDirection = DIRECTION_STOP; uint8_t gDirection = DIRECTION_STOP; uint8_t gOldDirection = DIRECTION_STOP; unsigned long pulse_time ; void setup() { Serial.begin(9600); attachInterrupt(0, calcThrottle, CHANGE); attachInterrupt(1, calcSteering, CHANGE); esc1.attach(PPM_SPEED_1); esc2.attach(PPM_SPEED_2); esc3.attach(PPM_SPEED_3); esc4.attach(PPM_SPEED_4); pulse_time = millis(); arm(); } void arm() { Serial.println("Arming start"); for(int i = 0; i < 50; i++) { esc1.write(140); esc2.write(140); esc3.write(140); esc4.write(140); delay(1); esc1.write(39); esc2.write(39); esc3.write(39); esc4.write(39); delay(20); } Serial.println("Arming done"); } void loop() { static uint16_t unThrottleIn; static uint16_t unSteeringIn; static uint8_t bUpdateFlags; Serial.print("Throttle: "); Serial.println(unThrottleInShared); Serial.print("Steering: "); Serial.println(unSteeringInShared); if(bUpdateFlagsShared) { noInterrupts(); pulse_time = millis(); bUpdateFlags = bUpdateFlagsShared; if(bUpdateFlags & THROTTLE_FLAG) { unThrottleIn = unThrottleInShared; } if(bUpdateFlags & STEERING_FLAG) { unSteeringIn = unSteeringInShared; } interrupts(); } if(bUpdateFlags & THROTTLE_FLAG) { unThrottleIn = constrain(unThrottleIn, unThrottleMin, unThrottleMax); if(unThrottleIn > (unThrottleCenter + TRC_INTERVAL)) { gThrottle = map(unThrottleIn,(unThrottleCenter + TRC_INTERVAL),unThrottleMax,pos_min,pos_max); gThrottleDirection = DIRECTION_FORWARD; } else if (unThrottleIn < (unThrottleCenter - TRC_INTERVAL)) { gThrottle = map(unThrottleIn,unThrottleMin,(unThrottleCenter-TRC_INTERVAL),pos_max,pos_min); gThrottleDirection = DIRECTION_REVERSE; } else { gThrottleDirection = DIRECTION_STOP; gThrottle=0; } } uint8_t throttleSlow = gThrottle; if(bUpdateFlags & STEERING_FLAG) { gDirection = gThrottleDirection; unSteeringIn = constrain(unSteeringIn, unSteeringMin, unSteeringMax); if(unSteeringIn > (unSteeringCenter + SRC_INTERVAL)) { gDirection = DIRECTION_ROTATE_RIGHT; throttleSlow = map(unSteeringIn, unSteeringCenter, unSteeringMax, gThrottle, gThrottle*0.8); } else if(unSteeringIn<(unSteeringCenter - SRC_INTERVAL)) { gDirection = DIRECTION_ROTATE_LEFT; throttleSlow = map(unSteeringIn, unSteeringMin, unSteeringCenter, gThrottle*0.8, gThrottle); } } if (gThrottleDirection == DIRECTION_FORWARD) { if (gDirection == DIRECTION_ROTATE_RIGHT) { esc1.write(39); esc2.write(39); esc3.write(gThrottle); esc4.write(throttleSlow); } else if (gDirection == DIRECTION_ROTATE_LEFT) { esc1.write(39); esc2.write(39); esc3.write(throttleSlow); esc4.write(gThrottle); } else { esc1.write(39); esc2.write(39); esc3.write(gThrottle); esc4.write(gThrottle); } } else if (gThrottleDirection == DIRECTION_REVERSE) { if (gDirection == DIRECTION_ROTATE_RIGHT) { esc1.write(throttleSlow); esc2.write(gThrottle); esc3.write(39); esc4.write(39); } else if (gDirection == DIRECTION_ROTATE_LEFT) { esc1.write(gThrottle); esc2.write(throttleSlow); esc3.write(39); esc4.write(39); } else { esc1.write(gThrottle); esc2.write(gThrottle); esc3.write(39); esc4.write(39); } } else { esc1.write(39); esc2.write(39); esc3.write(39); esc4.write(39); } bUpdateFlags = 0; } void calcThrottle() { if(digitalRead(THROTTLE_IN_PIN) == HIGH) { ulThrottleStart = micros(); } else { unThrottleInShared = (uint16_t)(micros() - ulThrottleStart); bUpdateFlagsShared |= THROTTLE_FLAG; } } void calcSteering() { if(digitalRead(STEERING_IN_PIN) == HIGH) { ulSteeringStart = micros(); } else { unSteeringInShared = (uint16_t)(micros() - ulSteeringStart); bUpdateFlagsShared |= STEERING_FLAG; } }