Program Tip

null의 'addEventListener'속성을 읽을 수 없습니다.

programtip 2020. 10. 22. 22:19
반응형

null의 'addEventListener'속성을 읽을 수 없습니다.


프로젝트에 바닐라 자바 ​​스크립트를 사용해야합니다. 몇 가지 기능이 있는데 그중 하나는 메뉴를 여는 버튼입니다. 대상 ID가있는 페이지에서는 작동하지만 ID가없는 페이지에서는 오류가 발생합니다. 함수가 ID를 찾을 수없는 페이지에서 "Cannot read property 'addEventListener'of null"오류가 발생하고 다른 함수가 작동하지 않습니다.

다음은 메뉴를 여는 버튼의 코드입니다.

function swapper() {
toggleClass(document.getElementById('overlay'), 'open');
}

var el = document.getElementById('overlayBtn');
el.addEventListener('click', swapper, false);

var text = document.getElementById('overlayBtn');
text.onclick = function(){
this.innerHTML = (this.innerHTML === "Menu") ? "Close" : "Menu";
return false;
};

어떻게 처리합니까? 이 코드를 다른 함수로 모두 래핑하거나 if / else 문을 사용하여 특정 페이지에서만 ID를 검색하지만 정확히 확실하지는 않습니다.


가장 쉬운 방법은 el이벤트 리스너를 추가하기 전에 null이 아닌지 확인하는 것 입니다.

var el = document.getElementById('overlayBtn');
if(el){
  el.addEventListener('click', swapper, false);
}

DOM이 완전히로드되기 전에 실행되기 때문에 document.getElementById('overlayBtn');반환 되는 것 같습니다 null.

이 코드 줄을 아래에 넣으면

window.onload=function(){
  -- put your code here
}

그러면 문제없이 실행됩니다.

예:

window.onload=function(){
    var mb = document.getElementById("b");
    mb.addEventListener("click", handler);
    mb.addEventListener("click", handler2);
}


function handler() {
    $("p").html("<br>" + $("p").text() + "<br>You clicked me-1!<br>");
}

function handler2() {
    $("p").html("<br>" + $("p").text() + "<br>You clicked me-2!<br>");
}

비슷한 상황에 직면했습니다. 페이지가로드되기 전에 스크립트가 실행되기 때문일 수 있습니다. 페이지 하단에 스크립트를 배치하여 문제를 피했습니다.


동일한 오류가 발생했지만 null 검사를 수행해도 도움이되지 않는 것 같습니다.

내가 찾은 해결책은 DOM이 언제로드를 완료했는지 확인하기 위해 전체 문서에 대한 이벤트 리스너 내부에 함수를 래핑하는 것입니다.

document.addEventListener('DOMContentLoaded', function () {
    el.addEventListener('click', swapper, false);
});

HTML 클래스와 ID를 동적으로 변경하는 프레임 워크 (Angular)를 사용하고 있기 때문이라고 생각합니다.


도움을 주신 @Rob M.에게 감사드립니다. 최종 코드 블록은 다음과 같습니다.

function swapper() {
  toggleClass(document.getElementById('overlay'), 'open');
}

var el = document.getElementById('overlayBtn');
if (el){
  el.addEventListener('click', swapper, false);

  var text = document.getElementById('overlayBtn');
  text.onclick = function(){
    this.innerHTML = (this.innerHTML === "Menu") ? "Close" : "Menu";
    return false;
  };
}

JS가 HTML 부분 이전에로드되는 bcz 일 뿐이므로 해당 요소를 찾을 수 없습니다. 윈도우가로드 될 때 호출 될 함수 안에 전체 JS 코드를 넣으십시오.

html 아래에 Javascript 코드를 넣을 수도 있습니다.


단순히 스크립트 태그에 '비동기'를 추가했는데 문제가 해결 된 것 같습니다. 누군가가 설명 할 수 있다면 왜 그런지 모르겠지만 그것은 나를 위해 일했습니다. 내 생각 엔 페이지가 스크립트가로드 될 때까지 기다리지 않기 때문에 페이지가 JavaScript와 동시에로드됩니다.

Async / Await를 사용하면 동기식으로 비동기 코드를 작성할 수 있습니다. 그것은 단지 제너레이터와 yield 문을 사용하여 실행을 "일시 중지"하는 구문 설탕 일 뿐이며, 변수에 할당 할 수있는 기능을 제공합니다!

다음의 참조 링크 - https://medium.com/siliconwat/how-javascript-async-await-works-3cab4b7d21da


다른 사람들이 말했듯이 문제는 페이지 (특히 대상 요소)가로드되기 전에 스크립트가 실행된다는 것입니다.

하지만 콘텐츠 순서를 변경하는 솔루션이 마음에 들지 않습니다.

선호하는 해결책은 페이지 onload 이벤트에 이벤트 핸들러를 넣고 거기에 리스너를 설정하는 것입니다. 그러면 할당이 실행되기 전에 페이지와 대상 요소가로드됩니다. 예 :

    <script>
    function onLoadFunct(){
            // set Listener here, also using suggested test for null
    }
    ....
    </script>

    <body onload="onLoadFunct()" ....>
    .....

이름과 함께 따옴표 모음이 있습니다. 특정 이름과 관련된 마지막 견적을 업데이트하기 위해 업데이트 버튼을 사용하고 있지만 업데이트 버튼을 클릭하면 업데이트되지 않습니다. 아래에 server.js 파일 및 외부 js 파일 (main.js)에 대한 코드가 포함되어 있습니다.

main.js (외부 js)

var update = document.getElementById('update');
if (update){
update.addEventListener('click', function () {

  fetch('quotes', {
  method: 'put',
  headers: {'Content-Type': 'application/json'},
  body: JSON.stringify({
    'name': 'Muskan',
    'quote': 'I find your lack of faith disturbing.'
  })
})var update = document.getElementById('update');
if (update){
update.addEventListener('click', function () {

  fetch('quotes', {
  method: 'put',
  headers: {'Content-Type': 'application/json'},
  body: JSON.stringify({
    'name': 'Muskan',
    'quote': 'I find your lack of faith disturbing.'
  })
})
.then(res =>{
    if(res.ok) return res.json()
})
.then(data =>{
    console.log(data);
    window.location.reload(true);
})
})
}

server.js 파일

app.put('/quotes', (req, res) => {
  db.collection('quotations').findOneAndUpdate({name: 'Vikas'},{
    $set:{
        name: req.body.name,
        quote: req.body.quote
    }
  },{
    sort: {_id: -1},
    upsert: true
  },(err, result) =>{
    if (err) return res.send(err);
    res.send(result);
  })

})

이는 번들 js가 실행될 때 요소가로드되지 않았기 때문입니다.

I'd move the <script src="sample.js" type="text/javascript"></script> to the very bottom of the index.html file. This way you can ensure script is executed after all the html elements have been parsed and rendered .


Add all event listeners when a window loads.Works like a charm no matter where you put script tags.

window.addEventListener("load", startup);

function startup() {

  document.getElementById("el").addEventListener("click", myFunc);
  document.getElementById("el2").addEventListener("input", myFunc);

}

myFunc(){}

참고URL : https://stackoverflow.com/questions/26107125/cannot-read-property-addeventlistener-of-null

반응형