Robototexnika · Mikrokontrollerlar · 7-sinf
Tugma va raqamli kirish
Bitta tugma chiroqni yoqib-o‘chirsin. Nega pin «suzib yuradi» va tugma «ikki marta» bosiladi?
Vaziyat
Avtobusda «to‘xtang» tugmasini bossangiz, haydovchi oldida chiroq yonadi. Siz ham shunday qilmoqchisiz: bitta tugma — chiroq yonadi, yana bossangiz — o‘chadi. Tugmani Arduino 2-piniga, chiroqni 13-pinga ulaysiz va… chiroq o‘zicha lipillaydi — tugmaga tegmagan bo‘lsangiz ham! Rezistor qo‘ysangiz tinchlanadi. Keyin almashtirgich dasturini yozasiz — ba’zan bir bosishda chiroq ikki marta almashib, o‘chganicha qoladi. Nega pin «suzib yuradi»? Nega tugma «ikki marta bosiladi»? Osillograf va `millis()` bilan sababini ham, davosini ham topamiz.
Mavzu
Tugma va raqamli kirish: INPUT_PULLUP, tebranish (debounce). Bitta tugma bilan chiroqni yoqish-o‘chirish: nega tugma «ikki marta» bosiladi
Asosiy tushunchalar
- digitalRead va pull-up
- INPUT_PULLUP
- Tebranish (debounce)
Formulalar
`digitalRead()` chegaralari (ATmega328P, 5 V): 3 V dan yuqori — HIGH, 1,5 V dan past — LOW, orasida — noaniq (kirish ≈ 0,5 V gisterezis bilan oldingi holatni saqlaydi).
Tugma bosilganda pull-up (yoki pull-down) rezistoridan oqadigan tok — arzimas. Ichki pull-up 20–50 kΩ: 0,1–0,25 mA.
RC filtr: kontakt bir zumga ochilsa, kondensator 3 V gacha zaryadlanib ulgurmaydi — tebranish pinga yetmaydi.
Dasturiy debounce: qabul qilingan o‘zgarishdan keyin oyna ichidagi o‘zgarishlar e’tiborga olinmaydi; oyna tebranish davomidan katta bo‘lsin (odatda 20–50 ms).
Xato: pin OUTPUT HIGH qilingan, tugma uni yerga tutashtirdi — chegaradan 5 marta ko‘p tok, chip kuyadi.
Nazariya
Raqamli kirish nima
`pinMode(2, INPUT)` pinni kirish qiladi: endi u kuchlanish bermaydi, balki o‘qiydi. `digitalRead(2)` kuchlanishni ikki holatga keltiradi: 5 V ga yaqin — HIGH (1), 0 V ga yaqin — LOW (0). Chegara aniq: ATmega328P 5 V da 3 V dan yuqorini HIGH, 1,5 V dan pastni LOW deb o‘qiydi; 1,5–3 V oralig‘i — «hech kim bilmaydi». Kirish pini deyarli tok olmaydi (1 mkA dan kam): u faqat «qaraydi».
Suzib yuruvchi kirish
Tugmani 2-pin bilan GND orasiga ulab, rezistor qo‘ymasangiz: tugma bosilganda pin yerga ulanadi — LOW, aniq. Lekin bosilmaganda pin hech narsaga ulanmagan — havoda «suzib yuradi». Yuqori qarshilikli kirish antennaga aylanadi: 50 Hz tarmoq shovqini, yaqin simlar, qo‘lingiz uni 0 dan 5 V gacha tebratadi. `digitalRead` tasodifiy HIGH va LOW beradi — chiroq o‘zicha lipillaydi, qo‘lingizni yaqinlashtirsangiz kuchayadi. Bu «buzilgan Arduino» emas, aniqlanmagan kirish.
Pull-down, pull-up va INPUT_PULLUP
Davo — pinni rezistor orqali ma’lum kuchlanishga «tortib» qo‘yish. Pull-down: 10 kΩ pin–GND, tugma pin–5V: tinch LOW, bosilsa HIGH (rezistordan 0,5 mA oqadi). Pull-up: 10 kΩ pin–5V, tugma pin–GND: tinch HIGH, bosilsa LOW — mantiq teskari, lekin tugmaning bir oyog‘i yerda — xavfsiz va qulay. ATmega328P da bu rezistor allaqachon chipning ichida (20–50 kΩ): `pinMode(2, INPUT_PULLUP)` uni yoqadi — tashqi rezistor kerak emas. Shuning uchun Arduino dasturlarida «bosilgan = LOW» odatiy hol.
Tugma qanday ishlaydi
Taktli tugmaning ichida metall gumbaz: bosganda u egilib ikki kontaktni tutashtiradi, qo‘yib yuborsangiz prujinadek qaytadi. To‘rtta oyoq — ikki juft: har juft ichida doimo ulangan, bosilganda juftlar tutashadi. Maketli platada tugma markaziy ariqcha ustiga qo‘yiladi; qaysi juft qayerdaligini adashtirmaslik uchun simlar diagonal oyoqlarga ulanadi — shunda ulanish har qanday tugmada to‘g‘ri bo‘ladi.
Tebranish (bounce) va davosi
Gumbaz kontaktga tegganda bir zumda tinchlanmaydi — 1–10 ms davomida bir necha marta tegib-ajraladi. Ko‘zga bir bosish, osillografda — bir nechta front. `loop()` sekundiga yuz minglab marta aylanadi va har frontni «yangi bosish» deb oladi: almashtirgich ikki marta almashib, o‘chganicha qoladi, Serial monitorda «bosildi» ikki marta chiqadi. Davolari: dasturiy — `millis()` bilan oyna: o‘zgarish qabul qilingach, OYNA ms davomida yangilari e’tiborsiz (oyna tebranishdan katta bo‘lsin: 20–50 ms); apparat — RC filtr: 10 kΩ + 1 mkF, = 10 ms, kondensator qisqa ochilishlarda 3 V gacha zaryadlanib ulgurmaydi, kirishning Shmitt triggeri esa bitta toza front beradi.
Model haqida
Pin kuchlanishi 50 mks qadam bilan hisoblanadi, kirish — Shmitt trigger (3 V / 1,5 V). Tebranish: har bosish va qo‘yib yuborishda 2 yoki 4 qo‘shimcha ulanish-uzilish, jami 2–12 ms (tasodifiy, qayta ko‘rsatishda takrorlanadi). Suzib yurgan pin shovqini — 50 Hz + sekin tasodifiy siljish (illyustrativ). Dastur har millisekundda ilgarilaydi; `digitalRead()` har chaqiriqda ≈ 60 mks keyingi nuqtani ko‘radi — haqiqiy `loop()` ham shunday «tez-tez qarab turadi». Qisqa tutashuvda chip 40 mA chegaradan oshgan tokni vaqt bo‘yicha yig‘ib kuyadi.
Bilasizmi?
- ATmega328P ning har bir kirish pinida dasturdan yoqiladigan ichki pull-up rezistor bor — datasheet bo‘yicha 20–50 kΩ. Shuning uchun Arduino da tugma uchun tashqi rezistor shart emas: `pinMode(pin, INPUT_PULLUP)` yetarli.
- Mikrokontroller muhandisi Jek Gansl (Jack Ganssle) 2004-yilda 18 xil tugma va kalitni osillograf bilan o‘lchab chiqqan: kontakt tebranishi ko‘pida 1–2 ms, eng yomonlarida 6 ms dan ortiq davom etgan — shuning uchun ko‘pchilik dasturlar 20–50 ms li debounce oynasi oladi.
Tajribada nima bor
Haqiqiy plata qo‘lda chizilgan rasmda: uni aylantirasiz, qismlarni joylaysiz, zanjirni ulaysiz, kodni yozib yuklaysiz — tok va kuchlanish o‘sha zahoti hisoblanadi, xato ulashda qism kuyadi. Ichida topshiriqlar, nazariya, test va ekskursiya bor.
Shu bo‘limdagi boshqa tajribalar
- Arduino Uno: birinchi dastur — 7-sinf
- Analog kirish va Serial monitor — 7-sinf
- PWM: yorqinlik va ovoz — 8-sinf
- millis() va ko‘p vazifa — 8-sinf