{"_id":"@acheddir/mat-datatable","_rev":"6-d38eb845e242a5acfe5346977c92a40b","name":"@acheddir/mat-datatable","dist-tags":{"latest":"1.0.5"},"versions":{"1.0.0":{"name":"@acheddir/mat-datatable","version":"1.0.0","keywords":["angular","angular21","material","datatable","table","pagination","sorting","filtering","data-grid"],"author":{"name":"Abderrahman Cheddir"},"license":"MIT","_id":"@acheddir/mat-datatable@1.0.0","maintainers":[{"name":"acheddir","email":"acheddir@outlook.fr"}],"homepage":"https://github.com/acheddir/mat-datatable#readme","bugs":{"url":"https://github.com/acheddir/mat-datatable/issues"},"dist":{"shasum":"1b5d4f1102790e4d7492baef219d4a6256d255dc","tarball":"https://registry.npmjs.org/@acheddir/mat-datatable/-/mat-datatable-1.0.0.tgz","fileCount":5,"integrity":"sha512-gzPYhJRY41ZQuhg+7n47QBm9Pva2oedQa99n2QIJRhpWXr1lFM4tRVvN0sdOn8+O8xN5TolEhknRjJZca6QQQQ==","signatures":[{"sig":"MEUCIQC6SJ1OjxUTaWVfaBfcb/KfgoJS43p8DA7MDXhoAkB9qQIgEQveHsgIiay/zf2+vQ5rSgur1EzD+0gU99AThfraT+0=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@acheddir%2fmat-datatable@1.0.0","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":158440},"module":"fesm2022/acheddir-mat-datatable.mjs","exports":{".":{"types":"./types/acheddir-mat-datatable.d.ts","default":"./fesm2022/acheddir-mat-datatable.mjs"},"./package.json":{"default":"./package.json"}},"gitHead":"0e2e1bc599b0cb4b3588b6cc483e91458e9a12ee","typings":"types/acheddir-mat-datatable.d.ts","_npmUser":{"name":"acheddir","email":"acheddir@outlook.fr"},"repository":{"url":"git+https://github.com/acheddir/mat-datatable.git","type":"git"},"_npmVersion":"10.8.2","description":"Angular 21 Material datatable with pagination, sorting, and column filtering support for both client and server-side data","directories":{},"sideEffects":false,"_nodeVersion":"20.19.6","dependencies":{"tslib":"^2.8.0"},"_hasShrinkwrap":false,"peerDependencies":{"rxjs":"^7.8.0","@angular/cdk":"^21.0.0","@angular/core":"^21.0.0","@angular/forms":"^21.0.0","@angular/common":"^21.0.0","@angular/material":"^21.0.0"},"_npmOperationalInternal":{"tmp":"tmp/mat-datatable_1.0.0_1766316370702_0.7142106040008389","host":"s3://npm-registry-packages-npm-production"}},"1.0.1":{"name":"@acheddir/mat-datatable","version":"1.0.1","keywords":["angular","angular21","material","datatable","table","pagination","sorting","filtering","data-grid"],"author":{"name":"Abderrahman Cheddir"},"license":"MIT","_id":"@acheddir/mat-datatable@1.0.1","maintainers":[{"name":"acheddir","email":"acheddir@outlook.fr"}],"homepage":"https://github.com/acheddir/mat-datatable#readme","bugs":{"url":"https://github.com/acheddir/mat-datatable/issues"},"dist":{"shasum":"d0357e59384c7e5908b0f9c16c7d1ed4f29b25c3","tarball":"https://registry.npmjs.org/@acheddir/mat-datatable/-/mat-datatable-1.0.1.tgz","fileCount":5,"integrity":"sha512-uwDPPBSTqPRKW4COBFnUgxKuDpLXbPwZc1nA2/Y3vJUuODOeEHMocPA9hmdozm6pjLoKJvEgdgs13jw6+ZrZEg==","signatures":[{"sig":"MEUCID8o1Z4yhK+vJJF8+58ERFnR7t3Bf8fYVHxS6RO+2wWWAiEAomhrBSInSTP17wswbtdB4Z7PCfx8xQzlrVjz2T2uX98=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@acheddir%2fmat-datatable@1.0.1","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":158654},"module":"fesm2022/acheddir-mat-datatable.mjs","exports":{".":{"types":"./types/acheddir-mat-datatable.d.ts","default":"./fesm2022/acheddir-mat-datatable.mjs"},"./package.json":{"default":"./package.json"}},"gitHead":"f99614067e2338609ae858f6b63b5657b8cec9b1","typings":"types/acheddir-mat-datatable.d.ts","_npmUser":{"name":"acheddir","email":"acheddir@outlook.fr"},"repository":{"url":"git+https://github.com/acheddir/mat-datatable.git","type":"git"},"_npmVersion":"10.8.2","description":"Angular 21 Material datatable with pagination, sorting, and column filtering support for both client and server-side data","directories":{},"sideEffects":false,"_nodeVersion":"20.19.6","dependencies":{"tslib":"^2.8.0"},"_hasShrinkwrap":false,"peerDependencies":{"rxjs":"^7.8.0","@angular/cdk":"^21.0.0","@angular/core":"^21.0.0","@angular/forms":"^21.0.0","@angular/common":"^21.0.0","@angular/material":"^21.0.0"},"_npmOperationalInternal":{"tmp":"tmp/mat-datatable_1.0.1_1766319195443_0.13084894998348928","host":"s3://npm-registry-packages-npm-production"}},"1.0.2":{"name":"@acheddir/mat-datatable","version":"1.0.2","keywords":["angular","angular21","material","datatable","table","pagination","sorting","filtering","data-grid"],"author":{"name":"Abderrahman Cheddir"},"license":"MIT","_id":"@acheddir/mat-datatable@1.0.2","maintainers":[{"name":"acheddir","email":"acheddir@outlook.fr"}],"homepage":"https://github.com/acheddir/mat-datatable#readme","bugs":{"url":"https://github.com/acheddir/mat-datatable/issues"},"dist":{"shasum":"611545fb54c436335c5d418189b521a29c466573","tarball":"https://registry.npmjs.org/@acheddir/mat-datatable/-/mat-datatable-1.0.2.tgz","fileCount":5,"integrity":"sha512-hefAlIfqxeoOH0/gaMGqsvR9Go6t3YaPdrbTEjNsMzroQFvr+aowUq09bMzcj5pWv1vkerxrM8TEM1lmBr/1Zw==","signatures":[{"sig":"MEUCIQDRm6/VYylwwqJPiansJHgQQidifH0u7/EBPrF+Ry0HqgIgeFQUGxY2Tz77MPKPubmKerOxgXvbg1SVFfS+Oj5+UJA=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@acheddir%2fmat-datatable@1.0.2","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":158953},"module":"fesm2022/acheddir-mat-datatable.mjs","exports":{".":{"types":"./types/acheddir-mat-datatable.d.ts","default":"./fesm2022/acheddir-mat-datatable.mjs"},"./package.json":{"default":"./package.json"}},"gitHead":"e8d91b8edde394850c5111faa9ee726ec852bcb3","typings":"types/acheddir-mat-datatable.d.ts","_npmUser":{"name":"acheddir","email":"acheddir@outlook.fr"},"repository":{"url":"git+https://github.com/acheddir/mat-datatable.git","type":"git"},"_npmVersion":"10.8.2","description":"Angular Material datatable with pagination, sorting, and column filtering support for both client and server-side data","directories":{},"sideEffects":false,"_nodeVersion":"20.19.6","dependencies":{"tslib":"^2.8.0"},"_hasShrinkwrap":false,"peerDependencies":{"rxjs":"^7.8.0","@angular/cdk":"^21.0.0","@angular/core":"^21.0.0","@angular/forms":"^21.0.0","@angular/common":"^21.0.0","@angular/material":"^21.0.0"},"_npmOperationalInternal":{"tmp":"tmp/mat-datatable_1.0.2_1766319937096_0.9858395487470499","host":"s3://npm-registry-packages-npm-production"}},"1.0.3":{"name":"@acheddir/mat-datatable","version":"1.0.3","keywords":["angular","angular21","material","datatable","table","pagination","sorting","filtering","data-grid"],"author":{"name":"Abderrahman Cheddir"},"license":"MIT","_id":"@acheddir/mat-datatable@1.0.3","maintainers":[{"name":"acheddir","email":"acheddir@outlook.fr"}],"homepage":"https://github.com/acheddir/mat-datatable#readme","bugs":{"url":"https://github.com/acheddir/mat-datatable/issues"},"dist":{"shasum":"a02d6e66e5c82b698812d094d85f52f381f9f068","tarball":"https://registry.npmjs.org/@acheddir/mat-datatable/-/mat-datatable-1.0.3.tgz","fileCount":5,"integrity":"sha512-prRDpJiFwTE/cc9UJe8haPk6e/12FnJlqphv5nXM9CUTdA/lvGN6OyBDWroGqnKTOhXjBU/S4Fo42BU+Hrj7JA==","signatures":[{"sig":"MEUCIQDTY0U91lq5Re/D1zyM7MRa9iHWoCMAi3BbfxMmZU+jNwIgU8UJqbnOkVUsTcnYD3airl5wMP+LNQ93J/48goOvL5U=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@acheddir%2fmat-datatable@1.0.3","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":158770},"module":"fesm2022/acheddir-mat-datatable.mjs","exports":{".":{"types":"./types/acheddir-mat-datatable.d.ts","default":"./fesm2022/acheddir-mat-datatable.mjs"},"./package.json":{"default":"./package.json"}},"gitHead":"27993a3a844409fd61540159117944593ef0aa75","typings":"types/acheddir-mat-datatable.d.ts","_npmUser":{"name":"acheddir","email":"acheddir@outlook.fr"},"repository":{"url":"git+https://github.com/acheddir/mat-datatable.git","type":"git"},"_npmVersion":"10.8.2","description":"Angular Material datatable with pagination, sorting, and column filtering support for both client and server-side data","directories":{},"sideEffects":false,"_nodeVersion":"20.19.6","dependencies":{"tslib":"^2.8.0"},"_hasShrinkwrap":false,"peerDependencies":{"rxjs":"^7.8.0","@angular/cdk":"^21.0.0","@angular/core":"^21.0.0","@angular/forms":"^21.0.0","@angular/common":"^21.0.0","@angular/material":"^21.0.0"},"_npmOperationalInternal":{"tmp":"tmp/mat-datatable_1.0.3_1766327005499_0.3502346188686061","host":"s3://npm-registry-packages-npm-production"}},"1.0.4":{"name":"@acheddir/mat-datatable","version":"1.0.4","keywords":["angular","angular21","material","datatable","table","pagination","sorting","filtering","data-grid"],"author":{"name":"Abderrahman Cheddir"},"license":"MIT","_id":"@acheddir/mat-datatable@1.0.4","maintainers":[{"name":"acheddir","email":"acheddir@outlook.fr"}],"homepage":"https://github.com/acheddir/mat-datatable#readme","bugs":{"url":"https://github.com/acheddir/mat-datatable/issues"},"dist":{"shasum":"a094222c2c7c27c31c591daea3040b8f720786cc","tarball":"https://registry.npmjs.org/@acheddir/mat-datatable/-/mat-datatable-1.0.4.tgz","fileCount":5,"integrity":"sha512-Q/ABPS0F2BnXQXb2ojUQ/yBUHPJU2qQrTpbPpoU9ODFY0WeYeGa+jPXlCxpK2rmxhKLfzwDG5RwW9Ms072y4qw==","signatures":[{"sig":"MEYCIQCcRruHM5NYAsONV4G8lgGkZLgRGCEMAMBBdPFWLoPlrwIhANDgeqS9294X5GotwAjtyBKXmg9NcJZA9YFbjR1q4PZb","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@acheddir%2fmat-datatable@1.0.4","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":159795},"module":"fesm2022/acheddir-mat-datatable.mjs","exports":{".":{"types":"./types/acheddir-mat-datatable.d.ts","default":"./fesm2022/acheddir-mat-datatable.mjs"},"./package.json":{"default":"./package.json"}},"gitHead":"f2531b789d9946858b1f49cce99132aea9d5d0f3","typings":"types/acheddir-mat-datatable.d.ts","_npmUser":{"name":"acheddir","email":"acheddir@outlook.fr"},"repository":{"url":"git+https://github.com/acheddir/mat-datatable.git","type":"git"},"_npmVersion":"10.8.2","description":"Angular Material datatable with pagination, sorting, and column filtering support for both client and server-side data","directories":{},"sideEffects":false,"_nodeVersion":"20.19.6","dependencies":{"tslib":"^2.8.0"},"_hasShrinkwrap":false,"peerDependencies":{"rxjs":"^7.8.0","@angular/cdk":"^21.0.0","@angular/core":"^21.0.0","@angular/forms":"^21.0.0","@angular/common":"^21.0.0","@angular/material":"^21.0.0"},"_npmOperationalInternal":{"tmp":"tmp/mat-datatable_1.0.4_1766428245285_0.025680585738844686","host":"s3://npm-registry-packages-npm-production"}},"1.0.5":{"name":"@acheddir/mat-datatable","version":"1.0.5","description":"Angular Material datatable with pagination, sorting, and column filtering support for both client and server-side data","keywords":["angular","angular21","material","datatable","table","pagination","sorting","filtering","data-grid"],"author":{"name":"Abderrahman Cheddir"},"license":"MIT","repository":{"type":"git","url":"git+https://github.com/acheddir/mat-datatable.git"},"peerDependencies":{"@angular/common":"^21.0.0","@angular/core":"^21.0.0","@angular/material":"^21.0.0","@angular/cdk":"^21.0.0","@angular/forms":"^21.0.0","rxjs":"^7.8.0"},"dependencies":{"tslib":"^2.8.0"},"sideEffects":false,"module":"fesm2022/acheddir-mat-datatable.mjs","typings":"types/acheddir-mat-datatable.d.ts","exports":{"./package.json":{"default":"./package.json"},".":{"types":"./types/acheddir-mat-datatable.d.ts","default":"./fesm2022/acheddir-mat-datatable.mjs"}},"_id":"@acheddir/mat-datatable@1.0.5","gitHead":"f43d86629989e0bc3b76ccac8cb04e0c28d260a3","bugs":{"url":"https://github.com/acheddir/mat-datatable/issues"},"homepage":"https://github.com/acheddir/mat-datatable#readme","_nodeVersion":"20.19.6","_npmVersion":"10.8.2","dist":{"integrity":"sha512-YChPYXRWT5o3YYhqEv9bN7I0GjYTpaLct1B/u6TaIVOiw2FqjDW6h9o6xJSDOcgjj4XM4/ucSYDlObZ0TYG0oQ==","shasum":"d2b0be962d785248411d960993a881622b99ace8","tarball":"https://registry.npmjs.org/@acheddir/mat-datatable/-/mat-datatable-1.0.5.tgz","fileCount":5,"unpackedSize":159808,"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@acheddir%2fmat-datatable@1.0.5","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"signatures":[{"keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U","sig":"MEYCIQC41mh8zgIr97oiborcbwhOcjZH7A+WaR2du0hFbwGNqgIhAINYdNM3tVHhifL36PTVzcKBy/F9Eb7hbynYovb7w6a9"}]},"_npmUser":{"name":"acheddir","email":"acheddir@outlook.fr"},"directories":{},"maintainers":[{"name":"acheddir","email":"acheddir@outlook.fr"}],"_npmOperationalInternal":{"host":"s3://npm-registry-packages-npm-production","tmp":"tmp/mat-datatable_1.0.5_1766509504727_0.1875638884768942"},"_hasShrinkwrap":false}},"time":{"created":"2025-12-21T11:26:10.539Z","modified":"2025-12-23T17:05:05.298Z","1.0.0":"2025-12-21T11:26:10.850Z","1.0.1":"2025-12-21T12:13:15.598Z","1.0.2":"2025-12-21T12:25:37.262Z","1.0.3":"2025-12-21T14:23:25.646Z","1.0.4":"2025-12-22T18:30:45.454Z","1.0.5":"2025-12-23T17:05:04.890Z"},"bugs":{"url":"https://github.com/acheddir/mat-datatable/issues"},"author":{"name":"Abderrahman Cheddir"},"license":"MIT","homepage":"https://github.com/acheddir/mat-datatable#readme","keywords":["angular","angular21","material","datatable","table","pagination","sorting","filtering","data-grid"],"repository":{"type":"git","url":"git+https://github.com/acheddir/mat-datatable.git"},"description":"Angular Material datatable with pagination, sorting, and column filtering support for both client and server-side data","maintainers":[{"name":"acheddir","email":"acheddir@outlook.fr"}],"readme":"# Angular Material Datatable\n\n[![CI](https://github.com/acheddir/mat-datatable/actions/workflows/ci.yml/badge.svg)](https://github.com/acheddir/mat-datatable/actions/workflows/ci.yml)\n[![npm](https://img.shields.io/npm/v/@acheddir/mat-datatable)](https://www.npmjs.com/package/@acheddir/mat-datatable)\n[![Angular](https://img.shields.io/badge/Angular-21.x-red.svg)](https://angular.io/)\n[![downloads](https://img.shields.io/npm/dm/@acheddir/mat-datatable.svg)](https://www.npmjs.com/package/@acheddir/mat-datatable)\n[![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)\n\nA production-ready Angular Material datatable library with built-in support for pagination, sorting, and column filtering. Works seamlessly with both client-side and server-side data sources.\n\n## Features\n\n- ✅ **Dual-Mode Data Handling**: Client-side and server-side data processing\n- ✅ **Column Filtering**: Per-column filters with support for text, number, date, boolean, and select inputs\n- ✅ **Sorting**: Single and multi-column sorting with Material Design UI\n- ✅ **Pagination**: Configurable page sizes with Material paginator\n- ✅ **Type-Safe**: Full TypeScript support with generics\n- ✅ **Decorator-Based**: Simple `@Column()` decorator for metadata\n- ✅ **Customizable**: Template slots for custom columns and actions\n- ✅ **Debounced Filters**: Optimized filter input with configurable debounce time\n- ✅ **Accessibility**: Built on Angular Material for WCAG compliance\n- ✅ **Production Ready**: 75+ unit tests, strict linting, and 51% code coverage\n\n## Features Roadmap\n\n- Row selection (single/multi)\n- Column reordering (drag & drop)\n- Column visibility toggle\n- Export to CSV/Excel\n- Inline editing\n- Row expansion (master-detail)\n- Virtual scrolling for large datasets\n- Saved user preferences\n- Global search across all columns\n- Advanced filters (date ranges, multi-select)\n- i18n support\n\n## Installation\n\n### From npm\n\n```bash\nnpm install @acheddir/mat-datatable\n```\n\nOr with pnpm:\n\n```bash\npnpm add @acheddir/mat-datatable\n```\n\n### Peer Dependencies\n\nEnsure you have the required peer dependencies installed:\n\n```bash\nnpm install @angular/common@^21.0.0 @angular/core@^21.0.0 \\\n            @angular/material@^21.0.0 @angular/cdk@^21.0.0 \\\n            @angular/forms@^21.0.0 rxjs@^7.8.0\n```\n\n## Quick Start\n\n### 1. Define Your Model\n\n```typescript\nimport { Column } from \"@acheddir/mat-datatable\";\n\nexport class User {\n  @Column({ display: \"ID\", propType: \"Number\", order: 1 })\n  id!: number;\n\n  @Column({ display: \"Name\", propType: \"String\", order: 2, filter: { enabled: true } })\n  name!: string;\n\n  @Column({ display: \"Email\", propType: \"String\", order: 3, filter: { enabled: true } })\n  email!: string;\n\n  @Column({ display: \"Active\", propType: \"Boolean\", order: 4, filter: { enabled: true } })\n  active!: boolean;\n\n  @Column({ display: \"Created Date\", propType: \"Date\", order: 5 })\n  createdAt!: Date;\n}\n```\n\n### 2. Configure the Datatable\n\n```typescript\nimport { Component } from \"@angular/core\";\nimport { DatatableComponent, DatatableOptions } from \"@acheddir/mat-datatable\";\n\n@Component({\n  selector: \"app-users\",\n  standalone: true,\n  imports: [DatatableComponent],\n  template: `\n    <mat-datatable [data]=\"users\" [options]=\"tableOptions\" [modelClass]=\"userModelClass\" />\n  `,\n})\nexport class UsersComponent {\n  userModelClass = User;\n  users: User[] = [\n    { id: 1, name: \"Alice\", email: \"alice@example.com\", active: true, createdAt: new Date() },\n    { id: 2, name: \"Bob\", email: \"bob@example.com\", active: false, createdAt: new Date() },\n  ];\n\n  tableOptions: DatatableOptions<User> = {\n    serverSide: false,\n    showHeader: true,\n    showRowNumber: true,\n    alternateRowColor: true,\n    sorting: {\n      defaultActive: \"name\",\n      defaultDirection: \"asc\",\n    },\n    paging: {\n      enabled: true,\n      sizeOptions: [10, 25, 50, 100],\n    },\n    filtering: {\n      enabled: true,\n    },\n  };\n}\n```\n\n## API Reference\n\n### DatatableComponent\n\nThe main datatable component that renders your data in a Material table.\n\n#### Inputs\n\n| Input        | Type                          | Description                                        |\n| ------------ | ----------------------------- | -------------------------------------------------- |\n| `data`       | `T[]`                         | Array of data to display (required)                |\n| `options`    | `DatatableOptions<T>`         | Configuration options (required)                   |\n| `modelClass` | `new () => T`                 | Model class constructor for metadata extraction    |\n| `dataLength` | `number`                      | Total number of items (for server-side pagination) |\n| `loading`    | `boolean`                     | Loading state indicator                            |\n| `templates`  | `Record<string, TemplateRef>` | Custom column templates                            |\n\n#### Outputs\n\n| Output         | Type                              | Description                                    |\n| -------------- | --------------------------------- | ---------------------------------------------- |\n| `sort`         | `EventEmitter<Sort>`              | Emitted when sort changes (server-side mode)   |\n| `changePage`   | `EventEmitter<PageEvent>`         | Emitted when page changes (server-side mode)   |\n| `filterChange` | `EventEmitter<FilterChangeEvent>` | Emitted when filter changes (server-side mode) |\n\n### DatatableOptions<T>\n\nConfiguration interface for the datatable component.\n\n```typescript\ninterface DatatableOptions<T> {\n  // Data source mode\n  serverSide: boolean;\n\n  // Display options\n  showHeader?: boolean;\n  showRowNumber?: boolean;\n  alternateRowColor?: boolean;\n\n  // Sorting configuration\n  sorting: SortingConfig;\n\n  // Pagination configuration\n  paging?: PagingConfig;\n\n  // Filtering configuration\n  filtering?: FilteringConfig;\n\n  // Custom templates\n  actionsTemplate?: TemplateRef<unknown>;\n\n  // Row click callback\n  callBack?: (row: T) => void;\n}\n```\n\n### @Column() Decorator\n\nDecorator for defining column metadata on model properties.\n\n```typescript\n@Column({\n  key?: string;              // Column key (defaults to property name)\n  display?: string;          // Display header text\n  propType: PropType;        // Data type: 'String' | 'Number' | 'Date' | 'Boolean' | 'Percent' | 'Link' | 'html'\n  order: number;             // Display order (required)\n  canSort?: boolean;         // Enable sorting (default: true)\n  hide?: boolean;            // Hide column (default: false)\n  inputLabel?: string;       // Fallback placeholder for filter input\n  filter?: FilterConfig;     // Column filter configuration\n})\n```\n\n### FilterConfig\n\nConfiguration for column filtering.\n\n```typescript\ninterface FilterConfig {\n  enabled: boolean;\n  type?: FilterType; // 'text' | 'number' | 'date' | 'boolean' | 'select'\n  placeholder?: string; // Custom placeholder text\n  options?: Array<{ label: string; value: unknown }>; // Options for select filter\n  customFilter?: (rowValue: unknown, filterValue: unknown) => boolean;\n}\n```\n\n## Usage Examples\n\n### Client-Side Mode\n\nProcess all data operations (filtering, sorting, pagination) in the browser.\n\n```typescript\n@Component({\n  selector: 'app-client-side-table',\n  template: `\n    <mat-datatable\n      [data]=\"products\"\n      [options]=\"options\"\n      [modelClass]=\"productClass\"\n    />\n  `,\n})\nexport class ClientSideTableComponent {\n  productClass = Product;\n  products: Product[] = [...]; // Your full dataset\n\n  options: DatatableOptions<Product> = {\n    serverSide: false,  // Client-side processing\n    showHeader: true,\n    sorting: {\n      defaultActive: 'name',\n      defaultDirection: 'asc',\n    },\n    paging: {\n      enabled: true,\n      sizeOptions: [10, 25, 50],\n    },\n    filtering: {\n      enabled: true,\n    },\n  };\n}\n```\n\n### Server-Side Mode\n\nDelegate data operations to your backend API.\n\n```typescript\n@Component({\n  selector: \"app-server-side-table\",\n  template: `\n    <mat-datatable\n      [data]=\"products\"\n      [dataLength]=\"totalCount\"\n      [loading]=\"loading\"\n      [options]=\"options\"\n      [modelClass]=\"productClass\"\n      (sort)=\"onSort($event)\"\n      (changePage)=\"onPageChange($event)\"\n      (filterChange)=\"onFilterChange($event)\"\n    />\n  `,\n})\nexport class ServerSideTableComponent implements OnInit {\n  productClass = Product;\n  products: Product[] = [];\n  totalCount = 0;\n  loading = false;\n\n  options: DatatableOptions<Product> = {\n    serverSide: true, // Server-side processing\n    showHeader: true,\n    sorting: {\n      defaultActive: \"name\",\n      defaultDirection: \"asc\",\n    },\n    paging: {\n      enabled: true,\n      sizeOptions: [10, 25, 50],\n    },\n    filtering: {\n      enabled: true,\n    },\n  };\n\n  constructor(private productService: ProductService) {}\n\n  ngOnInit(): void {\n    this.loadData();\n  }\n\n  onSort(sort: Sort): void {\n    this.loadData({ sort });\n  }\n\n  onPageChange(page: PageEvent): void {\n    this.loadData({ page });\n  }\n\n  onFilterChange(filter: FilterChangeEvent): void {\n    this.loadData({ filters: filter.allFilters });\n  }\n\n  private loadData(params?: {\n    sort?: Sort;\n    page?: PageEvent;\n    filters?: Record<string, unknown>;\n  }): void {\n    this.loading = true;\n    this.productService.getProducts(params).subscribe({\n      next: (result) => {\n        this.products = result.data;\n        this.totalCount = result.total;\n        this.loading = false;\n      },\n      error: () => {\n        this.loading = false;\n      },\n    });\n  }\n}\n```\n\n### Custom Column Templates\n\nAdd custom rendering for specific columns.\n\n```typescript\n@Component({\n  template: `\n    <ng-template #actionsTemplate let-row>\n      <button mat-icon-button (click)=\"edit(row)\">\n        <mat-icon>edit</mat-icon>\n      </button>\n      <button mat-icon-button (click)=\"delete(row)\">\n        <mat-icon>delete</mat-icon>\n      </button>\n    </ng-template>\n\n    <mat-datatable [data]=\"users\" [options]=\"options\" [templates]=\"{ actions: actionsTemplate }\" />\n  `,\n})\nexport class CustomTemplateComponent {\n  @ViewChild(\"actionsTemplate\") actionsTemplate!: TemplateRef<unknown>;\n\n  options: DatatableOptions<User> = {\n    serverSide: false,\n    actionsTemplate: this.actionsTemplate, // Assigned after view init\n    // ... other options\n  };\n\n  edit(user: User): void {\n    console.log(\"Edit\", user);\n  }\n\n  delete(user: User): void {\n    console.log(\"Delete\", user);\n  }\n}\n```\n\n### Filter Types\n\nThe library supports multiple filter input types, automatically inferred from `propType` or explicitly configured.\n\n```typescript\nexport class Product {\n  @Column({\n    display: \"Name\",\n    propType: \"String\",\n    order: 1,\n    filter: { enabled: true }, // Auto-detects 'text' filter\n  })\n  name!: string;\n\n  @Column({\n    display: \"Price\",\n    propType: \"Number\",\n    order: 2,\n    filter: { enabled: true }, // Auto-detects 'number' filter\n  })\n  price!: number;\n\n  @Column({\n    display: \"Release Date\",\n    propType: \"Date\",\n    order: 3,\n    filter: { enabled: true }, // Auto-detects 'date' filter\n  })\n  releaseDate!: Date;\n\n  @Column({\n    display: \"In Stock\",\n    propType: \"Boolean\",\n    order: 4,\n    filter: { enabled: true }, // Auto-detects 'boolean' filter (checkbox)\n  })\n  inStock!: boolean;\n\n  @Column({\n    display: \"Category\",\n    propType: \"String\",\n    order: 5,\n    filter: {\n      enabled: true,\n      type: \"select\", // Explicit 'select' filter\n      options: [\n        { label: \"Electronics\", value: \"electronics\" },\n        { label: \"Clothing\", value: \"clothing\" },\n        { label: \"Food\", value: \"food\" },\n      ],\n    },\n  })\n  category!: string;\n}\n```\n\n### Row Click Handling\n\nHandle row clicks with a callback function.\n\n```typescript\noptions: DatatableOptions<User> = {\n  serverSide: false,\n  callBack: (user: User) => {\n    console.log(\"Row clicked:\", user);\n    this.router.navigate([\"/users\", user.id]);\n  },\n  // ... other options\n};\n```\n\n## TypeScript Support\n\nThis library is fully typed with TypeScript generics for type-safe data handling.\n\n```typescript\n// Type-safe datatable\nconst options: DatatableOptions<User> = { /* ... */ };\n\n// Type-safe events\nonFilterChange(event: FilterChangeEvent): void {\n  const filters: Record<string, unknown> = event.allFilters;\n  const columnKey: string = event.columnKey;\n  const value: unknown = event.value;\n}\n```\n\n## Configuration Best Practices\n\n### Debounce Time for Filters\n\nAdjust debounce time for filter inputs (default: 300ms):\n\n```typescript\n@Column({\n  display: 'Search',\n  propType: 'String',\n  order: 1,\n  filter: {\n    enabled: true,\n    placeholder: 'Type to search...',\n    // Note: debounceTime is set on ColumnFilterComponent, not in decorator\n  },\n})\n```\n\n### Custom Filter Logic\n\nImplement custom filtering logic for complex scenarios:\n\n```typescript\n@Column({\n  display: 'Price Range',\n  propType: 'Number',\n  order: 1,\n  filter: {\n    enabled: true,\n    customFilter: (rowValue: unknown, filterValue: unknown) => {\n      const price = Number(rowValue);\n      const maxPrice = Number(filterValue);\n      return price <= maxPrice;\n    },\n  },\n})\nprice!: number;\n```\n\n## Browser Support\n\n- Chrome (latest)\n- Firefox (latest)\n- Safari (latest)\n- Edge (latest)\n\n## Requirements\n\n- Angular 21.x\n- Angular Material 21.x\n- TypeScript 5.7+\n- Node.js 20.x LTS or higher\n\n## Contributing\n\nContributions are welcome! Please feel free to submit a Pull Request.\n\n## License\n\nMIT License - see [LICENSE](https://github.com/acheddir/mat-datatable/blob/main/LICENSE) file for details\n\n## Changelog\n\nSee [CHANGELOG.md](https://github.com/acheddir/mat-datatable/blob/main/CHANGELOG.md) for version history and release notes.\n\n## Support\n\nFor questions or issues:\n\n- **GitHub Issues**: https://github.com/acheddir/mat-datatable/issues\n- **Email**: acheddir@outlook.fr\n\n## Demo\n\nCheck out the [demo application](https://github.com/acheddir/mat-datatable/tree/main/apps/demo) for examples of all features.\n","readmeFilename":"README.md"}