The ‘this' keyword in Javascript
Tags: javascript
Published: 2017-02-02 21:32:53

---
title: "The ‘this' keyword in Javascript"
published: true
description: "`this` is a powerful tool that helps developers easily refer to properties within specific contexts, but can get tricky when passing through different levels of scope."
cover_image: 
tags: javascript
---

The keyword `this` in Javascript can be a little slippery to wrap your had around at first.

> TL;DR When you refer to `this` in the global context, it refers to the global variable (which is `Window` in browsers). When you create a `new` object with `this` refers to the object's scope.

### What Does this Do?

When you call this on the root of a document, it refers to the document's root object, in the case of our browser `this` refers to `Window`.

![this keyword](https://cdn-images-1.medium.com/max/800/1*kzOiTYdPaV7pWhw5Noiy0Q.png)

So if we create a function and add a variable to the global scope then we can call it using `this`

![function example](https://cdn-images-1.medium.com/max/800/1*6LfsfamPpAvst0bC-EI8-Q.png)

At first `hello()` returns undefined because `saySomething` is undefined on `window`, but once `saySomething` is defined we get a proper greeting.

So what do we do if we want this to refer to something other than the global scope?

Our first approach is to use `call` or `apply` to specify the scope.

![code example](https://cdn-images-1.medium.com/max/800/1*0WowWN0ItvawtyVF2dq5ww.png)

### This in Objects

Now let's try this in a different way. Let's see what happens when we use `this` in a function that's been set as the property of an object. In this case, `this` will refer to the local scope of the `adventure` object.

![code example](https://cdn-images-1.medium.com/max/800/1*YdOlUzhOgCHzydwzyPX8tg.png)

In the above case we created the example in an object literal, but what happens when we wrap the example in a constructor function? When we instantiate it with the `new` keyword, an empty object is created and `this` will refer to that context.

![code example](https://cdn-images-1.medium.com/max/800/1*ZMbSP6XlHFQiX8yiXeSAGQ.png)

You can instantiate multiple versions of our Adventure class and this will refer to the local scope of each instance.

![code example](https://cdn-images-1.medium.com/max/800/1*MgD039CPKwYPVLoBneJLDw.png)

### Getting Tricky with 'this'

It's been simple enough to follow the context of ‘this' up to this point, but here's where it can start to get tricky. Take the following example:

```javascript
function Adventure() {
  console.log("Your this is: ", this)
  this.hasAdventure = false
  this.waterslide = function(numGoSlide) {
    if(numGoSlide > 0) {
    this.hasAdventure = true
    celebrate()
    }
  }
}
function celebrate() { 
  console.log("Your this is: ", this)
  if(this.hasAdventure) {
    alert("Yay, you've been on a soggy and thrilling adventure!")
  }
}
```


You might assume that we'd get the alert here, but when run we don't get much of anything. The reason is that `celebrate()` was defined on the global scope and so its `this` refers to the global scope. We can see that when we run this in the console, we're referring to the global scope, global scope doesn't have the attribute `hasAdventure`, so we don't get the alert.

![code example](https://cdn-images-1.medium.com/max/800/1*AGB6eFhaoX3wPrcmbx7iSw.png)

To fix this conundrum, we can pass `Adventure`'s local `this` into `celebrate` and modify `celebrate` to take an argument. When we update `celebrate` to take an argument you can't use the reserved word `this`, so pick another variable to hold that place.

```javascript
function Adventure() {
  console.log("Your this is: ", this)
  this.hasAdventure = false
  this.waterslide = function(numGoSlide) {
    if(numGoSlide > 0) {
    this.hasAdventure = true
    celebrate(this)
    }
  }
}
function celebrate(you) { 
  if(you.hasAdventure) {
    alert("Yay, you've been on a soggy and thrilling adventure!")
  }
}
```

Now when we call the function we get the alert!

![yay](https://cdn-images-1.medium.com/max/800/1*RfmCy7eQXtTOCzemfUCotg.png)

In conclusion, this is a powerful tool that helps developers easily refer to properties within specific contexts, but can get tricky when passing through different levels of scope.

Good Luck & Godspeed.