← Daftar materi Arduino

Bab 9 · Arduino Uno R3

Percabangan, Perulangan, dan Fungsi pada Arduino

Latihan if, else, for, dan fungsi dengan tombol serta LED bawaan Arduino Uno.

Saat program harus memilih

Pada program tombol, LED menyala hanya jika tombol ditekan. Keputusan seperti ini ditulis dengan if dan else. Siapkan tombol yang menghubungkan pin 2 ke GND ketika ditekan. Kita memakai INPUT_PULLUP, sehingga tombol yang dilepas terbaca HIGH dan tombol yang ditekan terbaca LOW.

Contoh utuh: tiga kedipan saat tombol ditekan

const int PIN_TOMBOL = 2;
const int PIN_LED = LED_BUILTIN;

void kedip(int banyak) {
  for (int i = 0; i < banyak; i++) {
    digitalWrite(PIN_LED, HIGH);
    delay(200);
    digitalWrite(PIN_LED, LOW);
    delay(200);
  }
}

void setup() {
  pinMode(PIN_TOMBOL, INPUT_PULLUP);
  pinMode(PIN_LED, OUTPUT);
}

void loop() {
  bool ditekan = digitalRead(PIN_TOMBOL) == LOW;
  if (ditekan) {
    kedip(3);
  } else {
    digitalWrite(PIN_LED, LOW);
  }
}

Jika tombol ditahan, tiga kedipan akan diulang lagi. Program ini belum mendeteksi satu kejadian penekanan; ia membaca keadaan tombol setiap kali loop berjalan. Selama rangkaian kedipan berlangsung, perubahan tombol belum dibaca lagi.

Cara membaca for

int i = 0 dijalankan sekali saat perulangan dimulai. i < banyak diperiksa sebelum setiap putaran. i++ menambah i setelah putaran selesai. Untuk banyak = 3, isi blok berjalan pada i = 0, 1, dan 2. Penghitung pendek seperti i wajar dipakai untuk perulangan sederhana.

Fungsi membantu memisahkan pekerjaan

kedip adalah nama fungsi, banyak adalah parameter, dan kedip(3) memberikan nilai 3 ke parameter tersebut. void berarti fungsi ini tidak mengembalikan nilai. Fungsi dapat juga menghitung dan mengembalikan hasil, misalnya:

int tambahDua(int angka) {
  return angka + 2;
}
// Contoh pemakaian di dalam loop():
// int hasil = tambahDua(5);  // hasil berisi 7

Lebih dari satu syarat

Gunakan && ketika kedua syarat harus benar, || jika cukup salah satunya, dan ! untuk membalik nilai benar/salah. Contohnya, cahaya < 400 && modeOtomatis berarti lampu hanya boleh menyala saat gelap sekaligus mode otomatis aktif. Untuk beberapa pilihan berurutan, gunakan if, else if, lalu else.

Latihan

Ganti kedip(3) menjadi kedip(5). Lalu ubah program agar tombol yang dilepas membuat LED menyala terus. Perkirakan hasilnya dulu sebelum mengunggah. Jika ingin tombol tetap responsif selama LED berkedip, lanjutkan ke materi millis().

Alur eksekusi if, else if, dan else

Komputer memeriksa syarat dari atas ke bawah dan berhenti pada syarat pertama yang benar. Cabang lain yang ada di bawahnya dilewati, walaupun syaratnya sebenarnya juga benar. Karena itu urutan penulisan syarat penting. Jika kamu menaruh syarat yang luas di atas syarat yang sempit, cabang yang sempit tidak akan pernah dijalankan.

Contoh kedua: tiga tingkat dengan potensiometer

Potensiometer punya tiga kaki. Hubungkan kaki kiri ke 5V, kaki kanan ke GND, dan kaki tengah (wiper) ke pin A0. Memutar kenop menggeser tegangan di A0 dari 0 V sampai 5 V, yang dibaca analogRead() sebagai angka 0 sampai 1023.

const int PIN_POT = A0;

void setup() {
  Serial.begin(9600);
}

void loop() {
  int nilai = analogRead(PIN_POT);
  if (nilai < 341) {
    Serial.println("Rendah");
  } else if (nilai < 682) {
    Serial.println("Sedang");
  } else {
    Serial.println("Tinggi");
  }
  delay(300);
}

Angka 341 dan 682 diperoleh dengan membagi rentang 0 sampai 1023 menjadi tiga bagian yang hampir sama. Putar kenop pelan-pelan dan lihat tulisan pada Serial Monitor berganti. Perhatikan bahwa syarat kedua tidak perlu menulis nilai >= 341, sebab jika program sudah sampai di cabang itu, syarat pertama pasti salah. Baris delay(300) hanya menjaga agar layar tidak banjir teks.

Perulangan while dan perbedaannya dengan for

for cocok ketika jumlah putaran sudah diketahui. while cocok ketika kita menunggu suatu keadaan berubah, seperti menunggu tombol dilepas.

void tungguDilepas() {
  while (digitalRead(2) == LOW) {
    // tidak melakukan apa-apa selama tombol masih ditekan
  }
}

Fungsi ini berputar selama pin 2 terbaca LOW, yaitu tombol masih ditekan pada rangkaian INPUT_PULLUP. Begitu tombol dilepas, pin menjadi HIGH dan perulangan berakhir. Hati-hati: jika kondisi while tidak pernah berubah, program tertahan selamanya di situ. Gejalanya LED atau Serial Monitor berhenti merespons sampai board di-reset.

Fungsi yang mengembalikan nilai

Fungsi yang baik melakukan satu pekerjaan dan namanya menjelaskan pekerjaan itu. Misalnya fungsi bool gelap(int cahaya) mengembalikan true bila cahaya kurang dari 400. Dengan begitu isi loop() terbaca seperti kalimat: if (gelap(analogRead(A0))) { ... }. Parameter di dalam fungsi hanyalah salinan; mengubahnya di dalam fungsi tidak mengubah variabel asli di luar fungsi.

Kesalahan yang sering terjadi

  • Tombol tanpa INPUT_PULLUP. Pin yang dibiarkan mengambang membaca HIGH dan LOW secara acak karena menangkap derau. Pasang INPUT_PULLUP di setup().
  • Logika terbalik. Dengan pull-up, ditekan berarti LOW. Banyak pemula menulis == HIGH lalu heran kenapa LED menyala saat tombol dilepas.
  • Titik koma setelah for atau if. Tulisan for (...); membuat perulangan berjalan tanpa isi, sedangkan blok di bawahnya hanya dijalankan sekali.
  • Kurung kurawal tidak berpasangan. Kompilator melaporkan kesalahan di tempat yang jauh dari sumbernya. Fitur Auto Format di Arduino IDE membantu melihat blok yang tidak seimbang.
  • Nama fungsi sama dengan nama variabel. Ini memicu pesan kesalahan yang membingungkan. Gunakan kata kerja untuk fungsi dan kata benda untuk variabel.

Ringkasan

if, else if, dan else memilih satu jalur dari beberapa kemungkinan. for mengulang dengan jumlah pasti, while mengulang selama syarat benar. Fungsi membungkus pekerjaan yang diberi nama agar program mudah dibaca dan dipakai ulang. Ketiganya dapat digabungkan dengan input tombol dan sensor untuk membuat perilaku yang lebih hidup.

Soal latihan

  1. Pada contoh potensiometer, apa yang tercetak jika analogRead bernilai 500?
    Lihat jawaban

    Sedang, karena 500 tidak kurang dari 341 tetapi kurang dari 682.

  2. Berapa kali isi for (int i = 0; i < 4; i++) dijalankan, dan berapa nilai i pada putaran terakhir?
    Lihat jawaban

    Empat kali, dengan nilai i berturut-turut 0, 1, 2, 3. Nilai terakhir di dalam blok adalah 3.

  3. Mengapa while (digitalRead(2) == LOW) bisa membuat program macet?
    Lihat jawaban

    Jika tombol terus ditahan atau pin tidak pernah naik ke HIGH, syaratnya tetap benar dan perulangan tidak berakhir.

  4. Tulis fungsi bool genap(int angka) yang mengembalikan true untuk bilangan genap.
    Lihat jawaban

    bool genap(int angka) { return angka % 2 == 0; }