setBackground vs setBackgroundDrawable (Android)


258

Bir görünümün çizilebilir arka planını ayarlamak istiyorum. Bunun için iki yöntem var (gördüğüm kadarıyla): setBackgroundve setBackgroundDrawable.

Kullandığımda setBackground, API seviye 16'da eklendiğini söylüyor, ancak projemin min SDK sürümü 7. Ancak setBackgroundDrawable'ı kullandığımda, kullanımdan kaldırıldığını söylüyor.

Ne kullanmam gerekiyor?


Kullanın: image.setImageResource (R.drawable.icon_dot1);
Cesur

Yanıtlar:


403

Kullanımdan kaldırıldı, ancak yine de kullanılabilir, böylece sadece kullanabilirsiniz. Ama tamamen doğru olmak istiyorsanız, sadece bunun tamlığı için ... Aşağıdaki gibi bir şey yaparsınız:

int sdk = android.os.Build.VERSION.SDK_INT;
if(sdk < android.os.Build.VERSION_CODES.JELLY_BEAN) {
    setBackgroundDrawable();
} else {
    setBackground();
}

Bunun çalışması için buildTarget api 16 ve min build'i 7 veya benzeri bir değere ayarlamanız gerekir.


4
Hala setBackgroundDrawable'ın kullanımdan kaldırılmasından şikayet ediyor. Google'ın yöntem adını değiştirmek istediği için uyarıları gerçekten bastırmam gerekiyor mu?
Charlie-Blake

2
@ santirivera92 Evet, alternatif olarak sorun çıkmadan önce 1 ve sonra 1 hedefleme olmak üzere 2 proje oluşturabilirsiniz. Bu kolay bir seçenek gibi mi geliyor? (Aslında bazen ICS'de pek çok düzeltme)
Warpzit

4
Ayarladım android:minSdkVersion="7" android:targetSdkVersion="17", ancak setBackground () hata olarak çıkıyor: Çağrı API seviye 16 gerektiriyor (geçerli min 7)
Jonny

20
Derlememi engelledi. Sorunlu kodu kendi işlevine koydum ve sadece bu işlev için tiftiği devre dışı bıraktım. @TargetApi(Build.VERSION_CODES.JELLY_BEAN) @SuppressWarnings("deprecation") private static void setBg(RelativeLayout layout, BitmapDrawable TileMe) { if (android.os.Build.VERSION.SDK_INT < android.os.Build.VERSION_CODES.JELLY_BEAN) { layout.setBackgroundDrawable(TileMe); } else { layout.setBackground(TileMe); } }
Jonny

2
@Snicolas Evet, IDE veya Android bizim için bu tür bir mantık yapabilmelidir.
Warpzit

111

Bunun setBackgroundResource()yerine API seviye 1'de kullanabilirsiniz.


78
... ancak oluşturduğunuz özel bir çekilebilir sınıf değil, bir kaynak kimliği varsa!
Zordid

referansınız olan bir çekmecenin kimliğini almak için bir yöntem yok mu?
Poutrathor

2
setBackgroundResource (), setBackgroundDrawable () işlevine alternatif değildir; veya setBackground () ;. Hiç alakalı değil, ilk kaynak çekilebilir eklemek ve diğerleri CUSTOM çekilebilir eklemek için.
MBH

Liste görünümünde arka planı tekrar tekrar ayarlamam gerekirse ne olur? setBackgroundResource(int)kaynak kimliğini kabul ettiğinden, arka planı ayarlamak için her seferinde görünümü şişirmek zorundadır. Zaten Drawable şişirilmiş varsayalım, böyle bir davranış istemiyorum. Bir şey mi kaçırıyorum?
azizbekian

sadece çekmecem varsa ne olacak?
MBH

55

gösterildiği gibi şu anda 2 işlevler arasında hiçbir fark yoktur gibi görünüyor kaynak koduna (kredi bu yazı ):

public void setBackground(Drawable background) {
    //noinspection deprecation
    setBackgroundDrawable(background);
}

@Deprecated
public void setBackgroundDrawable(Drawable background) { ... }

bu yüzden dolgu-ebeveyn ile maç-ebeveyn arasındaki karara benzer bir adlandırma kararıdır.


5
harika! Teşekkürler. Aptalca bir işlev yeniden adlandırma gibi topal bir şey için bir uyarı üretilir.
Bir Yerde

1
@ M.kazemAkhgary Bir şeyi sadece isim değişikliği için ilk kez kullanımdan kaldırmıyorlar. Düzen parametresi değerleri için "dolgu_parent" olarak "match_parent" olarak değiştirildiler. Her ikisi de tamamen aynı şey, aynı değere işaret ..
android geliştirici

18

bunun eski bir soru olduğunu biliyorum ama benzer bir durumum var ve benim çözümüm

button.setBackgroundResource( R.drawable.ic_button );
Drawable d = button.getBackground();

ve sonra "Çizilebilir" ile oynayabilir, renk filtreleri uygulayabilir vb.


6
Bu yalnızca orijinal görüntü bir kaynaktan geliyorsa çalışır.
Matt Huggins

Bu OP'nin sorusuna bile cevap vermiyor.
Petro

13

kullanım ViewCompat.setBackground(view, background);


12

setBackgroundResource()bunun yerine kullanabilirsinizrelativeLayout.setBackgroundResource(R.drawable.back);

bu benim için çalışıyor.


7

Artık bu seçeneklerden birini kullanabilirsiniz. Ve her durumda işe yarayacak. Renginiz bir HEX kodu olabilir , örneğin:

myView.setBackgroundResource(ContextCompat.getColor(context, Color.parseColor("#FFFFFF")));

Bunun gibi bir renk kaynağı :

myView.setBackgroundResource(ContextCompat.getColor(context,R.color.blue_background));

Veya şu şekilde özel bir xml kaynağı :

myView.setBackgroundResource(R.drawable.my_custom_background);

Umarım yardımcı olur!


6

Android studio 1.5.1 kullanarak aşağıdaki uyarıları aldım:

Call requires API level 16 (current min is 9): android.view.View#setBackground

ve kullanımdan kaldırma şikayetleri

'setBackgroundDrawable(android.graphics.drawable.Drawable)' is deprecated

Bu biçimi kullanarak, her ikisinden de kurtuldum:

    if (android.os.Build.VERSION.SDK_INT < android.os.Build.VERSION_CODES.JELLY_BEAN) {
        //noinspection deprecation
        layout.setBackgroundDrawable(drawable);
    } else {
        layout.setBackground(drawable);
    }

1

Bu benim için çalışıyor: Görünüm görünümü sizin editText, spinner ... vb. Ve int çekilebilir sizin çekilebilir rota örneğidir (R.drawable.yourDrawable)

 public void verifyDrawable (View view, int drawable){

        int sdk = Build.VERSION.SDK_INT;

        if(sdk < Build.VERSION_CODES.JELLY_BEAN) {
            view.setBackgroundDrawable(
                    ContextCompat.getDrawable(getContext(),drawable));
        } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
            view.setBackground(getResources().getDrawable(drawable));
        }    
    }


-2

Ayrıca bu sorun vardı, ama bir ImageView kullanarak bir geçici çözüm yaptı .

Bir RelativeLayout kullanmayı deneyin ve içine bir ImageView ekleyin (width ve height: fill_parent, scaleType: center).

Ayrıca , görüntülemenin RelativeLayout içindeki ilk öğe olduğundan emin olun , böylece arka plan görevi görür.


1
Aslında bir ifmaddeden başka bir şey olmamalıydı . Doğru cevaba bakınız.
Pijusn

-4

Bunu da yapabilirsiniz:

try {
     myView.getClass().getMethod(android.os.Build.VERSION.SDK_INT >= 16 ? "setBackground" : "setBackgroundDrawable", Drawable.class).invoke(myView, myBackgroundDrawable);
} catch (Exception ex) {
     // do nothing
}

EDIT: @BlazejCzapp tarafından işaret edildiği gibi, sorunu onsuz çözmeyi başarabilirseniz yansıma kullanmaktan kaçınmak tercih edilir. Yansıması olmadan çözemediğim bir kullanım durumum vardı, ancak bu durum böyle değil. Daha fazla bilgi için lütfen http://docs.oracle.com/javase/tutorial/reflect/index.html adresine bakın.


4
@BlazejCzapp LOL, ancak soruyu cevaplıyor, bu yüzden açıklama yapılmadan indirilmemelidir. Bir çocuğa neden bunu yapacaklarını söylemeden bir şey yapmamasını söylediğinizde;)
Fabricio

11
Konudan çıkmak istemiyorum, ancak bazı nedenler şunlardır: 1. Java statik olarak yazılmış bir dildir - derleyiciyi kullanın; 2. Bu sadece kılık değiştirmiş bir if ifadesidir (gerçek mantığı şaşırtmaktadır); 3. Bir sivrisinek öldürmek için bir top getiriyor - bu kod önemsiz bir sorunu çözmek için ciddi toplar kullanıyor; Biraz haklı umut
Błażej Czapp

Teşekkürler @ BlazejCzapp, haklısın, burada yukarıdaki kod gibi şeyler yapmak için gerekli bir kullanım durumu vardı ama bunu işlemek için uygun bir yol varsa kullanılmamalıdır.
Fabricio

2
Bu aptalca ... Bunu başarmak için yansımayı kullanmak için kesinlikle hiçbir sebep yok.
Alex Lockwood

Evet, "Ne kullanmam gerekiyor?" çalışma zamanını değiştirmeye başlayın.
Petro
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.