State: mi ez, állapotkezelés és működési elv

Szerző: IT Sectr Megjelenés: 2026-07-01 Olvasási idő: 9 perc

State — a Flutter központi adatkezelő objektuma, amely a StatefulWidgethez kapcsolódik és felelős a változtatható információk tárolásáért és a felület felépítéséért. A Flutter hivatalos dokumentációja szerint (Flutter.dev, 2026) a State a widget teljes életciklusa alatt létezik és túbbírja annak újraépítéseit, biztosítva az adatok konzisztenciáját az UI frissítések között. Magától a widgettől eltérően a State megváltoztathatja a mezőit és a setState meghívásával újraépítést kezdeményezhet.

FŐ PONTOK

  • State — a StatefulWidget változtatható adatait tároló és annak újraépítését a setState-en keresztül irányító objektum
  • Életciklus — a State átmegy az initState, didChangeDependencies, build, didUpdateWidget és dispose fázisokon, mindegyik világos céllal
  • mounted — jelző, amely azt mutatja, hogy a State még a widgetfában van és biztonságosan meghívhatja a setState-t
  • widget — hivatkozás a kapcsolódó StatefulWidgetre, a State tulajdonságán keresztül elérhető a szülő paramétereinek olvasásához
  • Elszigeteltség — a State el van szigetelve más State-ektől; adatcseréhez InheritedWidget vagy külső állapotkezelő eszközök használatosak

Mi az a State a Flutterben?

State — egy objektum a Flutter architektúrában, amely tárolja a StatefulWidget változtatható adatait és meghatározza, hogy ezek az adatok hogyan jelenjenek meg a felületen. Minden StatefulWidget a fába való beágyazáskor pontosan egy State objektumot hoz létre a createState metódussal. A State függetlenül létezik a widgettől: ha a szülő újraépíti a StatefulWidgetet új paraméterekkel, a State ugyanaz marad és a frissített widgetet a widget tulajdonságon keresztül kapja meg.

A Flutter Architectural Overview (Google, 2026) szerint a Widget és a State szétválasztása egy tudatos architektúrai döntés, amely lehetővé teszi a keretrendszer számára a faelemek újrafelhasználását. A widget (könnyű leírás) többször létrehozható és megsemmisíthető, de a State (nehéz objektum adatokkal) a memóriában marad, amíg az elem a fában van. Ez megakadályozza az adatvesztést a szülő widgetek gyakori újraépítésekor.

A State a StatefulWidget interfészt generikuson keresztül valósítja meg: class _MyState extends State<MyWidget>. A generikus a State-t egy konkrét StatefulWidget típushoz köti, típusbiztos hozzáférést biztosítva a mezőihez a widget tulajdonságon keresztül.

Hol tárolódik a State?

A State objektum a StatefulElement-ben tárolódik — a Widget és a RenderObject közötti közbenső rétegben. A StatefulElement a createState-en keresztül hozza létre a State-t, tárolja a rá való hivatkozást és átadja a State-t tulajdonosként. Az Element csak akkor semmisül meg, amikor a widget eltávolításra kerül a fából — addig a State a memóriában él.

A State életciklusa

A State életciklusa determinisztikus és szigorú hívási sorrendből áll. Ennek a sorrendnek a megértése az erőforrásokkal való helyes munkavégzes és a memóriaszivárgás megelőzésének alapja.

initState — inicializálás

initState elsőként hívódik meg a State létrehozásakor. Ebben a metódusban inicializálódnak a vezérlők, adatfolyam-előfizetések, időzítők és a mezők kezdeti értékei. A super.initState() meghívása az első sorban kötelező. Az initState fázisban a widgetfá még nincs teljesen felszerelve, ezért az olyan metódusok, mint a MediaQuery.of(context), helytelenül működhetnek.

didChangeDependencies

didChangeDependencies az initState után és az InheritedWidget függőségek minden változásakor hívódik meg. Itt, nem az initState-ben kell meghívni a MediaQuery.of(context) vagy Theme.of(context) metódusokat, mert ekkor a fá már fel van szerelve. Ez a metódus akkor is meghívódik, ha a widget egy másik kontextusba kerül, ahol az InheritedWidget eltérő értékeket biztosít.

build — UI építése

build — a State fő metódusa, amely visszaadja a widgetfát. Az initState után, a didChangeDependencies után és minden setState után hívódik meg. A build metódusnak nem lehetnek mellékhatásai — csak a State mezőinek aktuális értékei alapján írja le a felületet.

didUpdateWidget

didUpdateWidget akkor hívódik meg, amikor a szülő újraépíti a StatefulWidgetet új paraméterekkel. A State hozzáfér a régi widgethez az oldWidget-en keresztül, és összehasonlíthatja azt az újjal. Ha a paraméterek megváltoztak, frissíthető az állapot, betölthetők új adatok vagy újraindítható az animáció.

dispose — erőforrások felszabadítása

dispose — a záró metódus, amelyben az összes erőforrás felszabadul: vezérlők, előfizetések, időzítők. A dispose után a State halottként van megjelölve: a mounted false-értéket ad vissza, a setState meghívása kivételt dob. A super.dispose() meghívása a metódus utolsó sorában kötelező.

MetódusMikor hívódikKötelező super
initStateA State létrehozásakorIgen, az első sorban
didChangeDependenciesAz initState után és InheritedWidget változásakorIgen
buildAz initState, didChangeDependencies, setState utánNem
didUpdateWidgetÚj widget érkezésekor a szülőtőlIgen
setStateA fejlesztő hívásáraNem
disposeA fából való eltávolításkorIgen, az utolsó sorban

Hogyan működik a State?

A State működési mechanizmusa három kulcsfontosságú elven alapul: az Element-hez való kapcsolódás, a setState-en keresztüli reaktivitás és a szülőhöz való hozzáférés a widget tulajdonságon keresztül. Amikor a Flutter építi az elemfát és StatefulElement-re bukkan, meghívja a kapcsolódó widget createState metódusát. A létrehozott State az elemben tárolódik és addig létezik, amíg az elmet nem törlődik.

A setState meghívásakor a State „piszkos“nak” (dirty) jelöli meg magát és újraépítést ütemez a következő kockára. Fontos: a setState nem hívja meg azonnal a build-et — csak regisztrálja az újraépítés szükségességét. A Flutter összegyűjti az összes piszkos elemet az aktuális kockában és kötegenként építi őket újra, ami optimalizálja a teljesítményt. A build hívás után a State visszatér a „tiszta” (clean) állapotba.

A widget tulajdonság lehetővé teszi a State számára, hogy olvassa a StatefulWidget konstruktorának átadott paramétereket. Mivel a StatefulWidget megváltoztathatatlan (mint a StatelessWidget), a mezői nem változnak — a paraméterek változásakor a szülő új widgetet hoz létre, és a State azt a didUpdateWidget-en keresztül kapja meg. Ez garantálja, hogy a State mindig a szülő aktuális adataival dolgozik.

Kódpéldák Dartban

Alap példa State-re egy időzítő által módosított mezővel. Bemutatja az initState, setState és dispose metódusokat:

dart
class _TimerWidgetState extends State<TimerWidget> {
  int _seconds = 0;
  Timer? _timer;

  @override
  void initState() {
    super.initState();
    _timer = Timer.periodic(
      const Duration(seconds: 1),
      (_) => setState(() => _seconds++),
    );
  }

  @override
  void dispose() {
    _timer?.cancel();
    super.dispose();
  }

  @override
  Widget build(BuildContext context) {
    return Text('$_seconds másodperc telt el');
  }
}

Példa a widget tulajdonság használatára a szülő paramétereinek eléréséhez és azok változásaira való reagáláshoz a didUpdateWidget-en keresztül:

dart
class _GreetingState extends State<GreetingWidget> {
  String _displayName = '';

  @override
  void initState() {
    super.initState();
    _displayName = _formatName(widget.name);
  }

  @override
  void didUpdateWidget(GreetingWidget oldWidget) {
    super.didUpdateWidget(oldWidget);
    if (widget.name != oldWidget.name) {
      setState(() {
        _displayName = _formatName(widget.name);
      });
    }
  }

  String _formatName(String name) => name.trim().isEmpty ? 'Guest' : name;

  @override
  Widget build(BuildContext context) {
    return Text('Üdvözlöm, $_displayName!');
  }
}

A második példában a State nyomon követi a name bemeneti paraméter változását és csak tényleges változáskor formázza újra a megjelenítést. A widget.name != oldWidget.name ellenőrzés nélkül a metódus a szülő minden újraépítésekor meghívódna, még akkor is, ha a név nem változott — ez felesleges munka a keretrendszer számára.

State vs StatefulWidget

A State és a StatefulWidget két különböző osztály a Flutter architektúrában, különböző szerepkörrel. A StatefulWidget egy könnyű, megváltoztathatatlan burkoló, amely leírja a widget konfigurációját és létrehozza a State-t. A State egy nehéz objektum, amely tárolja a változtatható adatokat, kezeli az előfizetéseket és építi az UI-t. Ez a szétválasztás lehetővé teszi a Flutter számára, hogy állapotvesztés nélkül semmisítse meg és hozza létre a widgeteket.

A StatefulWidget összes mezőjének finalnek kell lennie és a konstruktorban kell beállítani — nem változnak a létrehozás után. A State ezzel szemben bármikor megváltoztathatja a mezőit, de minden változást meg kell előznie a setState meghívásának, hogy a Flutter tudomást szerezzen az újraépítés szükségességéről. Ez a fő különbség: a StatefulWidget az „hogy mit mutasson”, a State pedig az „hogyan mutasson és milyen adatokat használjon”.

A Flutter forráskód-elemzés (Flutter SDK, 2026) szerint a StatefulWidget csak egy kötelező mezőt tartalmaz — a createState-et, míg a State hozzáfér a BuildContext-hez, előfizethet adatfolyamokra, kezelhet animációkat és vezérlőket. Ajánlott a StatefulWidgetet a lehető legegyszerűbbé tenni, áthelyezve az összes logikát a State-be.

Miért nem lehet a StatefulWidget State?

A Widget és a State szétválasztása egy architektúrai döntés, amely biztosítja a konfiguráció megváltoztathatatlanságát. Ha a StatefulWidget maga tárolná az állapotot, a szülő minden újraépítésekor az állapot elveszne. Az állapot külön objektumba helyezésével a Flutter garantálja, hogy az adatok túbbírják az újraépítéseket, a widgetek pedig könnyűek és összehasonlíthatók maradnak.

Állapotkezelés widgetek között

A State objektum el van szigetelve — nincs közvetlen hozzáférése más widgetek State-jéhez. A widgetek közötti adatcseréhez InheritedWidget vagy külső állapotkezelő eszközök használatosak: Provider, Riverpod, Bloc, Redux. Minden megközelítés másképp oldja meg a feladatot: az InheritedWidget a widgetfán keresztül dolgozik, a Provider — DI-konténeren keresztül, a Bloc — eseményfolyamokon keresztül.

Az eszköz választása a projekt méretétől függ. Kis alkalmazáshoz elegendő az InheritedWidget és a helyi State. Közepes és nagy projekthez a Riverpod vagy a Bloc ajánlott — ezek tesztelhetőséget, kiszámíthatóságot és a logika UI-tól való elkülönítését biztosítják. A State ekkor csak a widget helyi adataihoz használatos (fókusz, görgetés, animáció).

A Flutter Community Survey 2025 (Flutter Foundation, 2025. december) szerint a Riverpod a legnépszerűbb állapotkezelő megoldás új projektekben (38%), ezt követi a Bloc (31%) és a Provider (22%). Mindhárom eszköz kompatibilis a State-tel és nem igényli a szabványos életciklus elhagyását.

Helyi vs globális állapot

  • Helyi állapot — az adott widget State-jében (görgetési pozíció, fókusz állapot)
  • Globális állapot — külső táróban (felhasználói adatok, beállítások, gyorsítótár)
  • Szabály: ha az adatokat csak egy widget használja — tárolja State-ben
  • Ha az adatokat 2+ widget használja — helyezze át Riverpod/Bloc/Provider-be

Tipikus hibák

Első hiba — elfelejteni ellenőrizni a mounted-et a setState előtt egy aszinkron visszahívásban. Amikor a widget eltávolításra került a fából (pl. a felhasználó elhagyta a képernyőt), de az aszinkron művelet (HTTP kérés) még fut, a befejezése után a State már halott. A setState meghívása egy halott State-ben kivételt dob. Az if (mounted) setState(...) ellenőrzés megoldja a problémát.

Második hiba — az InheritedWidget függőségek inicializálása az initState-ben a didChangeDependencies helyett. Az initState-ben a kontextus még nincs felszerelve, ezért a MediaQuery.of(context) kivételt dob. Az InheritedWidget-től származó összes függőséget a didChangeDependencies-ben vagy a build-ben kell konfigurálni.

Harmadik hiba — mezők mutálása a setState meghívása nélkül. Ha a fejlesztő setState nélkül módosít egy State mezőt, a Flutter nem értesül a változásról és az UI nem frissül. Például: a _list.add(item) az ezt követő setState((){}) nélkül megváltoztatja a listát, de a képernyő változatlan marad.

Mounted ellenőrzés a setState előtt

Biztonsági minta aszinkron műveletekhez a State-ben:

dart
Future<void> _fetchData() async {
  final data = await ApiService.fetch();
  if (mounted) {
    setState(() => _data = data);
  }
}

A mounted ellenőrzés garantálja, hogy a setState csak élő State esetén hívódik meg, megakadályozva a „setState called after dispose” kivételt.

Gyakran Ismételt Kérdések

Miben különbözik a State a StatefulWidgettől?

A StatefulWidget a widget megváltoztathatatlan konfigurációja, míg a State egy változtatható objektum, amely tárolja az adatokat és kezeli az életciklust. A widget újra létrehozható, a State — nem. A StatefulWidget a createState-en keresztül hozza létre a State-t.

Hány State objektum jön létre egy StatefulWidget számára?

Pontosan egy. A createState metódus egyszer hívódik meg a StatefulWidget első fába ágyazásakor. Még ha a szülő többször újraépül, a State objektum ugyanaz marad, amíg a widget típusa vagy Key-je meg nem változik.

Mi az a mounted a State-ben?

A mounted egy logikai jelző, amely megmutatja, hogy a State a widgetfában van-e. A dispose meghívása után a mounted false lesz. Aszinkron visszahívásokban a setState előtti ellenőrzésre használják a kivétel elkerülése érdekében.

Használható a State StatefulWidget nélkül?

Nem. A State mindig egy adott StatefulWidgethez van kötve generikuson keresztül: State<T extends StatefulWidget>. A State közvetlen létrehozása, widgethez való kapcsolódás nélkül, architektúrailag lehetetlen.

Mi történik, ha a setState-t a dispose-ban hívják meg?

Kivétel dobódik: „setState called after dispose”. A dispose meghívása után a State halottnak tekintendő és az UI setState-en keresztüli újraépítésére tett kísérletek tilosak. Megoldás — ellenőrizze a mounted-et minden setState előtt.

Összefoglaló

  • State — a StatefulWidget adatkezelő objektuma, változtatható mezőket tárol és UI újraépítést kezdeményez a setState-en keresztül
  • Életciklus tartalmazza a kötelező metódusokat: initState, didChangeDependencies, build, didUpdateWidget és dispose, mindegyik saját céllal
  • mounted — kritikus biztonsági jelző, amely megakadályozza a setState meghívását a widget fából való eltávolítása után
  • widget — a State tulajdonsága a kapcsolódó StatefulWidget paramétereinek eléréséhez, a didUpdateWidget-en keresztül frissül
  • Elszigeteltség — a State nem fér hozzá más State-ekhez; a widgetek közötti interakció InheritedWidget-on vagy külső eszközökön keresztül történik
  • setState — nem hívja meg azonnal a build-et, csak piszkosnak jelöli a State-t a következő kockában történő újraépítéshez
  • Szabály — a State használata a widget helyi adataihoz; a globális állapotot helyezze külső rétegekbe (Riverpod, Bloc)

Kulcsrakész mobilalkalmazást fejlesztünk

Az IT Sectr 2017 óta készít iOS és Android alkalmazásokat induló vállalkozásoknak és vállalkozásoknak. Tanácsot adunk, és a legjobb megoldást javasoljuk.

Projekt megbeszélése

Olvassa el is