upp-tab-bar
A tab bar navigation component composed of upp-tab-bar (the container) and upp-tab-button (individual tabs). Each tab button displays an icon and a label, and the bar manages which tab is currently selected.
When to Use
Use upp-tab-bar for bottom or section navigation where the user switches between a fixed set of views. Each tab is defined declaratively with a name, label, and icon. The component handles selection state internally and communicates changes via the Selected output.
In mobile view mode (body.mobile), tabs share the bar equally and long labels ellipsize so five or six tabs stay visible. In desktop, each tab keeps a 70 px minimum width. Layout follows application view mode, not window width.
Demo
Source Code
- HTML
- TypeScript
- SCSS
<div class="demo-scroll-container">
<upp-scrollable [scrollbar]="'y'">
<div class="demo-content">
<h2>upp-tab-bar</h2>
<p class="demo-description">POS navigation — a bottom tab bar for switching between point-of-sale sections.</p>
<!-- Primary POS tabs -->
<div class="demo-section">
<h3>Main POS Navigation</h3>
<div class="tab-content-area">
<ion-icon name="reader-outline" class="tab-content-icon"></ion-icon>
<p class="tab-content-text">{{ tabContent[selectedTab] }}</p>
</div>
<upp-tab-bar [selected]="selectedTab" (Selected)="onTabSelected($event)">
<upp-tab-button tabname="catalog" tablabel="Catalog" tabicon="grid-outline"></upp-tab-button>
<upp-tab-button tabname="cart" tablabel="Cart" tabicon="cart-outline"></upp-tab-button>
<upp-tab-button tabname="tickets" tablabel="Tickets" tabicon="receipt-outline"></upp-tab-button>
<upp-tab-button tabname="settings" tablabel="Settings" tabicon="settings-outline"></upp-tab-button>
</upp-tab-bar>
<p class="demo-label">Selected: <strong>{{ selectedTab }}</strong></p>
</div>
<!-- Secondary tabs (different icons) -->
<div class="demo-section">
<h3>Restaurant Mode (3 tabs)</h3>
<div class="tab-content-area">
<ion-icon name="reader-outline" class="tab-content-icon"></ion-icon>
<p class="tab-content-text">{{ tabContent2[selectedTab2] }}</p>
</div>
<upp-tab-bar [selected]="selectedTab2" (Selected)="onTab2Selected($event)">
<upp-tab-button tabname="tables" tablabel="Tables" tabicon="apps-outline"></upp-tab-button>
<upp-tab-button tabname="orders" tablabel="Orders" tabicon="list-outline"></upp-tab-button>
<upp-tab-button tabname="stats" tablabel="Stats" tabicon="bar-chart-outline"></upp-tab-button>
</upp-tab-bar>
<p class="demo-label">Selected: <strong>{{ selectedTab2 }}</strong></p>
</div>
</div>
</upp-scrollable>
</div>
import { Component } from '@angular/core';
import { ChangeDetectionStrategy, ChangeDetectorRef } from '@angular/core';
interface TabContent {
[key: string]: string;
}
@Component({
selector: 'demo-upp-tab-bar',
templateUrl: './demo-upp-tab-bar.html',
styleUrls: ['../demo-common.scss', './demo-upp-tab-bar.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
})
export class DemoUppTabBarComponent {
selectedTab = 'catalog';
selectedTab2 = 'tables';
tabContent: TabContent = {
catalog: 'Browse your product catalog — categories, items, prices, and stock levels.',
cart: 'Current order — 3 items totaling €12.50. Ready to checkout.',
tickets: 'Recent tickets — view, reprint, or void past transactions.',
settings: 'Configure tax rates, printers, payment methods, and staff permissions.',
};
tabContent2: TabContent = {
tables: 'Manage table layout and active orders per table.',
orders: 'Pending and completed orders for the current shift.',
stats: 'Daily sales summary, top products, and revenue breakdown.',
};
constructor(private change: ChangeDetectorRef) {
}
onTabSelected(tab: string) {
this.selectedTab = tab;
this.change.markForCheck();
}
onTab2Selected(tab: string) {
this.selectedTab2 = tab;
this.change.markForCheck();
}
}
:host {
display: block;
height: 100vh;
}
.tab-content-area {
display: flex;
align-items: flex-start;
gap: 12px;
padding: 16px;
margin-bottom: 12px;
min-height: 64px;
background: var(--ion-color-light, #f4f5f8);
border-radius: 8px;
}
.tab-content-icon {
font-size: 22px;
color: var(--ion-color-primary, #3880ff);
flex-shrink: 0;
margin-top: 2px;
}
.tab-content-text {
margin: 0;
font-size: 14px;
color: var(--ion-color-dark, #333);
line-height: 1.5;
}
API Reference
UppTabBarComponent (upp-tab-bar)
The container component that manages tab selection state.
Inputs
| Property | Type | Default | Description |
|---|---|---|---|
selected | string | null | null | The tabname of the currently selected tab. |
Outputs
| Event | Payload | Description |
|---|---|---|
Selected | string | Emitted when a tab is selected. The payload is the tabname of the selected tab. |
Content Projection
| Slot | Component | Description |
|---|---|---|
| Tabs | upp-tab-button | One or more tab buttons to render inside the bar. |
UppTabButtonComponent (upp-tab-button)
An individual tab button rendered inside upp-tab-bar. It displays an icon and a label, and highlights itself when its tabname matches the parent bar's selected value.
Inputs
| Property | Type | Default | Description |
|---|---|---|---|
tabname | string | null | null | Unique identifier for this tab. Used to match against the bar's selected property. |
tablabel | string | null | null | The label text displayed below the icon. |
tabicon | string | null | null | The Ionicon name for the tab icon (e.g. home-outline). |