简体   繁体   English

如何在闭包内部访问“ this”?

[英]How to access “this” inside a closure?

I'm very new to JavaScript and jQuery and I'm having trouble with a bit of code. 我对JavaScript和jQuery还是很陌生,但是在编写一些代码时遇到了麻烦。

HTML: HTML:

<div class="toggle" style="display: block; width: 200px; height: 200px; background-color: red;">test</div>

JavaScript: JavaScript的:

jQuery(document).ready(
    function()
    {
        jQuery(".toggle").on("click", function() {
            console.log("let the toggling begin!");

            jQuery(this).slideToggle(600, function(){ // slide up
                setTimeout(function(){ // wait 4 sec, then slide back down
                    jQuery(this).slideToggle(600)
                }, 4000);
            });
        });
    }
);

So the idea is that you click on the div, it slides up, then 4 seconds later slides back down. 因此,您的想法是单击div,然后将其向上滑动,然后在4秒钟后向下滑动。 It doesn't work. 没用

JSFIDDLE: http://jsfiddle.net/zEqN9/2/ JSFIDDLE: http : //jsfiddle.net/zEqN9/2/

However, if I change the this inside each of the closures to ".toggle" , then it does work. 但是,如果我将每个闭包内部的this更改为".toggle" ,则它确实可以工作。

JSFIDDLE: http://jsfiddle.net/YZxMb/ JSFIDDLE: http : //jsfiddle.net/YZxMb/

So clearly the issue is my use of this . 显然,问题是我this使用。

I tried passing this as a parameter into each of the two closure functions, but that gave the error Unexpected token this . 我尝试将this作为参数传递到两个闭包函数中的每个函数中,但这给了错误Unexpected token this

How can I access the this variable from the inner functions? 如何从内部函数访问this变量?

Create a reference to this in slideToggle function. 在slideToggle函数中创建this的引用。

 jQuery(document).ready(
    function()
    {
        jQuery(".toggle").on("click", function() {
            console.log("let the toggling begin!");

            jQuery(this).slideToggle(600, function(){ // slide up
                var self = this; // <-- notice this
                setTimeout(function(){ // wait 4 sec, then slide back down
                    jQuery(self).slideToggle(600)
                }, 4000);
            });
        });
    }
);

Use bind to specify a this for a function you expect to call out of context. 使用bind为您希望在上下文之外调用的函数指定一个this

var foo = {
    bar: function () {
        setTimeout(function () { // though in a setTimeout
            console.log(this);
        }.bind(this), 0); // binding to `this` here means
    }
};

foo.bar(); // invoking it still has `this` of `foo`

The reason is that for a jQuery event, the context of the function is explicitly set so that this refers to the target element - this is done for you by jQuery. 原因是,对于一个jQuery事件,函数的上下文中明确设置,使this指的是目标元素-这是由jQuery的为你做。 However, the anonymous function for setTimeout doesn't have that context set for you - it gets the default global context, so this refers to the window. 但是, setTimeout的匿名函数没有为您设置该上下文-它获取默认的全局上下文,因此this引用该窗口。

What you need to do is grab a reference to the click event's context, and then use the reference in the timeout: 您需要做的是获取对click事件上下文的引用,然后在超时中使用该引用:

jQuery(function () {
    jQuery(".toggle").on("click", function () {
        var $this = $(this);

        $this.slideToggle(600, function () { // slide up
            setTimeout(function () { // wait 4 sec, then slide back down
                $this.slideToggle(600);
            }, 4000);
        });
    });
});

However, as pointed out in a comment, this could be written as: 但是,正如评论中指出的那样,可以这样写:

jQuery(function () {
    jQuery(".toggle").click(function () {
        jQuery(this).slideToggle(600).delay(4000).slideToggle(600);
    });
});
var yourThing = jQuery(this);

yourThing.slideToggle(600, function(){ // slide up
     setTimeout(function(){ // wait 4 sec, then slide back down
          yourThing.slideToggle(600)
     }, 4000);
});

Just add this line in your code to understand why: 只需在代码中添加以下行即可了解原因:

setTimeout(function(){ // wait 4 sec, then slide back down
      console.log(jQuery(this)); //this one
      jQuery(this).slideToggle(600)
      }, 4000);

Open your console. 打开控制台。 You will see that, in the setTimeout function, $(this) refers to the window object. 您会看到,在setTimeout函数中,$(this)引用窗口对象。

You need a create a referente to this,so when runs the function associate to setTimeout you can pass this reference. 您需要为此创建一个引用,因此在运行与setTimeout关联的函数时可以传递此引用。

 jQuery(document).ready(
        function()
        {
            jQuery(".toggle").on("click", function() {
                console.log("let the toggling begin!");
                var that = this; // <--- reference to this
                jQuery(this).slideToggle(600, function(){ // slide up
                    setTimeout(function(){ // wait 4 sec, then slide back down
                        jQuery(that).slideToggle(600)
                    }, 4000);
                });
            });
        }
    );

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM