Установка ADC на 2 порта

dim3740

✩✩✩✩✩✩✩
17 Июн 2020
16
0
Здравствуйте. Помогите исправить настройку ADC порта А0. Он опрашивается по прерыванию, т.к. к нему подключен потенциометр. Еще на А5 - кнопка, т.к. иные порты заняты, опрашивается в loop. Вопросы дребезга и т.п. не стоят. Обработка кнопки не работает. Более того, код вообще стопорится при инициализации портов. Также неплохо бы применить библу "GyverButton.h" на кнопку. Примера не могу найти.

C++:
void setup() {
 int analog = analogRead(5);  // 1  работает
 
  ADMUX = 0  | _BV(ADLAR) | _BV(REFS0); // пин 0 - устанавливаем канал, используем 8 бит, ref=Vcc
  ADCSRA = _BV(ADEN) | // ADC enable
           _BV(ADSC) | // ADC start
           _BV(ADATE) | // Auto trigger
           _BV(ADPS2) | _BV(ADPS1) | _BV(ADPS0);

 // int analog = analogRead(5);   // 2   - если тут тот код стопорится
 
  Serial.begin(9600);
 
}
 
void loop() {
 
  Serial.print("111111111111");
 
}
 

poty

★★★★★★✩
19 Фев 2020
2,989
895
Если у Вас на А5 одна кнопка, то используйте его как цифровой порт.
analogRead перенастраивает ADC на однократное чтение, а так как он в МП один, то Ваши настройки с прерываниями уничтожаются. Если действительно надо считывать два аналоговых порта, то нужно вручную (через регистры) переключать мультиплексор, тогда все настройки будут сохраняться. И не забывайте, что при автоматической инициализации следующего цикла измерений переключение портов будет влиять только на следующее измерение.
 

dim3740

✩✩✩✩✩✩✩
17 Июн 2020
16
0
Спасибо огромное от отзыв! Я очень рассчитываю на помощь, ибо я тут заказчик - дилетант и мне надо просто немного доработать чужой код. К сожалению, я ошибся указав А5, а реально - это А7 с внешним резистором. Далее. Понимаю, что АЦП один и применяется мультиплексирование. Итак, "настройки с прерываниями на А0" уничтожаются кодом analogRead(7). Так? Кнопка нажимается редко и когда А0 не обрабатывается (потенциометр не крутится). Тогда можно же после обработчика А7 поместить скопированный код инициализации А0? А последнее ваше предложения я не понимаю(((

Могу привести более большой фрагмент реального кода.
 

poty

★★★★★★✩
19 Фев 2020
2,989
895
Я не знаю, откуда Вами взят код инициализации аналогового чтения по прерыванию. Но, думаю, Вы сможете в нём изменить номер порта мультиплексора (тем более, что этот оператор подписан). Это будет гораздо более прогнозируемый вариант, нежели постоянно переключаться со стандартного варианта (analogRead) на кастомный. Я к тому, что в определенный момент можно переключить на "кнопочный" порт на мультиплексоре, измерить вход кнопки, переключить порт обратно на вход потенциометра и измерять его до момента измерения кнопки.
Так вот, если ориентироваться на вышеописанный вариант:
  • используется автотриггер, то есть по окончании одного цикла измерений автоматически запускается другой;
  • изменение порта мультиплексора внутри цикла измерений не влияет на текущее измерение;
  • то есть, определили, что нужно измерить вход кнопки, поменяли ADMUX, произошло прерывание, результат отбрасываем и ждём следующего прерывания, результат во втором прерывании используем как код кнопки, меняем ADMUX на вход потенциометра, ждём прерывания, результат отбрасываем, результат второго и следующего прерываний используем как код потенциометра.
P.S. Похоже прерывания-то у Вас не включены, ADIE-бит отсутствует.
 
Изменено:

dim3740

✩✩✩✩✩✩✩
17 Июн 2020
16
0
Попробую по-цитатно ... или лучше описать задачу как-то иначе?)
1) "Вы сможете в нём изменить номер порта мультиплексора" -код А0 по прерыванию по потенциометру написан (не мною), отлажен, является частью проекта и менять его нельзя.
2) Нужно добавить, желательно, в loop опрос А7.
3) Я пробовал тестовые скетчи через GyverButton.h (она работает и с ана пинами), но найденные примеры (их мало) также предполагают analogRead, а затем примеру but.tick(analog < 100), что не решает проблему.
4) Я выявил случайно, что даже на этапе Setup , код чтения А7 ПОСЛЕ инициализации АЦП с А0 СТОПОРИТ код, что вообще необъяснимо для меня (компиляция в норме). Возможно, что я не точно делала тест. Замечу, что мне не важно понять причину "стопа", важнее решить практическую задачу.
5) одновременно потенциометр и кнопка не меняют состояний. Думаю, как писал выше, надо в цикле перед А7 конфигурировать АЦП по нее, и сразу же после опроса возвращать настройки под А0. Регистры менять не умею, желательна помощь. Или подтверждения этого решения и начну изучать матчасть.

Я признателен, но ваш совет очень сложно понять по уровню знаний.


 
Изменено:

poty

★★★★★★✩
19 Фев 2020
2,989
895
Отвечаю по пунктам:
1. Так как АЦП в микроконтроллере один, не трогать логику написанного кода для А0 не получится. Выходов 2:
  • попросить тех, кто написал Вам этот код, дописать опрос А7;
  • сделать по Вашему п. 5: перед опросом А7 переводить АЦП в режим однократного измерения, измерять А7, потом заново инициализировать существующим кодом А0 продолжение измерений; этот вариант также предполагает использование регистров АЦП напрямую, так как судя по п.4 Вашего сообщения, analogRead не восстанавливает настройки полностью;
2. см. п. 1, выход 2.
3. Если использовать "цифровую" кнопку в GyverButton, то можно считанный с А7 код использовать для определения нажатия. Пример есть в библиотеке, насколько я помню.
4. Нужно отходить от analogRead.
5. см. п. 1 выход 2.

Матчасть придётся изучать или ориентироваться на свободное время кого-либо из присутствующих, но тогда потребуется полный код.
 
  • Лойс +1
Реакции: dim3740