Template Syntax Examples
Practical examples of AngularDart template syntax.
Example 1: User Profile Card
@Component(
selector: 'user-card',
template: '<div class="card" [class.admin]="user.isAdmin">'
'<img [src]="user.avatarUrl" [alt]="user.name">'
'<h2>{{ user.name }}</h2>'
'<p>{{ user.bio }}</p>'
'<span *ngIf="user.isAdmin" class="badge">Admin</span>'
'<button (click)="onContact()">Contact</button>'
'</div>',
styles: ['.card { padding: 16px; border: 1px solid #ddd; border-radius: 8px; }'
'.card.admin { border-color: gold; }'
'.badge { background: gold; padding: 2px 8px; border-radius: 4px; }'],
)
class UserCardComponent {
@Input()
User? user;
@Output()
final contact = StreamController<User>.broadcast();
void onContact() {
if (user != null) contact.add(user!);
}
}
Example 2: Shopping Cart with ngFor
@Component(
selector: 'shopping-cart',
template: '<h2>Shopping Cart ({{ items.length }} items)</h2>'
'<ul class="cart-items">'
'<li *ngFor="let item of items; let i = index; trackBy: trackByItemId">'
'<span class="item-name">{{ item.name }}</span>'
'<span class="item-qty">'
'<button (click)="decrement(i)">-</button>'
'{{ item.quantity }}'
'<button (click)="increment(i)">+</button>'
'</span>'
'<span class="item-price">{{ item.price | currency:\'EUR\' }}</span>'
'<button (click)="remove(i)" class="remove-btn">Remove</button>'
'</li>'
'</ul>'
'<div class="total">'
'<strong>Total: {{ total | currency:\'EUR\' }}</strong>'
'</div>'
'<button (click)="checkout()" [disabled]="items.isEmpty">Checkout</button>',
)
class ShoppingCartComponent {
List<CartItem> items = [];
String trackByItemId(int index, CartItem item) => item.id;
double get total => items.fold(0, (sum, item) => sum + item.price * item.quantity);
void increment(int index) => items[index].quantity++;
void decrement(int index) {
if (items[index].quantity > 1) items[index].quantity--;
}
void remove(int index) => items.removeAt(index);
void checkout() { /* ... */ }
}
Example 3: Form with Validation Feedback
@Component(
selector: 'registration-form',
template: '<form #form="ngForm" (ngSubmit)="onSubmit(form)">'
'<div class="form-group">'
'<label for="name">Name</label>'
'<input id="name" ngModel name="name" #nameField="ngModel" required minlength="2" maxlength="50">'
'<div class="errors" *ngIf="nameField.invalid && nameField.touched">'
'<span *ngIf="nameField.errors?[\'required\']">Name is required</span>'
'<span *ngIf="nameField.errors?[\'minlength\']">Name must be at least 2 characters</span>'
'</div>'
'</div>'
'<div class="form-group">'
'<label for="email">Email</label>'
'<input id="email" ngModel name="email" #emailField="ngModel" required type="email">'
'<div class="errors" *ngIf="emailField.invalid && emailField.touched">'
'<span *ngIf="emailField.errors?[\'required\']">Email is required</span>'
'<span *ngIf="emailField.errors?[\'email\']">Please enter a valid email</span>'
'</div>'
'</div>'
'<button type="submit" [disabled]="form.invalid">Register</button>'
'</form>',
directives: [formDirectives],
)
class RegistrationFormComponent {
void onSubmit(NgForm form) {
print('Form submitted: ${form.value}');
}
}
Example 4: Dynamic Styling with ngClass and ngStyle
@Component(
selector: 'theme-demo',
template: '<div [ngClass]="themeClasses" [ngStyle]="themeStyles">'
'<h1>{{ title }}</h1>'
'<p>{{ content }}</p>'
'</div>'
'<button (click)="toggleTheme()">Toggle Theme</button>',
)
class ThemeDemoComponent {
String title = 'Themed Content';
String content = 'This content changes appearance based on the theme.';
bool isDark = false;
Map<String, bool> get themeClasses => {
'dark-theme': isDark,
'light-theme': !isDark,
'large-text': true,
};
Map<String, String> get themeStyles => {
'background-color': isDark ? '#1a1a2e' : '#ffffff',
'color': isDark ? '#ffffff' : '#333333',
'padding': '20px',
'border-radius': '8px',
};
void toggleTheme() {
isDark = !isDark;
}
}
Example 5: ngSwitch for Status Display
@Component(
selector: 'order-status',
template: '<div class="status-badge" [ngSwitch]="order.status">'
'<span *ngSwitchCase="\'pending\'" class="pending">Pending</span>'
'<span *ngSwitchCase="\'processing\'" class="processing">Processing</span>'
'<span *ngSwitchCase="\'shipped\'" class="shipped">Shipped ({{ order.trackingNumber }})</span>'
'<span *ngSwitchCase="\'delivered\'" class="delivered">Delivered</span>'
'<span *ngSwitchCase="\'cancelled\'" class="cancelled">Cancelled</span>'
'<span *ngSwitchDefault class="unknown">Unknown Status</span>'
'</div>',
)
class OrderStatusComponent {
@Input()
Order? order;
}
Example 6: Template Reference Variables
@Component(
selector: 'search-box',
template: '<input #searchInput (input)="onSearch(searchInput.value)" '
'(keyup.enter)="onSubmit(searchInput.value)" placeholder="Search...">'
'<button (click)="onSubmit(searchInput.value)">Search</button>'
'<button (click)="clear(searchInput)">Clear</button>'
'<div *ngIf="results.isNotEmpty">'
'<h3>Results for "{{ lastQuery }}":</h3>'
'<ul>'
'<li *ngFor="let result of results">{{ result }}</li>'
'</ul>'
'</div>',
)
class SearchBoxComponent {
List<String> results = [];
String lastQuery = '';
void onSearch(String query) {
lastQuery = query;
if (query.length >= 3) {
results = ['Result 1 for $query', 'Result 2 for $query'];
} else {
results = [];
}
}
void onSubmit(String query) {
print('Searching for: $query');
}
void clear(HtmlInputElement input) {
input.value = '';
results = [];
lastQuery = '';
input.focus();
}
}
Example 7: Two-Way Binding with ngModel
@Component(
selector: 'profile-editor',
template: '<h2>Edit Profile</h2>'
'<div class="form-group">'
'<label>Name:</label>'
'<input [(ngModel)]="user.name">'
'<p>Preview: {{ user.name }}</p>'
'</div>'
'<div class="form-group">'
'<label>Email:</label>'
'<input [(ngModel)]="user.email" type="email">'
'<p>Preview: {{ user.email }}</p>'
'</div>'
'<button (click)="save()">Save</button>'
'<button (click)="reset()">Reset</button>'
'<pre>{{ user | json }}</pre>',
directives: [formDirectives],
)
class ProfileEditorComponent {
User user = User(
name: 'John Doe',
email: 'john@example.com',
newsletter: true,
role: 'user',
);
late User _originalUser;
ProfileEditorComponent() {
_originalUser = user.clone();
}
void save() {
_originalUser = user.clone();
print('Saved: ${user.toJson()}');
}
void reset() {
user = _originalUser.clone();
}
}