返回 巧用Andro...... 登陆

巧用Android图片资源,打造更精致的APP

高洛峰 2016-11-03 16:36:26 555

由于android系统的开放性,以及IOS的相对封闭。第三方设备想要使用苹果的OS,目前来说是不可能。所以,各厂商纷纷的投入了android的怀抱,
android阵营也越来越强大,如今移动操作系统也就是android和ios的天下。也正是因为android的开放性,可定制度高,导致了各种屏幕尺寸、各种分辨率的android设备
铺满了手机、平板、智能电视、手表、盒子、智能硬件...等各种应用场景。

作为一名有逼格的程序猿,在面对如此众多的尺寸和分辨率设备上,想要打造一款通吃的app,势必是要花费一番功夫的。

还好google已经为我们想好了对策,为不同的分辨率提供不同的drawable资源。

先来看看微信的android客户端,在图片资源的使用

wKioL1gayqiA24f3AAGc29LICkg728.png

在res目录下,以drawable开头的文件夹占了一大半,后面以-hdpi、-land、-mdpi、-xhdpi...等文件夹以适配不同分辨率的机型。

可能有人会说,开发应用只用适配hdpi或者xhdpi就可以了,同样可以显示出来嘛!干嘛搞这么多版本,浪费空间,还麻烦!

如果是这样的想法,那只能说你的应用受众群体还没达到一定程度,或者不追求细节的完美。对于高逼格的应用来说,哪怕一个像素的缺失,都是不完美。

废话了这么多,先来看卡google官方对dp的定义

dp是一个与屏幕密度有关系的单位,dp与像素的换算关系为 px = dp * (dpi / 160)。例如在240密度(dpi)的屏幕上一个dp等于1.5个像素。以后我们应该尽量使用dp单位布局,不要使用像素单位。这样会使你的app屏幕兼容性更好

wKioL1gayqiA24f3AAGc29LICkg728.png

将同一张96x96像素的png图片,分别放到hdpi、xhdpi、xxhdpi文件夹中,宽高均以wrap_content显示

![](https://cscdn.maxleap.cn/2.0/download/NTgwZWMzNjA3ZWYyMGIwMDA3N2ViOGEx/zcf-b929ae8b-ace3-4e8d-ad2d-5cb311738b04.jpg)

可以看到,适配较低drawable-dpi的资源图片,显示尺寸相对较大,但是清晰度差。而适配高dpi的图片,显示尺寸相对较小,但是锐度高,比较清晰!

将像素分别为72x72、96x96、144x144像素的图片,分别放置于hdpi xhdpi xxhdpi文件夹中,宽高以wrap_content显示效果。

![](https://cscdn.maxleap.cn/2.0/download/NTgwZWMzNjA3ZWYyMGIwMDA3N2ViOGEx/zcf-bd311903-f4f9-4a40-baf5-0e8eaaf03e9d.jpg)

可以看到,不同大小的图片,放到不同的资源文件夹下,最终在屏幕上显示的大小居然一致!但是144x144像素对应的图片显示的最精致和清晰。

到这里,应该能看出图片资源与drawable文件夹对应的关系了。即使不使用高质量的图片,仍然可在高分辨率的屏幕上进行对应的显示,但是牺牲了控件显示的精细度,屏幕dpi越高显示越不清楚。如果一张高清晰度的照片,被放置在不恰当的drawable下也不能准确的还原应有的尺寸和清晰度。

对比IOS对图片的定义,2倍图即-xhdpi密度,3倍图即-xxhdpi密度。

531421-20161102144723533-301936887.jpg

所以,想要让应用中的icon显示的更加精致,那就需要对应的配置不同像素的图片。

很多人在处理带图片的icon的时候,会指定其大小,如:

            <ImageView
                android:layout_width="45dp"
                android:layout_height="45dp"
                android:src="@drawable/icon_hdpi" />

wrap_content可理解为包裹内容,当控件被设置为wrap_content将会根据实际大小进行显示。相比直接设置dip的方式,在图片的显示上或多或少的会存在缩放。也就会导致图标会显示的不够精致。

            <ImageView
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:src="@drawable/voip_camerachat_xhdpi" />

下面以应用中常用的tabbar,作为对比:(以1920x1080屏幕像素截图)

图1

wKioL1gayqiA24f3AAGc29LICkg728.png

图2

wKioL1gayqiA24f3AAGc29LICkg728.png

图1中的icon统一被设置了固定的大小24dp,同时只在drawable-xhdpi中进行图片的适配。可以看出图片被不同程度的拉伸,icon显示较模糊。

图2将icon的宽高均设置为wrap_content,同时在drawable-xxhdpi中进行了适配。图2的icon锐度有所提高,因为wrap_content属性的设置,本身icon图片大小不同,导致icon显示的大小不一致。所以完美的方案就是,需要UI提供尺寸均一的大图片,适配到drawable-xxhdpi下.

相比微信的高清图片资源,展现的精致效果:

wKioL1gayqiA24f3AAGc29LICkg728.png

SVG

Scalable Vector Graphics

在 Android 5.0(API 级别 21)及更高版本中,可定义矢量图片,而且图片可在不损失清晰度的情况下缩放。 只需一个资产文件即可创建一个矢量图像,而位图图像则需要为每个屏幕密度提供一个资产文件。 如果要创建一个矢量图像,在 <vector> XML 元素中定义形状的详情。

下列示例以定义一个矢量图像:

在drawable文件夹下-->new-->vector Asset

wKioL1gayqiA24f3AAGc29LICkg728.png

可以选择Material Icon,使用studio内置的icon资源。这里选择了Local SVG file,使用自己定义的svg文件。

wKioL1gayqiA24f3AAGc29LICkg728.png

确定保存文件的位置。svg文件会导出为xml文件:

wKioL1gayqiA24f3AAGc29LICkg728.png

生成的moon.xml内容如下,path节点下的fillColor属性,可以自定义颜色值。

<vector xmlns:android="http://schemas.android.com/apk/res/android"
    android:width="24dp"
    android:height="24dp"
    android:viewportHeight="22.0"
    android:viewportWidth="22.0">
    <path
        android:fillColor="#FF000000"
        android:pathData="M16,10l0.8,-3.2L20,6l-3.2,-0.8L16,2l-0.8,3.2L12,6l3.2,0.8L16,10zM6,8c0,-2.17 0.867,-4.134 2.269,-5.575C4.634,3.581 2,6.982 2,11c0,4.971 4.029,9 9,9c4.018,0 7.419,-2.634 8.575,-6.269C18.134,15.133 16.17,16 14,16C9.582,16 6,12.418 6,8z" />
</vector>

layout中使用和普通图片使用相同

            <ImageView
                android:layout_width="40dp"
                android:layout_height="40dp"
                android:src="@drawable/moon" />

界面显示效果:

wKioL1gayqiA24f3AAGc29LICkg728.png

控件的宽高可以任意以dp的方式设置,而清晰度并未受影响。

SVG除了可以用在矢量图片上,也可以在android上用来显示精美的动画效果。

有时间再对svg的生成,以及使用做更详细的介绍。


最新手记推荐

• 用composer安装thinkphp框架的步骤 • 省市区接口说明 • 用thinkphp,后台新增栏目 • 管理员添加编辑删除 • 管理员添加编辑删除

全部回复(0)我要回复

暂无评论~
  • 取消 回复 发送
  • PHP中文网