Implementing Multi-select Dropdowns with Search in Angular

Implementing multi-select dropdowns with search functionality in Angular enhances user experience by allowing users to select multiple options efficiently. This feature is especially useful in forms where users need to filter or choose from large datasets.

Understanding the Requirements

Before diving into the implementation, it’s important to understand the key features:

  • Allow multiple selections
  • Include a search input to filter options
  • Display selected items clearly

Choosing the Right Tools

Angular provides powerful tools for building custom components. For this feature, you can either build a custom multi-select dropdown or use existing libraries like Angular Material or ng-select. Here, we’ll demonstrate a custom implementation for educational purposes.

Creating the Component

Start by generating a new component:

ng generate component multi-select-dropdown

Component Template

In the component’s HTML file, add the following code:

<div class="multi-select">
  <input type="text" placeholder="Search..." [(ngModel)]="searchTerm" />
  <div class="options">
    <div *ngFor="let option of filteredOptions()" (click)="toggleSelection(option)" [class.selected]="isSelected(option)">
      <span>{{ option.label }}</span>
    </div>
  </div>
  <div class="selected-items">
    <span *ngFor="let item of selectedOptions" class="badge">{{ item.label }} ×

Component Logic

In the component's TypeScript file, define the logic:

import { Component } from '@angular/core';

interface Option {
  value: string;
  label: string;
}

@Component({
  selector: 'app-multi-select-dropdown',
  templateUrl: './multi-select-dropdown.component.html',
  styleUrls: ['./multi-select-dropdown.component.css']
})
export class MultiSelectDropdownComponent {
  options: Option[] = [
    { value: '1', label: 'Option 1' },
    { value: '2', label: 'Option 2' },
    { value: '3', label: 'Option 3' },
    { value: '4', label: 'Option 4' }
  ];
  selectedOptions: Option[] = [];
  searchTerm: string = '';

  toggleSelection(option: Option): void {
    const index = this.selectedOptions.findIndex(o => o.value === option.value);
    if (index > -1) {
      this.selectedOptions.splice(index, 1);
    } else {
      this.selectedOptions.push(option);
    }
  }

  isSelected(option: Option): boolean {
    return this.selectedOptions.some(o => o.value === option.value);
  }

  filteredOptions(): Option[] {
    return this.options.filter(option =>
      option.label.toLowerCase().includes(this.searchTerm.toLowerCase())
    );
  }
}

Styling the Component

Add some basic styles in the component's CSS file to improve appearance:

.multi-select {
  border: 1px solid #ccc;
  padding: 10px;
  width: 300px;
  position: relative;
}
.options {
  max-height: 150px;
  overflow-y: auto;
  margin-top: 10px;
}
.options div {
  padding: 5px;
  cursor: pointer;
}
.options div:hover {
  background-color: #f0f0f0;
}
.selected-items {
  margin-top: 10px;
}
.badge {
  background-color: #007bff;
  color: #fff;
  padding: 2px 8px;
  border-radius: 12px;
  margin-right: 5px;
  display: inline-block;
}
.selected {
  background-color: #e0e0e0;
}

Integrating into Your Angular App

Once your component is ready, include it in a module and use its selector in your templates:

<app-multi-select-dropdown></app-multi-select-dropdown>

This setup provides a flexible multi-select dropdown with search capabilities, enhancing forms and data filtering in Angular applications.