RelativeLayout‘un özünü açıklıyoruz — Android SDK'da alt öğeleri birbirine veya üst kapsayıcıya göre konumlandırmak için bir ViewGroup. Öğeleri kesin bir sırayla düzenleyen LinearLayout'un aksine, RelativeLayout, herhangi bir öğeyi kimliğine göre başka bir öğenin soluna, sağına, üstüne, altına veya ortasına yerleştirmenize olanak tanır. Bu, RelativeLayout'u iç içe geçirmeden örtüşen ve karmaşık düzenler için kullanışlı hale getirir. Temel kurallar Android Developers dokümantasyonunda açıklanmıştır.
Önemli Noktalar
RelativeLayout — API Level 1'den itibaren Android SDK'ya eklenen, alt öğeleri bildirimsel kurallar (layout rules) aracılığıyla üst öğeye veya diğer alt öğelere göre konumlandıran bir ViewGroup. Her kural, android:layout_above, android:layout_below, android:layout_toLeftOf gibi bir XML niteliği ile hedef öğenin kimliği değeri atanarak ayarlanır.
RelativeLayout ortaya çıkmadan önce, geliştiriciler standart olmayan her konumlandırma için iç içe LinearLayout kullanmak zorundaydı — bu derin iç içe geçmeye ve yavaş işlemeye yol açıyordu. RelativeLayout, tek bir hiyerarşi düzeyinde göreceli konumlandırma sunarak bu sorunu çözdü. Ancak, esnekliği modern ConstraintLayout ile karşılaştırıldığında sınırlıdır: RelativeLayout zincirleri, bariyerleri, kılavuzları veya yüzde tabanlı boyutları desteklemez.
RelativeLayout'un iki temel özelliği vardır: tek bir onMeasure geçişi (weight gerektiren LinearLayout'un aksine, iki geçiş gerektirir) ve bildirim sırasına bağımlılık — A öğesi B öğesine referans veriyorsa ve B, A'dan sonra bildirilmişse, A'nın ölçümü sırasında B'nin boyutu bilinmelidir. Android Developers Guide'a (2024) göre, RelativeLayout, tüm kurallar önceden ölçülmüş öğelere referans veriyorsa ölçümü tek geçişte gerçekleştirir. Aksi takdirde, ikinci bir geçiş gerekir ve bu da performansı düşürür.
RelativeLayout, göreceli konumlandırma gerektiren 3–7 öğeli basit düzenler için uygundur (bir düğmenin üstündeki etiket, metnin sağındaki simge, ekranın altındaki panel). Yeni projeler için ConstraintLayout önerilir, ancak RelativeLayout hâlâ eski kodlarda ve kütüphanelerde yaygın olarak kullanılmaktadır.
RelativeLayout iki tür kural kullanır: relative kuralları (başka bir öğeye göre konumlandırma) ve align kuralları (üst öğeye sabitleme). Her alt öğe sınırsız sayıda kurala sahip olabilir, ancak çakışan kurallar (ör. alignParentTop ve başka bir öğenin below'u) en son bildirilen nitelik lehine çözülür.
Relative kuralları:
- android:layout_above="@id/target" — öğenin alt kenarı, target'ın üst kenarına sabitlenir.
- android:layout_below="@id/target" — öğenin üst kenarı, target'ın alt kenarına sabitlenir.
- android:layout_toLeftOf="@id/target" — sağ kenar, target'ın sol kenarına sabitlenir.
- android:layout_toRightOf="@id/target" — sol kenar, target'ın sağ kenarına sabitlenir.
- android:layout_toStartOf="@id/target" — RTL yerel ayarları için toLeftOf ile benzer.
- android:layout_toEndOf="@id/target" — RTL için toRightOf ile benzer.
Align kuralları (üst öğeye):
- android:layout_alignParentTop="true" — öğenin üst kenarı, üst öğenin üst kenarıyla çakışır.
- android:layout_alignParentBottom="true" — alt kenar, üst öğenin alt kenarıyla çakışır.
- android:layout_alignParentLeft="true" — sol kenar, üst öğenin sol kenarıyla çakışır.
- android:layout_alignParentRight="true" — sağ kenar, üst öğenin sağ kenarıyla çakışır.
- android:layout_alignParentStart ve android:layout_alignParentEnd — RTL için.
Diğer öğelere align kuralları:
- android:layout_alignTop="@id/target" — öğenin üstü, target'ın üstüyle çakışır.
- android:layout_alignBottom, android:layout_alignLeft, android:layout_alignRight, android:layout_alignStart, android:layout_alignEnd — benzer.
- android:layout_alignBaseline="@id/target" — metin taban çizgisine göre hizalama (farklı yazı tipi boyutlarındaki dizeler için kullanışlı).
RelativeLayout'da ortalama üç nitelikle ayarlanır: android:layout_centerInParent="true" (her iki eksende üst öğenin merkezi), android:layout_centerHorizontal="true" (yatay merkez) ve android:layout_centerVertical="true" (dikey merkez). Ortalama diğer kurallarla uyumludur: bir öğe yatay olarak ortalanabilir ve aynı anda üst öğenin alt kenarına sabitlenebilir.
Z sırası (katman sırası) RelativeLayout'da XML'deki öğe bildirim sırasına göre belirlenir. İlk bildirilen öğe ilk çizilir (altta olur), son — son (üstte olur). XML'i değiştirmeden katman sırasını değiştirmeniz gerekiyorsa, android:elevation (API 21'den itibaren) kullanın — daha yüksek elevation'a sahip öğeler üste çizilir. API 21'in altındaki sürümlerde, katman sırası yalnızca bildirim sırasıyla kontrol edilir.
Önemli: RelativeLayout, üst öğe için android:elevation niteliğini desteklemez — her öğe kendi elevation'ını kontrol eder. Konumlandırma kuralları ve elevation çakıştığında (ör. örtüşen öğeler), elevation işleme için önceliklidir, ancak konumlandırma için değildir — daha yüksek elevation'a sahip bir öğe, düzen kuralları onu "arkaya" yerleştirse bile, görsel olarak başka bir öğenin üzerine gelebilir.
Avatar üstte ortalanmış, ad avatarın altında, durum adın altında, işlem düğmesi ekranın altında. Tüm öğeler sıralı sabitleme için relative kurallarını kullanır.
<RelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent">
<ImageView
android:id="@+id/avatar"
android:layout_width="100dp"
android:layout_height="100dp"
android:layout_centerHorizontal="true"
android:layout_marginTop="32dp"
android:src="@drawable/avatar_placeholder" />
<TextView
android:id="@+id/user_name"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_below="@+id/avatar"
android:layout_centerHorizontal="true"
android:layout_marginTop="12dp"
android:text="İvan İvanov"
android:textSize="20sp"
android:textStyle="bold" />
<TextView
android:id="@+id/user_status"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_below="@+id/user_name"
android:layout_centerHorizontal="true"
android:text="Çevrimiçi"
android:textColor="@color/green" />
<Button
android:id="@+id/edit_button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_centerHorizontal="true"
android:layout_marginBottom="24dp"
android:text="Profili düzenle" />
</RelativeLayout>
Avatar, marginTop + centerHorizontal ile üste sabitlenir, ad layout_below ile avatarın altında, durum adın altında ve düğme alignParentBottom ile üst öğenin alt kenarına sabitlenir. Tüm öğeler birbirinden bağımsızdır — zincir veya iç içe geçme yoktur.
Sağ üst köşede kırmızı rozet (sayı içeren daire) bulunan bir simge. Rozet, örtüşme için negatif kenar boşluklarıyla simgenin kenarlarına hizalama yoluyla simgeye göre konumlandırılır.
<RelativeLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content">
<ImageView
android:id="@+id/icon"
android:layout_width="48dp"
android:layout_height="48dp"
android:src="@drawable/ic_notification" />
<TextView
android:id="@+id/badge"
android:layout_width="20dp"
android:layout_height="20dp"
android:layout_alignTop="@+id/icon"
android:layout_alignRight="@+id/icon"
android:layout_marginTop="-6dp"
android:layout_marginRight="-6dp"
android:gravity="center"
android:background="@drawable/badge_background"
android:text="3"
android:textColor="@android:color/white"
android:textSize="10sp" />
</RelativeLayout>
Rozet, simgenin üst ve sağ kenarlarına sabitlenir. Negatif kenar boşlukları (-6dp), rozeti dışa doğru kaydırarak simgenin sınırını örtme etkisi yaratır. Bu, RelativeLayout olmadan FrameLayout veya özel çizim gerektirecek olan bildirimler için popüler bir desendir.
Giriş formu: logo üstte ortalanmış, altında e-posta alanı, e-postanın altında şifre alanı, şifrenin altında "Giriş Yap" düğmesi, "Kaydol" bağlantısı alta sabitlenmiş. Tüm öğeler layout_below ile sıralı olarak sabitlenir.
<RelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:padding="24dp">
<TextView
android:id="@+id/logo"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerHorizontal="true"
android:layout_marginTop="48dp"
android:text="MyApp"
android:textSize="32sp"
android:textStyle="bold" />
<EditText
android:id="@+id/email_input"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_below="@+id/logo"
android:layout_marginTop="32dp"
android:hint="Email" />
<EditText
android:id="@+id/password_input"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_below="@+id/email_input"
android:layout_marginTop="16dp"
android:hint="Şifre"
android:inputType="textPassword" />
<Button
android:id="@+id/login_button"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_below="@+id/password_input"
android:layout_marginTop="24dp"
android:text="Giriş Yap" />
<TextView
android:id="@+id/register_link"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_centerHorizontal="true"
android:layout_marginBottom="16dp"
android:text="Hesabınız yok mu? Kaydolun"
android:textColor="@color/primary" />
</RelativeLayout>
Ekran, tek bir hiyerarşi düzeyinde 5 öğe kullanır. Yukarıdan aşağıya akış (logo → e-posta → şifre → düğme) layout_below ile sağlanır ve bağlantı alignParentBottom ile aşağı itilir. Aynı işlevsellik için LinearLayout, iki iç içe kapsayıcı gerektirirdi (biri üst grup için, diğeri weight ile bağlantı için).
Göreceli konumlandırma için iki ViewGroup'un karşılaştırması: RelativeLayout (klasik, API 1+) ve ConstraintLayout (modern, Jetpack). Kriterler: esneklik, performans, RTL desteği ve uyarlanabilirlik.
| Özellik | RelativeLayout | ConstraintLayout |
|---|---|---|
| Yüzde boyutları | Hayır (sadece sabit ve match_parent) | Evet (width_percent, height_percent, guideline_percent) |
| RTL desteği | start/end ile (API 17+) | Yerleşik |
| Chain / zincirler | Hayır | Evet (spread, spread_inside, packed) |
| Barrier / Group / Flow | Hayır | Evet (sanal yardımcılar) |
| MotionLayout animasyonları | Hayır | Evet |
| onMeasure geçişleri | 1 (bağımlılık döngüsü yoksa) | 2 (her zaman, ancak optimize edilmiş) |
| Ortalama | centerInParent, centerHorizontal, centerVertical | Zıt kısıtlamalarla bias (0.0–1.0) ile |
| Ne zaman kullanılmalı | Eski kod, 3–7 öğeli basit düzenler | Yeni projeler, karmaşık ekranlar, uyarlanabilir düzenler |
RelativeLayout, bir konu dışında neredeyse her açıdan ConstraintLayout'tan daha düşüktür: API 1'den beri Android SDK'ya yerleşiktir ve ek bağımlılık gerektirmez. Hâlâ API 14'ün (Android 4.0) altında minSdk kullanan projeler için RelativeLayout, göreceli konumlandırma için tek standart seçenektir. Diğer tüm durumlarda Google, ConstraintLayout'u önerir.
Sıkça Sorulan Sorular
En olası neden yeterli konumlandırma kuralının olmamasıdır. RelativeLayout'daki her öğenin en az bir yatay kuralı (alignParentLeft, toRightOf, centerHorizontal) ve bir dikey kuralı (alignParentTop, below, centerVertical) olmalıdır. Kural yoksa, öğe (0,0) konumundadır ve diğer öğelerin altında veya ekran dışında gizlenebilir. İkinci neden, döngüsel bir bağımlılıktır (A öğesi B'ye, B öğesi A'ya bağlı), bu da öngörülemeyen davranışa yol açar.
android:layout_centerInParent="true" niteliğini kullanın. Öğeyi her iki eksende aynı anda ortalar. Yalnızca yatay gerekiyorsa — android:layout_centerHorizontal="true", yalnızca dikey — android:layout_centerVertical="true". Ortalama, kenar boşluklarıyla birlikte çalışır — öğe, belirtilen uzaklık kadar merkeze göre kaydırılır.
Evet, ancak önerilmez. RelativeLayout, döngüsel bağımlılıkların varlığında iki onMeasure geçişi gerçekleştirir ve RecyclerView listelerinde ConstraintLayout'tan %15–30 daha yavaştır. RecyclerView öğe düzenleri için ConstraintLayout kullanın — minimum ölçüm süresiyle düz bir hiyerarşi sağlar. RelativeLayout zaten eski bir projede kullanılıyorsa, öğelerin döngüsel bağımlılıklar oluşturmadığından emin olun ve Profile GPU Rendering ile kaydırma FPS'sini ölçün.
android:layout_margin tüm kenarlarda aynı anda kenar boşluğu ayarlar. android:layout_marginTop — yalnızca üstte. Daha spesifik olan nitelik önceliklidir: hem layout_margin (16dp) hem de layout_marginTop (8dp) ayarlanmışsa, üst kenar boşluğu 8dp olur. RelativeLayout'da kenar boşluğu, bitişik öğeye değil kısıtlamaya göre çalışır: layout_below="@id/target" ile layout_marginTop, öğenin üst kenarından target'ın alt kenarına kadar olan boşluktur.
Özet
Anahtar teslim bir mobil uygulama geliştireceğiz
IT Sectr, 2017'den beri girişimler ve işletmeler için iOS ve Android uygulamaları oluşturmaktadır. Size danışmanlık yapacak ve en iyi çözümü önereceğiz.
Ayrıca okuyun