10 Pipe

I pipes che tradotto letteralmente significa tubi, significando qualcosa che entra in un tubo ed esce differente dall’altra parte del tubo. Una classe con decoratore @Pipe definisce una funzione chiamata transform per trasformare i dati di input in valori differenti da mostrare in una visuale di output.

L’operatore per utilizzare una pipe è |

Angular dispone di un elenco di pipes predefinite che permettono di visualizzare i dati secondo i formati più comuni. Negli esempi precedenti abbiamo avuto modo di vedere dei dati in ingresso trasformati in pipe json

{{f | json}}

La lista delle pipes predefinite la si puà vedere nella documentazione ufficiale.

Vediamo subito degli esempi pratici, per esempio in un template HTML inseriamo un <div> con all’interno una stringa maiuscola che verrà visualizzata minuscola tramite la pipe lowercase

{{ 'PIPPO' | lowercase}}

stessa cosa se il dato arriva da una varibile, vediamolo in azione con la pipe uppercase

<div>
<h2>{{title | uppercase}}</h2>
</div>
title = 'pippo';

le pipes si possono concatenare , aggiungiamo all’esempio di prima la pipe titlecase

<h2>{{title | uppercase | titlecase}}</h2>

la stringa avrà l’iniziale in maiuscolo.

Vediamo la pipe currency per le valute, che di default mostra il dollaro ( $ )

<h2>possiedo {{45.50 | currency}}</h2>

le pipes possono ricevere più parametri per mostrare i dati differentemente. I parametri nelle pipes sono separati dai due punti ( : ), per esempio il primo parametro della pipe currency è il codice della valuta, vediamolo in euro

<h2>possiedo {{45.50 | currency : 'EUR'}}</h2>

Il secondo parametro è display per esempio mettiamo code che mostrerà EUR anzichè il simbolo €.

Il terzo parametro sono i digits, ovvero le cifre, che sono 3 tipi: il minIntegerDigits per il minimo valore della parte intera della cifra, il minFractionDigits per il minimo valore della parte decimale e il maxFractionDigits che è il massimo valore della parte decimale, dove per valore si intende la quantità di numeri da mostrare.

<h2>possiedo {{1450.50 | currency : 'EUR' : 'code' : '4.2-4'}}</h2>

4 valori interi con le migliaia separate da virgola, 2 valori minimi decimale e un massimo di 4.

L’ultimo parametro è il locale cioè il modo di presentare la valuta a seconda del paese

<h2>possiedo {{1450.50 | currency : 'EUR' : 'code' : '4.2-4' : 'it-IT'}}</h2>

Con it-IT otterremo un errore perchè il locale italiano, seguendo la guida di angular necessita di importare in app.module.ts il locale che ci interessa e precisamente la funzione registerLocalData e il tipo di locale del paese voluto

import {registerLocaleData} from '@angular/common';
import localeIt from '@angular/common/locales/it';
registerLocaleData(localeIt);

A questo punto avremo la notazione usata in italia, quindi il separatore delle migliaia col punto e i decimali con la virgola.

date

Una pipe interessante e molto usata e quella che formatta la data. I parametri sono il format, il timezone e il locale.

Dichiariamo una variabile birthday che prende la data attuale e richiamiamola nel template

birthday = new Date();

<h3>sono nato {{birthday | date}}</h3>

poi passiamo il primo parametro che è il formato che può essere short, che mostra solo 2 cifre per l’anno fino a full che mostra la data completa, guardare la documentazione per tutti i vari format.

<h3>sono nato {{birthday | date : 'dd/MM/yyyy'}}</h3>

aggiungiamo anche il timezone italiano e il locale e il format fullDate per la data in italiano

<h3>sono nato {{birthday | date : 'fullDate' : '+2' : 'it-IT'}}</h3>

Custom pipe

Se abbiamo necessità di visualizzare i dati in un modo diverso, non previsto dalle pipe predefinite, possiamo crearne una nostra. Sfruttando angular CLI lanciamo il comando dal terminale che crea una nostra pipe

ng g p primamaiuscola

a questo punto verrà creata la nostra pipe col nome scelto ( primamaiuscola.pipe.ts ) che servirà per richiamarla.

Ecco la struttura:

import { Pipe, PipeTransform } from '@angular/core';

@Pipe({
 name: 'primamaiuscola'
 })
 export class PrimamaiuscolaPipe implements PipeTransform {

 transform(value: unknown, ...args: unknown[]): unknown {
 return null;
 }
}

La parte dove andremo a lavorare è sulla funzione transform(), nel nostro caso vogliamo una pipe che trasformi una stringa con solo la prima parola in maiuscolo.

Vogliamo trasformare una stringa che può contenere più parole, solo con la prima lettera del primo carattere in maiuscolo

transform(value): any {
 const primalett = value[0].substr(0, 1).toUpperCase();
 return primalett + value.substr(1);
}

Se invece volessimo ogni primo carattere di ogni parola in maiuscolo, possiamo procedere come segue:

Usiamo il metodo split() che trasforma una stringa in un array di cui ogni elemento è una parola della stringa

ogni parola della stringa separata da un carattere che specifico tra gli apici della funzione split, nel nostro caso il separatore è uno spazio, verrà inserita come elemento dell’array.

transform(value: string): any {
value.split(' ')
}

Dal risultato dello split applico il metodo map() che esegue una funzione per ogni elemento di un array. Usando un’ arrow function passo una variabile, che chiamo per esempio parola di tipo string e come esecuzione aggiungerà uno spazio vuoto tra gli elementi dell’array, Concateno a parola il metodo substr() che prende parti di una stringa, il primo parametro stabilisce da dove cominciare a prendere caratteri e il secondo quanti, visto che vogliamo la prima lettera metteremo dalla posizione 0 prendi 1 carattere.

Trasformo in maiuscolo la prima lettera ottenuta col metodo toUpperCase()

valore.split(' ').map( (parola: string) => ' ' + parola.substr(0, 1).toUpperCase()

aggiungo il return davanti per restituire il valore della funzione transform e concateno il resto.

transform(valore: string): any {
 return valore.split(' ').map( (parola: string) => ' ' + parola.substr(0, 1).toUpperCase() +     parola.substr(1)).join('');
}

Da notare il secondo substr che parte dal secondo carattere e non specificando altro prende tutto il restante.

Inoltre il metodo join() che unisce tutti gli elementi di un array trasformandolo in stringa.

A questo punto possiamo usare la nostra pipe custom a nostro piacere

<h4>{{pippo | primamaiuscola}}</h4>

pippo = 'ciao come stai';

Se creiamo la pipe manualmente senza angular CLI dobbiamo importare i moduli Pipe e PipeTransform dal core di angular

import { Pipe, PipeTransform } from '@angular/core';