Flutter nello sviluppo mobile: cos'è, concetti chiave e come funziona

Autore: IT Sectr Pubblicato: 2026-07-09 Tempo di lettura: 11 min

Flutter è un framework UI di Google per applicazioni native multipiattaforma. Secondo Flutter Docs (2025), Flutter è utilizzato in oltre 500.000 app su Google Play. Comprendere Widget, StatefulWidget, BuildContext e l'albero di rendering è la base dello sviluppo Flutter.

Punti chiave

  • Widget — blocco di costruzione di base. StatelessWidget (immutabile) vs StatefulWidget (mutabile con setState()).
  • Tre alberi: Widget Tree (configurazione), Element Tree (elementi), RenderObject Tree (rendering).
  • BuildContext — accesso a InheritedWidget: Theme, MediaQuery, Navigator. InheritedWidget — passaggio dati verso il basso.
  • Navigator — pila di schermate (Routes). Navigator 2.0 (Router) — navigazione dichiarativa.
  • Hot Reload — iniezione di modifiche in 1-2 secondi. Preserva lo stato. Hot Restart — riavvio completo.

Flutter: basi di Widget, StatelessWidget e StatefulWidget

Widget — una descrizione dichiarativa di una parte dell'UI. Tutto in Flutter è un Widget: da un pulsante all'app stessa. Un Widget è configurazione (non l'UI stessa). StatelessWidget — un Widget immutabile. build() viene chiamato una volta. Non ha stato. Usato per contenuti statici. StatefulWidget — un Widget mutabile. Ha un oggetto State che può cambiare. setState() — attiva la ricostruzione. State — un oggetto mutabile legato a un StatefulWidget. Contiene dati che possono cambiare.

StatelessWidget vs StatefulWidget

StatelessWidget — build() viene chiamato una volta. Adatto per intestazioni, icone, testi statici. StatefulWidget — build() viene chiamato ogni volta che setState() viene invocato. Adatto per moduli, elenchi con modifiche, timer. InheritedWidget — passaggio di dati verso il basso senza passaggio esplicito tramite costruttori. Theme, MediaQuery, Navigator — InheritedWidget. BuildContext — posizione di un Widget nell'albero. context.of<T>, context.watch<T>, context.select<T,R> — accesso a InheritedWidget.

dart
// Esempio Flutter Widget: StatefulWidget con setState
class CounterWidget extends StatefulWidget {
  const CounterWidget({Key? key}) : super(key: key);

  @override
  State<CounterWidget> createState() => _CounterWidgetState();
}

class _CounterWidgetState extends State<CounterWidget> {
  int _counter = 0;

  void _increment() {
    setState(() {
      _counter++;
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: const Text('Flutter Counter')),
      body: const Center(
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: [
            const Text('You have pushed the button:'),
            Text(
              '$_counter',
              style: Theme.of(context).textTheme.headlineMedium,
            ),
          ],
        ),
      ),
      floatingActionButton: FloatingActionButton(
        onPressed: _increment,
        child: const Icon(Icons.add),
      ),
    );
  }
}

Widget — configurazione. StatelessWidget — immutabile. StatefulWidget — mutabile con setState(). IT Sectr consiglia di iniziare con StatelessWidget e passare a StatefulWidget solo quando serve lo stato.

Alberi (Widget Tree, Element Tree, RenderObject Tree)

Flutter usa tre alberi per un rendering efficiente. Widget Tree — albero di configurazione. I Widget vengono creati frequentemente (ogni build), leggeri. Element Tree — albero degli elementi. Un elemento per Widget (se il tipo non cambia). Element — ponte tra Widget e RenderObject. RenderObject Tree — albero di rendering. Gestisce dimensioni, posizioni, disegno. RenderObject — pesante, creato raramente. Flutter confronta il Widget Tree e aggiorna l'Element Tree, che attiva l'aggiornamento del RenderObject Tree.

Keys e Element Tree

Key — identificatore di Widget nell'Element Tree. ValueKey, ObjectKey, UniqueKey, PageStorageKey. Le Keys permettono a Flutter di abbinare Widget vecchi e nuovi durante la ricostruzione. Senza Keys, Flutter abbina per tipo di Widget e posizione. GlobalKey — accesso a State da un altro Widget. Usato per: moduli complessi, animazioni, accesso a State nei test. IT Sectr consiglia di usare Keys per le liste (List.generate) ed evitare GlobalKey se non necessario.

Expanded — Widget che riempie lo spazio disponibile in Row/Column/Flex. Flexible — non forza il riempimento (può essere più piccolo). MediaQuery — InheritedWidget con informazioni sul dispositivo: dimensioni schermo, orientamento, piattaforma, fattore di scala del testo. Theme/ThemeData — tema centralizzato. Theme.of(context) — accesso. MaterialApp — Widget radice per configurazione di routing, temi, impostazioni locali. Scaffold — layout base con AppBar, Drawer, BottomNavigationBar. AppBar — pannello superiore.

Navigator — pila di route (Routes). Navigator.push — aprire schermata (restituisce Future). Navigator.pop — chiudere (con risultato). MaterialPageRoute — transizione animata (slide da destra). Named Routes — identificatori di stringa. onGenerateRoute — gestore centralizzato. Navigator 2.0 (Router + RouteInformationParser + RouterDelegate) — navigazione dichiarativa per web, deep linking e scenari complessi.

Navigator 2.0 — navigazione dichiarativa. Router — Widget centrale. RouteInformationParser — parsing URL. RouterDelegate — gestione della pila. GoRouter (pacchetto) — wrapper semplificato su Navigator 2.0. Supporta: route nominate, parametri, redirect, deep linking. IT Sectr consiglia GoRouter per la maggior parte dei progetti e Navigator 2.0 solo per scenari complessi (web, desktop).

Async (FutureBuilder, StreamBuilder)

FutureBuilder — Widget che costruisce l'UI basata su un Future. connectionState: none, waiting, active, done. Usato per: richieste HTTP, letture DB, timer. StreamBuilder — Widget per Stream (flusso infinito di dati). snapshot.data, snapshot.hasError, snapshot.hasData. Usato per: WebSocket, Firebase, aggiornamenti di posizione. Entrambi i Widget si ricostruiscono al ricevimento di nuovi dati.

Gestione dello stato

Provider — DI semplice + gestione dello stato. ChangeNotifierProvider, MultiProvider. Riverpod — sostituto moderno di Provider: sicuro in compilazione, indipendente da BuildContext. Bloc — architettura Event-Driven: Cubit (eventi semplici) vs Bloc (complessi). GetX — gestione dello stato leggera + DI + routing. setState — il più semplice, per stato locale. IT Sectr consiglia Riverpod per nuovi progetti e Provider per progetti esistenti.

Temi e adattamento (MediaQuery, ThemeData)

MediaQuery — dimensioni schermo, orientamento, piattaforma, textScaleFactor. MediaQuery.of(context).size.width. ThemeData — tema dell'app: colori, font, forme. Theme.of(context).textTheme.bodyLarge. Hot Reload — iniezione di codice in un'app in esecuzione. Preserva lo stato. Non supporta: modifica di main(), variabili globali, campi statici. Hot Restart — riavvio completo dell'app (perdita di stato). Hot Reload — principale vantaggio di Flutter per gli sviluppatori.

Tipo di Widget Descrizione Esempi
StatelessWidgetImmutabile, build una voltaText, Icon, Padding, Center
StatefulWidgetMutabile, setState ricostruzioneTextField, Checkbox, AnimationController
InheritedWidgetPassaggio dati verso il bassoTheme, MediaQuery, Navigator
ProxyWidgetWrapper per altri WidgetParentDataWidget (Positioned, Expanded)
RenderObjectWidgetCrea RenderObjectColumn, Row, Stack (personalizzati)

StatelessWidget — per contenuti statici. StatefulWidget — per contenuti dinamici. InheritedWidget — per DI. IT Sectr consiglia StatelessWidget per impostazione predefinita e StatefulWidget solo quando necessario.

Layout responsive

LayoutBuilder — adattamento alle dimensioni del genitore. OrientationBuilder — adattamento all'orientamento. Expanded vs Flexible — distribuzione dello spazio in Row/Column. MediaQuery — breakpoint per tablet e desktop. SafeArea — margini dagli elementi di sistema (notch, barra di stato). AspectRatio — mantenimento delle proporzioni. IT Sectr consiglia LayoutBuilder per layout adattivi e OrientationBuilder per orientamento orizzontale.

Test (Widget, Integration, Unit)

Test unitari — test della logica di business, repository, modelli. dart test — esecuzione. Test Widget — test di widget in isolamento. WidgetTester — pumpWidget, tap, enterText. Test di integrazione — scenari completi su dispositivo/emulatore reale. Mockito — mock delle dipendenze. Golden test — confronto di screenshot (file golden). IT Sectr consiglia test Widget per ogni schermata e test unitari per la logica di business.

dart
void main() {
  testWidgets('Counter increments on tap', (tester) async {
    await tester.pumpWidget(const MaterialApp(home: CounterWidget()));

    expect(find.text('0'), findsOneWidget);

    await tester.tap(find.byType(FloatingActionButton));
    await tester.pump();

    expect(find.text('1'), findsOneWidget);
  });
}

Animazioni (Implicite, Esplicite, Hero)

Animazioni implicite — AnimatedContainer, AnimatedOpacity, AnimatedPadding, TweenAnimationBuilder. I cambi di proprietà vengono animati automaticamente. Animazioni esplicite — AnimationController con Tween. forward() / reverse(). Animazione Hero — Widget Hero con un tag — animazione di transizione tra schermate. Animazione scaglionata — catena di animazioni con Interval. Lottie — integrazione di animazioni After Effects. Rive — animazioni interattive (state machine). IT Sectr consiglia AnimatedContainer per l'80% dei casi e AnimationController per scenari complessi.

dart
class AnimatedBox extends StatefulWidget {
  @override
  State<AnimatedBox> createState() => _AnimatedBoxState();
}

class _AnimatedBoxState extends State<AnimatedBox> {
  bool _expanded = false;

  @override
  Widget build(BuildContext context) {
    return GestureDetector(
      onTap: () => setState(() => _expanded = !_expanded),
      child: AnimatedContainer(
        duration: const Duration(milliseconds: 300),
        curve: Curves.easeInOut,
        width: _expanded ? 200 : 100,
        height: _expanded ? 200 : 100,
        color: _expanded ? Colors.blue : Colors.red,
        child: const Center(child: Text('Tap me')),
      ),
    );
  }
}

Rete (http, dio, graphql)

http — client HTTP semplice (get, post, put, delete). dio — client avanzato con intercettori, timeout, retry, logging. graphql_flutter — client GraphQL per Flutter. json_serializable — generazione di fromJson/toJson tramite annotazioni. Retrofit Dart — client HTTP type-safe come Retrofit. WebSocket — tramite web_socket_channel. Firebase — Cloud Firestore, Realtime Database, Cloud Functions. IT Sectr consiglia dio per API REST e graphql_flutter per GraphQL.

Flutter DevTools — insieme di strumenti: Inspector (albero widget), Timeline (prestazioni), Memory, Network, Logging. Profile mode — profilazione senza debug. Performance overlay — FPS, tempi di build. Flame chart — tracciamento flame chart. DevTools — strumento essenziale per ottimizzare le applicazioni Flutter in produzione.

Flutter Web — compilazione di Flutter in WASM (WebAssembly). CanvasKit (Skia) vs HTML renderer. CanvasKit — pixel-perfect, ma più pesante. HTML renderer — leggero, ma con limitazioni. WASM (Flutter 3.22+) — prestazioni native. Adattamento responsive tramite LayoutBuilder e MediaQuery. IT Sectr consiglia CanvasKit per applicazioni web desktop e HTML renderer per siti di contenuto.

Domande frequenti

Qual è la differenza tra StatelessWidget e StatefulWidget?

StatelessWidget — immutabile, build una volta. StatefulWidget — con State mutabile e setState().

Cosa sono Widget Tree, Element Tree e RenderObject Tree?

Widget Tree — configurazione. Element Tree — ponte. RenderObject Tree — rendering (dimensioni, disegno).

Cosa sono BuildContext e InheritedWidget?

BuildContext — posizione del Widget nell'albero. InheritedWidget — passaggio dati verso il basso (Theme, MediaQuery).

Come funzionano Navigator e Route in Flutter?

Navigator — pila di schermate. push() → pop(). Named Routes — nomi di stringa. Navigator 2.0 — dichiarativo.

Come funziona Hot Reload in Flutter?

Hot Reload — iniezione di codice in 1-2 secondi, preservazione dello stato. Hot Restart — riavvio completo.

Riepilogo

  • Widget — tutto è Widget. StatelessWidget vs StatefulWidget — dicotomia di base.
  • Tre alberi: Widget → Element → RenderObject. Widget — configurazione, RenderObject — rendering.
  • BuildContext + InheritedWidget — accesso a Theme, MediaQuery, Navigator senza passaggio esplicito.
  • Navigator — pila di schermate. Navigator 2.0 — navigazione dichiarativa per web e deep link.
  • FutureBuilder — per Future. StreamBuilder — per Stream (Firebase, WebSocket).
  • MaterialApp + Scaffold — scheletro dell'app. ThemeData — tema centralizzato.
  • Hot Reload — killer feature di Flutter. Aggiornamento codice in secondi con preservazione dello stato.

Svilupperemo un'applicazione mobile chiavi in mano

IT Sectr crea applicazioni iOS e Android per startup e aziende dal 2017. Ti consulteremo e ti proporremo la soluzione migliore.

Discuti il progetto