Highly customizable Angular table and list components with pagination, sorting and filtering support. Built with Angular 19+ and Signal-based architecture.
npm install ng-hub-ui-paginable- π Quick Start
- β¨ Inspiration
- π§© Library Family
- π¦ Description
- π― Features
- ποΈ Component Architecture
- π Installation
- βοΈ Usage
- ποΈ Table Headers Configuration
- π§ Resizable Columns
- πͺ Additional Components
- πͺ API Reference
- π Templates
- π§© Styling
- β‘ Performance Tips
- π§ Troubleshooting
- βΏ Accessibility
- π§ͺ Testing Guide
- π Migration Guide
- β FAQ
- π Custom filters
- π§ Pagination and Data Handling
- 𧬠PaginationState Interface
- π Internationalization
- π Changelog
- π€ Contribution
- β Support
- π Contributors
- π License
---
Get up and running with ng-hub-ui-paginable in less than 5 minutes:
bash
npm install ng-hub-ui-paginable
`$3
`typescript
import { TableComponent } from 'ng-hub-ui-paginable';@Component({
imports: [TableComponent],
// ...
})
`$3
`html
[headers]="[{property: 'name', title: 'Name'}, {property: 'email', title: 'Email'}]"
[data]="[{name: 'John', email: 'john@example.com'}]">
`$3
`html
[headers]="headers"
[data]="data"
[searchable]="true"
[selectable]="true"
[(searchTerm)]="searchTerm"
[(page)]="currentPage">
`π‘ That's it! You now have a fully functional data table with search, pagination, and selection.
---
β¨ Inspiration
This library arises from the need to offer highly configurable, accessible, and modern data visualization components for Angular applications, enabling integrated lists, tables, and pagination with full support for signals, reactive forms, and complete render customization.
π§© Library Family
ng-hub-uing-hub-ui-paginable is part of the ng-hub-ui ecosystem, a family of modern Angular components focused on user experience, productivity, and compatibility with Angular Signals. Each package solves a specific interface problem without overloading business logic.π¦ Description
ng-hub-ui-paginable provides three main components that work together seamlessly:- Table Component (
or ): Advanced data table with pagination, filtering, sorting, and selection
- List Component ( or ): Hierarchical list with expandable items, selection, and custom templates
- Paginator Component ( or ): Standalone pagination controls
- Additional Components: Icons, dropdowns, resizable columns, range inputs, and filter menusAll components are built as standalone Angular components with full Angular Signals support.
---
π― Features
$3
- π Full Angular Signals Support: Built with modern Angular Signals architecture using model(), input(), computed(), and effect()
- π Flexible Data Input: Compatible with separate or grouped inputs via PaginationState for seamless integration
- π Advanced Filtering: Column-specific filters with multiple types (text, dropdown, boolean, date-range, number-range)
- π Smart Sorting: Ascending/descending column sorting with visual indicators
- βοΈ Row Selection: Single or multiple row selection with batch operations and ControlValueAccessor support
- π Expandable Content: Collapsible row content for detailed views with custom templates
- π Dual Pagination: Support for both local and remote pagination strategies
- π¨ Template Customization: Extensive custom templates for headers, cells, filters, states (empty, loading, error)
- π± Responsive Design: Configurable responsive breakpoints for optimal mobile experience
- βΏ Accessibility Ready: Built-in ARIA support and keyboard navigation
- β‘ Performance Optimized: Debounced search/filtering and efficient change detection
- π Internationalization: Full i18n support with customizable translations (English/Spanish included)$3
- π§ Resizable Columns: Interactive column width adjustment
- π Sticky Columns: Pin columns to start or end during horizontal scrolling
- π Dynamic Column Visibility: Show/hide columns based on conditions, permissions, or user preferences
- π Action Buttons: Row-level actions with dropdowns and conditional visibility
- πͺ Custom Icons: Support for FontAwesome, Material Icons, and Bootstrap Icons
- π¨ Visual Variants: Multiple styling options including striped, hoverable rows, and custom themes
- π Menu Filters: Advanced filtering with dedicated filter panels
- π§© Multi-rule Menu Filters: AND/OR operators, null checks, and match modes per rule
- π Hierarchical Lists: Tree-like data structures with expandable/collapsible nodesποΈ Component Architecture
$3
`
ng-hub-ui-paginable/
βββ π¦ Core Components
β βββ TableComponent - Main data table with all features
β βββ PaginatorComponent - Standalone pagination controls
β βββ PaginableListComponent - Hierarchical list with tree structure
βββ π¨ UI Components
β βββ HubIconComponent - Multi-library icon support
β βββ DropdownComponent - Action dropdowns and menus
β βββ MenuFilterComponent - Advanced filtering interfaces
β βββ PaginableTableRangeInputComponent - Date/number range inputs
βββ π§ Utility Components
β βββ ResizableComponent - Column width adjustment
βββ π Template Directives
β βββ PaginableTableHeaderDirective - Custom headers
β βββ PaginableTableCellDirective - Custom cells
β βββ PaginableTableFilterDirective - Custom filters
β βββ PaginableTableRowDirective - Custom rows
β βββ PaginableTableExpandingRowDirective - Expandable content
β βββ PaginableTableLoadingDirective - Loading states
β βββ PaginableTableErrorDirective - Error states
β βββ PaginableTableNotFoundDirective - Empty states
βββ βοΈ Services
β βββ PaginableService - Core configuration
β βββ HubTranslationService - i18n management
β βββ PaginationService - Pagination logic
βββ π― Utilities
βββ Pipes (get, translate, ucfirst, etc.)
βββ Interfaces (type definitions)
βββ Constants (defaults, breakpoints)
βββ Utils (helper functions)
`$3
`
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β TableComponent β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€
β β Header Row (with sorting, filtering, actions) β
β β βββ PaginableTableHeaderDirective (custom headers) β
β β βββ MenuFilterComponent (advanced filters) β
β β βββ ResizableDirective (column resizing) β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€
β β Data Rows β
β β βββ PaginableTableRowDirective (custom row templates) β
β β βββ PaginableTableCellDirective (custom cell content) β
β β βββ PaginableTableExpandingRowDirective (details) β
β β βββ DropdownComponent (row actions) β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€
β β State Templates β
β β βββ PaginableTableLoadingDirective β
β β βββ PaginableTableErrorDirective β
β β βββ PaginableTableNotFoundDirective β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€
β PaginatorComponent β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
`$3
`
ββββββββββββββββββββ βββββββββββββββββββ ββββββββββββββββββββ
β User Input β β Angular Signalsβ β Component State β
β βββββββββββββββ β β βββββββββββββββββ β ββββββββββββββββ β
β β Search β βββββΆβ β searchTerm() ββββββΆβ β Filtered Dataβ β
β β Filter β β β β filters() ββ β β Sorted Data β β
β β Sort β β β β ordination() ββ β β Paginated β β
β β Select β β β β page() ββ β β Selected β β
β βββββββββββββββ β β βββββββββββββββββ β ββββββββββββββββ β
ββββββββββββββββββββ βββββββββββββββββββ ββββββββββββββββββββ
β β β
β βΌ β
β βββββββββββββββββββ β
β β Effects β β
β β βββββββββββββββββ β
β β β Debounced ββ β
β β β Updates ββ β
β β β Change ββ β
β β β Detection ββ β
β β βββββββββββββββββ β
β βββββββββββββββββββ β
β β β
βββββββββββββββββββββββββΌβββββββββββββββββββββββββ
βΌ
βββββββββββββββββββ
β Template β
β Render β
β βββββββββββββββββ
β β Table HTML ββ
β β Custom Tpls ββ
β β Pagination ββ
β βββββββββββββββββ
βββββββββββββββββββ
`$3
The library leverages Angular Signals for optimal performance and reactivity:
`typescript
// Reactive data pipeline
data = signal([]);
searchTerm = signal('');
filters = signal({});
ordination = signal();// Computed derived state
filteredData = computed(() => {
let result = this.data();
// Apply search
if (this.searchTerm()) {
result = result.filter(item =>
item.name.toLowerCase().includes(this.searchTerm().toLowerCase())
);
}
// Apply filters
const filters = this.filters();
Object.keys(filters).forEach(key => {
if (filters[key]) {
result = result.filter(item => item[key] === filters[key]);
}
});
// Apply sorting
const sort = this.ordination();
if (sort) {
result.sort((a, b) => {
const aVal = a[sort.property];
const bVal = b[sort.property];
return sort.direction === 'ASC'
? aVal > bVal ? 1 : -1
: aVal < bVal ? 1 : -1;
});
}
return result;
});
// Pagination computed
paginatedData = computed(() => {
const filtered = this.filteredData();
const page = this.page() || 1;
const perPage = this.perPage() || 20;
const start = (page - 1) * perPage;
return filtered.slice(start, start + perPage);
});
`---
π Installation
`bash
npm install ng-hub-ui-paginable
`βοΈ Usage
$3
`typescript
import { Component, signal } from '@angular/core';
import { HubUITableModule } from 'ng-hub-ui-paginable';@Component({
selector: 'app-example',
standalone: true,
imports: [HubUITableModule],
template:
})
export class ExampleComponent {
// Data and pagination
data = signal([]);
page = signal(1);
totalItems = signal(0);
loading = signal(false);
// Search and filtering
searchTerm = signal('');
filters = signal({});
// Sorting
ordination = signal();
// Column configuration
headers = signal([
{
property: 'name',
title: 'User Name',
sortable: true,
filter: { type: 'text', placeholder: 'Search by name...' }
},
{
property: 'email',
title: 'Email',
align: 'center'
},
{
property: 'status',
title: 'Status',
filter: {
type: 'dropdown',
options: ['Active', 'Inactive'],
placeholder: 'Select status...'
}
}
]);
}
`$3
`html
[items]="items()"
[selectable]="true"
[bindLabel]="'name'"
[bindChildren]="'children'"
[options]="{ collapsed: false, searchable: true }"
[clickFn]="onItemClick">
{{ data.name }}
{{ data.type }}
`$3
`html
[(page)]="currentPage"
[numberOfPages]="totalPages()">
`ποΈ Table Headers Configuration (
PaginableTableHeader)The
PaginableTableHeader interface is the core configuration for defining table columns. It provides extensive customization options for headers, sorting, filtering, actions, and visibility control.$3
`typescript
const headers: PaginableTableHeader[] = [
{
property: 'name',
title: 'User Name',
sortable: true,
align: 'start'
},
{
property: 'email',
title: 'Email Address',
align: 'center',
wrapping: 'nowrap'
},
{
property: 'status',
title: 'Status',
align: 'end'
}
];
`$3
| Property | Type | Description | Default | Example |
|----------|------|-------------|---------|---------|
|
property | string | Required. Data property to display in this column | - | 'name', 'user.email' |
| title | string \| Observable | Column header title. Can be static or reactive | property value | 'User Name', this.translate.get('user.name') |
| icon | string \| Icon | Icon to display in header | - | 'fa-user', { type: 'material', value: 'person' } |
| align | 'start' \| 'end' \| 'center' | Text alignment for column | 'start' | 'center' for numbers |
| sortable | boolean | Enable sorting for this column | false | true |
| wrapping | 'wrap' \| 'nowrap' | Text wrapping behavior | 'wrap' | 'nowrap' for IDs |
| sticky | 'start' \| 'end' | Make column sticky during scroll | - | 'end' for actions |
| buttons | Array | Action buttons in this column | - | See Action Buttons |
| filter | InputFilter \| DropdownFilter \| BooleanFilter | Filter configuration | - | See Column Filters |
| onlyButtons | boolean | Optimize layout for button-only columns | false | true for action columns |
| hidden | boolean \| Function | Control column visibility | false | See Column Visibility |$3
The
hidden property provides powerful and flexible ways to control column visibility dynamically. It supports multiple types for different use cases:#### 1. Static Boolean Visibility
Simple show/hide based on a fixed value:
`typescript
const headers: PaginableTableHeader[] = [
{
property: 'id',
title: 'ID',
hidden: false // Always visible
},
{
property: 'internal_notes',
title: 'Internal Notes',
hidden: true // Always hidden
}
];
`#### 2. Dynamic Function-Based Visibility
Control visibility based on current application state:
`typescript
export class UsersComponent {
showAdvancedColumns = signal(false);
userRole = signal<'admin' | 'user'>('user'); headers: PaginableTableHeader[] = [
{
property: 'name',
title: 'Name',
// Always visible
},
{
property: 'email',
title: 'Email',
hidden: () => !this.showAdvancedColumns() // Reactive to signal changes
},
{
property: 'salary',
title: 'Salary',
hidden: () => this.userRole() !== 'admin' // Permission-based visibility
},
{
property: 'last_login',
title: 'Last Login',
hidden: () => this.userRole() !== 'admin' && !this.showAdvancedColumns()
}
];
toggleAdvancedColumns() {
this.showAdvancedColumns.update(show => !show);
}
}
`#### 3. Asynchronous Promise-Based Visibility
For visibility that depends on API calls or async operations:
`typescript
export class UsersComponent {
constructor(
private permissionService: PermissionService,
private configService: ConfigService
) {} headers: PaginableTableHeader[] = [
{
property: 'sensitive_data',
title: 'Sensitive Information',
// Check permissions asynchronously
hidden: () => this.permissionService.checkPermission('view.sensitive.data')
.then(hasPermission => !hasPermission)
},
{
property: 'feature_column',
title: 'Feature Data',
// Check feature flags
hidden: () => this.configService.getFeatureFlag('show_feature_column')
.then(enabled => !enabled)
}
];
}
`#### 4. Reactive Observable-Based Visibility
For real-time visibility updates from streams or state management:
`typescript
export class UsersComponent {
constructor(
private store: Store,
private websocketService: WebSocketService
) {} headers: PaginableTableHeader[] = [
{
property: 'real_time_data',
title: 'Live Data',
// Visibility controlled by store state
hidden: () => this.store.select(selectShowLiveData).pipe(
map(showLive => !showLive)
)
},
{
property: 'admin_tools',
title: 'Admin Tools',
// Visibility from WebSocket updates
hidden: () => this.websocketService.userRole$.pipe(
map(role => role !== 'admin')
)
}
];
}
`#### 5. Complex Visibility Logic
Combine multiple conditions for sophisticated visibility control:
`typescript
export class UsersComponent {
screenSize = signal<'mobile' | 'tablet' | 'desktop'>('desktop');
userPreferences = signal({ showOptionalColumns: true });
isLoading = signal(false); headers: PaginableTableHeader[] = [
{
property: 'description',
title: 'Description',
hidden: () => {
// Hide on mobile or when loading
if (this.screenSize() === 'mobile' || this.isLoading()) {
return true;
}
// Hide if user disabled optional columns
return !this.userPreferences().showOptionalColumns;
}
}
];
@HostListener('window:resize')
onResize() {
const width = window.innerWidth;
if (width < 768) {
this.screenSize.set('mobile');
} else if (width < 1024) {
this.screenSize.set('tablet');
} else {
this.screenSize.set('desktop');
}
}
}
`#### Template Usage Example
`html
type="button"
class="btn btn-outline-primary"
(click)="toggleAdvancedColumns()"
>
{{ showAdvancedColumns() ? 'Hide' : 'Show' }} Advanced Columns
class="form-check-input"
type="checkbox"
[(ngModel)]="userPreferences().showOptionalColumns"
>
[headers]="headers"
[data]="users()"
[loading]="isLoading()"
>
`$3
You can also programmatically manage columns:
`typescript
export class DynamicTableComponent {
availableColumns = [
{ key: 'name', label: 'Name', required: true },
{ key: 'email', label: 'Email', required: false },
{ key: 'phone', label: 'Phone', required: false },
{ key: 'department', label: 'Department', required: false }
]; selectedColumns = signal(new Set(['name', 'email']));
headers = computed(() => {
const selected = this.selectedColumns();
return this.availableColumns
.filter(col => col.required || selected.has(col.key))
.map(col => ({
property: col.key,
title: col.label,
hidden: !selected.has(col.key) && !col.required
}));
});
toggleColumn(columnKey: string) {
this.selectedColumns.update(selected => {
const newSelected = new Set(selected);
if (newSelected.has(columnKey)) {
newSelected.delete(columnKey);
} else {
newSelected.add(columnKey);
}
return newSelected;
});
}
}
`$3
1. Performance: Use signals and computed values for reactive visibility
2. UX: Provide clear UI controls for users to manage column visibility
3. Persistence: Consider saving column preferences to localStorage or user settings
4. Accessibility: Ensure hidden columns are properly handled by screen readers
5. Mobile: Hide non-essential columns on smaller screens automatically
6. Permissions: Use the hidden property for role-based column access control
π§ Resizable Columns
The library includes a resizable component for interactive column width adjustment:
`html
Resizable Column
``typescript
// Enable resizing programmatically
import { ResizableComponent, ResizableDirective } from 'ng-hub-ui-paginable';// Use the resizable directive on table headers
@Component({
imports: [ResizableDirective]
})
`$3
- Interactive Resize: Click and drag column borders to adjust width
- Minimum Width: Prevent columns from becoming too narrow
- Persistence: Column widths can be saved and restored
- Responsive: Works with responsive table layoutsπͺ Additional Components
$3
Supports multiple icon libraries with unified interface:
`html
`$3
Used internally for action buttons and filters:
`typescript
interface PaginableTableDropdown {
title: string;
buttons: RowButton[];
fill?: string;
position?: 'start' | 'end';
color?: string;
}
`$3
Specialized component for number and date range filters:
`html
[type]="'number'"
[placeholder]="'Min - Max'"
[formControl]="rangeControl">
`$3
Menu filters are rendered automatically when a column filter uses
mode: 'menu'.
You do not need to use a dedicated component directly; the table wires the menu filter
based on the header configuration and the filters model.`typescript
import { MenuFilterOperators, StringMatchModes } from 'ng-hub-ui-paginable';const headers: PaginableTableHeader[] = [
{
property: 'name',
title: 'Name',
filter: { type: 'text', mode: 'menu' }
}
];
filters = signal({
name: {
operator: MenuFilterOperators.And,
rules: [
{ value: 'john', matchMode: StringMatchModes.Contains }
]
}
});
`Note: Null checks use
NullMatchModes.IsNull / NullMatchModes.IsNotNull and do not
require a value.$3
Configure action buttons in table columns for row-level operations:
`typescript
const headers: PaginableTableHeader[] = [
{
property: 'actions',
title: 'Actions',
onlyButtons: true,
sticky: 'end',
buttons: [
{
icon: 'fa-edit',
title: 'Edit',
color: 'primary',
handler: (row) => this.editUser(row.data),
hidden: (row) => !row.data.canEdit
},
{
title: 'More Actions',
buttons: [
{ title: 'Archive', handler: (row) => this.archiveUser(row.data) },
{ title: 'Delete', handler: (row) => this.deleteUser(row.data) }
]
}
]
}
];
`$3
Add filtering capabilities to columns with various filter types:
#### Text Filter
`typescript
{
property: 'name',
title: 'Name',
filter: {
type: 'text',
mode: 'row',
placeholder: 'Search by name...'
}
}
`#### Dropdown Filter
`typescript
{
property: 'status',
title: 'Status',
filter: {
type: 'dropdown',
mode: 'menu',
options: ['Active', 'Inactive', 'Pending'],
placeholder: 'Select status...'
}
}
`#### Boolean Filter
`typescript
{
property: 'verified',
title: 'Verified',
filter: {
type: 'boolean',
mode: 'row',
trueLabel: 'Verified',
falseLabel: 'Not Verified'
}
}
`#### Date Range Filter
`typescript
{
property: 'created_at',
title: 'Created Date',
filter: {
type: 'date-range',
mode: 'menu',
placeholder: 'Select date range...'
}
}
`#### Number Range Filter
`typescript
{
property: 'price',
title: 'Price',
filter: {
type: 'number-range',
mode: 'row',
placeholder: 'Min - Max price'
}
}
`$3
Filters can be displayed in two modes:
-
row: Filter appears directly under the column header in a dedicated filter row
- menu: Filter appears in a dropdown menu accessible via a filter button in the header$3
When a filter uses
mode: 'menu', the value stored in filters is a structured
MenuFilterValue (operator + rules). For row filters, the value is the raw input
value (string/number/boolean/date).`typescript
import { MenuFilterOperators, StringMatchModes } from 'ng-hub-ui-paginable';filters = signal({
name: {
operator: MenuFilterOperators.And,
rules: [
{ value: 'john', matchMode: StringMatchModes.Contains }
]
}
});
`$3
| Type | Description | Input Controls |
|------------------|---------------------------------------|-----------------------------------|
|
text | Text search filter | Single text input |
| number | Numeric value filter | Single number input |
| number-range | Range of numeric values | Two number inputs (min/max) |
| date | Single date filter | Date picker |
| date-range | Date range filter | Two date pickers (from/to) |
| boolean | True/false filter | Dropdown with custom labels |
| dropdown | Selection from predefined options | Dropdown/select control |πͺ API Reference
$3
#### Inputs
| Name | Type | Default | Description |
|---------------------|----------------------------------|---------|-----------------------------------------------------------------------------|
|
headers | PaginableTableHeader[] | [] | Column definitions with titles, sorting, filtering, and actions. |
| data / rows | T[] or PaginationState | [] | Table data - can be flat array or paginated object with metadata. |
| page | number | null | Current page number (1-based, model signal). |
| perPage | number | null | Number of items per page. |
| perPageOptions | number[] | [20, 50, 100] | Available options for items per page. |
| totalItems | number | null | Total number of items across all pages. |
| searchable | boolean | true | Whether to show the global search input. |
| searchTerm | string | '' | Current search term (model signal). |
| searchFn | (a: T, b: T) => boolean | null | Custom search function for filtering. |
| selectable | boolean | false | Whether rows can be selected. |
| multiple | boolean | false | Whether multiple row selection is allowed. |
| bindValue | string | null | Property used to uniquely identify selected items. |
| ordination | PaginableTableOrdination | null | Current sorting configuration (model signal). |
| filters | Record | {} | Active column filters (model signal). |
| debounce | number | 0 | Debounce time in ms for search and filter inputs. |
| loading | boolean | false | Loading state indicator (model signal). |
| paginate | boolean | true | Whether to enable pagination. |
| paginationPosition| 'top' \| 'bottom' \| 'both' | 'bottom' | Where to display pagination controls. |
| paginationInfo | boolean | true | Whether to show pagination info (e.g., "Showing 1 to 10 of 100"). |
| stickyActions | boolean | false | Whether action buttons should stick during scrolling. |
| batchActions | Array | [] | Actions available for selected rows. |
| responsive | TableBreakpoint | null | Responsive breakpoint for table layout. |
| options | PaginableTableOptions | {} | Visual configuration (cursor, hover, striped, variant). |
| clickFn | (event: TableRowEvent | null | Handler for row click events. |
| rowClass | string \| ((item: T) => string) | null | Custom CSS class for a row. Can be a fixed string or a function that returns a class based on item data. |#### Outputs & Events
The table component implements
ControlValueAccessor, enabling two-way binding with [(ngModel)] or reactive forms:`html
`Row Click Event (
TableRowEvent):
`typescript
interface TableRowEvent {
data: T; // Row data
selected: boolean; // Selection state
collapsed: boolean; // Expansion state
event: MouseEvent; // Original mouse event
}
`$3
#### Inputs
| Name | Type | Default | Description |
|------------------|----------------------------------------------|-------------|----------------------------------------------------------------|
|
items | T[] | [] | Hierarchical list data. |
| bindValue | string | null | Property for unique item identification. |
| bindLabel | string | 'label' | Property to display as item label. |
| bindChildren | string | 'children'| Property containing child items. |
| selectable | string | null | Selection mode configuration. |
| options | PaginableTableOptions | {} | Visual and behavioral options. |
| batchActions | Array | [] | Actions for selected items. |
| clickFn | (event: ListClickEvent | null | Handler for item click events. |
| rowClass | string \| ((item: T) => string) | null | Custom CSS class for a list item. Can be a fixed string or a function that returns a class based on item data. |List Click Event (
ListClickEvent):
`typescript
interface ListClickEvent {
depth: number; // Nesting level
index: number; // Item position
selected: boolean; // Selection state
collapsed: boolean; // Expansion state
value: any; // Item value (based on bindLabel)
item: T; // Full item data
mouseEvent: MouseEvent; // Original mouse event
}
`$3
#### Inputs
| Name | Type | Default | Description |
|----------------|----------|---------|--------------------------------|
|
page | number | 1 | Current page (model signal). |
| numberOfPages| number | null | Total number of pages. |---
π Templates
The
hub-ui-table component allows you to override almost any visual section using Angular templates (). This allows you to adapt the visualization of each cell, header, or special content to your specific needs.
βΉ
$3
Allows replacing the content of a specific header.
`html
Full Name
``html
Date of Birth
`$3
Overrides the visualization of a specific cell.
`html
{{ data.name.toUpperCase() }}
``html
= 18"> {{ data.age }} years
``html
[config]="{ type: 'material', value: data.adult ? 'check' : 'close' }"
>
`$3
Displays custom content when there is no data to show.
`html
No results found for your search.
`$3
Renders content while
loading is true.`html
Loading data, please wait...
`$3
Displayed if there is an error template configured and it is manually triggered from the component.
`html
An unexpected error has occurred. Try reloading the table.
`$3
Allows you to completely redefine the structure of a row. Useful when the table is not used as a
| {{ item.name }} | {{ item.lastname }} | {{ item.age }} years | Name |
|---|