analogRead需要太多时间

时间:2017-02-22 21:26:00

标签: arduino arduino-uno electronics

我在面包板上制作了一个带有Arduino Uno和梯形电阻梯的基本波形发生器。我使用loop函数和micros()根据需要更改电压电平,以在每次电压变化之间进行延迟。它并不完美,但它适用于压电。

我的问题是我在我的代码中设置信号频率,我希望能够使用例如一个锅来改变它。但是只要我在代码中放置analogRead(所有代码都在loop()函数中),输出信号就会改变。我发现analogRead函数运行时间可能长达100μs,并且大于每次电压变化之间的延迟,因此实际信号周期不正确:

unsigned long now, next;
int freq;

void loop(){

    //if I put analogRead() here it takes to much time

    now = micros();

    if(now >= next){
        //Here I change the output analog value using a R-2R ladder
        //then I change the value of next 
    }
}

我尝试了一些解决方案,包括使用开关而不是使用开关,但digitalRead结合if语句似乎效率更高。我也尝试过使用中断的开关,但结果与digitalRead相同。

有人知道另一种解决方案吗?

谢谢!

1 个答案:

答案 0 :(得分:2)

analogRead等待转换完成,所以如果你想做其他事情,你必须以不同的方式处理它。

您可以使用ADC中断和自由运行模式。或者您可以通过多个来源触发ADC转换周期,例如定时器比较。

或者你可以通过“基于事件”的方法来做 - 通过检查ADC转换完成并通过将逻辑1写入该标志来重置它。

// in setup:
ADCSRA |= _BV(ADATE); // enable auto trigger mode 
ADCSRB = 0; // free running mode for the auto trigger

// and in the loop:
if (ADCSRA & _BV(ADIF)) {
    value = ADC; // get ADC value
    ADCSRA |= _BV(ADIF); // reset flag by writing logic one into it
    // whatever you want with the current value
    // or  ADCSRA |= _BV(ADSC); // start another conversion if you don't want free running mode
}

顺便说一句:宏_BV(BIT)被替换为1<<(BIT)(如果你想知道我为什么要使用它)