Проблемы с шаговиками и ультразвуковым датчиком в связке
- Войдите на сайт для отправки комментариев
Всем привет. Возможно я пложу темы, извините, но похожих тем много , а схожей проблемы я не нашёл. Суть проблемы такова - вот видео http://www.youtube.com/watch?v=r4kN3lEvER4&list=PLj_E1AdSVXNJnP2S9gUzfplKMUphPgh7j . Цель - заставить ехать робота вперёд, пока расстояние до препятствия будет более 50 см, если меньше, то включаем один двигатель из двух до тех пор , пока расстояние не увеличется, после чего включаем 2 двигаеля. Проблема в том , что почемуто если просто использовать скетч без условий (включить двигатели оба), то оба двигателя одновременно довольно шустро крутятся , если же вставить код определения расстояния и условия то получается картина что когда нужно чтобы крутилось 2 привода - они еле крутятся рывками как видно на видео (иногда вообще не предсказуемо - то быстро то медленно), а вот когда расстояние меньше 50 и нужно включить 1 двигатель для поворота, то он вполне нормально работает. Вот скетч
#include <AccelStepper.h> #include <AFMotor.h> #include "Ultrasonic.h" AF_Stepper motor1(48, 1); AF_Stepper motor2(48, 2); Ultrasonic sonic(22, 24); const int Trig = 22; //Ultrasonic const int Echo = 24; int time_us; int distance_sm; int dist; // you can change these to DOUBLE or INTERLEAVE or MICROSTEP! void forwardstep1() { motor1.onestep(FORWARD, DOUBLE); } void backwardstep1() { motor1.onestep(BACKWARD, DOUBLE); } void forwardstep2() { motor2.onestep(FORWARD, DOUBLE); } void backwardstep2() { motor2.onestep(BACKWARD, DOUBLE); } AccelStepper stepper1(backwardstep1, forwardstep1 ); // use functions to step AccelStepper stepper2(forwardstep2, backwardstep2); // use functions to step void setup() { Serial.begin(9600); // set up Serial library at 9600 bps Serial.println("Stepper test!"); stepper1.setMaxSpeed(100); stepper1.setSpeed(100); stepper2.setMaxSpeed(100); stepper2.setSpeed(100); } void loop() { dist=sonic.Ranging(CM); Serial.println(dist); if (dist>0 & dist<50) { // stepper1.runSpeed(); stepper2.runSpeed(); } else { stepper2.runSpeed(); stepper1.runSpeed(); } }
Подскажите пож в чём тут проблема, не могу понять.
Странное ж дело...
Извините, не совсем понимаю этот код , что это за процедура
millis()
и смысл этой строчкиstatic
uint32_t miilis_prev;
Программирование
Сори за ликбез )) , но поменяв код процедуры loop на Ваш, ситуация не изменилась, при расстоянии больше 50 оба дигателя медленно дёргаясь крутятся вперёд, при расстоянии меньше 50 первый двигатель стоит и нормально начинает крутиться второй двигатель
Serial тормозит шаговики. Попробуйте закомментировать строку 45.
Что-то я вообще запутался, в коде нигде не указано, что при расстоянии менее 50 см крутится только один двигатель, но происходит именно так .
Потому что это вам только кажется что не указано.
vvadim - закоментировал, но не помогло. Ситуация таже. Не могу понять в чём проблема. Причём иногда всётаки оба моторв на пару секунд начинают работать нормально. Может проблема в схеме подключения?
НУ если без условий крутятся, значит подключены нормально. Я сталкивался с тем, что даже антидребезг и вывод на дисплей тормозит шаговик. Вполне может датчик тормозить. Попробуйте его вывести в отдельную функцию
Кажись я заметил какую-то закономерность (если расстояние меньше 50 один мотор крутится норм, если расстояние больше 50 но меньше гдето 70 оба крутятся нормально, но когда на датчике проскакивает 1000-5000 то моторы сразу начинают еле крутиться дёргаясь ). Общим ещё поексперементирую с условиями, но гдето здесь зарыта собака. Паралельно попробую вынести измерение расстояния в функцию.
Проблема оказывается не в этом, maksim был прав, частично, его код действительно заработал, только 200 нужно было поменять минимум на 1000 , и тогда в теч 1 с. моторы работали нормально, поставим 2000 то 2с. мотры работают нормально, но если в теч этих 2-х с. изменяется расстояние например до 20см реакции никакой, тоесть моторы так и крутятся, так что эксперементируем дальше.
Проблема в том что функция sonic.Ranging(CM); блокирующая, а значит пока датчик измеряет расстояние моторы останавливаются и чем больше расстояние тем дольше происходит измерение - тем тодьше стоят моторы.
Я об этом догадывался, а как эту проблему решить ?Попробовал загнать измерение расстояния в процедуру, не помогло.
Конечно не помогло. Нужно писать неблокирующую функцию работы с датчиком.
что то в этом роде ?
это тоже не помогло(((. Кто знает как решить проблему, подскажите пож.
Это и не поможет, неблокирующие функции не имеют задержек, в то время как у вас есть delayMicroseconds();, и pulseIn(); - которая тоже блокирующая.
Измерить расстояние без задержки нельзя.
Ну если вам нельзя - значит нельзя. Мне, например, да и многим другим можно.
All, можно ли на одном МК держать датчик а на другом двигатели? Будет ли блокировка на время обмена инфой, если связать их по i2c?
А зачем, если на одном мк можно
Конечно. Все просто.
Примером мигаем без делэй дергаем Trig и ловим в прерывании фронты Echo подключив заведомо на ногу с прерыванием.
Спасибо максим за направление в котром нужно копать, смысл функции attachinterrupt вроде бы понятен, но видимо у меня не получается правильно её применить. вот мой вариант кода (он ситуацию не изменил)))
Как я понимаю , садим выход Trig датчика на 21 пин ардуины, для функции attachinterrupt это параметр 2, задаем функцию , которая должна вызываться по внешнему прерыванию - у меня это startt() и CHANGE прерывание вызывается при смене значения на порту, с LOW на HIGH и наоборот. Но я явно чтото не то делаю либо недопонимаю. Укажите пож на ошибку и если можно правильный код. Спасибо конечно maksim за направление, я уже понял что он знает намного больше меня, но хотелось бы более проще и нагляднее нежели коментарии типа многие знают а ты сюда зря зашёл и в качестве снисхождения обратим на это внимание.
Trig может быть на любом выводе, на прерывание нужно подключить Echo. И библиотеку Ultrasonic тут никак нельзя использовать - она блокирующая. И вы не поняли о чем идет речь.
Я понял что я напутал ))) сейчас пытаюсь вырулить, пока не уснул мож чего стоящее и придумаю.)
Вот новый код, направление правильное ? Код правда не компилится на 35 строке выдаёт expected `)' before ';' token. Но чтото не соображу где там не хватает ). Но больше меня интересует ход мыслей , правильно или нет.
Правильное.
Проблемы с компиляцией в процедуре
выдает следующую ошибку по строке
sketch_4.ino: In function 'void sonar()':
sketch_4:59: error: void value not ignored as it ought to be
А что вы пытаетесь сделать этой строкой?
считать в переменнную time параметр ножки Echo , после чего рассчитать расстояние в переменную dist. Чтобы потом эту dist использовать в условиях для алгоритма поведения моторов.
мдааа, в элементарных вещах запутался. Но у меня вопроос функция pulseIn в моей процедупе sonar использовать можно? А то она у меня кроме 0 ничего не выдаёт.
#17
да блокирующая, но мож во внешнем прерывании она бы и сработала, вот и спрашиваю. Но раз тут тупик, тогда как правильно функцию sonar описать ?