【问题标题】:Refactoring : Would like a single function/event handler to do the same thing重构:希望单个函数/事件处理程序做同样的事情
【发布时间】:2021-12-25 10:17:57
【问题描述】:

从我的代码中可以看出,我是编程和 JS 的新手。页面上的背景颜色和文本会根据单击的目标 <li> 标记而变化,可能是函数、对象、数组或使用 eventListeners 和事件处理程序的 if 语句。

我在这里寻找灵感,以便最终了解编程的真正工作原理。

在下面查看我的代码。

let navLink1 = document.querySelector('color1');
let navLink2 = document.querySelector('color2');
let navLink3 = document.querySelector('color3');
let navLink4 = document.querySelector('color4');

let p1 = document.querySelector('para');

navLink1.addEventListener('click', function (e) {
    document.body.style.background = "color1";
    document.innerHTML(p1) = "New text!";  
});

navLink2.addEventListener('click', function (e) {
    document.body.style.background = "color2";
    document.innerHTML(p1) = "New text!";  
});

navLink3.addEventListener('click', function (e) {
    document.body.style.background = "color3";
    document.innerHTML(p1) = "New text!";
});

navLink4.addEventListener('click', function (e) {
    document.body.style.background = "color4";
    document.innerHTML(p1) = "New text!";
});
<ul class ='nav'>
   <li class ='color1'><a href=''>color1</a></li>
   <li class ='color2'><a href=''>color2</a></li>
   <li class ='color3'><a href=''>color3</a></li>
   <li class ='color4'><a href=''>color4</a></li>
</ul>

<h2>The text in the <p> tag below changes according to clicked link in the menu</h2>

<p class ='para'>This is (color)</p>
<!-- if color1 is clicked in the menu then the <body> background will be changed to color1 and the innerHTML will also be changed to color1. The background color and targeted text changes according to the menu item clicked ->

【问题讨论】:

标签: javascript dom-events javascript-objects


【解决方案1】:

该代码存在一些问题,但基本上:是的,您可以使用单个事件处理程序来处理所有四个链接。该过程称为“事件委托”——将事件的处理委托给某个祖先元素。在这种情况下,ul 是放置click 处理程序的好地方。 click 事件“冒泡”从目标元素(li)到其父元素,然后是 父元素等,因此我们可以处理对 @987654332 中任何 li 的点击@通过在ul上处理它。

见 cmets:

// Handle click on the `ul.nav`:
document.querySelector(".nav").addEventListener("click", function(event) {
    // `event.target` is the element the event was targeted at (the `li`
    // element). We can use the `closest` method to find the first element
    // starting with that one and then working through its parent, parent's
    // parent, etc., until we find one that matches the selector. The
    // selector looks for an element that has a `data-color` attribute.
    const li = event.target.closest("[data-color]");
    // If we found one and it's within the element we hooked `click` on
    // (the `ul`), we handle the click
    if (li && this.contains(li)) {
        // Get the color from the attribute
        const color = li.getAttribute("data-color");
        // Assign it to the body
        document.body.style.backgroundColor = color;
        // Show the color name in the `span`
        document.querySelector(".color").textContent = color;
    }
});
li[data-color] {
    cursor: pointer;
}
<ul class="nav">
    <!-- I've removed the classes and set a data-* attribute with the color to set -->
    <!-- I've also removed the `a` elements. Because they're links, clicking follows them -->
    <li data-color="#E0E0E0">color1</li>
    <li data-color="#D0D0D0">color2</li>
    <li data-color="#C0C0C0">color3</li>
    <li data-color="#B0B0B0">color4</li>
</ul>

<!-- Note that I've changed the opening angle bracket in the `p` tag below to its
     character reference form (&lt;) so it's not handled as a paragraph -->
<h2>The text in the &lt;p> tag below changes according to clicked link in the menu</h2>

<!-- I've added a span with a class so we can set the color name -->
<p class="para">This is <span class="color">(no color yet)</span></p>

更多

如果你想用a 元素来做这件事(所以我们可以在各种用户手势上获得默认的选项卡和“激活”,比如按下 Enter),我们可以做同样的事情使用event.preventDefault() 调用告诉浏览器不要关注ahref。这样做时,通常最好让href 向用户指示它将要做什么,这样我们就可以使用它而不是data-* 属性:

// The prefix used on `a` element `href`s:
const prefix = "#set-color-";

// Handle click on the `ul.nav`:
document.querySelector(".nav").addEventListener("click", function(event) {
    // `event.target` is the element the event was targeted at (the `li`
    // element). We can use the `closest` method to find the first element
    // starting with that one and then working through its parent, parent's
    // parent, etc., until we find one that matches the selector. The
    // selector looks for an `a` element whose `href` *starts with* the
    // text `set-color-`
    const anchor = event.target.closest(`a[href^="${prefix}"]`);
    // If we found one and it's within the element we hooked `click` on
    // (the `ul`), we handle the click
    if (anchor && this.contains(anchor)) {
        // Get the color from the `href` by grabbing the part after the
        // prefix
        const color = anchor.getAttribute("href").substring(prefix.length);
        // Assign it to the body
        document.body.style.backgroundColor = color;
        // Show the color name in the `span`
        document.querySelector(".color").textContent = color;
        // Prevent the default of following the anchor
        event.preventDefault();
    }
});
li[data-color] {
    cursor: pointer;
}
<ul class="nav">
    <!-- I've removed the classes and set a data-* attribute with the color to set -->
    <!-- I've also removed the `a` elements. Because they're links, clicking follows them -->
    <li><a href="#set-color-#E0E0E0">color1</a></li>
    <li><a href="#set-color-#D0D0D0">color2</a></li>
    <li><a href="#set-color-#C0C0C0">color3</a></li>
    <li><a href="#set-color-#B0B0B0">color4</a></li>
</ul>

<!-- Note that I've changed the opening angle bracket in the `p` tag below to its
     character reference form (&lt;) so it's not handled as a paragraph -->
<h2>The text in the &lt;p> tag below changes according to clicked link in the menu</h2>

<!-- I've added a span with a class so we can set the color name -->
<p class="para">This is <span class="color">(no color yet)</span></p>

【讨论】:

  • @yanus - 很高兴有帮助! FWIW,@ 987654326@。编码愉快!
猜你喜欢
  • 2016-07-20
  • 1970-01-01
  • 1970-01-01
  • 2016-09-06
  • 2012-09-19
  • 1970-01-01
  • 2011-06-15
  • 2013-01-18
  • 2016-03-09
相关资源
最近更新 更多