Ölçeklendirmeden katman listesinde vektör çekilebilir vektör nasıl ortalanır


104

Vektörü ölçeklendirmeden bir VectorDrawablein a kullanmaya çalışıyorum LayerList. Örneğin:

<layer-list>
    <item android:drawable="@color/grid_item_activated"/>
    <item android:gravity="center" android:drawable="@drawable/ic_check_white_48dp"/>
</layer-list>

Çekilebilir ic_check_white_48dpkimlik şu şekilde tanımlanır:

<vector xmlns:android="http://schemas.android.com/apk/res/android"
        android:width="48dp"
        android:height="48dp"
        android:viewportWidth="24.0"
        android:viewportHeight="24.0">
    <path
        android:fillColor="#FFFFFFFF"
        android:pathData="M9,16.17L4.83,12l-1.42,1.41L9,19 21,7l-1.41,-1.41z"/>
</vector>

İstenen efekt, onay simgesinin ölçeklendirme olmadan çekilebilir katman içinde ortalanmasıdır. Sorun şu ki, yukarıdaki katman listesi, onay simgesinin katman boyutuna sığacak şekilde ölçeklenmesine neden oluyor.

I olabilir Her yoğunluk PNG vektör çekilebilir yerine ve bu şekilde tabaka listeyi değiştirmek, istenen etkiyi üretmek:

<layer-list>
    <item android:drawable="@color/grid_item_activated"/>
    <item>
        <bitmap android:gravity="center" android:src="@drawable/ic_check_white_48dp"/>
    </item>
</layer-list>

Bunu a kullanarak yapmamın bir yolu var mı VectorDrawable?


11
Görünüşe göre bu, API 21 / 22'deki bir hata olabilir. Bir API 23 cihazında test ettim ve vektör çizimi doğru şekilde ortalandı.
ashughes

1
Kendi sorunuzu cevaplamalı ve kabul etmelisiniz. Bu şekilde daha görünür hale gelir ve soru cevapsız olarak görünmez.
Marcin Koziński

1
Soruma cevap vermedim çünkü API 21 / 22'de ne yapacağım konusunda henüz bir cevabım yok. Geçici çözümüm vektörler yerine PNG kullanmaktı. Yine de vektörleri çalıştırmanın bir yolunu bulmayı umuyorum.
ashughes


Bu, API 23'te zaten düzeltildi, bu nedenle hata raporunuzun düzeltildi olarak işaretleneceğini tahmin ediyorum.
ashughes

Yanıtlar:


30

Çekilebilir vektörleri katmanlı bir listede ortalamaya çalışırken aynı problemle karşılaştım.

Bir çözümüm var, tam olarak aynı değil ama işe yarıyor, tüm çekilebilir öğe için bir boyut ayarlamanız ve vektör öğesine dolgu eklemeniz gerekiyor:

<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
    <item>
        <shape>
            <size android:height="120dp" android:width="120dp"/>
            <solid android:color="@color/grid_item_activated"/>
        </shape>
    </item>
    <item android:top="24dp"
          android:bottom="24dp"
          android:left="24dp"
          android:right="24dp"
          android:drawable="@drawable/ic_check_white_48dp"/>
</layer-list>

Yukarıdaki şeklin boyutu, tüm çekilebilir ürünün boyutunu belirler, bu örnekte 120 dp, ikinci öğedeki dolgu, bu örnekte 24 dp, vektör görüntüsünü ortalar.

gravity="center"API 21 ve 22'deki vektörleri kullanmakla aynı şey değil .


2
Bu, içinde ortalanmış çek çekmecesi ile ayarlandığı tüm alanı doldurmasına izin vermek yerine, (şekil boyutunu ayarlamak için) çekilebilirin tam boyutunu bilmenizi gerektirecek gibi görünüyor.
ashughes

1
boyutu bilmemek mümkündür ancak bu yöntemle dolguyu değiştiremezsiniz, resim görünümlerinde çekilebilir öğeleri üst üste katmanlayabilirsiniz. Yukarıda belirttiğim gibi gravity="center", API 21 ve 22'de a için mükemmel bir çözüm yok .
Nicolas Tyler

İle kullanıldığında çalışmıyor windowBackground. Bu durumda açık boyutlar hiçbir şey yapmaz. Ve katman listesini başka bir katman listesine koyarsam da çalışmıyor.
Vsevolod Ganin

20

Aynı problemle mücadele ediyorum. Bunu düzeltmenin ve ölçek büyütmekten kaçınmanın tek yolu, çekilebilir boyutu ayarlamak ve onu hizalamak için yerçekimi kullanmaktı:

<layer-list>
    <item android:drawable="@color/grid_item_activated"/>
     <item
        android:gravity="center"
        android:width="48dp"
        android:height="48dp"
        android:drawable="@drawable/ic_check_white_48dp"/>
</layer-list>

Umarım yardımcı olur!


34
Bu, API 21-22'de yardımcı olmaz, çünkü widthöznitelik bu API seviyelerinde mevcut değildir. API 23'te bunlar gerekli değildir, çünkü hata düzeltilmiştir ve çekilebilirlik artık uzatılmamaktadır.
WonderCsabo

3
Bu API 27 için doğru çalışmıyor, görüntü tam ekrana
uzatılıyor

8

SplashScreen'inizin API21'den API23'e kadar tüm API'larda harika görünmesini sağlayacak düzenlenmiş çözüm

Öncelikle bu makaleyi okuyun ve bir açılış ekranı yapmanın İYİ yolunu izleyin.

Logonuz bozuksa veya sığmıyorsa ve yalnızca APIs24 + 'yı hedefliyorsanız, vektör çekilebilirinizi doğrudan xml dosyasında şu şekilde küçültebilirsiniz:

<vector xmlns:android="http://schemas.android.com/apk/res/android" xmlns:aapt="http://schemas.android.com/aapt"
android:viewportWidth="640"
android:viewportHeight="640"
android:width="240dp"
android:height="240dp">
<path
    android:pathData="M320.96 55.9L477.14 345L161.67 345L320.96 55.9Z"
    android:strokeColor="#292929"
    android:strokeWidth="24" />
</vector>

Yukarıdaki kodda 640x640 tuvale çizdiğim bir çizimi 240x240 olarak yeniden ölçeklendiriyorum. sonra onu açılış ekranıma öylece koydum ve harika çalışıyor:

<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android" android:opacity="opaque"
android:paddingBottom="20dp" android:paddingRight="20dp" android:paddingLeft="20dp" android:paddingTop="20dp">

<!-- The background color, preferably the same as your normal theme -->
<item>
    <shape>
        <size android:height="120dp" android:width="120dp"/>
        <solid android:color="@android:color/white"/>
    </shape>
</item>

<!-- Your product logo - 144dp color version of your app icon -->
<item
    android:drawable="@drawable/logo_vect"
    android:gravity="center">

</item>
</layer-list>

benim kodum aslında sadece alttaki resimde bulunan üçgeni çizmek ama burada bununla neler yapabileceğinizi görüyorsunuz. Bitmap'i kullanırken elde ettiğim pikselli kenarların aksine çözünürlük nihayet harika. öyleyse kesinlikle çizilebilir bir vektör kullanın (özel bir yazılım indirmeden benimkini oluşturmak için kullandığım vectr adında bir site var).

API21-22-23 üzerinde de çalışmasını sağlamak için DÜZENLE

Yukarıdaki çözüm API24 + çalıştıran cihazlar için işe yarasa da, uygulamamı API22 çalıştıran bir cihaz kurduktan sonra gerçekten hayal kırıklığına uğradım. Açılış ekranının yine tüm görünümü doldurmaya çalıştığını ve bok gibi göründüğünü fark ettim. Yarım gün kaşlarımı yırttıktan sonra, sonunda saf irade ile bir çözümü kaba kuvvetle zorladım.

tam olarak açılış ekranı xml'sine benzeyen ikinci bir dosya oluşturmanız (örneğin splash_screen.xml) ve res / klasörde oluşturacağınız drawable-v22 ve drawable-v21 adlı 2 klasöre yerleştirmeniz gerekir (sizi görmek için proje görünümünüzü Android'den Project'e değiştirmeniz gerekir). Bu, ilgili cihaz çekilebilir klasördeki -vXX sonekine karşılık gelen bir API çalıştırdığında telefonunuza bu klasörlere yerleştirilen dosyalara yeniden yönlendirme yapmasını söylemeye yarar, bu bağlantıya bakın . aşağıdaki kodu, bu klasörlerde oluşturduğunuz splash_screen.xml dosyasının Katman listesine yerleştirin:

<item>
<shape>
    <size android:height="120dp" android:width="120dp"/>
    <solid android:color="@android:color/white"/>
</shape>
</item>

<!-- Your product logo - 144dp color version of your app icon -->
<item android:gravity="center">
    <bitmap android:gravity="center"
        android:src="logo_vect"/>

</item>

klasörler böyle görünüyor

Bazı nedenlerden dolayı, bu API'ların çalışması ve jet sonucunun aynı görünmesini sağlamak için çekilebilir dosyanızı bir bitmap'e sarmanız gerekir. Sorun şu ki, splash_screen.xml dosyasının ikinci sürümü açılış ekranınızın 23'ten daha yüksek API'leri çalıştıran cihazlarda hiç gösterilmemesine yol açacağından yaklaşımı ek çekilebilir klasörlerle kullanmanız gerekmesidir. Ayrıca yerleştirmeniz gerekebilir. android varsayılan olarak kaynaklar için bulabileceği en yakın çekilebilir-vXX klasörüne ayarlandığından, splash_screen.xml'nin ilk sürümü drawable-v24'e dönüştürülür.

açılış ekranım


4

Şu anda hem yatay hem de dikey olarak ortalanmış bir vektör çizilebilir bir açılış ekranı üzerinde çalışıyorum. İşte API seviyesi 25'te elde ettiğim şey:

<layer-list xmlns:android="http://schemas.android.com/apk/res/android" android:opacity="opaque">

<!-- background color, same as theme -->
<item android:drawable="@android:color/white"/>

<!-- app logo -->

<item
    android:drawable="@drawable/my_app_logo"
    android:gravity="center_horizontal|center_vertical"
    android:width="200dp"
    android:height="200dp"
    />
</layer-list>

Vektör çizilebilir boyutunu ayarlamak istiyorsanız, yukarıdaki değişiklikleri android:widthve android:heightnitelikleri, mutlaka orijinal çizimi değiştirmeyin.

Ek olarak, benim deneyimim, çizilebilir vektörü bir bitmap etiketine KOYMAYIN, benim için asla çalışmıyor. Bit eşlem .png, .jpg ve .gif biçimli dosyalar içindir, vektör çizilebilirler için değildir.

Referans

https://developer.android.com/guide/topics/resources/drawable-resource#LayerList

https://developer.android.com/guide/topics/resources/more-resources.html#Dimension


1
<bitmap> etiketi yerine bir <item> etiketinin içinde olması gereken vektör çekilebilir öğeleri hakkında iyi bilgi.
FrostRocket
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.