Flutter’da Widget Kavramı: Stateless vs Stateful Widget

Flutter’da her şey bir widget‘tır. Widget’lar, uygulamanızın kullanıcı arayüzünü (UI) oluşturan yapı taşlarıdır. Bu yazıda, Flutter’ın temelini oluşturan Stateless ve Stateful widget’ları arasındaki farkları, kullanım senaryolarını ve widget yaşam döngüsünü örneklerle açıklayacağız.


1. Widget Nedir?

Widget, Flutter’da UI bileşenlerini tanımlayan bir sınıftır. Her widget:

  • Ekranda bir öğeyi (buton, metin, resim vb.) temsil eder.
  • Diğer widget’ları içerebilir (composition).
  • Props (özellikler) alabilir ve bu özelliklere göre görünümünü değiştirebilir.

Örnek widget hiyerarşisi:

Scaffold(
  appBar: AppBar(title: Text("Başlık")),
  body: Center(
    child: Column(
      children: [
        Text("Merhaba"),
        ElevatedButton(onPressed: () {}, child: Text("Tıkla")),
      ],
    ),
  ),
)

2. Stateless Widget

2.1. Nedir?

  • Değişmez (immutable) widget’lardır.
  • İç durumları (state) yoktur.
  • Bir kez oluşturulur ve yeniden çizilmezler (rebuild).

2.2. Ne Zaman Kullanılır?

  • Sabit veri gösteren bileşenler (başlık, metin, ikon).
  • Dışarıdan aldığı verilerle (props) çalışan bileşenler.
  • Durum değişikliği gerektirmeyen statik içerikler.

2.3. Örnek Stateless Widget

class SabitBaslik extends StatelessWidget {
  final String baslikMetni; // Dışarıdan alınan veri (değişmez)

  const SabitBaslik({super.key, required this.baslikMetni});

  @override
  Widget build(BuildContext context) {
    return Text(
      baslikMetni,
      style: const TextStyle(fontSize: 24, fontWeight: FontWeight.bold),
    );
  }
}
// Kullanım: SabitBaslik(baslikMetni: "Hoş Geldiniz")

3. Stateful Widget

3.1. Nedir?

  • Değişebilir (mutable) widget’lardır.
  • İç durumları (state) vardır ve bu durum değiştiğinde yeniden çizilirler.
  • İki parçadan oluşur:
    1. StatefulWidget: Durumu yöneten sınıf.
    2. State: Durumun verilerini ve build metodunu tutan sınıf.

3.2. Ne Zaman Kullanılır?

  • Kullanıcı etkileşimine göre değişen bileşenler (sayac, formlar).
  • Animasyonlar ve geçiş efektleri.
  • Dinamik veri güncellemeleri (API’den gelen veriler).

3.3. Örnek Stateful Widget

class SayacWidget extends StatefulWidget {
  const SayacWidget({super.key});

  @override
  State<SayacWidget> createState() => _SayacWidgetState();
}

class _SayacWidgetState extends State<SayacWidget> {
  int sayac = 0; // Durum değişkeni

  void arttir() {
    setState(() { // Yeniden çizim tetikler
      sayac++;
    });
  }

  @override
  Widget build(BuildContext context) {
    return Column(
      children: [
        Text("Sayaç: $sayac"),
        ElevatedButton(
          onPressed: arttir,
          child: const Text("Arttır"),
        ),
      ],
    );
  }
}

4. Stateless vs Stateful Widget Farkları

ÖzellikStateless WidgetStateful Widget
Durum YönetimiYokVar
Yeniden ÇizimProps değişirse çizilirsetState() ile çizilir
PerformansDaha hafifDaha fazla kaynak kullanır
Kullanım AlanıStatik içerikDinamik içerik
Yaşam DöngüsüBasitKarmaşık

5. Widget Yaşam Döngüsü (Stateful Widget)

5.1. Başlangıç Aşamaları

  1. createState(): State nesnesi oluşturulur.
  2. initState(): State ilk kez oluşturulduğunda çağrılır (API çağrıları için ideal).
  3. didChangeDependencies(): Bağımlılıklar değiştiğinde çağrılır.
  4. build(): Widget arayüzü oluşturulur.

5.2. Güncelleme Aşamaları

  1. didUpdateWidget(): Widget yeniden oluşturulduğunda çağrılır.
  2. setState(): Durum değişikliği ve yeniden çizim tetikler.

5.3. Sonlandırma Aşamaları

  1. deactivate(): Widget ağaçtan kaldırıldığında.
  2. dispose(): Widget tamamen yok edildiğinde (kaynak temizleme).

Örnek Yaşam Döngüsü Kullanımı:

class OrnekWidget extends StatefulWidget {
  const OrnekWidget({super.key});

  @override
  State<OrnekWidget> createState() => _OrnekWidgetState();
}

class _OrnekWidgetState extends State<OrnekWidget> {
  @override
  void initState() {
    super.initState();
    print("Widget oluşturuldu");
  }

  @override
  void dispose() {
    print("Widget yok edildi");
    super.dispose();
  }

  @override
  Widget build(BuildContext context) {
    return const Placeholder();
  }
}

6. Hangi Durumda Hangisi Kullanılmalı?

Stateless Kullanım Senaryoları

  • ✅ Sabit metinler, ikonlar, resimler.
  • ✅ Verileri dışarıdan alan bileşenler (props).
  • ✅ Durum değişikliği gerektirmeyen listeler.

Stateful Kullanım Senaryoları

  • ✅ Kullanıcı etkileşimli bileşenler (buton, form).
  • ✅ Zamanla değişen veriler (geri sayım, animasyon).
  • ✅ API’den gelen dinamik verilerin gösterimi.

7. Örnek Uygulama: Durum Değişimi

class RenkDegistirenButton extends StatefulWidget {
  const RenkDegistirenButton({super.key});

  @override
  State<RenkDegistirenButton> createState() => _RenkDegistirenButtonState();
}

class _RenkDegistirenButtonState extends State<RenkDegistirenButton> {
  Color arkaplanRengi = Colors.blue;

  void renkDegistir() {
    setState(() {
      arkaplanRengi = Colors.primaries[Random().nextInt(Colors.primaries.length)];
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      backgroundColor: arkaplanRengi,
      body: Center(
        child: ElevatedButton(
          onPressed: renkDegistir,
          child: const Text("Rastgele Renk Değiştir"),
        ),
      ),
    );
  }
}

Sonuç

  • Stateless Widget: Sabit, hafif ve performanslı bileşenler için.
  • Stateful Widget: Dinamik, etkileşimli ve durumu değişen bileşenler için.
  • setState(): Durum değişikliğinde yeniden çizim tetikler.
guest
0 Yorum
Eskiler
En Yeniler Beğenilenler
Inline Feedbacks
View all comments