Ардуино ПРО МИНИ + 2 ULN2003A + 2 шаговика
- Войдите на сайт для отправки комментариев
Вс, 26/04/2015 - 12:31
Нашел способ заставить моторы крутиться только в случае нажатой кнопки. Но почему-то работает только с первой кнопкой. Когда аналогично прописываю вторую кнопку - пишет: collect2.exe: error: ld returned 5 exit status.
/* Исходный скетчДмитрий Осипов. http://www.youtube.com/user/d36073?feature=watch v.01 button resistor Arduino Шаговый двигатель 28BYJ-48 – 5V Stepper Motor ---------------------------------------- Скачать sketch. v.01 вправо влево Arduino Шаговый двигатель 28BYJ-48 – 5V Stepper Motor https://yadi.sk/d/9trcfiK7ULkQS v.01 button resistor Arduino Шаговый двигатель 28BYJ-48 – 5V Stepper Motor */ /////////////////////////////////////////////////////////////// // Назначение пинов выводам для UNL 2003A 1 мотора int motorPin1 = 6; int motorPin2 = 7; int motorPin3 = 8; int motorPin4 = 9; // Назначение пинов выводам для UNL 2003A 2 мотора int motorPin5 = 10; int motorPin6 = 11; int motorPin7 = 12; int motorPin8 = 13; // Назначение пинов выводам кнопок (один вывод кнопок - соответственно, а второй - на GND) int buttonPin_1 = 2; int buttonPin_2 = 3; // фиксируем нажатие на первую и вторую кнопку соответственно. boolean q; boolean w; // установить скорость шагового двигателя. //variable to set stepper speed. int motorSpeed = 14000; int lookup_1[8] = { B01000, B01100, B00100, B00110, B00010, B00011, B00001, B01001}; int lookup_2[8] = { B01000, B01100, B00100, B00110, B00010, B00011, B00001, B01001}; ///////////////////////////////////////////////////////////////// void setup() { // Заявляем пины моторов как выходные pinMode(motorPin1, OUTPUT); pinMode(motorPin2, OUTPUT); pinMode(motorPin3, OUTPUT); pinMode(motorPin4, OUTPUT); pinMode(motorPin5, OUTPUT); pinMode(motorPin6, OUTPUT); pinMode(motorPin7, OUTPUT); pinMode(motorPin8, OUTPUT); // Заявляем пины кнопок как входные pinMode(buttonPin_1, INPUT); pinMode(buttonPin_2, INPUT); //Устанавливаем высокий сигнал на пинах отжатых кнопок digitalWrite(buttonPin_1, HIGH); digitalWrite(buttonPin_2, HIGH); // Serial.begin(9600); } //////////////////////////////////////////////////////////////// void loop(){ if (digitalRead(buttonPin_1) == LOW) // если кнопка 1 нажата. { q = !q; // меняем значение q на противоположное 0 на 1 или 1 на 0. delay(500); // защита от дребезга кнопки. } if (digitalRead(buttonPin_1) == LOW) {// если кнопка 1 нажата. if (q == 1){ while (digitalRead(buttonPin_1) == LOW){ anticlockwise_1(); // Мотор 1 крутим влево. } } else { while (digitalRead(buttonPin_1) == LOW){ clockwise_1(); // Мотор 1 крутим вправо. } } } else { digitalWrite(motorPin1, LOW); digitalWrite(motorPin2, LOW); digitalWrite(motorPin3, LOW); digitalWrite(motorPin4, LOW); } ///////////////////////////// if (digitalRead(buttonPin_2) == LOW) // если кнопка 2 нажата. { w = !w; // меняем значение q на противоположное 0 на 1 или 1 на 0. delay(500); // защита от дребезга кнопки. } // эти две строки - работают, но постоянно с перерывом на время работы мотора_1 if (w == 1) anticlockwise_2(); // Мотор_2 крутим влево. else clockwise_2(); // Мотор_2 крутим вправо. } /* // А вот с этим фрагментом вместо предыдущих двух строчек почему-то не работает пишет collect2.exe: error: ld returned 5 exit status. if (w == 1){ while (digitalRead(buttonPin_2) == LOW){ anticlockwise_2(); // Мотор 2 крутим влево. } } else { while (digitalRead(buttonPin_2) == LOW){ clockwise_2(); // Мотор 2 крутим вправо. } } } else { digitalWrite(motorPin5, LOW); digitalWrite(motorPin6, LOW); digitalWrite(motorPin7, LOW); digitalWrite(motorPin8, LOW); } */ // ////////////////////////////////////////////////////////////// // функция поворачивает мотор 1 против часовой стрелки. void anticlockwise_1() { for(int i = 0; i < 8; i++) { setOutput_1(i); delayMicroseconds(motorSpeed); } } // функция поворачивает мотор 1 по часовой стрелке. void clockwise_1() { for(int i = 7; i >= 0; i--) { setOutput_1(i); delayMicroseconds(motorSpeed); } } // функция поворачивает мотор 2 против часовой стрелки. void anticlockwise_2() { for(int j = 0; j < 8; j++) { setOutput_2(j); delayMicroseconds(motorSpeed); } } // функция поворачивает мотор 2 по часовой стрелке. void clockwise_2() { for(int j = 7; j >= 0; j--) { setOutput_2(j); delayMicroseconds(motorSpeed); } } ///////////////////////////////////////////////////////////// void setOutput_1(int out) { digitalWrite(motorPin1, bitRead(lookup_1[out], 0)); digitalWrite(motorPin2, bitRead(lookup_1[out], 1)); digitalWrite(motorPin3, bitRead(lookup_1[out], 2)); digitalWrite(motorPin4, bitRead(lookup_1[out], 3)); } void setOutput_2(int out) { digitalWrite(motorPin5, bitRead(lookup_2[out], 0)); digitalWrite(motorPin6, bitRead(lookup_2[out], 1)); digitalWrite(motorPin7, bitRead(lookup_2[out], 2)); digitalWrite(motorPin8, bitRead(lookup_2[out], 3)); } void setStop_1(int out) { digitalWrite(motorPin1, LOW); digitalWrite(motorPin2, LOW); digitalWrite(motorPin3, LOW); digitalWrite(motorPin4, LOW); } void setStop_2(int out) { digitalWrite(motorPin5, LOW); digitalWrite(motorPin6, LOW); digitalWrite(motorPin7, LOW); digitalWrite(motorPin8, LOW); }
Все проверил - вроде все правильно. Убираю "while (digitalRead(buttonPin_1) == LOW)" - ошибки нет, но мотор_2 продолжает крутиться при разомкнутой кнопке.
Мне же нужно чтоб кнопка_2 работала точно так же, как кнопка_1 и при замыкании двух кнопок оба мотора работали одновременно и независимо.
Помогите, пожалуйста.
Исправил сам - обе кнопки работают аналогично. Но как сделать, чтоб они работали одновременно и независимо?
AccelStepper пример MultiStepper
Спасибо, но поскольку это мой первый опыт с Ардуино, я в AccelStepper только запутался больше и сделал может быть не очень грамотно, но успешно.
Есть маленькие нюансы, которые хотелось бы исправить, но после теста вижу, что скетч на 95% удовлетворяет моим требованиям.
Если кому пригодится - вот материалы по моему проэкту.
Солнечный трекер на Ардуино ПРО МИНИ + 2 ULN2003A + 2 шаговика - вот он:
Детали:
Макетная плата - 1шт
Подставка под микросхему подходящая к ПРО МИНИ - 1 шт
Ардуино ПРО МИНИ - 1 шт
ULN2003A - 2 шт
шаговики - 2 шт
оры 10 КОм - 5 шт
Фото резисторы - 3 шт
Концевики - 2 шт
Проводки, гнезда, гнезда питания - по потребности
Скетч:
#define TILTL 2 #define TILTH 3 #define BOTTOM 2 #define TOPLEFT 0 #define TOPRIGHT 1 #include "math.h" // Назначение пинов выводам для UNL 2003A 1 мотора int motorPin1 = 6; int motorPin2 = 7; int motorPin3 = 8; int motorPin4 = 9; // Назначение пинов выводам для UNL 2003A 2 мотора int motorPin5 = 10; int motorPin6 = 11; int motorPin7 = 12; int motorPin8 = 13; // Назначение пинов выводам кнопок (один вывод кнопок - соответственно, а второй - на GND) int tlsense; int trsense; int bsense; int tavg; int diff; int spd; int divisor; int sensitivity; int tiltl; int tilth; // установить скорость шагового двигателя. //variable to set stepper speed. int motorSpeed = 14000; int lookup_1[8] = { B01000, B01100, B00100, B00110, B00010, B00011, B00001, B01001}; int lookup_2[8] = { B01000, B01100, B00100, B00110, B00010, B00011, B00001, B01001}; ///////////////////////////////////////////////////////////////// void setup () { divisor = 10; // this controls the speed of the servo. lower number = higher speed sensitivity = 30; // this controls the sensitivity of the tracker. lower number = higher sensitivity. if your tracker is constantly jittering back and forth increase the number Serial.begin(9600); // open serial com Serial.print("SolarTracker ready!"); pinMode(BOTTOM, INPUT); // set the inputs pinMode(TOPLEFT, INPUT); pinMode(TOPRIGHT, INPUT); pinMode(TILTL, INPUT); pinMode(TILTH, INPUT); pinMode(motorPin1, OUTPUT); pinMode(motorPin2, OUTPUT); pinMode(motorPin3, OUTPUT); pinMode(motorPin4, OUTPUT); pinMode(motorPin5, OUTPUT); pinMode(motorPin6, OUTPUT); pinMode(motorPin7, OUTPUT); pinMode(motorPin8, OUTPUT); } /////////////////////////////////////////////////////// void loop () { tiltl = digitalRead(TILTL); // read the tilt sensor tilth = digitalRead(TILTH); tlsense = analogRead(TOPLEFT); // read the light sensors trsense = analogRead(TOPRIGHT); bsense = analogRead(BOTTOM); bsense = bsense * 1.05; // I had to adjust the value of this sensor to make it more accurate. you might have to do the same but start by leaving it alone tavg = (tlsense + trsense)/2; // get an average value for the top 2 sensors diff = abs(tavg - bsense); // this judges how far the tracker must turn spd = diff/divisor; // and adjusts the speed of the reaction accordingly spd = max(spd, 1); // sets the minimum speed to 1 Serial.print("\nTOP: "); Serial.print(tavg, DEC); // print the sensor values to the serial com Serial.print("\tBOTTOM:"); Serial.print(bsense, DEC); Serial.print("\tLEFT:"); Serial.print(tlsense, DEC); Serial.print("\tRIGHT:"); Serial.print(trsense, DEC); if((tavg < bsense) && (diff > sensitivity) && (tiltl == HIGH) && (tilth == HIGH)){ // if the average value of the top sensors is smaller (more light) than the bottom sensor and the tilt sensor is in the correct range clockwise_1(); // Мотор 1 крутим вправо. Serial.print("\tState: "); Serial.print("V_UP!"); }else if((tavg < bsense) && (diff > sensitivity) && (tiltl == HIGH) && (tilth == LOW)){ // if the average value of the top sensors is smaller (more light) than the bottom sensor and the tilt sensor is in the correct range digitalWrite(motorPin1, LOW); //останавливаем мотор digitalWrite(motorPin2, LOW); digitalWrite(motorPin3, LOW); digitalWrite(motorPin4, LOW); Serial.print("\tState: "); Serial.print("V_STOP!"); }else if((tavg > bsense) && (diff > sensitivity) && (tiltl == HIGH) && (tilth == HIGH)){ // if the value of the bottom sensor is smaller (more light) than the average value of the top sensors and the tilt sensor is in the correct range anticlockwise_1(); // Мотор 1 крутим влево. Serial.print("\tState: "); Serial.print("V_DOWN!"); }else if((tavg > bsense) && (diff > sensitivity) && (tiltl == LOW) && (tilth == HIGH)){ // if the value of the bottom sensor is smaller (more light) than the average value of the top sensors and the tilt sensor is in the correct range digitalWrite(motorPin1, LOW); //останавливаем мотор digitalWrite(motorPin2, LOW); digitalWrite(motorPin3, LOW); digitalWrite(motorPin4, LOW); Serial.print("\tState: "); Serial.print("V_STOP!"); }else{ // for every other instance digitalWrite(motorPin1, LOW); digitalWrite(motorPin2, LOW); digitalWrite(motorPin3, LOW); digitalWrite(motorPin4, LOW); } tlsense = analogRead(TOPLEFT); // read the top 2 sensors again because they have probably changed trsense = analogRead(TOPRIGHT); trsense = trsense * 1.03; // again I had to adjust the value of one sensor to make the tracker more accurate diff = abs(tlsense - trsense); // reset the diff variable for the new values spd = diff/divisor; // and generate a speed accordingly spd = max(spd, 1); // set the minimum speed to 1 if((tlsense < trsense) && (diff > sensitivity)){ // if the top left sensor value is smaller (more light) than the top right sensor clockwise_2(); // Мотор 2 крутим вправо. Serial.print("\tState: "); Serial.print("H_RIGHT!"); }else if((tlsense > trsense) && (diff > sensitivity)){ // if the top left sensor value is larger (less light) than the top right sensor anticlockwise_2(); // Мотор 2 крутим влево. Serial.print("\tState: "); Serial.print("H_LEFT!"); }else{ // for every other instance digitalWrite(motorPin5, LOW); digitalWrite(motorPin6, LOW); digitalWrite(motorPin7, LOW); digitalWrite(motorPin8, LOW); Serial.print("\tState: "); Serial.print("H_STOP!"); } delay(10); // delay 10ms } // ////////////////////////////////////////////////////////////// // функция поворачивает мотор 1 против часовой стрелки. void anticlockwise_1() { for(int i = 0; i < 8; i++) { setOutput_1(i); delayMicroseconds(motorSpeed); } } // функция поворачивает мотор 1 по часовой стрелке. void clockwise_1() { for(int i = 7; i >= 0; i--) { setOutput_1(i); delayMicroseconds(motorSpeed); } } // функция поворачивает мотор 2 против часовой стрелки. void anticlockwise_2() { for(int j = 0; j < 8; j++) { setOutput_2(j); delayMicroseconds(motorSpeed); } } // функция поворачивает мотор 2 по часовой стрелке. void clockwise_2() { for(int j = 7; j >= 0; j--) { setOutput_2(j); delayMicroseconds(motorSpeed); } } ///////////////////////////////////////////////////////////// void setOutput_1(int out) { digitalWrite(motorPin1, bitRead(lookup_1[out], 0)); digitalWrite(motorPin2, bitRead(lookup_1[out], 1)); digitalWrite(motorPin3, bitRead(lookup_1[out], 2)); digitalWrite(motorPin4, bitRead(lookup_1[out], 3)); } void setOutput_2(int out) { digitalWrite(motorPin5, bitRead(lookup_2[out], 0)); digitalWrite(motorPin6, bitRead(lookup_2[out], 1)); digitalWrite(motorPin7, bitRead(lookup_2[out], 2)); digitalWrite(motorPin8, bitRead(lookup_2[out], 3)); }Успехов!