为什么必须单击两次才能使此JavaScript函数起作用?

时间:2020-03-14 22:34:46

标签: javascript html

为了使功能可以将显示更改为“隐藏”然后又返回“阻止”,每次需要两次单击。为什么是这样?如何将其减少到一键?

function showOfferMessage() {                                        
  var coll = document.getElementsByClassName("collapsible");
  var i;

  for (i = 0; i < coll.length; i++) {
    coll[i].addEventListener("click", function() {
      this.classList.toggle("active");
      var content = this.nextElementSibling;
      if (content.style.display === "block") {
        content.style.display = "none";
      } else {
        content.style.display = "block";
      }
    });
  }
}
<div class="offer-row collapsible" id="'.$oid.'" onclick="showOfferMessage()">
    <div class="offer-info-item">
        <div class="offcatreview-title">
            <h3>Cat. Rating</h3>
        </div>
        <div class="offer-cat-rating">
        </div>
    </div>
</div>
<div class="content">
    <p>'.$message.'</p>
</div>

2 个答案:

答案 0 :(得分:2)

那是因为您每次点击都会注册一个事件监听器!因此,您的听众每次单击都会再次执行。

您的固定代码:

var name = "Bob";
if (name == "Bob") {
    var fullName = "Bob Smith";

}
console.log(fullName); 
                    
function showOfferMessage(element) {
    element.classList.toggle("active");
    var content = element.nextElementSibling;
    if (content.style.display === "block") {
      content.style.display = "none";
    } else {
      content.style.display = "block";
    }
}

答案 1 :(得分:0)

onclick事件执行showOfferMessage() {}函数,该函数将事件侦听器放在"collapsible"元素上。然后第二次单击将执行事件侦听器的内容。

但首先要注意的是,只要您只有一个名为"collapsible"的元素,为什么要尝试获取多个元素。做一个document.querySelector并使用css样式选择器定位元素,然后将addEventListener直接链接在该选择器上。

当您像查询样式一样,您将获得明确设置的样式。在您的情况下,如果没有单击"collapsible"元素,则不会设置任何显示样式。即使div的默认显示样式为block,也没有明确设置,所以...style.display将返回一个空字符串-> falsy。 您必须使用getComputedStyle方法获得隐式样式,

例如(codepen):

document.querySelector(".collapsible").addEventListener("click", function() {
  console.log(this);
  this.classList.toggle("active");
  var content = document.querySelector(".content");
  console.log(window.getComputedStyle(content).display);
  if (window.getComputedStyle(content).display === "block") {
    content.style.display = "none";
  } else {
    content.style.display = "block";
  }
});

我可能会在事件监听器中使用arrow function

document.querySelector(".collapsible").addEventListener("click", event => {
  console.log(event.target);
  event.target.classList.toggle("active");
  var content = document.querySelector(".content");
  console.log(window.getComputedStyle(content).display);
  if (window.getComputedStyle(content).display === "block") {
    content.style.display = "none";
  } else {
    content.style.display = "block";
  }
});