أزرار الضغط في الدارات الرقمية

a person pressing a lift button

توصيل أزرار الضغط بالدارات الرقمية و الأردوينو

المقدمة

تُعد أزرار الضغط من أبسط وأكثر المكونات استخدامًا في الإلكترونيات. سواء كنت تستخدمها لتشغيل برنامج، أو تبديل وضع، أو التنقل في قائمة، فإن زر الضغط يمكّنك من التفاعل مع الأنظمة الرقمية. في هذا المقال، سنشرح كيفية توصيل أزرار الضغط بالميكروكنترولر مثل Arduino، ونوضح الفرق بين المقاومات المسحوبة لأعلى أو لأسفل، ونناقش مشكلة الاهتزاز (Debounce) عند الضغط، مع مثال عملي باستخدام كود منظم وواضح.

a collection of push buttons

ما هو زر الضغط؟

زر الضغط هو مفتاح ميكانيكي يقوم بإغلاق أو فتح الدارة مؤقتًا عند الضغط عليه. عادةً ما يكون من النوع "مفتوح في الوضع الطبيعي" (NO)، أي أن الدارة تكون مفتوحة ولا يُمرر التيار حتى يتم الضغط.

عند توصيله بميكروكنترولر مثل Arduino، يتم ربطه إلى أحد أطراف الإدخال الرقمية، حيث يتم قراءة حالته إما كـ HIGH (1) أو LOW (0)، بناءً على كيفية توصيله.

momentary push button switch
Push button internal details

المقاومات المسحوبة لأعلى (Pull-Up) أو لأسفل (Pull-Down)

لا يمكن ترك طرف الإدخال الرقمي معلقًا بدون اتصال، لأن ذلك يؤدي إلى قراءات غير مستقرة أو عشوائية. يتم استخدام مقاومة تسحب الجهد نحو HIGH أو LOW لتثبيت الحالة في وضع الزر غير مضغوط.

التوصيل باستخدام مقاومة مسحوبة لأسفل

  • التوصيل: أحد أطراف الزر إلى 5V، الطرف الآخر إلى دبوس الإدخال ومقاومة إلى GND.
  • النتيجة:
    • الزر غير مضغوط: القراءة LOW.
    • الزر مضغوط: القراءة HIGH.
Pull dow resistor connected to MCU

التوصيل باستخدام مقاومة مسحوبة لأعلى

  • التوصيل: أحد أطراف الزر إلى GND، والطرف الآخر إلى دبوس الإدخال والمقاومة إلى 5V.
  • النتيجة:
    • الزر غير مضغوط: القراءة HIGH.
    • الزر مضغوط: القراءة LOW.

هذا هو الأسلوب المُفضل عند استخدام Arduino لأنه يحتوي على مقاومات سحب داخلية يمكن تفعيلها برمجيًا.

Pull up resistor connected to MCU

استخدام المقاومة الداخلية المسحوبة لأعلى في Arduino

يمكن تفعيل المقاومة الداخلية بكل سهولة باستخدام السطر التالي:


1pinMode(buttonPin, INPUT_PULLUP);

عند استخدام هذا الخيار، يتم توصيل الزر بين الدبوس و GND فقط، دون الحاجة لمقاومة خارجية.

اختيار قيمة المقاومة المناسبة

إذا كنت تستخدم مقاومات خارجية:

  • القيمة النموذجية: 10kΩ
  • أقل من 4.7kΩ: استهلاك طاقة زائد.
  • أكبر من 50kΩ: قد تؤدي إلى ضعف في ثبات الإشارة.

10kΩ هي الخيار الآمن والمناسب لمعظم التطبيقات.

Internal pull up resisitor

ما هو الاهتزاز في أزرار الضغط (Debounce)؟

عند الضغط على الزر أو تحريره، يحدث ارتداد في التلامس الميكانيكي، ما يؤدي إلى اهتزاز الإشارة خلال عدد أجزاء من الميلي ثانية. هذا الارتداد قد يتم تفسيره كعدة ضغطات من قبل المتحكم الدقيق.

Bouncing signal due to push button click

كيفية التعامل مع الاهتزاز (Debounce)

لمنع القراءة الخاطئة أو التكرار غير المقصود، يمكن استخدام أحد الخيارين التاليين:

الخيار 1: إزالة الاهتزاز عبر قطع إضافية (Hardware Debouncing)

يمكن استخدام دارة بسيطة مكونة من مقاومة ومكثف لتصفية الاهتزاز.

الدارة:

  • مقاومة 10kΩ توصل بين الزر ودبوس الإدخال.
  • مكثف 100nF يوصل بين دبوس الإدخال و GND.

هذا يمنع تغير الجهد المفاجئ الناتج عن الاهتزاز ويُنعّم الإشارة المقروءة.

هذه الطريقة بسيطة وفعالة، وتُستخدم عندما تكون الموارد البرمجية محدودة.

pull-down-resistor-with-debounce-capacitor
de-bouncing-button-with-capacitor-graph

الخيار 2: إزالة الاهتزاز عبر البرمجة (Software Debouncing)

يتم تأخير قراءة الزر لعدة ميلي ثانية بعد اكتشاف تغير في حالته للتأكد من ثباتها، قبل اعتبارها قراءة صحيحة.


مثال عملي: زر للعد وآخر لإعادة التعيين (لإعادة العداد إلى الصفر)

سنقوم باستخدام زرين مع الأردوينو:


  • الزر A (الدبوس 2): لزيادة العداد.
  • الزر B (الدبوس 3): لإعادة العداد إلى الصفر.

التوصيل

يتم توصيل كل زر على النحو التالي:


أحد أطراف الزر إلى GND.

الطرف الآخر إلى دبوس الإدخال في الأردوينو.

لا حاجة لمقاومات خارجية بفضل استخدام INPUT_PULLUP.

عند عدم الضغط، يقرأ الأردوينو HIGH، وعند الضغط يقرأ LOW.


الكود البرمجي (مع شرح)

1const int buttonA = 2;
2const int buttonB = 3;
3
4const unsigned long debounceDelay = 50;
5int counter = 0;
6
7// هيكل لتتبع حالة كل زر وزمن الاهتزاز
8struct Button {
9 int pin;
10 int lastState;
11 unsigned long lastDebounceTime;
12};
13
14Button btnA = {buttonA, HIGH, 0};
15Button btnB = {buttonB, HIGH, 0};
16
17void setup() {
18 pinMode(btnA.pin, INPUT_PULLUP);
19 pinMode(btnB.pin, INPUT_PULLUP);
20 Serial.begin(9600);
21}
22
23bool debounce(Button &btn) {
24 int reading = digitalRead(btn.pin);
25 bool pressed = false;
26
27 if (reading != btn.lastState) {
28 btn.lastDebounceTime = millis();
29 }
30
31 if ((millis() - btn.lastDebounceTime) > debounceDelay) {
32 if (reading == LOW && btn.lastState == HIGH) {
33 pressed = true;
34 }
35 }
36
37 btn.lastState = reading;
38 return pressed;
39}
40
41void loop() {
42 if (debounce(btnA)) {
43 counter++;
44 Serial.print("Count: ");
45 Serial.println(counter);
46 }
47
48 if (debounce(btnB)) {
49 counter = 0;
50 Serial.println("Counter Reset");
51 }
52}
53
arduino board connected to 2 switches

شرح الكود

  • يتم تعريف هيكل (struct) لتخزين معلومات كل زر.
  • دالة debounce:
    • تقرأ حالة الزر.
    • تتحقق مما إذا تغيرت الحالة.
    • تنتظر 50 ميلي ثانية ثم تتحقق من أن الضغط حقيقي (تحول من HIGH إلى LOW).
  • في loop:
    • إذا تم الضغط على الزر A، يزداد العداد ويتم طباعته.
    • إذا تم الضغط على الزر B، يتم إعادة تعيين العداد.

ما تراه في الشاشة التسلسلية:


1Count: 1
2Count: 2
3Count: 3
4Counter Reset
5Count: 1
6...
7

يتم تسجيل كل ضغطة حقيقية مرة واحدة فقط بفضل نظام إزالة الاهتزاز.

الخلاصة

  • أزرار الضغط بسيطة ولكنها ضرورية في الأنظمة الرقمية.
  • لا تترك دبابيس الإدخال معلقة — استخدم مقاومات سحب لأعلى أو لأسفل.
  • استخدم INPUT_PULLUP لتسهيل التوصيل في أردوينو.
  • إزالة الاهتزاز ضرورية للحصول على قراءة دقيقة.
  • يمكنك استخدام دارة RC لإزالة الاهتزاز عبر العتاد.
  • أو استخدم التأخير الزمني عبر البرمجة لتحقيق نفس الهدف.
  • تنظيم الكود يجعل من السهل إضافة المزيد من الأزرار أو الميزات لاحقًا.

أو بإمكانك إستكشاف تصنيفات أخرى

Arduino robot and rover

عالم الإلكترونيات

A DIY made aircraft rc model with a transmitter

الفيزياء وميكانيكا الطيران

Children looking into a microscop in turns

استكشف العالم الخفي تحت المجهر