0

今天我将我的一些javascript代码迁移到coffeescript中并陷入了一些非常愚蠢的事情,但即使我不知道如何让它工作。

我想在触发点击事件时更新全局变量的值,请查看下面的代码以了解我的猜测之一

这是代码

@activeObject = null

# Some other code

$ ->
  $('#header').click ->
    if !headerSelected  
      showMenu '#header-menu', event
    else
      @activeObject = "#header"
      showMenu '#menu-style-header', event

不幸的是,即使触发了点击事件,变量也没有得到更新。

我想出了一个解决方法。我创建了一个函数来设置变量的值并调用它而不是赋值,这一次它起作用了。

我只是想知道为什么我不能以另一种方式做到这一点。对我来说,这是一个简单的操作,为此定义一个新函数似乎很愚蠢。

4

2 回答 2

2

我认为混淆是关于使用的@,这基本上只是一个捷径。如果您编译您的代码并查看它生成的 CoffeeScript 编译器,那么混淆就会变得清晰

this.activeObject = null;

$(function() {
  return $('#header').click(function() {
    if (!headerSelected) {
      return showMenu('#header-menu', event);
    } else {
      this.activeObject = "#header";
      return showMenu('#menu-style-header', event);
    }
  });
});

如果 activeObject 是全局的,你应该引用它

window.activeObject = null

window.activeObject = "#header";

在这段代码的两次出现中,导致有人可能会在第二次出现时试图在没有窗口的情况下使用它,但这会导致一个新的局部变量被隐式定义。

通常从 CoffeeScript 开始时, 在选项卡上的http://coffeescript.org/中尝试这样的小片段很有用Try Now

于 2012-08-26T20:36:27.020 回答
2

您的问题是单击处理程序内部的@(AKA this) 与外部不同,因此:

@activeObject = null

和这个:

@activeObject = "#header"

指的是两个不同activeObject的s。您应该能够将所有内容绑定=>到正确的位置this

$ =>
  $('#header').click =>
    #...

或者更好(恕我直言),只需window.activeObject在两个地方直接引用,这样每个人都可以清楚地看到您指的是全局变量:

window.activeObject = null
$ ->
  $('#header').click ->
    if !headerSelected  
      showMenu '#header-menu', event
    else
      window.activeObject = "#header"
      showMenu '#menu-style-header', event

或者,您可以完全停止使用全局变量,而改用数据属性:

$ ->
  $('#header').data 'activeObject', null
  $('#header').click ->
    if !headerSelected  
      showMenu '#header-menu', event
    else
      $(@).data 'activeObject', '#header'
      showMenu '#menu-style-header', event
于 2012-08-26T08:11:04.280 回答