Components are the atoms of the Angular world. Mastering them is the key to creating fast, interactive, and modular user interfaces.
1Logic and View Separation
One of Angular's greatest strengths is the clear separation between logic (TypeScript) and presentation (HTML/CSS). By keeping these concerns separate, your code remains clean and testable. The @Component decorator acts as the bridge, telling Angular exactly how to wire these files together into a single, cohesive unit.
2Reusability and Scaling
Because components are self-contained, they can be reused across your entire application. A 'User Profile' component built for one page can easily be dropped into another, with its logic and styles coming along for the ride. This component-based approach is what allows small teams to build and maintain massive, enterprise-grade web applications.
3Step-by-Step Breakdown
Welcome to the heart of Angular. Components are the fundamental building blocks of your UI. Every Angular app is just a tree of components.
A component is a TypeScript class decorated with @Component. This decorator tells Angular how to handle the class and which files belong to it.
The 'selector' defines the custom HTML tag you use to display the component. In this case, we'd use <app-user></app-user> in our templates.
Checkpoint: Which property in the @Component decorator defines the custom HTML tag name?
- βtag
- βselector
- βtemplate
Components hold state in their properties. These variables are immediately available to the HTML template through interpolation using double curly braces.
When a property changes in the class, Angular's change detection engine automatically updates the view. No manual DOM manipulation is required!
Checkpoint: What syntax is used for string interpolation in an Angular template?
- βSingle braces { }
- βDouble braces {{ }}
- βSquare brackets [ ]
Components also have a Lifecycle. You can hook into specific moments, like when a component is created, using 'ngOnInit'.
Excellent! You've mastered the core concepts of Angular components. Next, we'll look at how to build complex templates with directives.
Level Up π
Advanced cheat sheets, SEO tricks, and interview prep for this topic.
Browser Support
Fully supported.
Fully supported.
Fully supported.
Fully supported.
Accessibility (A11y)
1A Component's Template Is Ordinary HTML β It Doesn't Get Free Semantics
Wrapping markup in an `@Component` decorator changes nothing about accessibility; a template built entirely from unlabeled `<div>`s is exactly as inaccessible as raw HTML with the same structure. Semantic tags and ARIA still have to be written deliberately inside the template.
2View Encapsulation Doesn't Isolate Accessibility Semantics
Angular's default view encapsulation scopes CSS to the component, but it has no effect on the accessibility tree β a component's ARIA roles and labels are just as globally visible to assistive technology as if there were no encapsulation at all.
SEO Implications
- 1
Deeply Nested Component Trees Don't Change What Crawlers See β Rendering Strategy Does
Whether content lives in one component or is split across twelve nested child components makes no difference to a crawler; what matters is whether that content is present in the server-rendered HTML at all, which depends on whether Angular Universal or prerendering is in place.
- 2
Component-Level Lazy Loading Can Delay Meaningful Content From Appearing
If a component containing primary page content is deferred behind a lazy-loaded chunk or an async guard, that delay can push back Largest Contentful Paint β reserve lazy loading for genuinely secondary, below-the-fold, or route-gated content.
Best Practices
Keep Components Focused on a Single Responsibility
A component that both fetches data, manages complex state, and renders a large template becomes hard to test and reuse β extract data-fetching into a service and consider splitting large templates into smaller, focused child components.
Use `OnPush` Change Detection for Presentational Components
Components that only render based on `@Input()` values (and don't rely on mutation of objects in place) can safely use `ChangeDetectionStrategy.OnPush`, meaningfully reducing unnecessary change-detection cycles in large component trees.
Frequent Bugs
A child component doesn't re-render when a parent's bound object property changes.
The component uses `OnPush` change detection but the parent mutated the existing object in place rather than passing a new object reference β `OnPush` only re-checks a component when an `@Input()` reference actually changes, not when a nested property is mutated.
Styles defined in one component's stylesheet unexpectedly leak into or get overridden by another component.
This typically points to a change in `ViewEncapsulation` (e.g., set to `None`) or overly broad global styles bleeding in β verify the component's encapsulation mode and check for global stylesheets asserting higher-specificity rules.
Real-World Examples
Focused, OnPush Presentational Component
A reusable product card component receives all its data via `@Input()`, uses `OnPush` change detection for performance, and contains no data-fetching logic of its own, keeping it easy to test and reuse across the app.
@Component({
selector: 'app-product-card',
templateUrl: './product-card.component.html',
changeDetection: ChangeDetectionStrategy.OnPush
})
export class ProductCardComponent {
@Input() product!: Product;
}