17 of 17 menu

Kesalahan Duplikasi Fungsi Edit Elemen DOM di JavaScript

Misalkan kita memiliki sebuah daftar:

<ul> <li>1</li> <li>2</li> <li>3</li> </ul>

Mari dapatkan daftar itu sendiri dan item-itemnya ke dalam variabel terpisah:

let ul = document.querySelector('ul'); let lis = document.querySelectorAll('li');

Mari kita buat agar item-item dari daftar kita dapat diedit dengan input yang muncul:

for (let li of lis) { li.addEventListener('click', function func() { let input = document.createElement('input'); input.value = li.textContent; li.textContent = ''; li.append(input); input.addEventListener('blur', function() { li.textContent = this.value; li.addEventListener('click', func); }); li.removeEventListener('click', func); }); }

Sekarang misalkan kita ingin menambahkan item baru ke dalam daftar. Misalkan untuk ini, di bawah daftar kita ada input yang sesuai:

<input id="adder">

Dapatkan referensi ke input ini ke dalam variabel:

let adder = document.querySelector('#adder');

Mari kita buat agar ketika kehilangan fokus, input menambahkan item baru ke daftar dengan teks yang diambil dari input kita:

adder.addEventListener('blur', function() { let li = document.createElement('li'); li.textContent = this.value; ul.append(li); });

Sekarang misalkan kita ingin item yang baru ditambahkan juga dapat diedit. Secara sendiri, pengeditan tidak akan bekerja untuk mereka, karena ketika kita memasang penangan klik pada item daftar, item-item ini belum ada.

Mari kita lihat beberapa opsi yang memungkinkan untuk memecahkan masalah ini.

Solusi Pertama

Solusi paling sederhana adalah menduplikasi kode fungsi func, dengan mengikatnya juga untuk item yang baru dibuat:

adder.addEventListener('blur', function() { let li = document.createElement('li'); li.textContent = this.value; li.addEventListener('click', function func() { // di sini kita menduplikasi kode }); ul.append(li); });

Tentu saja, dalam solusi ini kita langsung melihat kelemahannya - menduplikasi kode itu tidak benar.

Solusi Kedua

Untuk menyelesaikan masalah duplikasi, masuk akal untuk mengambil fungsi func keluar, menjadikannya Function Declaration:

function func() { let input = document.createElement('input'); input.value = li.textContent; li.textContent = ''; li.append(input); input.addEventListener('blur', function() { li.textContent = this.value; li.addEventListener('click', func); }); li.removeEventListener('click', func); }

Di sinilah masalah menunggu kita. Masalahnya adalah fungsi kita menggunakan variabel li, yang didapatkan dari ruang lingkup luar. Tapi setelah fungsi dikeluarkan, variabel itu sekarang tidak terlihat!

Untuk memecahkan masalah, kita akan meneruskan li kita sebagai parameter:

function func(li) { let input = document.createElement('input'); input.value = li.textContent; li.textContent = ''; li.append(input); input.addEventListener('blur', function() { li.textContent = this.value; li.addEventListener('click', function() { func(li); }); }); li.removeEventListener('click', function() { func(li); }); }

Dan di sini solusi kita menimbulkan masalah lain. Masalahnya adalah kita tidak bisa begitu saja meneruskan parameter ke penangan event:

for (let li of lis) { li.addEventListener('click', func(li)); // tidak bekerja! }

Untuk mengatasi masalah ini, cukup panggil fungsi kita di dalam penangan anonim:

for (let li of lis) { li.addEventListener('click', function() { func(li); }); }

Dan lakukan hal yang sama saat membuat item daftar baru:

adder.addEventListener('blur', function() { let li = document.createElement('li'); li.textContent = this.value; li.addEventListener('click', function() { func(li); }); ul.append(li); });

Solusi Ketiga

Ada solusi yang lebih elegan. Kita bisa memanfaatkan delegasi event. Dalam hal ini masalah dengan item daftar baru tidak akan muncul:

ul.addEventListener('click', function(event) { if (event.target.tagName === 'LI') { // tangkap klik tepat pada li, bukan pada input let li = event.target; let input = document.createElement('input'); input.value = li.textContent; li.textContent = ''; li.append(input); input.addEventListener('blur', function() { li.textContent = this.value; }); } });

Dalam hal ini, loop melalui item daftar pada dasarnya tidak akan kita butuhkan, dan kode untuk membuat item daftar baru akan dipersingkat menjadi seperti ini:

adder.addEventListener('blur', function() { let li = document.createElement('li'); li.textContent = this.value; ul.append(li); });
Indonesia
AfrikaansAzərbaycanБългарскиবাংলাБеларускаяČeštinaDanskDeutschΕλληνικάEnglishEspañolEestiSuomiFrançaisहिन्दीMagyarՀայերենItaliano日本語ქართულიҚазақ한국어КыргызчаLietuviųLatviešuМакедонскиMelayuမြန်မာNederlandsNorskPolskiPortuguêsRomânăРусскийසිංහලSlovenčinaSlovenščinaShqipСрпскиSrpskiSvenskaKiswahiliТоҷикӣไทยTürkmenTürkçeЎзбекOʻzbekTiếng Việt
Kami menggunakan cookie untuk operasi situs, analitik, dan personalisasi. Pemrosesan data dilakukan sesuai dengan Kebijakan Privasi.
terima semua atur tolak