← Back to Chapters

Introduction to Signals

⚡Introduction to Signals

? Quick Overview

Signals are a new reactivity model introduced in Angular 16+ to handle state changes in a simpler and more efficient way.

They offer a reactive way to manage and share data across components without relying heavily on RxJS or manual ChangeDetectionStrategy configuration.

Think of a signal as a reactive variable — when its value changes, any place that uses it is automatically updated.

? Key Concepts

  • Signal: A reactive value that can be read and updated.
  • Getter style: You read a signal by calling it like a function, e.g. count().
  • Automatic UI updates: Any template or computed value using a signal is updated when the signal changes.
  • Local state: Signals are great for component-local state such as counters, toggles, or simple form values.
  • Simpler debugging: Signals follow a clear, pull-based reactivity model — making it easier to trace where values come from.

? Syntax & Theory

You can create a signal in an Angular component using the signal() function from @angular/core.

? View Basic Signal Syntax
// Creating and using a simple signal
import { signal } from '@angular/core';

const counter = signal(0);          // initial value is 0

counter();                          // read the current value (returns 0)
counter.set(5);                     // set a new value
counter.update(value => value + 1); // update based on the previous value

In templates, you must always call the signal like a function:

  • ✅ Correct: {{ count() }}
  • ❌ Incorrect: {{ count }}

? Code Example – Counter Component

? View Component Code (TypeScript)
// counter.component.ts
import { Component, signal } from '@angular/core';

@Component({
  selector: 'app-counter',
  templateUrl: './counter.component.html'
})
export class CounterComponent {
  count = signal(0);                      // reactive state

  increment() {
    this.count.update(value => value + 1); // increase the current value
  }

  reset() {
    this.count.set(0);                     // reset to the initial value
  }
}
? View Template Code (HTML)
<!-- counter.component.html -->
<p>Current Count: {{ count() }}</p>
<button (click)="increment()">Increment</button>
<button (click)="reset()">Reset</button>

? Live Output & Explanation

The count signal holds the current value of the counter. Whenever increment() or reset() is called, the signal’s value changes and Angular automatically re-renders any bindings that use count().

?️ Simulated Output

Initial state: Current Count: 0

After clicking "Increment" 3 times: Current Count: 3

After clicking "Reset": Current Count: 0

This happens without you manually triggering change detection — the signal triggers it automatically for all dependents.

✅ Tips & Best Practices

  • Use signal() for local component state that changes frequently (counters, toggles, small forms).
  • Always remember to call the signal in templates: {{ mySignal() }}.
  • Import signal from @angular/core before using it.
  • Use update() when the new value depends on the previous one (e.g., counters).
  • Prefer signals for simple state before switching to more complex patterns with observables.

? Try It Yourself

  • Create a dark mode signal (e.g., isDark = signal(false)) and toggle it with a button in the template.
  • Build a simple shopping cart counter using a signal that tracks the number of items.
  • Use multiple signals in a single component (e.g., username, isLoggedIn) and display them in the template.
  • Experiment with update() vs set() and observe how your UI reacts.