【问题标题】:Toggle color on click单击时切换颜色
【发布时间】:2021-05-11 09:42:04
【问题描述】:

我有一个带有<a href> 的列表,我正在尝试设置点击颜色。

<a id="mls-category-terms" class="621">Test 1</a>
<a id="mls-category-terms" class="622">Test 2</a>
<a id="mls-category-terms" class="639">Test 3</a>
<a id="mls-category-terms" class="641">Test 4</a>

我通过以下代码实现了这一点:

const homeCategoryList = document.querySelectorAll('#mls-category-terms');
for (let i = 0; i < homeCategoryList.length; i++) {
    homeCategoryList[i].addEventListener('click', () => homeCategoryList[i].setAttribute('style', 'background: #3d5b9a;color: #fff;'));
}

这可行,但是这样当我点击另一个链接时,颜色也会显示在该链接上,但它也会保留在上一个链接上。

因此,完美的结果将是当用户点击一个链接时,它会获得不同的颜色,但如果点击该列表中的另一个链接,前一个链接将被重置,最后点击的链接将获得颜色。

这是当前结果的图片:https://prnt.sc/12sr23w

希望这是有道理的。我是 JavaScript 的新手。

【问题讨论】:

  • 首先,ID 应该是唯一的。其次,为什么不使用 CSS?
  • 是的,如果不需要,是否使用唯一 ID。并使用 CSS!

标签: javascript toggle


【解决方案1】:

正如评论中提到的,ID 应该是唯一的,因此 mls-category-terms 应该是一个 CSS 类。一旦你解决了这个问题,你可以这样做:

const links = document.querySelectorAll('.mls-category-terms');

links.forEach(link => {
  link.addEventListener('click', () => {
    links.forEach(l => l.classList.remove('active')); // remove the 'active' class from all links
    link.classList.add('active'); // add the 'active' class only to the clicked one
  })
});
.mls-category-terms.active {
  background-color: #3d5b9a;
  color: #fff;
}
<a id="link1" class="mls-category-terms 621">Test 1</a>
<a id="link2" class="mls-category-terms 622">Test 2</a>
<a id="link3" class="mls-category-terms 639">Test 3</a>
<a id="link4" class="mls-category-terms 641">Test 4</a>

【讨论】:

    【解决方案2】:

    您需要跟踪获得样式的前一个并相应地删除它:

    const homeCategoryList = document.querySelectorAll('#mls-category-terms');
    let PREV=0;
    for (let i = 0; i < homeCategoryList.length; i++) {
        homeCategoryList[i].addEventListener('click', () => {
          homeCategoryList[PREV].removeAttribute('style');
          homeCategoryList[i].setAttribute('style', 'background: #3d5b9a;color: #fff;')
          PREV=i;
        });
    }
    <a id="mls-category-terms" class="621">Test 1</a>
    <a id="mls-category-terms" class="622">Test 2</a>
    <a id="mls-category-terms" class="639">Test 3</a>
    <a id="mls-category-terms" class="641">Test 4</a>

    【讨论】:

    • 您可以使用let 代替全局变量。
    【解决方案3】:

    每次点击都会删除之前设置的样式,然后再将样式添加到新点击的元素。

    const homeCategoryList = document.querySelectorAll('#mls-category-terms');
    homeCategoryList.forEach(h => h.addEventListener('click', () => toggleColor(h)));
    
    function toggleColor(e) {
      homeCategoryList.forEach(f => f.setAttribute('style', 'background:;color:;'));
      e.setAttribute('style', 'background: #3d5b9a;color: #fff;');
    }
    <a id="mls-category-terms" class="621">Test 1</a>
    <a id="mls-category-terms" class="622">Test 2</a>
    <a id="mls-category-terms" class="639">Test 3</a>
    <a id="mls-category-terms" class="641">Test 4</a>

    【讨论】:

      【解决方案4】:

      这实际上可以通过 CSS :focus 伪类来完成:

      .mls-category-terms:link {color:#000}
      .mls-category-terms:visited {color:#000}
      .mls-category-terms:hover {color:#FF00FF}
      .mls-category-terms:active {color:#0000FF}
      .mls-category-terms:focus {
        background: #3d5b9a;
        color: #fff;
      }
      <a class="mls-category-terms 621" href="#">Test 1</a>
      <a class="mls-category-terms 622" href="#">Test 2</a>
      <a class="mls-category-terms 639" href="#">Test 3</a>
      <a class="mls-category-terms 641" href="#">Test 4</a>

      我的首选方法,但正如下面的secan's comment 所示,因为:focus 伪类会失去焦点,无论单击其他什么元素。因此,使用 .active 类和 Javascript 最适合大多数用例。

      还要注意mls-category-terms id 已经变成了一个类。

      【讨论】:

      • 使用:focus伪类的问题是,一旦用户点击页面中的任何其他元素,链接就会失去焦点并回滚到默认样式。如果从单击链接到单击另一个链接的那一刻应该保留“活动”样式,我认为您必须使用 JavaScript。
      猜你喜欢
      • 1970-01-01
      • 2021-03-28
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-03-05
      • 1970-01-01
      • 1970-01-01
      • 2019-08-19
      相关资源
      最近更新 更多