Как выцепить первое подходящее значение с аналогового датчика?
- Войдите на сайт для отправки комментариев
Доброго времени суток!
В программировании не силен, столкнулся с такой проблемой...
Имеется скетч, выводящий рандомные слова на матрицу, слова выводятся на реакцию с датчика шума.
То есть необходимо при превышении порогового значения с датчика выводить новое рандомное слово.
Проблема в следующем:
порог срабатывания- >800
хлопок рядом с датчиком
реакция датчика 799-800-801-802-801-800-799
На данный момент выводятся рандомные слова на каждое подряд значение.
Необходимо выцепить первое подходящее по условию т.е. 800 и не обращать внимания на остальные.
Сейчас на один хлопок меняется несколько слов, а надо 1 хлопок-1 слово.
Преполагаю что нужно ставит таймер где то, но не знаю где и как.
Помогите, пожалуйста!
#include <SPI.h> //библиотека #include <Adafruit_GFX.h> //библиотека #include <Max72xxPanel.h> //библиотека #include <WString.h> #include <time.h> #define LOUDNESS_SENSOR_PIN A0 //Датчик громкости подключён к пину А0 #define TRESHOLD 800 //Устанавливаем порог срабатывания int pinCS = 10; // Attach CS to this pin, DIN to MOSI and CLK to SCK (cf http://arduino.cc/en/Reference/SPI ) int numberOfHorizontalDisplays = 2; int numberOfVerticalDisplays = 1; Max72xxPanel matrix = Max72xxPanel(pinCS, numberOfHorizontalDisplays, numberOfVerticalDisplays); int delay_sensor = 10; int wait = 150; //скорость прокрутки строки int spacer = 1; int width = 5 + spacer; // The font width is 5 pixels // max максимальный индекс внутри массива (не забываем, что массив начинается с 0) int max = 3; char * messages[4]; void setup() { Serial.begin(9600); matrix.setIntensity(15); // Use a value between 0 and 15 for brightness messages[0] = "You"; messages[1] = "are"; messages[2] = "so"; messages[3] = "good"; matrix.setRotation(0, 10); // варианты отображения текста по направлению 1 матрицы matrix.setRotation(1, 10); // варианты отображения текста по направлению 2 матрицы } void loop() { // Считаем текущее значение громкости int loudness = analogRead(LOUDNESS_SENSOR_PIN); Serial.println(loudness); delay (50); if (loudness < TRESHOLD) { return; } // генерим рандомное число от 3 до 0 (в моем примере), чтобы получить произвольное сообщение из массива int index = rand() % (max + 1); // получаем рандомное сообщение char * cur_msg = messages[index]; int len = strlen(cur_msg); for (int i = 0; i < width * len + matrix.width() - 1 - spacer; i++) { matrix.fillScreen(LOW); int letter = i / width; int x = (matrix.width() - 1) - i % width; int y = (matrix.height() - 8) / 2; // center the text vertically while (x + width - spacer >= 0 && letter >= 0) { if (letter < len) { matrix.drawChar(x, y, cur_msg[letter], HIGH, LOW, 1); } letter--; x -= width; } matrix.write(); // Send bitmap to display delay(wait); } }
Надо уточнить задачу.
Требуется только один раз вывести слово. Или несколько раз?
Если несколько, то каков (по времени или по количеству сэмлов) должен быть интервал низких (<800) значений, что появление нового значения считать новым сигналом, а не "отголоском" старого?
"Надо уточнить задачу" (С)
Какой звуковой сенсор используется и есть ли в самом сенсоре регулировка порога?
А еще лучше-посмотреть осциллограмму на его выходе при хлопке.
Где-то тут были ссылки типа "осциллограф из звуковой карты" и из самой Ардуинки.
На каждый новый громкий звук- выводится новое рандомное слово и крутится в цикле пока не будет нового громкого звука.
Например:
хлопок
крутится слово "good"
хлопок
крутится "so"
Про интервал... наверное секунды 3.
Звуковой сенсор- аналоговый датчик шума из амперки.
Регулировка чувствительности имеется, с этим проблем нет.
Осцилографа не имеется, очень далек от этой темы.
Проблема в отбросе лишних значений с громкого звука или в объединении их в один.
Читайте 10 ( 100 ) раз, суммируйте, делите на 10 ( 100 ).....
Т.е. логика такова.
Есть два события:
1) шум начался (Ш), т.е. текущее значение >=800 && предыдущее значение < 800
2) шум смолк (Т), т.е. текущее значение < 800 && предыдущее значение >= 800
Есть период игнорирования событий (ПИ). Он отсчитывается от события Т и имеет продолжительность 3 сек.
Наконец, есть два дкйствия:
1) стартовать период ПИ
2) запустить новое слово
Теперь можно расписать логику:
Такая должна быть логика?
Если такая, добавляйте работу с millis (стартовать период ПИ - значит установить начальсное значение millis, а когда текущий миллис станет на 3+ секунды больше начального значение - период закончился.
Вот и всё. Программируется за 5 минут.
Вот и всё. Программируется за 5 минут.
Это довольно сложно для человека, который связался в первый раз с программированием пару дней назад)
Логика ясна, не ясно как это выразить в с++ и в правильном месте, в существующем коде.
Можно попросить Вас помочь в этом деле?
Что вышло написать...
Логика ясна, не ясно как это выразить в с++ и в правильном месте, в существующем коде.
Можно попросить Вас помочь в этом деле?
Что вышло написать...
Никак не выражайте, просто храните. Типа так
Посчитав среднее и умножив его на какое-то число измерений мы как-бы знаем что наш "массив" состоит из этого количества измерений и все измерения равны среднему. Поэтому зачем помнить каждое измерение?
Они все равны среднему...
NeiroN прав , но более "читабельно и понятно "
[среднее] = ( [среднее] * [число измерений - 1] + [ текущее показание ] ) / ( [число измерений] )
http://arduino.ru/forum/programmirovanie/array-massivy#comment-86084
http://arduino.ru/forum/programmirovanie/array-massivy#comment-86238
Ну Вы и в дебри полезли, господа! Нужно после вывода очередного слова просто сделать паузу в работе программы, вполне годится delay(200). За это время шум от хлопка утихнет и ждем следующего хлопка.
Ну Вы и в дебри полезли, господа! Нужно после вывода очередного слова просто сделать паузу в работе программы, вполне годится delay(200). За это время шум от хлопка утихнет и ждем следующего хлопка.
Ну, а я не то же самое написал? Только с миллис вместо делэя.
Ну Вы и в дебри полезли, господа! Нужно после вывода очередного слова просто сделать паузу в работе программы, вполне годится delay(200). За это время шум от хлопка утихнет и ждем следующего хлопка.
Ну, а я не то же самое написал? Только с миллис вместо делэя.
Да. Тоже. Я как формулы увидел, испугался что ща БПФ кто предложит, и поторопился ))))
Ну Вы и в дебри полезли, господа! Нужно после вывода очередного слова просто сделать паузу в работе программы, вполне годится delay(200). За это время шум от хлопка утихнет и ждем следующего хлопка.
А не подскажешь где именно delay впихнуть?
И как быть с тем, что слово должно в цикле отображаться до следующего срабатывания?