@@ -227,24 +227,32 @@ export class CustomDataSource<T> implements SelectDataSource<T> {
227227
228228The ` MerSelect ` supports typeahead functionality, allowing you to search for options as you type. The library provides a generic ` TypeaheadDataSource ` implementation that handles common typeahead requirements including search request cancellation, loading states, and result management.
229229
230+ ### TypeaheadSearchFn Type
231+
232+ A simple function type that can be used to perform typeahead searches:
233+
234+ ``` typescript
235+ export type TypeaheadSearchFn <T > = (query : string ) => Observable <T []>;
236+ ```
237+
230238### TypeaheadSearchService Interface
231239
232- First, implement the ` TypeaheadSearchService ` interface to define how search operations will be performed:
240+ Alternatively, you can implement the ` TypeaheadSearchService ` interface to define how search operations will be performed:
233241
234242``` typescript
235243export interface TypeaheadSearchService <T > {
236- /**
237- * Search method that takes a query string and returns an Observable of results
238- * @param query The search query string
239- * @returns Observable of search results
240- */
241- search(query : string ): Observable <T []>;
244+ /**
245+ * Search method that takes a query string and returns an Observable of results
246+ * @param query The search query string
247+ * @returns Observable of search results
248+ */
249+ search(query : string ): Observable <T []>;
242250}
243251```
244252
245253### TypeaheadDataSourceOptions Interface
246254
247- The ` TypeaheadDataSource ` now accepts a configuration options object:
255+ The ` TypeaheadDataSource ` accepts a configuration options object:
248256
249257``` typescript
250258export interface TypeaheadDataSourceOptions <T > {
@@ -273,6 +281,65 @@ The `TypeaheadDataSource` provides a robust solution for typeahead functionality
273281
274282#### Implementation
275283
284+ You can implement typeahead functionality in two ways:
285+
286+ ##### 1. Using a Simple Search Function
287+
288+ ``` typescript
289+ import { Injectable } from ' @angular/core' ;
290+ import { Observable , of } from ' rxjs' ;
291+ import { delay } from ' rxjs/operators' ;
292+ import { HttpClient } from ' @angular/common/http' ;
293+ import { TypeaheadDataSource , TypeaheadDataSourceOptions } from ' @merelis/angular/select' ;
294+
295+ // Define your data model
296+ interface User {
297+ id: number ;
298+ name: string ;
299+ email: string ;
300+ }
301+
302+ @Component ({
303+ selector: ' app-user-search' ,
304+ standalone: true ,
305+ imports: [MerSelect ],
306+ template: `
307+ <mer-select
308+ [(value)]="selectedUser"
309+ [dataSource]="userDataSource"
310+ [displayWith]="displayUserName"
311+ [placeholder]="'Search for users...'">
312+ </mer-select>
313+ `
314+ })
315+ export class UserSearchComponent implements OnDestroy {
316+ selectedUser: User | null = null ;
317+ userDataSource: TypeaheadDataSource <User >;
318+
319+ constructor (private http : HttpClient ) {
320+ // Define a search function that returns an Observable
321+ const searchFn = (query : string ): Observable <User []> => {
322+ return this .http .get <User []>(` /api/users?q=${query } ` );
323+ };
324+
325+ // Define options for the data source
326+ const options: TypeaheadDataSourceOptions <User > = {
327+ compareWith : (a , b ) => a .id === b .id
328+ };
329+
330+ // Create the data source with the search function and options
331+ this .userDataSource = new TypeaheadDataSource <User >(searchFn , options );
332+ }
333+
334+ // Display function for the select component
335+ displayUserName(user : User ): string {
336+ return user ?.name || ' ' ;
337+ }
338+ }
339+ ```
340+
341+ ##### 2. Using a TypeaheadSearchService
342+
276343``` typescript
277344import { Injectable } from ' @angular/core' ;
278345import { Observable , of } from ' rxjs' ;
@@ -295,32 +362,8 @@ export class UserSearchService implements TypeaheadSearchService<User> {
295362 search(query : string ): Observable <User []> {
296363 // Real implementation would use HttpClient
297364 return this .http .get <User []>(` /api/users?q=${query } ` );
298-
299- // Example of a mock implementation for testing:
300- /*
301- const users = [
302- { id: 1, name: 'John Smith', email: 'john@example.com' },
303- { id: 2, name: 'Mary Johnson', email: 'mary@example.com' },
304- { id: 3, name: 'Peter Williams', email: 'peter@example.com' }
305- ];
306-
307- const results = query
308- ? users.filter(user => user.name.toLowerCase().includes(query.toLowerCase()))
309- : users;
310-
311- return of(results).pipe(delay(300)); // Simulate network delay
312- */
313365 }
314366}
315- ```
316-
317- #### Usage in a Component
318-
319- ``` typescript
320- import { Component , OnDestroy } from ' @angular/core' ;
321- import { MerSelect } from ' @merelis/angular/select' ;
322- import { TypeaheadDataSource , TypeaheadDataSourceOptions } from ' @merelis/angular/select' ;
323- import { UserSearchService , User } from ' ./user-search.service' ;
324367
325368@Component ({
326369 selector: ' app-user-search' ,
@@ -331,50 +374,35 @@ import { UserSearchService, User } from './user-search.service';
331374 [(value)]="selectedUser"
332375 [dataSource]="userDataSource"
333376 [displayWith]="displayUserName"
334- [placeholder]="'Search for users...'"
335- [debounceTime]="300">
377+ [placeholder]="'Search for users...'">
336378 </mer-select>
337- <p *ngIf="selectedUser">Selected: {{selectedUser.name}}</p>
338379 `
339380})
340381export class UserSearchComponent implements OnDestroy {
341382 selectedUser: User | null = null ;
342383 userDataSource: TypeaheadDataSource <User >;
343384
344385 constructor (private userSearchService : UserSearchService ) {
345- // Define options for the data source
346- const options: TypeaheadDataSourceOptions <User > = {
347- alwaysIncludeSelected: true ,
348- compareWith : (a , b ) => a .id === b .id ,
349- suppressLoadingEvents: false
350- };
351-
352386 // Create the data source with the service and options
353387 this .userDataSource = new TypeaheadDataSource <User >(
354388 userSearchService ,
355- options
389+ {
390+ compareWith : (a , b ) => a .id === b .id
391+ }
356392 );
357393 }
358394
359- ngOnDestroy(): void {
360- // Cleanup resources
361- this .userDataSource .disconnect ();
362- }
363-
364- // Display function for the select component
365- displayUserName(user : User ): string {
366- return user ?.name || ' ' ;
367- }
395+ // Rest of the component...
368396}
369397```
370398
371399### TypeaheadDataSource API
372400
373- The ` TypeaheadDataSource ` constructor now accepts the following parameters:
401+ The ` TypeaheadDataSource ` constructor accepts the following parameters:
374402
375403| Parameter | Type | Required | Description |
376404| -----------| ------| ----------| -------------|
377- | searchService | TypeaheadSearchService<T > | Yes | The service implementing the search functionality |
405+ | searchService | TypeaheadSearchFn< T > \| TypeaheadSearchService<T > | Yes | A function or service that implements the search functionality |
378406| options | TypeaheadDataSourceOptions<T > | No | Configuration options object |
379407
380408#### TypeaheadDataSourceOptions Properties
@@ -397,11 +425,12 @@ The `TypeaheadDataSource` constructor now accepts the following parameters:
397425
398426### Benefits of Using TypeaheadDataSource
399427
400- 1 . ** Performance** : Efficiently handles rapid typing by cancelling outdated requests
401- 2 . ** User Experience** : Shows loading indicators at appropriate times
402- 3 . ** Resilience** : Provides graceful error handling
403- 4 . ** Flexibility** : Works with any data type and search implementation
404- 5 . ** Integration** : Seamlessly works with MerSelect's search capabilities
428+ 1 . ** Flexibility** : Supports two ways to implement search - through a simple function or a full service
429+ 2 . ** Performance** : Efficiently handles rapid typing by cancelling outdated requests
430+ 3 . ** User Experience** : Shows loading indicators at appropriate times
431+ 4 . ** Resilience** : Provides graceful error handling
432+ 5 . ** Adaptability** : Works with any data type and search implementation
433+ 6 . ** Integration** : Seamlessly works with MerSelect's search capabilities
405434
406435The ` TypeaheadDataSource ` implementation follows best practices for reactive programming with RxJS and works with both simple and complex typeahead scenarios.
407436
0 commit comments