带有正交编码器600ppr的Arduino RPM代码

时间:2018-07-12 04:35:11

标签: c++ arduino arduino-uno encoder

我正在尝试以一种可以在编码器上测量RPM的方式设置arduino uno。到目前为止,我已经能够弄清楚如何准确地测量第一个值的RPM,但是我正在努力在循环结束时重置该值,因此与其给我实际的转数,不如将其与先前的数据一起递增。这是我的代码,可以更好地理解我的意思...

// Red - 5V
// Black - GND

const int encoder_a = 2; // Green - pin 2 - Digital
const int encoder_b = 3; // White - pin 3 - Digital
long encoder = 0;
long encoderO=0;


void setup() {
    Serial.begin(9600);
    pinMode(encoder_a, INPUT_PULLUP);
    pinMode(encoder_b, INPUT_PULLUP);

    attachInterrupt(0, encoderPinChangeA, CHANGE);
    attachInterrupt(1, encoderPinChangeB, CHANGE);
}

void loop() {
    Serial.println(encoder/2400.00*60);
    delay(1000);
}

void encoderPinChangeA() {
    encoder += digitalRead(encoder_a) == digitalRead(encoder_b) ? -1 : 1;
}

void encoderPinChangeB() {
    encoder += digitalRead(encoder_a) != digitalRead(encoder_b) ? -1 : 1;
}

3 个答案:

答案 0 :(得分:0)

我会尝试对代码进行一些重组。这主要是为了区分速度和方向,因为它们彼此不依赖。例如:

long encoder_pulse_counter = 0;
long direction = 1


void setup() {
    Serial.begin(9600);
    pinMode(encoder_a, INPUT_PULLUP);
    pinMode(encoder_b, INPUT_PULLUP);

    attachInterrupt(0, encoderPinChangeA, CHANGE);
    attachInterrupt(1, encoderPinChangeB, CHANGE);
}

void loop(){
    long speed = encoder_pulse_counter/2400.00*60; // Not sure, encoder not specified
    Serial.println(direction*speed);
    encoder_pulse_counter = 0; // Clear variable just before counting again 
    delay(1000);
}


void encoderPinChangeA(){
    encoder_pulse_counter += 1;
    direction = digitalRead(encoder_a) == digitalRead(encoder_b) ? -1 : 1;
}

void encoderPinChangeB(){
    encoder_pulse_counter += 1;
    direction = digitalRead(encoder_a) != digitalRead(encoder_b) ? -1 : 1;
}

我没有测试此代码,因此可能存在一些小错误。但是我认为分开计算会容易得多。希望这会有所帮助!

答案 1 :(得分:0)

Wessels的回答很好。所提供的代码中的一些小错误,完整的工作代码和经过测试的代码:

const int encoder_a = 3; // Pin 3
const int encoder_b = 5; // Pin 5
long encoder_pulse_counter = 0;
long direction = 1;

void encoderPinChangeA()
{
    encoder_pulse_counter += 1;
    direction = digitalRead(encoder_a) == digitalRead(encoder_b) ? -1 : 1;
}

void encoderPinChangeB()
{
    encoder_pulse_counter += 1;
    direction = digitalRead(encoder_a) != digitalRead(encoder_b) ? -1 : 1;
}

void setup() 
{
    Serial.begin(9600);
    pinMode(encoder_a, INPUT_PULLUP);
    pinMode(encoder_b, INPUT_PULLUP);
    attachInterrupt(0, encoderPinChangeA, CHANGE);
    attachInterrupt(1, encoderPinChangeB, CHANGE);
}

void loop()
{
    long speed = encoder_pulse_counter/1024.00*60; // For encoder plate with 1024 Pulses per Revolution
    Serial.print("RPM: ");
    Serial.println(direction*speed);
    encoder_pulse_counter = 0; // Clear variable just before counting again 
    delay(1000);
}

答案 2 :(得分:0)

volatile long encoder_pulse_counter = 0;
volatile long direction = 1


void setup() {
    Serial.begin(9600);
    pinMode(encoder_a, INPUT_PULLUP);
    pinMode(encoder_b, INPUT_PULLUP);

    attachInterrupt(0, encoderPinChangeA, CHANGE);
    attachInterrupt(1, encoderPinChangeB, CHANGE);
}

void loop(){
    long speed = encoder_pulse_counter/2400.00*60; // Not sure, encoder not specified
    Serial.println(direction*speed);
    encoder_pulse_counter = 0; // Clear variable just before counting again 
    delay(1000);
}


void encoderPinChangeA(){
    encoder_pulse_counter += 1;
    direction = digitalRead(encoder_a) == digitalRead(encoder_b) ? -1 : 1;
}

void encoderPinChangeB(){
    encoder_pulse_counter += 1;
    direction = digitalRead(encoder_a) != digitalRead(encoder_b) ? -1 : 1;
}

同意看起来不错,只需在ISR中使用的任何变量中添加volatile。