和设计师很好沟通的Android适配方案

来源:互联网 发布:io域名备案 编辑:程序博客网 时间:2024/04/29 01:05

经常遇到这样的问题,设计师给的单位是px,而我们用的单位是dip或sp,所以交流经常出现问题。后来研究出一套方案,可以很好地适配,而且与设计师很好的沟通。最好是设计师说设置多少px我们就设置多少px,免得设计师告状设没按他的来做。这样做我们就需要将px转成我们对应的dp值了。关于px和dp的对应关系,借用别人的介绍如下:


======================================================================================================

dp、dip、dpi、sp、px

px我们应该是比较熟悉的,前面的分辨率就是用的像素为单位,大多数情况下,比如UI设计、Android原生API都会以px作为统一的计量单位,像是获取屏幕宽高等。

dip和dp是一个意思,都是Density Independent Pixels的缩写,即密度无关像素,上面我们说过,dpi是屏幕像素密度,假如一英寸里面有160个像素,这个屏幕的像素密度就是160dpi,那么在这种情况下,dp和px如何换算呢?在Android中,规定以160dpi为基准,1dip=1px,如果密度是320dpi,则1dip=2px,以此类推。

假如同样都是画一条320px的线,在480*800分辨率手机上显示为2/3屏幕宽度,在320*480的手机上则占满了全屏,如果使用dp为单位,在这两种分辨率下,160dp都显示为屏幕一半的长度。这也是为什么在Android开发中,写布局的时候要尽量使用dp而不是px的原因。

而sp,即scale-independent pixels,与dp类似,但是可以根据文字大小首选项进行放缩,是设置字体大小的御用单位。

mdpi、hdpi、xdpi、xxdpi

其实之前还有个ldpi,但是随着移动设备配置的不断升级,这个像素密度的设备已经很罕见了,所在现在适配时不需考虑。

mdpi、hdpi、xdpi、xxdpi用来修饰Android中的drawable文件夹及values文件夹,用来区分不同像素密度下的图片和dimen值。

那么如何区分呢?Google官方指定按照下列标准进行区分:

未标题-1.jpg

在进行开发的时候,我们需要把合适大小的图片放在合适的文件夹里面。下面以图标设计为例进行介绍。

devices_displays_density@2x.jpg

在设计图标时,对于五种主流的像素密度(MDPI、HDPI、XHDPI、XXHDPI 和 XXXHDPI)应按照 2:3:4:6:8 的比例进行缩放。例如,一个启动图标的尺寸为48x48 dp,这表示在 MDPI 的屏幕上其实际尺寸应为 48x48 px,在 HDPI 的屏幕上其实际大小是 MDPI 的 1.5 倍 (72x72 px),在 XDPI 的屏幕上其实际大小是 MDPI 的 2 倍 (96x96 px),依此类推。

虽然 Android 也支持低像素密度 (LDPI) 的屏幕,但无需为此费神,系统会自动将 HDPI 尺寸的图标缩小到 1/2 进行匹配。

下图为图标的各个屏幕密度的对应尺寸:

QQ截图20151029145212.jpg

=======================================================================================================


根据上面的理论知识,我设计出了一套方案。使得我们只要按照设计师标注的px值来给控件设置值就行了。我生成了一套dimen,看下图:





文件见下载地址:http://download.csdn.net/detail/nnmmbb/9866090


上面截图中的文件是用我写的一个工具类生成的,工具类如下:

package com;import java.io.File;import java.io.FileNotFoundException;import java.io.FileOutputStream;import java.io.PrintWriter;/** * @author zhougang * @date 2017/6/9 15:29 */public class DipHelper {    private static String SIZE_MDPI = "mdpi";    private static String SIZE_HDPI = "hdpi";    private static String SIZE_XHDPI = "xhdpi";    private static String SIZE_XXHDPI = "xxhdpi";    private static String SIZE_XXXHDPI = "xxxhdpi";    private final static String rootPath = "F:\\layoutroot\\values-{0}\\";    private final static String WTemplate = "<dimen name=\"px_{0}\">{1}dp</dimen>\n";    private final static String WTemplate2 = "<dimen name=\"px_text_{0}\">{1}sp</dimen>\n";    public static void main(String[] args) {        makeString(SIZE_MDPI, 1);        makeString(SIZE_HDPI, 1.5f);        makeString(SIZE_XHDPI, 2);        makeString(SIZE_XXHDPI, 3);        makeString(SIZE_XXXHDPI, 4);    }    public static void makeString(String size, float scale) {        StringBuffer sb = new StringBuffer();        sb.append("<?xml version=\"1.0\" encoding=\"utf-8\"?>\n");        sb.append("<resources>");        for (int i = 1; i <= 480; i++) { //1px - 480px            sb.append(WTemplate.replace("{0}", i + "").replace("{1}",                    change( i/scale) + ""));        }        sb.append("\n//-------------------sp-----------------------//\n");        for (int i = 1; i <= 180; i++) { //1px - 480px            sb.append(WTemplate2.replace("{0}", i + "").replace("{1}",                    change( i/scale) + ""));        }        sb.append("</resources>");        String path = rootPath.replace("{0}", size);        File rootFile = new File(path);        if (!rootFile.exists()) {            rootFile.mkdirs();        }        File dimens = new File(path + "dimens.xml");        try {            PrintWriter pw = new PrintWriter(new FileOutputStream(dimens));            pw.print(sb.toString());            pw.close();        } catch (FileNotFoundException e) {            e.printStackTrace();        }    }    public static float change(float a) {        int temp = (int) (a * 100);        return temp / 100f;    }}



原创粉丝点击