主要讲解应用程序锁涉及的主要元素,包括资源、组件、事件处理、应用风格、数据适配等。
1.布局文件
布局文件通常由根布局和子布局构成,在布局文件的应用程序中,会涉及不同的控件和目标环境。布局文件看似简单,实则需要很多技巧和经验,本节仅介绍布局加载、密度和一些特殊标签的使用。
(1)加载布局
通过setContextView方法可以隐式地加载布局文件,如果希望显示地加载布局文件,可以在Activity中通过getLayoutInflater方法来获取LAYOUT_INFLATER_SERVICE服务将布局文件实例化。另外也可以获取已有LayoutInflater对象的副本来实例化布局文件。
通过getLayoutInflater方法实例化布局文件:View demo=getLayoutInflater().Inflate(R.layout.demo, null);
通过系统服务实例化布局文件:LayoutInflater inflater=(LayoutInflater)context.getSystemServiceContext.LAYOUT_INFLATER_SERVICE); View demo=inflater.Inflater(R.layout.demo, null);
通过已有LayoutInflater对象的副本实例化布局文件:LayoutInflater inflater=from(context); View demo=inflater.Inflater(R.layout.demo, null);
(2)密度的逻辑
在构建布局文件时,自然会涉及像素的问题,在Android中,有dp、px、dip等几种单位,其中最常用的是dip。
dip的设置与分辨率无关,但与屏幕密度有关。在默认情况下,LDPI的密度为120,系数为0.75;MDPI的密度为160,系数为1.0;HDPI的密度为240,系数为1.5;XHDPI的密度为320,系数为2.0。所谓密度即单位平方英寸中含像素的数量。
px与dip的关系如下:px=(int)(dip*density+0.5f)
(3)特殊标签
在Android布局文件中,除了普通的UI控件标签外,还有几个特殊标签,他们是viewStub、reuqestFocus、merge和include。
1)viewStub标签
viewStub标签实际上是一个特殊的控件,在默认情况下,其所包含的控件是不可见的,并且不占用任何内存空间,开发者可以通过setVisibility和inflater加载viewStub标签包含的布局。
viewStub标签所包含的布局是通过android:layout属性引用的外部布局文件。
2)requestFocus标签
requestFocus标签0可以使相应的UI控件获得焦点,在使用时,用在UI控件标签内部。
3)merge标签
merge标签在优化UI布局中具有重要的作用,可以减少多余或额外的层级。在应用中,merge标签主要用于优化根布局或者在使用viewStub标签和include标签时减少引用冗余。需要注意的时,merge标签仅能作为布局文件的根布局,如果希望通过布局加载器(LayoutInflater)加载以merge标签为根布局的布局文件,需要使用View inflate(int resource, ViewGroup root, boolean attachToRoot)指定一个ViewGroup作为其容器。并且要设置attachToRoot为true。
4)include标签
include标签的作用类似于C语言中的include关键字,用于引用外部布局文件,起到复用布局文件的作用。
(4)可用空间的分配
在布局文件中,如何使编写的布局文件能够尽可能地适配不同的目标环境。虽然Android为实现目标环境适配进行了诸多考虑,可以精确指明布局文件适配的分辨率、密度、横竖屏等,但是没有人喜欢针对同一个界面编写多个布局文件,因为这样的维护成本过于巨大,所以应尽可能地在布局文件本身的结构上下工夫。
笔者的经验是尽可能灵活地运用LinearLayout和RelativeLayout等布局控件。对于LinearLayout来说,关键在于其android:layout_weight属性的灵活运用,RelativeLayout则相对简单些。
2.值文件
值文件是Android应用必需的资源文件,其承担着应用的UI配置和文字显示工作。值文件包括字符串文件、字符串数组文件、配置文件、整数数组文件、维度文件、属性文件、颜色文件、风格文件、主题文件、表示符文件等,其中英文目录为res\value。
(1)字符串文件
字符串是最常用的值资源,其常用的设置方法:<string name="edit_event_from_lable">From</string>
如果该字符串资源不必本地化,则需要设置其translatable属性为false,具体设置方法:<string name="voice_mode_off" translatable="false">2</string>
在加载资源的过程中,会以资源的ID为线索进行加载,Android不允许在同一名字空间中出现相同的ID。
在Android中,资源分系统资源和应用资源两种,这两种资源在应用中引用的方式略有差异。系统资源并不全部对应用层开发,对应用层开放的系统资源在frameworks\base\core\res\res\values\目录下的public.xml中定义。不对应用层开发的系统资源的加载方式:getString(com.android.internal.R.string.using)
在Android中,文件特效目前仅支持加粗和斜体两种,实现加下划线的功能,则需要借组HTML语法,实现方法:textView.setText(Html.fromHtml("<u>"+helloStr+"</u>"))
语言的切换是通过资源管理器进行的,实现方法:Resource resource=getResources(); Configuration config=resource.getConfiguration(); DisplayMetrics dm=resource.getDisplayMetrice(); config.locale=Locale.SIMPLIFIED_CHINESE; resource.updateConfiguration(config,
dm);
(2)字符串数组文件
字符串数组通常用于下拉框等场景,如果不希望该字符串数组随着语言环境的变化而变化,可以将字符串数组的translatable属性设为false。
(3)配置文件
配置文件在应用开发中并不常用,通常用于应用的设置等场景,配置文件的实现:
<resources>
<bool name="config_sf_limitedAlpha">false</bool>
<integer name="config_shortAnimTime">150</integer>
</resources>
在Java中配置文件的加载方法:mLimitedAlphaCompositing=context.getResource().getBoolean(com.android.internal.R.bool.config_sf_limitedAlpha);
(4)整数数据文件
整数数组和字符串数据的使用方法类似。
在Java中整数数组的加载方式:int[] tmpArray=getResource().getIntArray(com.android.internal.R.array.config_virtualKeyVibePattern);
(5)维度文件
在Java中维度文件的加载方法:Int w=getResource().getDimensionPixelSize(com.android.internal.R.dimen.thumbnail_width);
(6)属性文件
在Android中,属性文件通常由多个标签组成,
declare-styleable标签用于声明一个属性组,一个属性组可以由多个属性构成。
加载属性组的方法:TypeArray a=context.obtainStyledAttributes(attrs, com.android.internal.R.styleable.Animation); a.recycle();
eat-comment标签用于声明标签上的内容为注释。attr标签用于声明属性。一个属性包括属性名和属性格式两部分。
偏好值的实现分为enum、flag两种类型,其中flag表示以二进制方式表示偏好值。
(7)颜色文件
颜色的设置文件通常会放在框架层的资源目录中,对颜色属性进行引用而不是在应用层显示声明,有利于在系统层面保持UI的一致性。在颜色的声明中,采用的时ARGB的格式
<resource>
<color name="magic_flame">#00ffffff</color>
</resource>
在Java中颜色设置的加载方式:setBackgroundColor(getResources().getColor(R.color.candidate_background));
(8)风格文件
一个好的应用除了技术上应设计得优雅外(即代码具有高的可读性、可扩展性、复用性、性能),用户体验也非常重要(包括文字的用语和观感和交互设计),风格的设计决定了用户体验中文字和图片的效果。
(9)主题文件
主题文件在框架层比较常用,对于进行差异化工作的厂商而言,保持同一个主题是一个基本的UI需求,定义统一的风格文件供公司所有产品引用,是个不错的选择。
(10)标识符文件
标识符文件对于应用层开发者来说并不常见,但这并不意味着开发者完全接触不到。在使用系统提供的ListView、Tab等就会涉及。
3.创建菜单
根据应用场景的不同,菜单可以分为选项菜单(OptionsMenu)、上下文菜单(Context Menu)、子菜单(SubMenu)等3种,选项菜单是最普通的菜单(按Menu键弹出的菜单就是选项菜单),上下文菜单通常用于列表等场景中。
除了OptionsMenu、SubMenu、ContextMenu外。Android在构建菜单时还经常涉及MenuItem、MenuInflater等类。MenuInflater在加载XML资源文件时采用的解析器为XmlPullParser。出于性能方面的考虑,目前MenuInflater尚不支持加载未经处理的XML资源文件。
上下文菜单和子菜单不支持图标。菜单组和快捷键的概念在当前基于触摸屏的智能终端中并不常用。
(1)选项菜单