【问题标题】:Toggle a button using JavaScript in an ASP.NET Core MVC app在 ASP.NET Core MVC 应用程序中使用 JavaScript 切换按钮
【发布时间】:2021-04-26 21:56:33
【问题描述】:

我正在尝试使用 JavaScript 在单击时将按钮从标签“连接”切换到标签“忘记”,然后在再次单击时将按钮切换回“连接”。

我的代码没有像我期望的那样切换按钮。该代码位于 ASP.NET Core MVC 应用程序的视图模板 (.cshtml) 文件中。我也愿意接受使用 JQuery 来实现我的目标的答案。

HTML:

<button type="button" class="buttonOne">Connect</button>

代码:

const $ = document.querySelector.bind(document);
$(".buttonOne").addEventListener("click", (e) => {
  let clicked = false;
  if (clicked) {
    e.target.innerText = "Forget";
  } else {
    e.target.innerText = "Connect";
  }
  clicked = !clicked;
});

$(".buttonTwo").addEventListener("click", (e) => {
  let clicked = false;
  if (clicked) {
    e.target.innerText = "Forget";
  } else {
    e.target.innerText = "Connect";
  }
  clicked = !clicked;
});

$(".buttonThree").addEventListener("click", (e) => {
  let clicked = false;
  if (clicked) {
    e.target.innerText = "Forget";
  } else {
    e.target.innerText = "Connect";
  }
  clicked = !clicked;
});

更新

此代码将按钮从“连接”更改为“忘记”,但由于某种原因您需要单击该按钮两次,如果再次单击该按钮,则按钮状态不会返回“连接”。还需要“onclick” HTML 属性,不知道为什么。

<button type="button" class="buttonOne" onclick="myFunction2();">Connect</button>

<script>

function myFunction2(){
    const $ = document.querySelector.bind(document);

        $(".buttonOne").addEventListener("click", (e) => {
            let clicked = false;
            if (clicked)
            {
                e.target.innerText = "Connect";
            } else {
                e.target.innerText = "Forget";

            }
            
            clicked = !clicked;
        });

        $(".buttonTwo").addEventListener("click", (e) =>
        {
            let clicked = false;
            if (clicked)
            {
                e.target.innerText = "Forget";
            } else {
                e.target.innerText = "Connect";
            }

            clicked = !clicked;
        });
        
        $(".buttonThree").addEventListener("click", (e) => {
            let clicked = false;
            if (clicked)
            {
                e.target.innerText = "Forget";
            }else {
                e.target.innerText = "Connect";
            }

            clicked = !clicked;
    });
    }
</script>

更新 2

感谢@John Ronald 的评论(@mplungjan 的回答)我编写了以下有效的代码:

const $ = document.querySelector.bind(document);

let clickedOne = false;
let clickedTwo = false;
let clickedThree = false;
$(".buttonOne").addEventListener("click", (e) => {
  // When method executes it means the button has been clicked      
  if (clickedOne) {
    // When unclicked change button label to "Connect"
    e.target.innerText = "Connect";
  } else {
    // When first clicked change button label to "Forget"
    e.target.innerText = "Forget";

  }

  clickedOne = !clickedOne;
});

$(".buttonTwo").addEventListener("click", (e) => {
  if (clickedTwo) {
    e.target.innerText = "Connect";
  } else {
    e.target.innerText = "Forget";
  }

  clickedTwo = !clickedTwo;
});

$(".buttonThree").addEventListener("click", (e) => {
  if (clickedThree) {
    e.target.innerText = "Connect";
  } else {
    e.target.innerText = "Forget";
  }

  clickedThree = !clickedThree;
});
<button class="buttonOne">Connect</button>
<button class="buttonTwo">Connect</button>
<button class="buttonThree">Connect</button>

更新 3

我的 HTML 文档中的按钮包含一个带有空 href 属性值 (&lt;a href=""&gt;) 的锚元素,这导致按钮在单击时闪烁标签“忘记”,而不是按钮切换到“忘记”直到它再次被点击。这就是为什么在 Update 2 中使用 JavaScript 代码时,单击时按钮没有切换。

【问题讨论】:

  • $ 绑定为 jQuery 非常令人困惑。请点击编辑,然后点击 [&lt;&gt;] 并提供相关 RENDERED HTML、相关 CSS 和任何框架的 minimal reproducible example。您的预期结果并不明显let clicked = false; 不是很有用
  • 如果在onclick方法中设置了“clicked=false”,则永远为false。
  • @JohnRonald 怎么样? clicked = !clicked 翻转布尔值。
  • 是的,你在方法结束时翻转它,这很有用。每次调用 onclick 方法时,它都会被重写为 false。而且它只是局部变量。您需要将其设置为全局变量。

标签: javascript c# asp.net-core asp.net-core-mvc


【解决方案1】:

您在函数开头的let clicked = false; 每次都会阻止您的尝试。

如果您在函数开始时将其设置为 false,则在您将其翻转为 true 之前它是 false。下次点击,在测试前设置为false。

我建议你委托。把class改成ID,把class改成button

然后从容器中委托

测试是按钮上的文本 - 现在不需要点击 var 如果您要使用不同的语言,请在按钮上使用数据属性而不是一些全局布尔值

document.getElementById("buttonContainer").addEventListener("click", function(e) {
  const tgt = e.target;
  if (tgt.classList.contains("button")) {
    const text = tgt.textContent;
    console.log("Clicked",tgt.id,"to",text)
    tgt.textContent = text === "Forget" ? "Connect" : "Forget"
  }
});
<div id="buttonContainer">
  <button id="buttonOne" class="button">Connect</button>
  <button id="buttonTwo" class="button">Connect</button>
  <button id="buttonThree" class="button">Connect</button>
</div>

【讨论】:

  • 你能解释一下为什么let clicked = false; 每次都阻止我的尝试吗?也许我错过了什么。
  • @BlackPanther 在我的脚本中,我有一个事件处理程序,没有全局变量,也不需要特殊变量来保持“已单击” - 只需在单击按钮时测试每个按钮的状态
  • 你的回答很简洁,还是可以理解和清晰的。
【解决方案2】:

您可以为每个按钮声明 3 个全局变量。它应该看起来像这样:

let clicked1 = false;
let clicked2 = false;
let clicked3 = false;

    const $ = document.querySelector.bind(document);
    $(".buttonOne").addEventListener("click", (e) => {
      
      if (clicked1) {
        e.target.innerText = "Forget";
      } else {
        e.target.innerText = "Connect";
      }
      clicked1 = !clicked1;
    });

    $(".buttonTwo").addEventListener("click", (e) => {
     
      if (clicked2) {
        e.target.innerText = "Forget";
      } else {
        e.target.innerText = "Connect";
      }
      clicked2 = !clicked2;
    });

    $(".buttonThree").addEventListener("click", (e) => {
     
      if (clicked3) {
        e.target.innerText = "Forget";
      } else {
        e.target.innerText = "Connect";
      }
      clicked3 = !clicked3;
    });

【讨论】:

  • 不是我的反对意见,但是如果不需要全局变量,没有人会喜欢它们
  • @freedomn-m 他声明变量的地方有什么问题?
  • 代码效率低下,污染全局范围。正如您在我的回答中看到的,最简单的测试只是测试按钮属性或文本。同样在我的回答中,您会看到委派如何使用 ONE 脚本处理所有三个按钮。它被称为 DRY(不要重复自己)
  • @BlackPanther 这不是“错误的”。当您花时间回答问题时获得反对票可能会令人沮丧,因此我想就匿名(非评论者)可能反对票的原因提供一个建议
  • @freedomn-m 感谢您的建议。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-01-04
  • 2012-09-23
  • 2017-07-14
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多