-
手机屏幕适配
2016-02-01 18:02:59手机屏幕适配: 在开发中美工一般只给一套图。所以就有屏幕适配; 一共五种适配模式: 图片适配 : 根据手机的象素密度来选择不同文件夹中的图片进行适配 dimens适配 : 根据手机的象素密度来选择不同文件夹...手机屏幕适配:
在开发中美工一般只给一套图。所以就有屏幕适配;
一共五种适配模式:
图片适配 : 根据手机的象素密度来选择不同文件夹中的图片进行适配
dimens适配 : 根据手机的象素密度来选择不同文件夹中的尺寸进行适配
布局适配 : 根据手机的象素密度来选择不同文件夹中的布局进行适配
代码适配 : 在java代码中动态设置控件的大小,进行适配
layout_weight权重适屏 : 巧妙利用线性布局的layout_weight属性进行适配
一般使用图片适配,代码适配,权重适屏
===========================================================================
图片适配 : 根据手机的象素密度来选择不同drawable文件夹中的图片 进行适配
比如小米NOTE是386的PPI
默认情况下,会根据手机的象素密度,加载对应drawable文件夹下的图片[note默认加载xxhdpi下的图片]
如果对应drawable文件夹下没有当前图片,会向上查找(向分辨率更高的文件夹中查找)[如果xxhdpi下没有图片会去xxxhdpi找]
如果向上找不到,才会向低分辨率的文件夹中去找。[如果xxhdpi和xxxhdpi都没图片会找xhdpi]
** 在开发中,让美工做一套大小适配市场上占比例最多的分辨率的图片**
------------------------------------------------------------------------------------
dimens尺寸适配
ldpi 的手机中 240 * 320 的屏幕
160 dp x 0.75 = 120 px
mdpi 的手机 320 * 480 的屏幕
160 dp x1 = 160 px
xhdpi 手机 1280 * 720 的屏幕
160 dp x2 = 320 个像素
屏幕的一半 为 360 个象素或 180 个 dp
使用步骤:
1、 在values 文件夹中新建文件 dimens.xml ,将需要动态指定的尺寸声明成变量,在布局文件中由变量来引用
<resources>
<dimen name="text_width">160dp</dimen>
</resources>
2、创建不同分辨率下的尺寸的文件夹,如:values-xhdpi 在文件夹中创建文件 dimens.xml
<resources>
<dimen name="text_width">180dp</dimen>
</resources>
这样,不同的手机中显示的text_width 根据手机象素密度的不同,就可以显示不同的值。
** 注意:文件夹的名称也可以直接指定分辨率 如 values-1280x720 其中x是xyz的x不是数字中的乘号
但这种写法,只能适配这一个分辨率,只有特殊情况下才用。
不同的象素密度下, dp 与 px 之间的转换关系
ldpi 1 dp 0.75 px
mdpi 1 dp 1 px
hdpi 1 dp 1.5 px
xhdpi 1 dp 2 px
**使用的时候,还是使用dp,如果测试时发现不视频的机型,针对某种机型,做dimens适配。
------------------------------------------------------------------------------------------------------------------------------------
布局适配 : 根据手机的象素密度来选择不同layout文件夹中的布局进行适配
新建文件夹 layout-xhdpi 该文件夹用于存放 xhdpi 分辨率的手机所需的布局文件
如果该文件夹中没有需要的布局,就从layout 文件夹中查找默认的布局。
谷歌推荐做法,但一般不采用。layout布局编写非常麻烦,工作量大
**注意: 为不同分辨率的手机指定不同的布局文件,功能虽然强大,但如果布局较多,使用起来会非常繁琐,使用时要注意**
--------------------------------------------------------------------------------------------------------------------
代码适配 : 在java代码中动态设置控件的大小,进行适配
在代码中根据屏幕的宽高,动态设置控件的大小:
TextView textView = (TextView) findViewById(R.id.textview);
//获取屏幕宽度
int screenWidth = getResources().getDisplayMetrics().widthPixels;//屏幕宽度:px
// 指定textView的宽度为屏幕的 80%
int textViewWidth = (int) (screenWidth*0.8+0.5f);
LayoutParams params = new LayoutParams(textViewWidth, LayoutParams.WRAP_CONTENT);
textView.setLayoutParams(params);
-----------------------------------------------------------------------------------------------------------------------------------------------------
layout_weight 权重适配
线性布局的布局参数 layout_weight 不仅能指定控件计算大小的优先级
还可以,使用权重,按比例分配控件的大小。
** 注意,按比例分配大小的尺寸布局中要先声明为0dp,不能是包括内容或填充满父元素**
-----------------------------------------------------------------------------------------------------------------------------初写博客,菜鸟一枚,如有错误,希望指出;
zhengjiaovip@163.com
-
Android 手机屏幕适配解决办法
2020-09-01 11:36:29主要介绍了Android 手机屏幕适配的相关资料,在开发Android 手机开发的时候经常会有很多手机品牌和手机屏幕尺寸问题,需要的朋友可以参考下 -
安卓app手机屏幕适配技巧.zip
2021-01-10 19:44:11安卓app手机屏幕适配技巧.zip 让android app适合不同尺寸的屏幕 分辨率mdpi、hdpi 、xhdpi、xxhdpi 4条黄金法则 9-patch PNG -
经验总结-Android手机屏幕适配问题
2017-10-28 23:45:39从事Android开发起,就在工作中就遇到了Android手机屏幕适配的问题,每次遇到都是查找资料解决,也没有进行回顾总结,最近又遇到了屏幕适配问题,我醒悟的发现,我必须进行一次屏幕适配总结了。 我相信从事Android...从事Android开发起,就在工作中就遇到了Android手机屏幕适配的问题,每次遇到都是查找资料解决,也没有进行回顾总结,最近又遇到了屏幕适配问题,我醒悟的发现,我必须进行一次屏幕适配总结了。
我相信从事Android开发的程序员,或多或少都接触过屏幕适配的问题,那大家清楚为什么要对Android的屏幕进行适配吗?原因是,Android的屏幕已经碎片化,屏幕尺寸这么多,为了让我们开发的程序能够比较美观的显示在不同尺寸、分辨率、像素密度的设备上,那就要在开发的过程中进行处理。至于如何去进行处理,这就是我们今天的主题了。开始主题之前,很多重要的关于屏幕适配的基础知识大家还是要有所准备的,不过我就不贴出来了,大家事先了解啦,可从这个网址去预习:http://www.cocoachina.com/android/20151030/13971.html,那么现在开始我的经验总结吧:
一、首先是一些特殊屏幕需要屏幕适配
我的这个特殊也不是很特殊了,只是说Android应用程序开发中,有的页面需要横竖屏切换,各个控件需要适配横竖屏的屏幕,同时也是说要满足各种屏幕尺寸,那我的方案一就是:
尽量恰当的使用wrap_content、match_parent、weight的布局属性,要确保布局的灵活性并适应各种尺寸的屏幕,应使用 “wrap_content” 和 “match_parent” 控制某些视图组件的宽度和高度。使用 “wrap_content”,系统就会将视图的宽度或高度设置成所需的最小尺寸以适应视图中的内容,而 “match_parent”(在低于API 级别8 的级别中称为 “fill_parent”)则会展开组件以匹配其父视图的尺寸。如果使用 “wrap_content” 和 “match_parent” 尺寸值而不是硬编码的尺寸,视图就会相应地仅使用自身所需的空间或展开以填满可用空间。此方法可让布局正确适应各种屏幕尺寸和屏幕方向。weight是线性布局的一个独特的属性,我们可以使用这个属性来按照比例对界面进行分配,完成一些特殊的需求。既然要用weight属性,当然布局的时候就要使用线性布局了。那么我们对于weight这个属性的计算应该如何理解呢?android:layout_weight的真实含义是:如果View设置了该属性并且有效,那么该View的宽度等于原有宽度(android:layout_width)加上剩余空间的占比。从这个角度我们来解释一下上面的现象。在上面的代码中,我们设置每个Button的宽度都是match_parent,假设屏幕宽度为L,那么每个Button的宽度也应该都为L,剩余宽度就等于L-(L+L)= -L。Button1的weight=1,剩余宽度占比为1/(1+2)= 1/3,所以最终宽度为L+1/3*(-L)=2/3L,Button2的计算类似,最终宽度为L+2/3(-L)=1/3L。这是在水平方向上的,那么在垂直方向上也是这样吗?答案是,也是一样的,这里我就不重复解释了。
那我的方案二就是:
使用官方提供的百分比布局,同时可借助第三方开源框架的增强版百分比布局。官方提供了android-percent-support这个库,这个库提供了两种布局供大家使用:PercentRelativeLayout、PercentFrameLayout,通过名字就可以看出,这是继承自FrameLayout和RelativeLayout两个容器类;支持的属性有:
layout_widthPercent、layout_heightPercent、
layout_marginPercent、layout_marginLeftPercent、
layout_marginTopPercent、layout_marginRightPercent、
layout_marginBottomPercent、layout_marginStartPercent、layout_marginEndPercent。
可以看到支持宽高,以及margin。
也就是说,大家只要在开发过程中使用PercentRelativeLayout、PercentFrameLayout替换FrameLayout、RelativeLayout即可。
是不是很简单,不过貌似没有LinearLayout,有人会说LinearLayout有weight属性呀。但是,weight属性只能支持一个方向呀~~哈,没事,刚好给我们一个机会去自定义一个PercentLinearLayout。有人说自定义我不会呀,或者太花时间呀,没关系,我们可以借助第三方开源库,这里我借助的是博主张鸿洋的:(我的水平有待提高,总是没创新,大家谅解下了)http://blog.csdn.net/lmj623565791/article/details/46695347。
1.首先是对官方百分比布局使用的讲解:
关于使用,其实及其简单,并且github上也有例子,android-percent-support-lib-sample。我们就简单过一下:首先在build.gradle添加依赖:compile 'com.android.support:percent:22.2.0',这里请注意:每个控件的百分比使用,都是针对直接的父布局来说的。然后就可以开始写布局了:
(一)PercentFrameLayout
<?xml version="1.0" encoding="utf-8"?>
<android.support.percent.PercentFrameLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_gravity="left|top"
android:background="#44ff0000"
android:text="width:30%,height:20%"
app:layout_heightPercent="20%"
android:gravity="center"
app:layout_widthPercent="30%"/>
<TextView
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_gravity="right|top"
android:gravity="center"
android:background="#4400ff00"
android:text="width:70%,height:20%"
app:layout_heightPercent="20%"
app:layout_widthPercent="70%"/>
<TextView
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_gravity="bottom"
android:background="#770000ff"
android:text="width:100%,height:10%"
android:gravity="center"
app:layout_heightPercent="10%"
app:layout_widthPercent="100%"/>
</android.support.percent.PercentFrameLayout>
(二) PercentRelativeLayout
<?xml version="1.0" encoding="utf-8"?>
<android.support.percent.PercentRelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:clickable="true">
<TextView
android:id="@+id/row_one_item_one"
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_alignParentTop="true"
android:background="#7700ff00"
android:text="w:70%,h:20%"
android:gravity="center"
app:layout_heightPercent="20%"
app:layout_widthPercent="70%"/>
<TextView
android:id="@+id/row_one_item_two"
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_toRightOf="@+id/row_one_item_one"
android:background="#396190"
android:text="w:30%,h:20%"
app:layout_heightPercent="20%"
android:gravity="center"
app:layout_widthPercent="30%"/>
<ImageView
android:id="@+id/row_two_item_one"
android:layout_width="match_parent"
android:layout_height="0dp"
android:src="@drawable/tangyan"
android:scaleType="centerCrop"
android:layout_below="@+id/row_one_item_one"
android:background="#d89695"
app:layout_heightPercent="70%"/>
<TextView
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_below="@id/row_two_item_one"
android:background="#770000ff"
android:gravity="center"
android:text="width:100%,height:10%"
app:layout_heightPercent="10%"
app:layout_widthPercent="100%"/>
</android.support.percent.PercentRelativeLayout>
就上面两个例子,图我就不上了,大家谅解谅解哈。
2.其次是第三方百分比布局使用的讲解:
这里我使用的是博主张鸿洋的框架,首先也是要添加依赖了,在build.gradle添加依赖:dependencies {
//...
compile 'com.zhy:percent-support-extends:1.0.1'
}
然后不需要导入官方的percent-support-lib了,提供了三个类:
com.zhy.android.percent.support.PercentLinearLayout
com.zhy.android.percent.support.PercentRelativeLayout
com.zhy.android.percent.support.PercentFrameLayout
对于eclipse的用户:github上自行下载源码,就几个类和一个attrs.xml,也可以在bintray.com/percent-support-extends下载相关文件。
下面是几个代码的具体使用示例:
Demo 1
<?xml version="1.0" encoding="utf-8"?>
<com.zhy.android.percent.support.PercentFrameLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<com.zhy.android.percent.support.PercentFrameLayout
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_gravity="center"
android:background="#ff44aacc"
app:layout_heightPercent="50%w"
app:layout_widthPercent="50%w">
<com.zhy.android.percent.support.PercentFrameLayout
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_gravity="center"
android:background="#ffcc5ec7"
app:layout_heightPercent="50%w"
app:layout_widthPercent="50%w">
<TextView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_gravity="center"
android:background="#ff7ecc16"
android:gravity="center"
android:text="margin 15% of w"
app:layout_marginPercent="15%w"
/>
</com.zhy.android.percent.support.PercentFrameLayout>
</com.zhy.android.percent.support.PercentFrameLayout>
<TextView android:layout_width="0dp"
android:layout_height="0dp"
android:layout_gravity="bottom|right"
android:background="#44ff0000"
android:gravity="center"
android:text="15%w,15%w"
app:layout_heightPercent="15%w"
app:layout_marginPercent="5%w"
app:layout_widthPercent="15%w"/>
</com.zhy.android.percent.support.PercentFrameLayout>
Demo 2
<?xml version="1.0" encoding="utf-8"?>
<com.zhy.android.percent.support.PercentRelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:clickable="true">
<TextView
android:id="@+id/row_one_item_one"
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_alignParentTop="true"
android:background="#7700ff00"
android:text="w:70%,h:20%"
android:gravity="center"
app:layout_heightPercent="20%"
app:layout_widthPercent="70%"/>
<TextView
android:id="@+id/row_one_item_two"
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_toRightOf="@+id/row_one_item_one"
android:background="#396190"
android:text="w:30%,h:20%"
app:layout_heightPercent="20%"
android:gravity="center"
app:layout_widthPercent="30%"/>
<ImageView
android:id="@+id/row_two_item_one"
android:layout_width="match_parent"
android:layout_height="0dp"
android:src="@drawable/tangyan"
android:scaleType="centerCrop"
android:layout_below="@+id/row_one_item_one"
android:background="#d89695"
app:layout_heightPercent="70%"/>
<TextView
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_below="@id/row_two_item_one"
android:background="#770000ff"
android:gravity="center"
android:text="width:100%,height:10%"
app:layout_heightPercent="10%"
app:layout_widthPercent="100%"/>
</com.zhy.android.percent.support.PercentRelativeLayout>
Demo 3
<?xml version="1.0" encoding="utf-8"?>
<ScrollView
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent">
<com.zhy.android.percent.support.PercentLinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<TextView
android:layout_width="0dp"
android:layout_height="0dp"
android:background="#ff44aacc"
android:gravity="center"
android:text="width:60%,height:5%,ts:3%"
android:textColor="#ffffff"
app:layout_heightPercent="5%"
app:layout_marginBottomPercent="5%"
app:layout_textSizePercent="3%"
app:layout_widthPercent="60%"/>
<TextView
android:layout_width="0dp"
android:layout_height="0dp"
android:background="#ff4400cc"
android:gravity="center"
android:text="width:70%,height:10%"
android:textColor="#ffffff"
app:layout_heightPercent="10%"
app:layout_marginBottomPercent="5%"
app:layout_widthPercent="70%"/>
<TextView
android:layout_width="0dp"
android:layout_height="0dp"
android:background="#ff44aacc"
android:gravity="center"
android:text="w:80%,h:15%,textSize:5%"
android:textColor="#ffffff"
app:layout_heightPercent="15%"
app:layout_marginBottomPercent="5%"
app:layout_textSizePercent="5%"
app:layout_widthPercent="80%"/>
<TextView
android:layout_width="0dp"
android:layout_height="0dp"
android:background="#ff4400cc"
android:gravity="center"
android:text="width:90%,height:5%"
android:textColor="#ffffff"
app:layout_heightPercent="20%"
app:layout_marginBottomPercent="5%"
app:layout_widthPercent="90%"/>
<TextView
android:layout_width="match_parent"
android:layout_height="0dp"
android:background="#ff44aacc"
android:gravity="center"
android:text="width:100%,height:25%"
android:textColor="#ffffff"
app:layout_heightPercent="25%"
app:layout_marginBottomPercent="5%"
/>
<TextView
android:layout_width="match_parent"
android:layout_height="0dp"
android:background="#ff44aacc"
android:gravity="center"
android:text="width:100%,height:30%"
android:textColor="#ffffff"
app:layout_heightPercent="30%"
app:layout_marginBottomPercent="5%"
/>
</com.zhy.android.percent.support.PercentLinearLayout>
</ScrollView>
依然是我就不上图了啦,有点懒哈。使用的话对大家应该是不难的,大家自己去多试试啦。还有百分比布局的源码,不管是官方的还是张鸿洋博主的,我都不贴出来一一解释了,大家有时间的话就自己多看看啦。
二、对整个Android应用页面都需要进行屏幕适配
对于这种情况,我有做过两个大型的国有App应用项目,这两个国有项目用的方案都是自己引入百分比概念进行适配(我觉得那样做,是因为那时百分比布局还没有普及吧,我猜的)。我给出的方案就是结合上面两个项目方法,再结合一下自己的思路。我就不饶圈子啦,直接结合自己的经验,给出自己的解决方案:首先也是自己引入百分比概念,然后结合上面给出的的一、的情况进行结合来适配。
自己引入百分比概念:
1.在项目中针对你所需要适配的手机屏幕的分辨率各自新建一个文件夹。
2.然后我们选择一个基准,基准的意思就是:
比如选择480*320的分辨率为基准:
宽度为320,将任何分辨率的宽度分为320份,取值为x1-x320
高度为480,将任何分辨率的高度分为480份,取值为y1-y480
其他分辨率类似上面的分析~~
例如对于例如对于800*480的宽度480:它的份数就是x1=1.5px,x2=3px,x3=4.5px...以此类推。。。。
那么,你可能有个疑问,这么写有什么好处呢?
假设我现在需要在屏幕中心有个按钮,宽度和高度为我们屏幕宽度的1/2,我可以怎么编写布局文件呢?
<FrameLayout >
<Button
android:layout_gravity="center"
android:gravity="center"
android:text="@string/hello_world"
android:layout_width="@dimen/x160"
android:layout_height="@dimen/x160"/>
</FrameLayout>
可以看到我们的宽度和高度定义为x160,其实就是宽度的50%;不论在什么分辨率的机型,我们的按钮的宽和高始终是屏幕宽度的一半。
你可能又会问,这么多文件,难道我们要手算,然后自己编写?不会啦,有方法,我们可以用一个工具类自动生成,生成代码步骤如下:
1.分析需要的支持的分辨率
对于主流的分辨率我已经集成到了我们的程序中,当然对于特殊的,你可以通过参数指定。关于屏幕分辨率信息,可以通过该网站查询:http://screensiz.es/phone
2.根据分析编写自动生成文件的程序,代码如下:
import java.io.File; import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.io.PrintWriter; /** * Created by zhy on 15/5/3. */ public class GenerateValueFiles { private int baseW; private int baseH; private String dirStr = "./res"; private final static String WTemplate = "<dimen name=\"x{0}\">{1}px</dimen>\n"; private final static String HTemplate = "<dimen name=\"y{0}\">{1}px</dimen>\n"; /** * {0}-HEIGHT */ private final static String VALUE_TEMPLATE = "values-{0}x{1}"; private static final String SUPPORT_DIMESION = "320,480;480,800;480,854;540,960;600,1024;720,1184;720,1196;720,1280;768,1024;800,1280;1080,1812;1080,1920;1440,2560;"; private String supportStr = SUPPORT_DIMESION; public GenerateValueFiles(int baseX, int baseY, String supportStr) { this.baseW = baseX; this.baseH = baseY; if (!this.supportStr.contains(baseX + "," + baseY)) { this.supportStr += baseX + "," + baseY + ";"; } this.supportStr += validateInput(supportStr); System.out.println(supportStr); File dir = new File(dirStr); if (!dir.exists()) { dir.mkdir(); } System.out.println(dir.getAbsoluteFile()); } /** * @param supportStr * w,h_...w,h; * @return */ private String validateInput(String supportStr) { StringBuffer sb = new StringBuffer(); String[] vals = supportStr.split("_"); int w = -1; int h = -1; String[] wh; for (String val : vals) { try { if (val == null || val.trim().length() == 0) continue; wh = val.split(","); w = Integer.parseInt(wh[0]); h = Integer.parseInt(wh[1]); } catch (Exception e) { System.out.println("skip invalidate params : w,h = " + val); continue; } sb.append(w + "," + h + ";"); } return sb.toString(); } public void generate() { String[] vals = supportStr.split(";"); for (String val : vals) { String[] wh = val.split(","); generateXmlFile(Integer.parseInt(wh[0]), Integer.parseInt(wh[1])); } } private void generateXmlFile(int w, int h) { StringBuffer sbForWidth = new StringBuffer(); sbForWidth.append("<?xml version=\"1.0\" encoding=\"utf-8\"?>\n"); sbForWidth.append("<resources>"); float cellw = w * 1.0f / baseW; System.out.println("width : " + w + "," + baseW + "," + cellw); for (int i = 1; i < baseW; i++) { sbForWidth.append(WTemplate.replace("{0}", i + "").replace("{1}", change(cellw * i) + "")); } sbForWidth.append(WTemplate.replace("{0}", baseW + "").replace("{1}", w + "")); sbForWidth.append("</resources>"); StringBuffer sbForHeight = new StringBuffer(); sbForHeight.append("<?xml version=\"1.0\" encoding=\"utf-8\"?>\n"); sbForHeight.append("<resources>"); float cellh = h *1.0f/ baseH; System.out.println("height : "+ h + "," + baseH + "," + cellh); for (int i = 1; i < baseH; i++) { sbForHeight.append(HTemplate.replace("{0}", i + "").replace("{1}", change(cellh * i) + "")); } sbForHeight.append(HTemplate.replace("{0}", baseH + "").replace("{1}", h + "")); sbForHeight.append("</resources>"); File fileDir = new File(dirStr + File.separator + VALUE_TEMPLATE.replace("{0}", h + "")// .replace("{1}", w + "")); fileDir.mkdir(); File layxFile = new File(fileDir.getAbsolutePath(), "lay_x.xml"); File layyFile = new File(fileDir.getAbsolutePath(), "lay_y.xml"); try { PrintWriter pw = new PrintWriter(new FileOutputStream(layxFile)); pw.print(sbForWidth.toString()); pw.close(); pw = new PrintWriter(new FileOutputStream(layyFile)); pw.print(sbForHeight.toString()); pw.close(); } catch (FileNotFoundException e) { e.printStackTrace(); } } public static float change(float a) { int temp = (int) (a * 100); return temp / 100f; } public static void main(String[] args) { int baseW = 320; int baseH = 400; String addition = ""; try { if (args.length >= 3) { baseW = Integer.parseInt(args[0]); baseH = Integer.parseInt(args[1]); addition = args[2]; } else if (args.length >= 2) { baseW = Integer.parseInt(args[0]); baseH = Integer.parseInt(args[1]); } else if (args.length >= 1) { addition = args[0]; } } catch (NumberFormatException e) { System.err .println("right input params : java -jar xxx.jar width height w,h_w,h_..._w,h;"); e.printStackTrace(); System.exit(-1); } new GenerateValueFiles(baseW, baseH, addition).generate(); } }
注:其实编写代码生成文件还是挺麻烦的,如果你比较懒的话,其实已经有大神制作了自动生成文件的jar包了,默认情况下,双击jar包即可生成,下载地址即使用说明可参考http://blog.csdn.net/lmj623565791/article/details/45460089
按照java -jar xx.jar width height width,height_width,height的格式即可生成我们需要的屏幕分辨率文件。到此,我们通过编写一个工具,根据某基准尺寸,生成所有需要适配分辨率的values文件,做到了编写布局文件时,可以参考屏幕的分辨率;在UI给出的设计图,可以快速的按照其标识的px单位进行编写布局。基本解决了适配的问题。
虽然这个适配方法还可以,但是相对于百分布局来说还是逊色一点,如果大家以后做屏幕适配,我还是建议大家更多的考虑使用百分比布局。而且像张鸿洋这样的博主大神,有自己的封装好的百分比布局框架开源,已经能很好的满足适配要求了。
最后来个面试题,看一下我的想法:
面试官:一个控件width设置了match_parent,height设置了100dp,在不同的手机上可能会出现适配比较差的情况,那你会怎么解决?
我:按照您说的情况,在当前手机上测试显示的效果是满足要求,但如果在屏幕更小、或屏幕更大的手机上显示的话height就会不理想。我想到就是要height占屏幕高的百分比,不管什么屏幕的话,height都能显示合理高度了。
面试官:怎么设置百分比呢
我:我首先想到的方案是用百分比布局,可以直接设置控件height占屏幕的高度。
第二,也可以针对现在比较流行的手机尺寸,分别创建对应的values文件夹,在对应创建dp和px转换的资源文件,然后在控件的height属性中引用对应的值就可以了。
-
屏幕适配之带虚拟按键手机屏幕适配
2017-05-25 10:43:08最近,在项目开发中遇到带虚拟按键屏幕适配的问题。例如,华为P9、小米MAX等机型,整个屏幕的布局都往上了,觉得应该是虚拟按键的问题。所以,经过一番折腾,找到如下解决方案: 获取屏幕实际显示尺寸高度 //获取...最近,在项目开发中遇到带虚拟按键屏幕适配的问题。例如,华为P9、小米MAX等机型,整个屏幕的布局都往上了,觉得应该是虚拟按键的问题。所以,经过一番折腾,找到如下解决方案:
- 获取屏幕实际显示尺寸高度
//获取屏幕尺寸,不包括虚拟功能高度 getWindowManager().getDefaultDisplay().getHeight();
- 获取屏幕原始尺寸高度
private int getHeight() { int dpi = 0; Display display = getWindowManager().getDefaultDisplay(); DisplayMetrics dm = new DisplayMetrics(); Class c; try { c = Class.forName("android.view.Display"); @SuppressWarnings("unchecked") Method method = c.getMethod("getRealMetrics", DisplayMetrics.class); method.invoke(display, dm); dpi = dm.heightPixels; } catch (Exception e) { e.printStackTrace(); } return dpi; }
经过两个高度对比,就可以得到虚拟按键的高度。带虚拟键盘的屏幕分辨率是1920*1080,但实际上他是识别真实高度((1920-虚拟键盘高度)*1080)。解决:可以写一套特定尺寸dimens文件。例如,华为p9的虚拟按键的高度为120px。那就可以再加一套values-1800X1080,把1920X1080复制到 values-1800X1080里面就可以了。完美解决! -
涉及Android手机屏幕适配的相关知识
2016-11-12 15:14:45涉及Android手机屏幕适配的相关知识昨天上班的时候无意间发现了个问题。在我做的项目里,需要自定义重写的框架有很多,对触摸事件要求很高。在自己的几个手机上测试一切正常,然后拿了同事新买的一只比较好的手机测试,发现,字体明显比我手机小了很多,这还不是什么严重的问题,重点是,我明明是点击,它却认为我是在滑动!让我瞬间想感叹:天哪噜!这手机的分辨率是有多高!
分析下来,这现象就因为一句判断它为挪动的语句上出了问题。很low的我,在代码中是设定的死值,只要手指滑动超过了25个像素点,我就把它判为滑动。所以在一个分辨率极高的手机上就完犊子了。
因此,我决定要把这个很蠢的定值给换掉,于是就用了屏幕密度来做了这个数值的控制,代码是非常的简单,我就不粘出来了,但是我意识到手机频幕像素适配的重要性。于是决定趁着因为双十一壕的太猛被爹妈禁足的时间来好好学习一下频幕适配相关知识(壕的是我妈的钱,我依旧那么富有,哈哈哈哈哈哈哈)。
首先,需要理清一些术语及常见度量单位
Density 屏幕密度:屏幕的屋里面积内的像素数量,通常指dpi(每英寸点数)
Resolution 分辨率:在屏幕上的像素总数。
dp(与密度无关的像素,独立像素密度) Density-independent pixel:在定义UI布局时应该使用的虚拟像素单元,它用一种密度无关的方式来表达布局尺寸或位置。
px(像素):屏幕上的点,绝对长度,与硬件相关。
in(英寸):长度单位。[ 1英寸(in)=2.54厘米(cm) ]
dip:Dots Per Inch,每英寸所打印的点数(密度)。
sp:scaled pixels(放大像素)。主要用于字体显示best for textsize。
那么接下来就跟着我偶像——张鸿洋大神的《Android 屏幕适配方案》开启学习路程。
在安卓中,px = dp * (dpi / 160),以160dip(1英寸160个像素点)为标准,即1dp对应1个pixel(px),计算公式如:屏幕密度越大(dip越大),那么一个像素点对应的dp越小,反过来说就是1dp对应的像素点越多。
从上面的分析中,简而易见。dp,脱离了像素的限制,是解决屏幕适配问题的希望。然而,现实很残酷,为4.3寸屏幕准备的UI,运行在5.0寸的屏幕上,很可能在右侧和下侧存在大量的空白。而5.0寸的UI运行到4.3寸的设备上,很可能显示不下。这么情况下,dp就显得无能为力了。
总结:dp能够让同一数值在不同的分辨率展示出大致相同的尺寸大小。但是当设备的尺寸差异较大的时候,就无能为力了。
在大神文中提到了两个解决这个适配问题的方案:
一个就是Android-percent-support这个库!按百分比来布局。
还有一个就是,在项目中针对你所需要适配的手机屏幕的分辨率各自简历一个文件夹(dimens.xml文件,目前我搜到的字体适配方案只有这一个)。这两个等我有空了自己测试一下,今天就对手机屏幕适配做个了解。
此外,屏幕适配还需要注意的事项:
1、AndroidManifest.xml设置
在中Menifest中添加子元素android:anyDensity=”true”时,应用程序安装在不同密度的终端上时,程序会分别加载xxhdpi、xhdpi、hdpi、mdpi、ldpi文件夹中的资源。
相反,如果设为false,即使在文件夹下拥有相同资源,应用不会自动地去相应文件夹下寻找资源:
1) 如果drawable-hdpi、drawable-mdpi、drawable-ldpi三个文件夹中有同一张图片资源的不同密度表示,那么系统会去加载drawable_mdpi文件夹中的资源;
2) 如果drawable-hpdi中有高密度图片,其它两个文件夹中没有对应图片资源,那么系统会去加载drawable-hdpi中的资源,其他同理;
3) 如果drawable-hdpi,drawable-mdpi中有图片资源,drawable-ldpi中没有,系统会加载drawable-mdpi中的资源,其他同理,使用最接近的密度级别。2、横屏竖屏目录区分
1) drawable
a) drawable-hdpi该图片即适用于横屏,也适用于竖屏;
b) drawable-land-hdpi,当屏幕为横屏,且为高密度时,加载此文件夹的资源;
c) drawable-port-hdpi,当屏幕为竖屏,且为高密度时,加载此文件夹中的资源。其他同理。
2) layout
在res目录下建立layout-port和layout-land两个目录,里面分别放置竖屏和横屏两种布局文件,以适应对横屏竖屏自动切换。 -
android手机屏幕适配解决方案(1)
2017-11-08 16:24:23一篇关于手机屏幕适配的博客 -
了解真实的REM手机屏幕适配
2019-08-10 07:43:58rem 作为一个低调的长度单位,由于手机端网页的兴起,在屏幕适配中得到重用。使用 rem 前端开发者可以很方便的在各种屏幕尺寸下,通过等比缩放的方式达到设计图要求的效果。 -
android随笔19——手机屏幕适配
2016-01-09 21:53:08手机屏幕适配 让应用在不同分辨率下的手机有较好的显示效果。 1. 图片适配: 根据手机的像素密度,选择不同drawable文件夹下的图片 2. dimens 尺寸 适配:根据手机的像素密度,选择不同values文件夹... -
Android手机屏幕适配
2015-11-26 15:39:08Android屏幕适配可能一些开发者都会遇到这样的问题,今天就来分享下屏幕适配,其实Android屏幕适配也可以很简单。 基本概念 Android屏幕适配必须要理解的一些概念: px 是英文单词pixel的缩写,意为像素,屏幕上... -
Android 手机屏幕适配
2018-12-19 18:06:233.使用约束布局并且合理的利用约束和偏移比例能解决绝大部分屏幕适配问题 4.准备多套图片:根据不同屏幕密度准备多套分辨率的图片(正常来说要准备6套图片,或者准备2套:一套高分辨率的,一套主流分辨... -
了解真实的『REM』手机屏幕适配
2016-11-23 14:10:10了解真实的『REM』手机屏幕适配 rem 作为一个低调的长度单位,由于手机端网页的兴起,在屏幕适配中得到重用。使用 rem 前端开发者可以很方便的在各种屏幕尺寸下,通过等比缩放的方式达到设计图要求的效果。 ... -
Vue-cli中使用hotcss解决手机屏幕适配问题
2019-12-19 10:28:07Vue-cli中使用hotcss解决手机屏幕适配问题 1、下载hotcss地址:http://imochen.github.io/hotcss/ 2、以下载压缩包为例,将hotcss中的src文件放置在自己的项目中: 3、以项目中使用sass为例,在scss文件中添加$... -
移动端手机屏幕适配
2019-12-11 15:22:09(function (doc, win) { let docEl; docEl = doc.documentElement; let resizeEvt = ‘orientationchange’ in window ? ‘orientationchange’ : ‘resize’; let recalc = function () { let clientWidth = docEl.... -
android app 手机屏幕适配
2017-01-02 04:45:13android屏幕适配是怎么做的,一般需要配置哪些文件,具体是怎么配置的。一般适配哪几种屏幕尺寸,是否需要准备各种屏幕的相应的图片 -
手机屏幕适配问题
2016-06-24 09:14:46可以动态的设置手机屏幕中控件的宽和高或者 获取屏幕信息然后自己写一个百分比 下面是获取屏幕高度和宽度的方法 /** * 获取屏幕高度 * @param context * @return */ @SuppressWarnings("deprecation&... -
unity实战 手机屏幕适配
2019-01-04 21:59:00使用背景 为了在UI中使用特效层,项目Canvas采用了Screen ...在该选择下,会自动根据分辨率适配宽度/高度。 自动适配的规则是: 屏幕实际宽高比值的 <画布大小的宽高比值 采用以宽度缩放 屏幕实际宽高比值的... -
手机屏幕适配解决方案
2016-10-26 17:45:30除此之外还要考虑APP在实际应用场景中,用户千奇百怪的设置,最常见的用户设置行为就是设置手机的字体大小,比如把字体设置成超大或者超小,这对屏幕适配又带来额外的问题。解决这个问题的方法之一是通过在...
-
C++ STL(十五):常用拷贝算法(copy)和替换算法(replace、replace_if、swap)
-
mysql-8.0.21-winx64.zip
-
C#--PictureBox绘制自动换行的文字
-
MySQL 事务和锁
-
2005-2020信息系统项目管理师历年真题(含上午题、案例分析、论文)试题和答案.rar
-
vue项目学习笔记(工程化,前后端分离)
-
ELF视频教程
-
马士兵 mybatis学习笔记
-
Amoeba 实现 MySQL 高可用、负载均衡和读写分离
-
MySQL 主从复制 Replication 详解(Linux 和 W
-
【硬核】一线Python程序员实战经验分享(1)
-
【Zookeeper】集群模式:架构设计猜想
-
设计模式详解:Composite(组合模式)
-
MySQL 触发器
-
项目管理工具与方法
-
零基础极简以太坊智能合约开发环境搭建并开发部署
-
投标方法论
-
C++ STL(十三):常用查找算法(find、find_if、adjacent_find、binary_search、count、count_if)
-
01-虚拟机的安装使用.pdf
-
MATLAB最邻近插值算法的实现