أحيانًا عندما ننشئ مشروعًا باستخدام مشغل خطي، نكون بصدد حل مشكلة لا يمكن حلّها دون المزايا التي توفّرها هذه الآليات. وأحيانًا أخرى، نحاول تسهيل مهمة معيّنة عبر أتمتتها. لكن بين الحين والآخر، ننشئ شيئًا لمجرد أننا نستطيع. هذا واحد من تلك المشاريع.
في هذه المقالة، سنستعرض كيف يمكنك استخدام مستشعر فوق صوتي لقياس مسافة المشغل الخطي إلى جسم ما واستخدامها لتغيير موضع طول الشوط للمشغل تلقائيًا. ورغم أن هذا لم يُنشأ من أجل تطبيق محدد بعينه، إلا أن الاحتمالات لا نهائية.
إليك ما ستحتاج إليه
- 1 × درع قيادة محرك RobotPower MegaMoto
- 1 × Arduino Uno
- 1 × مستشعر فوق صوتي
- 1 × PA-04-12-400-HS-24VDC (يمكن أن يكون أي مشغل مزوّد بتغذية راجعة من تأثير هول)
- 1 × PS-20-24 (أو أي مزوّد طاقة 24VDC بقدرة لا تقل عن 6 أمبير)
لأجل التحكم، نستخدم لوحة Arduino Uno مع برنامج تشغيل محرك MegaMoto. مشغلنا هو PA-04-12-400-HS-24VDC. من المهم أن يحتوي المشغل على شكل من أشكال التغذية الراجعة كي يتمكن Arduino من مراقبة موضعه — أي نظام تغذية راجعة لمشغل خطي قد يعمل، فعلى سبيل المثال ستكون تغذية راجعة من مقاوم دوّار (Potentiometer) فعّالة هنا أيضًا. سيكون القياس بالمقاوم الدوّار أقل دقة، لكنه يتمتع بميزة عدم الحاجة إلى إجراء معايرة الرجوع إلى نقطة الصفر بعد انقطاع الكهرباء. كما سيتطلب ذلك تعديل الشيفرة.
الخطوة 1: التوصيلات

التوصيلات في هذا المشروع بسيطة للغاية. سنستخدم هنا واحدًا فقط من مستشعري تأثير هول في PA-04-HS — ولا يهم أيهما (الرجل 4 أو 5). يوضّح التخطيط أدناه أرجل موصل Molex ذو 6 سنون الذي يأتي مع PA-04-HS:

موصل المشغل ذو 6 سنون إلى Arduino/MegaMoto
- Pin 3 إلى 5V
- Pin 2 إلى GND
- Pin 1 إلى الرجل 2 في Arduino
- Pin 4 إلى A على MegaMoto
- Pin 5 إلى B على MegaMoto
توصيل المستشعر الفوق صوتي بـ Arduino/Megamoto
- VCC إلى 5V
- GND إلى GND
- Trig إلى الرجل 8
- Echo إلى الرجل 7
توصيل MegaMoto بمزوّد الطاقة
- + إلى V+
- - إلى V-
الخطوة 2: برمجة Arduino
الشيفرة المستخدمة في هذا الدرس نسخة معدّلة مما استخدمناه في منشور آخر، Hall Effect Sensors 1: Position Control. لا تتردد في الاطلاع على هذا الدرس لفهم أفضل لكيفية استخدامنا لمستشعر تأثير هول للتحكم بالموضع! يعمل المستشعر الفوق صوتي عبر إرسال نبضة فوق صوتية يتم تحفيزها بواسطة أحد أرجل GPIO على Arduino. تنعكس هذه النبضة عن جسم وتلتقطها وحدة الاستقبال. وعندما تلتقط وحدة الاستقبال النبضة، ترسل إشارة نبضة إلى Arduino. ومن خلال ذلك، يمكننا إجراء معادلة لحساب المسافة لمشغل خطي عن طريق قياس الزمن بين الإرسال والاستقبال واستخدام صيغة لتحويل هذه القياس إلى بوصات.
نحدد موضع المشغل عبر عدّ عدد النبضات التي يخرجها مستشعر تأثير هول (وذلك موضّح بمزيد من التفصيل في المنشور المذكور أعلاه). يمكننا تحديد موضع طول الشوط بالبوصات من خلال معرفة عدد النبضات/البوصة التي يخرجها مشغلنا المحدد، ثم قسمة عدد نبضاتنا على هذا الرقم. إن تحويل قراءة المستشعر الفوق صوتي وقراءة مستشعر تأثير هول كليهما إلى بوصات يجعل البرمجة أنظف وأسهل بكثير. من هناك، نقول عمليًا لـ Arduino: "إذا كان الجسم يبعد x بوصة، فمدِّد المشغل x بوصة". سيسمح لك رفع الشيفرة أدناه بتطبيق نموذج المسافة المتحكَّم بها بالمشغل الخطي على أحد مشغلاتنا PA-04-12-400-HS-24VDC. في الخطوة التالية سنستعرض التعديلات الممكن إجراؤها على الشيفرة.
[code]
/* The purpose of this code it to be able to measure the distance of an object and position the stroke of a linear acuator accordingly.
* The required components are an Arduion Uno, a PobotPower MegaMoto Driver, and an Ultra sonic sensor.
* Written by Progressive Automations 2/02/21
*/
#define PWMA0 6
#define PWMB0 5
#define enable0 13 //pins for MegaMoto
#define hall0 2 //interrupt pins for hall effect sensors
#define echoPin 7 //echo pin on ultra sonic sensor
#define trigPin 8 //output on ultra sonic sensor
float duration, distance;
int enable = 0; //enable pin for megaMoto
int count[] = {0};
int currentPos = 0;//current position
int threshold = 100;//position tolerance
int destination = 0;
bool forwards = false;
bool backwards = false;// motor states
void setup() {
pinMode(PWMA0, OUTPUT);
pinMode(PWMB0, OUTPUT);//set PWM outputs
pinMode(enable0, OUTPUT);
digitalWrite(enable0, LOW);//set enable and turn board OFF
pinMode(hall0, INPUT);
digitalWrite(hall0, LOW);//set hall, set low to start for rising edge
attachInterrupt(0, speed0, RISING); //enable the hall effect interupts
pinMode(trigPin,OUTPUT);
pinMode(echoPin, INPUT);
Serial.begin(9600);
//homeActuator();//fully retracts actuator
Serial.println("READY");
}//end setup
void loop() {
getDistance();//measure distance of object from ultra sonic sensor
currentPos = count[0];
if(distance < 13) //ignore value if greater than stroke length
{
destination = distance * 275; //translate measured distance (in inches) to desired stroke position (in pulses)
}
if ((destination >= (currentPos - threshold)) && (destination <= (currentPos + threshold))) stopMoving();//stop acuator if it is in the desired position
else if (destination > currentPos) goForwards();
else if (destination < currentPos) goBackwards();
Serial.print("Counts: "); Serial.println(count[0]);
Serial.print("currentPos: "); Serial.println(currentPos);
Serial.print("Destination: "); Serial.println(destination);
}//end loop
void speed0() {
//Serial.println("Update 1");
if (forwards == true) count[0]++; //if moving forwards, add counts
else if (backwards == true) count[0]--; //if moving back, subtract counts
}//end speed0
/*void ReadInputs() {
sw[0] = digitalRead(switch0), sw[1] = digitalRead(switch1);//check switches
currentPos = count[0];
}//end read inputs
*/
void goForwards()
{
forwards = true;
backwards = false;
//Serial.println("Moving forwards");
digitalWrite(enable0, HIGH);//enable board
//Serial.print(" Speeds "), Serial.print(spd[0]), Serial.print(", "), Serial.print(spd[1]);
//Serial.print(" Counts "), Serial.println(count[0]);
analogWrite(PWMA0, 255);
analogWrite(PWMB0, 0);//apply speeds
}//end goForwards
void goBackwards()
{
forwards = false;
backwards = true;
//Serial.println("Moving backwards");
digitalWrite(enable0, HIGH);//enable board
//Serial.print(" Speeds "), Serial.print(spd[0]), Serial.print(", "), Serial.print(spd[1]);
//Serial.print(" Counts "), Serial.println(count[0]);
analogWrite(PWMA0, 0);
analogWrite(PWMB0, 255);//apply speeds
}//end goBackwards
void stopMoving()
{
forwards = false;
backwards = false;
Serial.println("Stopped");
analogWrite(PWMA0, 0);
analogWrite(PWMB0, 0);//set speeds to 0
delay(10);
digitalWrite(enable0, LOW);//disable board
}//end stopMoving
void getDistance()
{
digitalWrite(trigPin, LOW);
delayMicroseconds(10);
digitalWrite(trigPin, HIGH);
delayMicroseconds(10);
digitalWrite(trigPin, LOW);
duration = pulseIn(echoPin, HIGH);
distance = duration/58.2/2.5;
Serial.print("Distance:"); Serial.println(distance);
}
void homeActuator() //fully retract actuator and set count to 0
{
goBackwards();
delay(25000);//change this value to the amount of time it takes for the actuator to fully retract
count[0] = {0};
}
[/code]
الخطوة 3: تعديل الشيفرة
يحدّد مقدار العتبة مدى دقة مطابقة موضع المشغل لقراءة المستشعر الفوق صوتي. زيادته ستُقلّل الدقة، وتقليصه سيؤدي إلى العكس. من خلال ضبط هذه القيمة على 100، نحن عمليًا نطلب من Arduino عدم تحريك المشغل طالما كانت نبضات مستشعر تأثير هول والمستشعر الفوق صوتي ضمن 100 نبضة من بعضهما. إذا كانت هذه القيمة منخفضة جدًا، فقد ينتج عن ذلك تحركات متقطعة ومتكررة للمشغل أثناء محاولته الوصول إلى الموضع الدقيق.

غيّر هذه القيمة إلى طول الشوط لمشغلك (أو أطول ببوصة واحدة). سيؤدي ذلك إلى إخبار Arduino بتجاهل أي قيم مرتفعة جدًا.

غيّر هذه القيمة إلى عدد النبضات/البوصة لمشغلك.

الخلاصة
نأمل بصدق أن تجد هذا المشروع مفيدًا — أو على الأقل مثيرًا للاهتمام! لا تتردد في تعديله وجعله بطابعك الخاص. وكما هو الحال دائمًا، سنسعد برؤية أي مشاريع ذات صلة لديك، سواء استخدمت هذه الفكرة أو أنشأت شيئًا مختلفًا باستخدام منتجاتنا! يمكنك أيضًا التواصل معنا عبر البريد الإلكتروني على sales@progressiveautomations.com أو عبر الهاتف على 1-800-676-6123.