Flutter: Spacer Widget ile Esnek Boşluklar
Spacer, Row veya Column içindeki widget'lar arasında esnek boşluklar oluşturmak için kullanılan özel bir widget'tır. En az iki widget arasında "sonsuz" boşluk yaratır.
Spacer Nedir?
Spacer, içinde bulunduğu Flex container'da (Row, Column) mevcut boş alanı kaplamak için genişler. Birden fazla widget arasında boşluk dağıtmak için idealdir.
Temel Kullanım
Row içinde Spacer
Row(
children: [
Text('Sol'),
Spacer(),
Text('Sağ'),
],
)Bu örnekte "Sol" ve "Sağ" metinleri arasındaki tüm boş alan Spacer tarafından doldurulur, böylece metinler iki uca yaslanır.
Column içinde Spacer
Column(
children: [
Text('Üst'),
Spacer(),
Text('Alt'),
],
)"Üst" ve "Alt" metinleri arasında maksimum dikey boşluk oluşturulur.
Birden Fazla Spacer
Birden fazla Spacer kullanarak boşlukları eşit şekilde dağıtabilirsiniz:
Row(
children: [
Text('Sol'),
Spacer(),
Text('Orta'),
Spacer(),
Text('Sağ'),
],
)İki Spacer eşit boşluk paylaşır, üç metin eşit aralıklarla dağılır.
Flex Parametresi
Spacer'ın flex parametresi ile boşlukların oranını ayarlayabilirsiniz:
Row(
children: [
Text('Sol'),
Spacer(flex: 1), // 1 birim boşluk
Text('Orta'),
Spacer(flex: 2), // 2 birim boşluk
Text('Sağ'),
],
)İkinci Spacer, birinci Spacer'ın iki katı kadar alan kaplar. "Orta" ile "Sağ" arasındaki boşluk, "Sol" ile "Orta" arasındaki boşluktan iki kat fazla olur.
Flex Oranları
Column(
children: [
Container(height: 50, color: Colors.red),
Spacer(flex: 1), // 1/4 boşluk
Container(height: 50, color: Colors.blue),
Spacer(flex: 3), // 3/4 boşluk
Container(height: 50, color: Colors.green),
],
)Toplam flex değeri 4 (1+3), ilk boşluk %25, ikinci boşluk %75 alan kaplar.
Pratik Kullanım Örnekleri
Örnek 1: App Bar Benzeri Düzen
Row(
children: [
IconButton(icon: Icon(Icons.menu), onPressed: () {}),
Text('Başlık', style: TextStyle(fontSize: 20)),
Spacer(),
IconButton(icon: Icon(Icons.search), onPressed: () {}),
IconButton(icon: Icon(Icons.more_vert), onPressed: () {}),
],
)Örnek 2: Kart Alt Kısmı
Row(
children: [
Text('Fiyat: ₺99'),
Spacer(),
ElevatedButton(
onPressed: () {},
child: Text('Satın Al'),
),
],
)Örnek 3: Dikey Düzen
Column(
children: [
// Üst içerik
Padding(
padding: EdgeInsets.all(16),
child: Text('Üst İçerik'),
),
Spacer(), // Ortada boşluk
// Alt buton
Padding(
padding: EdgeInsets.all(16),
child: ElevatedButton(
onPressed: () {},
child: Text('Alt Buton'),
),
),
],
)Örnek 4: Üç Bölümlü Düzen
Row(
children: [
Icon(Icons.arrow_back),
Spacer(flex: 1),
Text('Başlık'),
Spacer(flex: 1),
Icon(Icons.settings),
],
)Başlık tam ortada, ikonlar iki yanda eşit uzaklıkta.
Spacer vs SizedBox
SizedBox - Sabit Boşluk
Row(
children: [
Text('Sol'),
SizedBox(width: 20), // Her zaman 20 piksel
Text('Sağ'),
],
)- Sabit boyutta boşluk
- Ekran boyutu değişse bile aynı kalır
Spacer - Esnek Boşluk
Row(
children: [
Text('Sol'),
Spacer(), // Mevcut tüm boşluğu kaplar
Text('Sağ'),
],
)- Mevcut alana göre genişler
- Responsive düzenlerde kullanışlı
Spacer vs Expanded
Spacer aslında Expanded(child: SizedBox()) ile aynı işlevi görür:
Spacer Kullanımı
Row(
children: [
Text('Sol'),
Spacer(),
Text('Sağ'),
],
)Expanded ile Eşdeğeri
Row(
children: [
Text('Sol'),
Expanded(child: SizedBox()),
Text('Sağ'),
],
)Fark: Spacer daha okunabilir ve niyeti daha açık gösterir. Sadece boşluk için Spacer, içerik için Expanded kullanın.
Spacer ile Expanded Birlikte
Row(
children: [
Text('Sabit'),
Spacer(flex: 1),
Expanded(
flex: 2,
child: Container(
color: Colors.blue,
child: Text('Genişleyen'),
),
),
Spacer(flex: 1),
Text('Sabit'),
],
)Boşluklar ve genişleyen içerik birlikte oransal olarak paylaşılır.
⚠️ Önemli Uyarılar
1. Sonsuz Boyutta Kullanmayın
Spacer, sonsuz boyutta ekranlarda ASLA kullanılmamalıdır:
// ❌ YANLIŞ - Hata verir
ListView(
children: [
Text('Üst'),
Spacer(), // HATA! ListView sonsuz yüksekliğe sahip
Text('Alt'),
],
)Neden? ListView gibi scrollable widget'lar sonsuz boyuta sahiptir. Spacer bu durumda ne kadar genişlemesi gerektiğini bilemez.
2. Sınırlı Alan İçinde Kullanın
// ✅ DOĞRU
Container(
height: 300, // Sınırlı yükseklik
child: Column(
children: [
Text('Üst'),
Spacer(),
Text('Alt'),
],
),
)3. SingleChildScrollView ile Dikkatli Olun
// ❌ YANLIŞ
SingleChildScrollView(
child: Column(
children: [
Text('Üst'),
Spacer(), // Sorun çıkarabilir
Text('Alt'),
],
),
)Çözüm: ScrollView içinde Spacer yerine SizedBox kullanın:
// ✅ DOĞRU
SingleChildScrollView(
child: Column(
children: [
Text('Üst'),
SizedBox(height: 100), // Sabit boşluk
Text('Alt'),
],
),
)En Az İki Widget Gerekir
Spacer tek başına veya tek widget ile kullanılamaz:
// ❌ YANLIŞ
Row(
children: [
Spacer(),
Text('Tek widget'),
],
)// ✅ DOĞRU
Row(
children: [
Text('Sol'),
Spacer(),
Text('Sağ'),
],
)mainAxisAlignment ile Karşılaştırma
Spacer yerine bazı durumlarda mainAxisAlignment kullanabilirsiniz:
mainAxisAlignment.spaceBetween
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Text('Sol'),
Text('Sağ'),
],
)Spacer Eşdeğeri
Row(
children: [
Text('Sol'),
Spacer(),
Text('Sağ'),
],
)Fark: Spacer daha esnek, oranlar ile oynayabilirsiniz. mainAxisAlignment daha basit ve önceden tanımlıdır.
Ne Zaman Kullanmalı?
Spacer kullanın:
- İki veya daha fazla widget arasında esnek boşluk istediğinizde
- Boşluk oranlarını kontrol etmek istediğinizde
- Widget'ları iki uca yerleştirmek istediğinizde
- Sınırlı boyutlu container içinde çalışırken
Spacer kullanmayın:
- ListView, GridView gibi scrollable widget'larda
- SingleChildScrollView içinde
- Sonsuz boyutlu alanlarda
- Sabit boşluk yeterli olduğunda (SizedBox kullanın)
Özet
Spacer:
- Row ve Column içinde esnek boşluk oluşturur
flexparametresi ile oransal boşluk dağıtır- En az iki widget arasında kullanılmalıdır
- Sonsuz boyutlu scrollable widget'larda kullanılmamalıdır
Expanded(child: SizedBox())ile eşdeğerdir- Boşluk için tasarlanmıştır, içerik için Expanded kullanın
Altın Kural: Spacer'ı sadece sınırlı boyutlu (bounded) Flex container'larda (Row, Column) kullanın. Scrollable widget'larda kesinlikle kullanmayın!