How to center vector drawable in layer-list without scaling

I am attempting to use a VectorDrawable in a LayerList without scaling the vector. For example:

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

The drawable ic_check_white_48dp id defined as:

<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>

The desired effect is for the check icon to be centered in the layer drawable, without scaling. The issue is, the layer-list above causes the check icon to be scaled to fit the layer size.

I can produce the desired effect if I replace the vector drawable with PNGs for each density and modify the layer-list as such:

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

Is there any way I can do this using a VectorDrawable?

54231 次浏览

我遇到了同样的问题,试图在分层列表中集中向量绘制。

我有一个解决方案,它不完全相同,但它的工作原理,你需要设置一个大小为整个绘图,并添加填充到矢量项目:

<?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>

上面的形状大小设置了整个可绘制图像的大小,在本例中为120dp,第二个项目的填充(在本例中为24dp)使矢量图像居中。

它不同于使用 gravity="center",而是它在 API 21和22中使用向量的工作方式。

一直在纠结同样的问题。我发现解决这个问题的唯一方法是设置可拉伸的尺寸,并利用重力来调整它:

<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>

希望能有帮助!

我目前正在创建一个水平和垂直都居中的矢量绘制屏幕。以下是我得到的 API 级别25的信息:

<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>

如果要调整矢量绘图的尺寸,修改上面的 android:widthandroid:height属性,不一定要修改原始绘图。

此外,我的经验是不要把矢量绘制在一个位图标记,这从来没有为我工作。位图是给。PNG,.JPG 和。Gif 格式文件,不适合矢量绘制。

Reference

Https://developer.android.com/guide/topics/resources/drawable-resource#layerlist

Https://developer.android.com/guide/topics/resources/more-resources.html#dimension

编辑的解决方案,将使您的 SplashScreen 看起来很棒的所有 API,包括 API21到 API23

首先阅读 这个文章,并遵循制作闪屏的好方法。

If your logo is distorted or wont fit and you are only targeting APIs24+ you can simply scale down your vector drawable directly in its xml file like so:

<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>

在上面的代码中,我将在640x640的画布上绘制的可画性重新缩放为240x240。然后我把它放在我的启动画面上,像这样,它工作得很好:

<?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>

我的代码实际上只是绘制底部图片中的三角形,但在这里你可以看到你可以实现这一点。分辨率最终是伟大的相对于像素化的边缘,我得到的时候使用位图。因此,使用一个可以通过各种方式绘制的向量(有一个叫做 vectr 的网站,我用它来创建我的向量,而无需下载专门的软件)。

编辑,以使其工作也在 API21-22-23

虽然上面的解决方案适用于运行 API24 + 的设备,但是在安装了运行 API22的设备后,我感到非常失望。我注意到屏幕又在试图填满整个视野,看起来糟透了。在把我的眉毛撕掉半天之后,我终于用纯粹的意志力强迫自己想出了一个解决办法。

你需要创建第二个名称与 splashscreen xml 完全相同的文件(比方说 splashscreen xml) ,并将其放入两个文件夹,分别命名为 draable-v22和 draable-v21,这两个文件夹将在 res/文件夹中创建(为了看到它们,你必须将项目视图从 Android 更改为 Project)。每当相关设备运行对应于可绘制文件夹 看看这个链接中的-vXX 后缀的 API 时,它就会告诉您的手机重定向到放置在这些文件夹中的文件。将下面的代码放在在这些文件夹中创建的 splash _ screen. xml 文件的图层列表中:

<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:opacity="opaque">


<!-- The background color, preferably the same as your normal theme -->
<item
android:gravity="center">
<shape android:shape="rectangle">
<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="@drawable/logo_vect"/>


</item>
</layer-list>

these is how the folders look

For some reason for these APIs you have to wrap your drawable in a bitmap in order to make it work and jet the final result looks the same. The issue is that you have to use the aproach with the aditional drawable folders as the second version of the splash_screen.xml file will lead to your splash screen not being shown at all on devices running APIs higher than 23. You might also have to place the first version of the splash_screen.xml into drawable-v24 as android defaults to the closest drawable-vXX folder it can find for resources.

my splashscreen