Çekilebilir öğelere genel bakış

"Oluştur" yöntemini deneyin
Jetpack Compose, Android için önerilen kullanıcı arayüzü araç setidir. Compose'da grafiklerin nasıl gösterileceğini öğrenin.

Uygulamanızda statik resimler göstermeniz gerektiğinde şekil çizmek veDrawable resim. Drawable, şunun için genel bir soyutlamadır: çizilebilecek bir şey. Çeşitli alt sınıflar, belirli bir resim konusunda ve bunları genişleterek kendi çekilebilir nesnelerinizi tanımlayabilirsiniz. davranış biçimleri vardır.

Sınıf oluşturucuları kullanmanın yanı sıra bir Drawable öğesini tanımlamanın ve örneklendirmenin iki yolu vardır:

  • Projenize kaydedilen bir resim kaynağını (bit eşlem dosyası) şişirin.
  • Çekilebilir özellikleri tanımlayan bir XML kaynağını şişirin.

Not: Bunun yerine, noktaları, çizgileri ve eğrileri ve bunlarla ilişkili renk bilgilerini gösterir. Bu şekilde, vektörel çizimlere izin verilir ölçeklendirilmesine neden olabilir. Daha fazla bilgi için bkz. Vektör çizimlere genel bakış bölümüne göz atın.

Kaynak görüntülerden çekilebilir öğeler oluşturma

Uygulamanızdan bir resim dosyasına başvurarak uygulamanıza grafik ekleyebilirsiniz etkili müzakere becerilerini kullanacaksınız. Desteklenen dosya türleri PNG (tercih edilen), JPG (kabul edilebilir), ve GIF (önerilmez). Uygulama simgeleri, logolar ve diğer grafikler (kullanılanlar gibi) bu tekniğe çok uygundur.

Resim kaynağı kullanmak için dosyanızı res/drawable/ dizin oluşturun. Projenize girdikten sonra görüntüye referans verebilirsiniz. kaynak kodu kullanabilirsiniz. Her iki durumda da, kaynak kimliği (dosya türü uzantısı olmadan dosya adıdır). Örneğin, my_image.png öğesine my_image olarak bakın.

Not: Resim kaynakları res/drawable/ dizini şununla otomatik olarak optimize edilebilir: oluşturma sırasında aapt aracı tarafından kayıpsız resim sıkıştırma bahsedeceğim. Örneğin, 256'dan fazla renk gerektirmeyen gerçek renkli bir PNG dosyası renk paletine sahip 8 bitlik bir PNG'ye dönüştürülebilir. Bu işlem, bir resimle sonuçlanır Bu da daha az bellek gerektirir. Sonuç olarak, resim ikili programları derleme sırasında değişebilir. Bir dönüştürmek için resimlerinizi bit eşlem olarak kullanın, resimlerinizi res/raw/ klasörü (aapt aracı şunları yapmaz) bu bilgileri değiştirebilirsiniz.

Aşağıdaki kod snippet'i,ImageView Çekilebilir bir kaynaktan oluşturulan bir görüntü ve bunu düzene ekler:

Kotlin

private lateinit var constraintLayout: ConstraintLayout

override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)

    // Instantiate an ImageView and define its properties
    val i = ImageView(this).apply {
        setImageResource(R.drawable.my_image)
        contentDescription = resources.getString(R.string.my_image_desc)

        // set the ImageView bounds to match the Drawable's dimensions
        adjustViewBounds = true
        layoutParams = ViewGroup.LayoutParams(
                ViewGroup.LayoutParams.WRAP_CONTENT,
                ViewGroup.LayoutParams.WRAP_CONTENT)
    }

    // Create a ConstraintLayout in which to add the ImageView
    constraintLayout = ConstraintLayout(this).apply {

        // Add the ImageView to the layout.
        addView(i)
    }

    // Set the layout as the content view.
    setContentView(constraintLayout)
}

Java

ConstraintLayout constraintLayout;

protected void onCreate(Bundle savedInstanceState) {
  super.onCreate(savedInstanceState);

  // Create a ConstraintLayout in which to add the ImageView
  constraintLayout = new ConstraintLayout(this);

  // Instantiate an ImageView and define its properties
  ImageView i = new ImageView(this);
  i.setImageResource(R.drawable.my_image);
  i.setContentDescription(getResources().getString(R.string.my_image_desc));

  // set the ImageView bounds to match the Drawable's dimensions
  i.setAdjustViewBounds(true);
  i.setLayoutParams(new ViewGroup.LayoutParams(
          ViewGroup.LayoutParams.WRAP_CONTENT,
          ViewGroup.LayoutParams.WRAP_CONTENT));

  // Add the ImageView to the layout and set the layout as the content view.
  constraintLayout.addView(i);
  setContentView(constraintLayout);
}

Diğer durumlarda, resim kaynağınızı aşağıda gösterildiği gibi bir Drawable nesnesi olarak kullanmak isteyebilirsiniz. örnek:

Kotlin

val myImage: Drawable = ResourcesCompat.getDrawable(context.resources, R.drawable.my_image, null)

Java

Resources res = context.getResources();
Drawable myImage = ResourcesCompat.getDrawable(res, R.drawable.my_image, null);

Uyarı: Projenizdeki her benzersiz kaynak kaç farklı nesne olursa olsun, yalnızca tek bir örneklendirirsiniz. Örneğin, aynı görüntü kaynağından iki Drawable nesnesini örneklendirir ve bir nesne için bir özelliği (alfa gibi) değiştirirseniz bu değişiklik, diğeri. Bir görüntü kaynağının birden fazla örneğiyle çalışırken Drawable nesnesini doğrudan dönüştürmenin bir yolu. tweet animasyon ekleyin.

Aşağıdaki XML snippet'i, XML düzeninde bir ImageView öğesine çekilebilir bir kaynağın nasıl ekleneceğini gösterir:

<ImageView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:src="@drawable/my_image"
        android:contentDescription="@string/my_image_desc" />

Proje kaynaklarını kullanma hakkında daha fazla bilgi için Kaynaklar ve öğeler bölümüne bakın.

Not: Çekilebilir videolarınızın kaynağı olarak resim kaynaklarını kullanıyorsanız Resimlerin çeşitli piksel yoğunlukları için uygun boyutta olduğundan emin olun. Öğe resimlerin doğru olmaması nedeniyle, resimler sığacak şekilde ölçeklendirilir. Bu da, çekilebilir resimlerinizde yapıya neden olabilir. Daha fazla bilgi için Destek farklı piksel yoğunlukları.

XML kaynaklarından çekilebilir öğeler oluşturma

Drawable varsa oluşturmak istediğiniz bir nesnedir. Bu nesne, başlangıçta kod veya kullanıcı etkileşimi söz konusuysa, Drawable öğesini XML'de tanımlamak iyi bir seçenektir. Eşit Kullanıcı etkileşimi sırasında Drawable öğenizin özelliklerini değiştirmesini bekliyorsanız uygulamanızla kullanmayı tercih ederseniz, nesneyi XML'de tanımlamayı düşünmeniz gerekir, çünkü daha sonra özellikleri örneklendirilir.

Drawable öğenizi XML'de tanımladıktan sonra dosyayı Projenizin res/drawable/ dizini. Aşağıdaki örnekte, bir TransitionDrawable. Drawable kaynağından devralan kaynak:

<!-- res/drawable/expand_collapse.xml -->
<transition xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:drawable="@drawable/image_expand"/>
    <item android:drawable="@drawable/image_collapse"/>
</transition>

Ardından, şunu çağırarak nesneyi alın ve örneklendirin: Resources#getDrawable(). ve XML dosyanızın kaynak kimliğini iletme hakkında bilgi edinin. Herhangi biri Drawable alt sınıf inflate() yöntemini destekleyen bir işlev XML'de tanımlanabilir ve örneklenebilir elde edebilirsiniz.

XML şişirmeyi destekleyen her çekilebilir sınıf, belirli XML özelliklerini kullanır başka faydalı grafiklerdir. Aşağıdaki kod, TransitionDrawable. ve bunu bir videodaki ImageView nesne:

Kotlin

val transition= ResourcesCompat.getDrawable(
        context.resources,
        R.drawable.expand_collapse,
        null
) as TransitionDrawable

val image: ImageView = findViewById(R.id.toggle_image)
image.setImageDrawable(transition)

// Description of the initial state that the drawable represents.
image.contentDescription = resources.getString(R.string.collapsed)

// Then you can call the TransitionDrawable object's methods.
transition.startTransition(1000)

// After the transition is complete, change the image's content description
// to reflect the new state.

Java

Resources res = context.getResources();
TransitionDrawable transition =
    (TransitionDrawable) ResourcesCompat.getDrawable(res, R.drawable.expand_collapse, null);

ImageView image = (ImageView) findViewById(R.id.toggle_image);
image.setImageDrawable(transition);

// Description of the initial state that the drawable represents.
image.setContentDescription(getResources().getString(R.string.collapsed));

// Then you can call the TransitionDrawable object's methods.
transition.startTransition(1000);

// After the transition is complete, change the image's content description
// to reflect the new state.

Desteklenen XML özellikleri hakkında daha fazla bilgi için listelenenler gibi.

Şekil çekilebilir öğeleri

ShapeDrawable nesnesi iyi bir seçenek olabilir iki boyutlu grafik çizmek istediğinizde Şunları yapabilirsiniz: bir ShapeDrawable nesnesi üzerinde programatik olarak temel şekiller çizin ve uygulamanızın ihtiyacı olan stilleri uygulayın.

ShapeDrawable, Drawable sınıfının bir alt sınıfıdır. Bu nedenle, Drawable beklenen her yerde ShapeDrawable. Örneğin, Örneğin, arka planı ayarlamak için bir ShapeDrawable nesnesi kullanabilirsiniz setBackgroundDrawable() yöntemine geçirerek söz konusu görünümün görünümlerini değiştirebilirsiniz. Şeklinizi uygulamanızdaki bir düzene ekleyebilirsiniz.

ShapeDrawable kendi draw() yöntemine sahip olduğundan, bir ShapeDrawable çeken View alt sınıfı onDraw() etkinliği sırasında nesne (aşağıda gösterildiği gibi) aşağıdaki kod örneği:

Kotlin

class CustomDrawableView(context: Context) : View(context) {
    private val drawable: ShapeDrawable = run {
        val x = 10
        val y = 10
        val width = 300
        val height = 50
        contentDescription = context.resources.getString(R.string.my_view_desc)

        ShapeDrawable(OvalShape()).apply {
            // If the color isn't set, the shape uses black as the default.
            paint.color = 0xff74AC23.toInt()
            // If the bounds aren't set, the shape can't be drawn.
            setBounds(x, y, x + width, y + height)
        }
    }

    override fun onDraw(canvas: Canvas) {
        drawable.draw(canvas)
    }
}

Java

public class CustomDrawableView extends View {
  private ShapeDrawable drawable;

  public CustomDrawableView(Context context) {
    super(context);

    int x = 10;
    int y = 10;
    int width = 300;
    int height = 50;
    setContentDescription(context.getResources().getString(
            R.string.my_view_desc));

    drawable = new ShapeDrawable(new OvalShape());
    // If the color isn't set, the shape uses black as the default.
    drawable.getPaint().setColor(0xff74AC23);
    // If the bounds aren't set, the shape can't be drawn.
    drawable.setBounds(x, y, x + width, y + height);
  }

  protected void onDraw(Canvas canvas) {
    drawable.draw(canvas);
  }
}

Kod örneğinde CustomDrawableView sınıfını kullanabilirsiniz olduğu gibi kullanabilirsiniz. Örneğin, şunları yapabilirsiniz: aşağıda gösterildiği gibi uygulamanızdaki bir etkinliğe programatik olarak ekleyebilirsiniz örnek:

Kotlin

private lateinit var customDrawableView: CustomDrawableView

override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    customDrawableView = CustomDrawableView(this)

    setContentView(customDrawableView)
}

Java

CustomDrawableView customDrawableView;

protected void onCreate(Bundle savedInstanceState) {
  super.onCreate(savedInstanceState);
  customDrawableView = new CustomDrawableView(this);

  setContentView(customDrawableView);
}

Bunun yerine XML düzeninde özel görünümü kullanmak isterseniz CustomDrawableView sınıfı, sınıf değiştirildiğinde çağrılan View(Context, AttributeSet) oluşturucusunu geçersiz kılmalıdır. XML'den şişirilmiş bir biçimde görünür. Aşağıdaki örnekte, XML düzeninde CustomDrawableView:

<com.example.shapedrawable.CustomDrawableView
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        />

Diğer birçok sınıf gibi ShapeDrawable sınıfı android.graphics.drawable paketindeki çekilebilir türler, herkese açık yöntemler kullanarak nesnenin çeşitli özelliklerini tanımlayabilir. Bir örnek ayarlamak isteyebilirsiniz. Örneğin, alfa şeffaflığı, renk filtresi, dither, opaklık ve renk.

Ayrıca, XML kaynaklarını kullanarak temel çekilebilir şekilleri tanımlayabilirsiniz. Daha fazla (bkz. ) dilinde çekilebilir şekil Çekilebilir kaynak türleri.

NinePatch çekilebilir öğeleri

NinePatchDrawable grafiği, bir görünümün arka planı olarak kullanabileceğiniz uzatılabilir bit eşlem resmi. Android grafiği, görünümün içeriğine uyacak şekilde otomatik olarak yeniden boyutlandırır. örnek olarak standart Android tarafından kullanılan arka planın NinePatch resmi kullanımı düğmeler: Düğmeler, çeşitli uzunluklardaki dizeleri içerebilecek şekilde uzatılmalıdır. CEVAP NinePatch grafiği, fazladan 1 piksel kenarlık içeren standart bir PNG resmidir. 9.png uzantısıyla birlikte Projenizin res/drawable/ dizini.

Resmin uzatılabilir ve statik alanlarını tanımlamak için kenarlığı kullanın. 1 piksel genişliğinde bir (veya daha fazla) çizerek uzatılabilir bir bölümü belirtirsiniz kenarlığın sol ve üst tarafında siyah çizgiler (diğer kenarlık pikselleri) tamamen şeffaf veya beyaz olmalıdır). Google Etiket Yöneticisi'nde istediğiniz gibi değiştirebilirsiniz. Esnek bölümlerin göreceli boyutu aynı kalır. en büyük bölüm her zaman en büyük bölüm olarak kalır.

Ayrıca resmin isteğe bağlı bir çekilebilir bölümünü de tanımlayabilirsiniz (etkili biçimde dolgu çizgileri) sağa ve alta bir çizgi çizin. View nesnesi, NinePatch grafiğini arka plan olarak ayarlıyor görünüm metnini belirtir ve kendisini uzatır. Böylece tüm metin yalnızca sağ ve alt satırlarla (varsa) belirtilen alanı kaplar. Dolgu çizgileri eklenmezse Android, aşağıdaki işlemleri yapmak için sol ve üst satırları kullanır: tanımlayabilirsiniz.

Satırlar arasındaki farkı netleştirmek için, sol ve üst satırlar uzatmak için resmin hangi piksellerinin çoğaltılmasına izin verildiğini görüntüsüdür. Alt ve sağ çizgiler resmin içindeki bu orantısal alanı görünüm içeriğinin işgal edilmesine izin verilir.

Şekil 1'de bir düğmeyi tanımlamak için kullanılan NinePatch grafiği örneği gösterilmektedir:

Uzatılabilir alan resmi
ve dolgu kutusu

Şekil 1: NinePatch grafiği örneği bir düğmeyi tanımlayan

Bu NinePatch grafiğinde, sol ve üst taraf olmak üzere bir uzatılabilir alan tanımlanmaktadır çerçeveleri, alt ve sağ çizgileri gösteren çekilebilir alanı da içerir. Üstteki resimde noktalı gri çizgiler, resmin kopyalanan bölgelerini gösterir kullanarak resmi esnetin. Alttaki resimdeki pembe dikdörtgen, görünümün içeriğine izin verilen bölge. İçerikler uyumlu değilse resim, bu bölgeye sığacak şekilde uzatılır.

9 yama çizin aracı, WYSIWYG grafiklerini kullanarak NinePatch resimlerinizi oluşturmanın son derece pratik yardımcı olur. Hatta, esnek çalışma için belirlediğiniz bölge, alanı, piksel nedeniyle çizim kusurları oluşturma riskiyle karşı karşıyadır kopyalama.

Aşağıdaki örnek düzen XML'i, NinePatch grafiğinin nasıl ekleneceğini gösterir ekleyebilirsiniz. NinePatch resmi şuraya kaydedilir: res/drawable/my_button_background.9.png

<Button android:id="@+id/tiny"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentTop="true"
        android:layout_centerInParent="true"
        android:text="Tiny"
        android:textSize="8sp"
        android:background="@drawable/my_button_background"/>

<Button android:id="@+id/big"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentBottom="true"
        android:layout_centerInParent="true"
        android:text="Biiiiiiig text!"
        android:textSize="30sp"
        android:background="@drawable/my_button_background"/>

layout_width ve layout_height özellikleri, düğmenin düzgün sığması için wrap_content olarak ayarlandı etrafına bakın.

Şekil 2'de XML ve NinePatch görüntüsünden oluşturulan iki düğme gösterilmektedir aşağıda gösterildiği gibidir. Düğmenin genişliğinin ve yüksekliğinin metne göre nasıl değiştiğine dikkat edin. ve arka plan resmi buna uyum sağlayacak şekilde genişliyor.

Küçük ve resmin resmi
normal boyutlu düğmeler

Şekil 2: XML kullanılarak oluşturulan düğmeler kaynak ve NinePatch grafiği

Özel çekilebilir öğeler

Bazı özel çizimler oluşturmak istediğinizde, Drawable sınıfını (veya alt sınıflarından herhangi birini) genişleterek bunu yapabilirsiniz.

Uygulanacak en önemli yöntem draw(Canvas) çünkü bu, sağlamak için kullanmanız gereken Canvas nesnesini sağlar eklemeyi deneyin.

Aşağıdaki kodda basit bir Drawable alt sınıfı gösterilmektedir şöyle bir şey çizer:

Kotlin

class MyDrawable : Drawable() {
    private val redPaint: Paint = Paint().apply { setARGB(255, 255, 0, 0) }

    override fun draw(canvas: Canvas) {
        // Get the drawable's bounds
        val width: Int = bounds.width()
        val height: Int = bounds.height()
        val radius: Float = Math.min(width, height).toFloat() / 2f

        // Draw a red circle in the center
        canvas.drawCircle((width / 2).toFloat(), (height / 2).toFloat(), radius, redPaint)
    }

    override fun setAlpha(alpha: Int) {
        // This method is required
    }

    override fun setColorFilter(colorFilter: ColorFilter?) {
        // This method is required
    }

    override fun getOpacity(): Int =
        // Must be PixelFormat.UNKNOWN, TRANSLUCENT, TRANSPARENT, or OPAQUE
        PixelFormat.OPAQUE
}

Java

public class MyDrawable extends Drawable {
    private final Paint redPaint;

    public MyDrawable() {
        // Set up color and text size
        redPaint = new Paint();
        redPaint.setARGB(255, 255, 0, 0);
    }

    @Override
    public void draw(Canvas canvas) {
        // Get the drawable's bounds
        int width = getBounds().width();
        int height = getBounds().height();
        float radius = Math.min(width, height) / 2;

        // Draw a red circle in the center
        canvas.drawCircle(width/2, height/2, radius, redPaint);
    }

    @Override
    public void setAlpha(int alpha) {
        // This method is required
    }

    @Override
    public void setColorFilter(ColorFilter colorFilter) {
        // This method is required
    }

    @Override
    public int getOpacity() {
        // Must be PixelFormat.UNKNOWN, TRANSLUCENT, TRANSPARENT, or OPAQUE
        return PixelFormat.OPAQUE;
    }
}

Ardından, çekilebilir öğenizi istediğiniz yere ekleyebilirsiniz. Örneğin, Burada gösterildiği gibi ImageView:

Kotlin

val myDrawing = MyDrawable()
val image: ImageView = findViewById(R.id.imageView)
image.setImageDrawable(myDrawing)
image.contentDescription = resources.getString(R.string.my_image_desc)

Java

MyDrawable mydrawing = new MyDrawable();
ImageView image = findViewById(R.id.imageView);
image.setImageDrawable(mydrawing);
image.setContentDescription(getResources().getString(R.string.my_image_desc));

Android 7.0 (API düzeyi 24) ve sonraki sürümlerde, özel çekilebilir öğenizin örneklerini de tanımlayabilirsiniz aşağıdaki yöntemlerle XML ile değiştirebilirsiniz:

  • XML öğe adı olarak tam sınıf adını kullanma. Bu yaklaşımda, özel çekilebilir sınıf, herkese açık üst düzey bir sınıf olmalıdır:
    <com.myapp.MyDrawable xmlns:android="http://schemas.android.com/apk/res/android"
        android:color="#ffff0000" />
    
  • XML etiketi adı olarak drawable kullanma ve tam sınıfı belirtme adını yazın. Bu yaklaşım hem herkese açık üst düzey sınıflarda hem de genel statik iç sınıflar:
    <drawable xmlns:android="http://schemas.android.com/apk/res/android"
        class="com.myapp.MyTopLevelClass$MyDrawable"
        android:color="#ffff0000" />
    
ziyaret edin.

Çekilebilir öğelere tonlama ekleyin

Android 5.0 (API düzeyi 21) ve sonraki sürümlerde, bit eşlemlere ve kullanılmasını istiyoruz. Temaları renge dönüşen renk kaynakları veya tema özellikleriyle renklendirebilirsiniz kaynaklar (örneğin, ?android:attr/colorPrimary). Bu öğeleri genelde ve temanıza uyacak şekilde otomatik olarak renklendirebilirsiniz.

BitmapDrawable, NinePatchDrawable veya VectorDrawable için tonlama uygulayabilirsiniz nesneleri setTint() yöntemi ile değiştirin. Şunları yapabilirsiniz: ton rengini ve modunu da düzenlerinizde android:tint ve android:tintMode özellikleri.

Resimden belirgin renkleri çıkarabilirsiniz

Android Destek Kitaplığı, bir resimden belirgin renkler çıkarmanızı sağlayan Palette sınıfını içerir. Çekilebilir öğelerinizi Bitmap olarak yükleyebilir ve renklerine erişmek için Palette uygulamasına aktarabilirsiniz. Daha fazla bilgi için Aşağıdakileri kullanarak renk seçme: Palet API.