Skip to main content

Command Palette

Search for a command to run...

Understanding Object-Oriented Programming in JavaScript

Updated
5 min readView as Markdown

You use a smartphone every day. You know that every contact in your phone has a name, a number, maybe a photo. Each contact looks the same structurally but they all have different data.

That right there? That's Object-Oriented Programming. You've been living it. Now let's actually understand it

What Even IS Object-Oriented Programming?

OOP (Object-Oriented Programming) is just a way of organizing your code so it's clean, reusable, and actually makes sense when you come back to it 3 months later at 2am panicking.

Instead of writing the same code over and over, you create a template and then use that template to stamp out as many copies as you need.

What is a Class in JavaScript?

A class is like a factory blueprint. It defines:

  • What properties (data) an object will have

  • What actions (methods) the object can perform

The Constructor

When you create a new object from a class, JavaScript automatically runs a special method called constructor

Creating Objects From a Class

Now let's actually build some cars from that blueprint using the new keyword:

class Car {
  constructor(color, speed) {
    this.color = color;
    this.speed = speed;
  }
}

// Creating objects (instances)
const myCar  = new Car("red",   120);
const hisCar = new Car("blue",  180);
const herCar = new Car("black", 200);

console.log(myCar.color);   // "red"
console.log(hisCar.speed);  // 180
console.log(herCar.color);  // "black"
```

Each time you write `new Car(...)`, JavaScript:
1. Creates a fresh, empty object
2. Runs the `constructor` with whatever values you passed
3. Hands you back a fully set-up object
```
new Car("red", 120)
        │
        ▼
  constructor runs
  ┌─────────────────┐
  │ this.color = "red"  │
  │ this.speed = 120    │
  └─────────────────┘
        │
        ▼
  Returns → myCar object ✅

Three cars. Zero repeated code. That's reusability doing its thing.

Methods — Giving Your Objects Superpowers

Properties store data. Methods are actions the object can perform. You define them right inside the class:

class Car {
  constructor(color, speed) {
    this.color = color;
    this.speed = speed;
  }

  // METHOD: an action the car can perform
  drive() {
    console.log(`The \({this.color} car is driving at \){this.speed} km/h!`);
  }

  honk() {
    console.log("Beep beep! 📯");
  }
}

const myCar = new Car("red", 120);
myCar.drive();  // "The red car is driving at 120 km/h!"
myCar.honk();   // "Beep beep! 📯"

const hisCar = new Car("blue", 180);
hisCar.drive(); // "The blue car is driving at 180 km/h!"

Notice how myCar.drive() and hisCar.drive() print different things even though they use the same method. That's because this.color refers to each object's own color.

Encapsulation

Encapsulation sounds fancy. It just means: keep related stuff together, and hide what doesn't need to be public.

Imagine your phone. You press the volume button you don't need to know how the speaker firmware works internally. The complexity is hidden. You just get a simple interface.

In code, encapsulation means bundling your data (properties) and behavior (methods) inside the class, so the outside world only sees what it needs to:

class BankAccount {
  constructor(owner, balance) {
    this.owner = owner;
    this._balance = balance; // _ means "treat this as private, don't touch directly"
  }

  deposit(amount) {
    this._balance += amount;
    console.log(`Deposited $${amount}. New balance: $${this._balance}`);
  }

  getBalance() {
    return this._balance; // controlled access — you can see it, but through me
  }
}

const myAccount = new BankAccount("Alex", 1000);
myAccount.deposit(500);          // Deposited \(500. New balance: \)1500
console.log(myAccount.getBalance()); // 1500

// You CAN'T (shouldn't) do this:
// myAccount._balance = 999999; ← bad practice, bypasses all logic

Putting It All Together — The Person Class

Let's build one clean example that shows everything:

class Person {
  constructor(name, age) {
    this.name = name;
    this.age  = age;
  }

  greet() {
    console.log(`Hey! I'm \({this.name} and I'm \){this.age} years old.`);
  }

  haveBirthday() {
    this.age++;
    console.log(`Happy Birthday \({this.name}! You're now \){this.age}! 🎂`);
  }
}

const alice = new Person("Alice", 22);
const bob   = new Person("Bob",   19);

alice.greet();         // Hey! I'm Alice and I'm 22 years old.
bob.greet();           // Hey! I'm Bob and I'm 19 years old.

alice.haveBirthday();  // Happy Birthday Alice! You're now 23! 🎂
alice.greet();         // Hey! I'm Alice and I'm 23 years old.

// bob is completely unaffected ✅
bob.greet();           // Hey! I'm Bob and I'm 19 years old.

One class → unlimited unique objects. Write once, use forever.

Assignment

Build a Student class from scratch:

class Student {
  constructor(name, age) {
    this.name = name;
    this.age  = age;
  }

  printDetails() {
    console.log(`Student: \({this.name}, Age: \){this.age}`);
  }
}

// Now create 3 different students
const s1 = new Student("Priya",  20);
const s2 = new Student("Jordan", 22);
const s3 = new Student("Mei",    19);

s1.printDetails(); // Student: Priya, Age: 20
s2.printDetails(); // Student: Jordan, Age: 22
s3.printDetails(); // Student: Mei, Age: 19

Once you've got that working, try adding:

  • A grade property (like "A", "B", "C")

  • A study() method that prints "${this.name} is studying hard! 📚"

  • A pass() method that checks if grade is "A" or "B" and prints whether they passed

More from this blog