17 of 17 menu

Ralat Penduaan Fungsi Pengeditan Unsur DOM dalam JavaScript

Katakan kita mempunyai senarai tertentu:

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

Dapatkan senarai itu sendiri dan itemnya ke dalam pembolehubah berasingan:

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

Mari kita buat supaya item senarai kita boleh diedit menggunakan 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 katakan kita mahu menambah item baharu ke dalam senarai. Katakan untuk ini, di bawah senarai kita mempunyai input yang sepadan:

<input id="adder">

Dapatkan pautan ke input ini ke dalam pembolehubah:

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

Mari kita buat supaya apabila input kehilangan fokus, item baharu dengan teks yang diambil dari input kami ditambahkan ke senarai:

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

Sekarang katakan kita mahu item yang baru ditambah juga boleh diedit. Dengan sendirinya, pengeditan tidak akan berfungsi untuk mereka, kerana ketika kami melampirkan pengendali klik pada item senarai, item tersebut belum wujud.

Mari kita lihat pilihan penyelesaian yang mungkin untuk masalah ini.

Penyelesaian Pertama

Penyelesaian paling mudah - ialah menduakan kod fungsi func, dengan melampirkannya 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 menduakan kod }); ul.append(li); });

Sudah tentu, dalam penyelesaian ini kita langsung nampak kelemahannya - menduakan kod adalah tidak betul.

Penyelesaian Kedua

Untuk menyelesaikan masalah penduaan, adalah logik untuk mengeluarkan fungsi func ke luar, 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 ialah fungsi kami menggunakan pembolehubah li, yang diperoleh dari skop luaran. Tetapi selepas fungsi dikeluarkan, pembolehubah itu sekarang tidak kelihatan!

Untuk menyelesaikan masalah, kami akan menghantar li kami 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', func); }); li.removeEventListener('click', func); }

Dan di sini penyelesaian kami menimbulkan satu lagi masalah. Masalahnya ialah kita tidak boleh begitu sahaja menghantar parameter kepada pengendali peristiwa:

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

Untuk menyelesaikan masalah ini, panggil sahaja fungsi kami di dalam pengendali tanpa nama:

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

Dan lakukan perkara yang sama apabila mencipta item senarai baharu:

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

Penyelesaian Ketiga

Terdapat penyelesaian yang lebih elegan. Anda boleh menggunakan delegasi acara. Dalam kes ini masalah dengan item senarai baharu sahaja tidak akan timbul:

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 kes ini, gelung melalui item senarai langsung tidak diperlukan oleh kami, dan kod untuk mencipta item senarai baharu akan dipendekkan kepada ini:

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