Android 计算控件尺寸(转)
onMeasure方法在控件的父元素正要放置它的子控件时调用。它会问一个问题,“你想要用多大地方啊?”,然后传入两个参数—— widthMeasureSpec和heightMeasureSpec。它们指明控件可获得的空间以及关于这个空间描述的元数据。比返回一个结果要好的 方法是你传递View的高度和宽度到setMeasuredDimension方法里。
接下来的代码片段给出了如何重写onMeasure。注意,调用的本地空方法是来计算高度和宽度的。它们会译解widthHeightSpec和heightMeasureSpec值,并计算出合适的高度和宽度值。
Java代码:
@Override
protectedvoidonMeasure(intwidthMeasureSpec,intheightMeasureSpec){
intmeasuredHeight=measureHeight(heightMeasureSpec);
intmeasuredWidth=measureWidth(widthMeasureSpec);
setMeasuredDimension(measuredHeight,measuredWidth);
}
privateintmeasureHeight(intmeasureSpec){
//高度测量窗口的回归.
}
privateintmeasureWidth(intmeasureSpec){
//还测量窗口的宽度.
}
边界参数——widthMeasureSpec和heightMeasureSpec,效率的原因以整数的方式传入。在它们使用之前,首先要做的是使用MeasureSpec类的静态方法getMode和getSize来译解,如下面的片段代码所示:
Java代码:
intspecMode=MeasureSpec.getMode(measureSpec);
intspecSize=MeasureSpec.getSize(measureSpec);
接下来的框架代码给出了处理View测量的典型实现:
Java代码:
@Override
protectedvoidonMeasure(intwidthMeasureSpec,intheightMeasureSpec){
intmeasuredHeight=measureHeight(heightMeasureSpec);
intmeasuredWidth=measureWidth(widthMeasureSpec);
setMeasuredDimension(measuredHeight,measuredWidth);
}
privateintmeasureHeight(intmeasureSpec){
intspecMode=MeasureSpec.getMode(measureSpec);
intspecSize=MeasureSpec.getSize(measureSpec);
//如果没有限制默认大小是指定的.
intresult=500;
if(specMode==MeasureSpec.AT_MOST)
{
//你理想的大小的计算
//在这个最大值控制.
//如果你能控制的充满可用
//外太空返回束缚.
result=specSize;
}
elseif(specMode==MeasureSpec.EXACTLY)
{
//如果你的控制能符合这些界限返回那个价值.
result=specSize;
}
returnresult;
}
privateintmeasureWidth(intmeasureSpec){
intspecMode=MeasureSpec.getMode(measureSpec);
intspecSize=MeasureSpec.getSize(measureSpec);
//如果没有限制默认大小是指定的.
intresult=500;
if(specMode==MeasureSpec.AT_MOST)
{
//理想尺寸的计算你的控制
//在这个最大的尺寸。
//如果你的控制填充的可用空间
//返回外面的束缚。
result=specSize;
}
elseif(specMode==MeasureSpec.EXACTLY)
{
//如果你的控制能符合这些界限返回那个价值.
result=specSize;
}
returnresult;
}
的要求。一个MeasureSpec包含一个尺寸和模式。
有三种可能的模式:
UNSPECIFIED:父布局没有给子布局任何限制,子布局可以任意大小。
EXACTLY:父布局决定子布局的确切大小。不论子布局多大,它都必须限制在这个界限里。
AT_MOST:子布局可以根据自己的大小选择任意大小。
为了减少内存分配,MeasueSpecs用整数表示。这个类提供打包和解包<size,mode>元组为整型。参考方法:public static int makeMeasureSpec(int size,int mode)。
转:http://blog.csdn.net/zjl5211314/article/details/6952698
一个MeasureSpec封装了父布局传递给子布局的布局要求,每个MeasureSpec代表了一组宽度和高度的要求。一个MeasureSpec由大小和模式组成。它有三种模式:UNSPECIFIED(未指定),父元素部队自元素施加任何束缚,子元素可以得到任意想要的大小;EXACTLY(完全),父元素决定自元素的确切大小,子元素将被限定在给定的边界里而忽略它本身大小;AT_MOST(至多),子元素至多达到指定大小的值。
它常用的三个函数:
1.static int getMode(int measureSpec):根据提供的测量值(格式)提取模式(上述三个模式之一)
2.static int getSize(int measureSpec):根据提供的测量值(格式)提取大小值(这个大小也就是我们通常所说的大小)
3.static int makeMeasureSpec(int size,int mode):根据提供的大小值和模式创建一个测量值(格式)
这个类的使用呢,通常在view组件的onMeasure方法里面调用但也有少数例外,看看几个例子:
a.首先一个我们常用到的一个有用的函数,View.resolveSize(int size,int measureSpec)
8421 public static int resolveSize(int size, int measureSpec) { 8422 int result = size; 8423 int specMode = MeasureSpec.getMode(measureSpec); 8424 int specSize = MeasureSpec.getSize(measureSpec); 8425 switch (specMode) { 8426 case MeasureSpec.UNSPECIFIED: 8427 result = size; 8428 break; 8429 case MeasureSpec.AT_MOST: 8430 result = Math.min(size, specSize); 8431 break; 8432 case MeasureSpec.EXACTLY: 8433 result = specSize; 8434 break; 8435 } 8436 return result; 8437 }
上面既然要用到measureSpec值,那自然表示这个函数通常是在onMeasure方法里面调用的。简单说一下,这个方法的主要作用就是根据你提供的大小和模式,返回你想要的大小值,这个里面根据传入模式的不同来做相应的处理。
再看看MeasureSpec.makeMeasureSpec方法,实际上这个方法很简单:
9023 public static int makeMeasureSpec(int size, int mode) { 9024 return size + mode; 9025 }
这样大家不难理解size跟measureSpec区别了。看看它的使用吧,ListView.measureItem(View child)
2464 private void measureItem(View child) { 2465 ViewGroup.LayoutParams p = child.getLayoutParams(); 2466 if (p == null) { 2467 p = new ViewGroup.LayoutParams( 2468 ViewGroup.LayoutParams.MATCH_PARENT, 2469 ViewGroup.LayoutParams.WRAP_CONTENT); 2470 } 2471 2472 int childWidthSpec = ViewGroup.getChildMeasureSpec(mWidthMeasureSpec, 2473 mListPadding.left + mListPadding.right, p.width); 2474 int lpHeight = p.height; 2475 int childHeightSpec; 2476 if (lpHeight > 0) { 2477 childHeightSpec = MeasureSpec.makeMeasureSpec(lpHeight, MeasureSpec.EXACTLY); 2478 } else { 2479 childHeightSpec = MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED); 2480 } 2481 child.measure(childWidthSpec, childHeightSpec); 2482 }
measureSpec方法通常在ViewGroup中用到,它可以根据模式(MeasureSpec里面的三个)可以调节子元素的大小。
注意,使用EXACTLY和AT_MOST通常是一样的效果,如果你要区别他们,那么你就要使用上面的函数View.resolveSize(int size,int measureSpec)返回一个size值,然后使用你的view调用setMeasuredDimension(int,int)函数。
8406 protected final void setMeasuredDimension(int measuredWidth, int measuredHeight) { 8407 mMeasuredWidth = measuredWidth; 8408 mMeasuredHeight = measuredHeight; 8409 8410 mPrivateFlags |= MEASURED_DIMENSION_SET; 8411 }
然后你调用view.getMeasuredWidth,view.getMeasuredHeigth 返回的就是上面函数里的mMeasuredWidth,mMeasuredHeight的值。
mode共有三种情况,取值分别为MeasureSpec.UNSPECIFIED, MeasureSpec.EXACTLY, MeasureSpec.AT_MOST。
MeasureSpec.EXACTLY是精确尺寸,当我们将控件的layout_width或layout_height指定为具体数值时如andorid:layout_width="50dip",或者为FILL_PARENT是,都是控件
大小已经确定的情况,都是精确尺寸。
MeasureSpec.AT_MOST 是最大尺寸,当控件的layout_width或layout_height指定为WRAP_CONTENT时,控件大小一般随着控件的子空间或内容进行变化,此时控件尺寸
只要不超过父控件允许的最大尺寸即可。因此,此时的mode是AT_MOST,size给出了父控件允许的最大尺寸。
MeasureSpec.UNSPECIFIED是未指定尺寸,这种情况不多,一般都是父控件是AdapterView,通过measure方法传入的模式。
Android 计算控件尺寸(转)相关推荐
- android 电量控件,Android实现显示电量的控件代码
下面介绍了Android实现显示电量的控件代码,具体代码如下: 1.目录结构,本人是使用安卓死丢丢. 2.运行界面,输入框中输入数值,点击刷新,会再电池中显示出相应的电量 3.绘制自定义电池控件,首先 ...
- android 绘制控件,Android_开发_Day29_自己绘制控件
Android_开发Day29自己绘制控件 目的: 在Android中很多时候系统的控件是不能满足需要的,组合方式定义控件又非常繁琐,因此此时需要自己画一个控件,才能满足需要 技术: <1> ...
- android 获取控件在屏幕中的坐标
今天,简单讲讲android如何获取控件在屏幕中的坐标. 这个其实也很简单,但是昨天做一个功能时,需要功能控件的坐标做一些逻辑操作时,居然不知道怎么做.所以在网上查找了资料后,解决了这个问题.这里记录 ...
- 一个Demo让你掌握Android所有控件
一个Demo让你掌握Android所有控件 原文:一个Demo让你掌握Android所有控件 本文是转载收藏,侵删,出处:"安卓巴士" 下面给出实现各个组件的源代码: 1 ...
- Android图片控件,跟随列表(recyclerView)的上下滚动而同步平移。
一个用于放置在RecycleView中的图片控件,其主要功能是跟随列表的上下滚动而上下平移,使得呈现出一种图像相对列表静止的感觉. Overview ScrollingImageView 提供以下特性 ...
- Android 画廊控件Gallary
Android 画廊控件Gallary.将图片显示成连续的带状. package com.gallerydemo;import java.lang.reflect.Field; import java ...
- Android图表控件MPAndroidChart——BarChart实现多列柱状图以及堆积柱状图
目录 前言 1. 数据准备 1.1 数据来源 2. 图表展示 2.1 MPAndroidChart获取 2.2 数据对象获取 2.3 数据展示 3. 柱状图外观完善 3.1 去掉图表外框,描述内容以及 ...
- Android图表控件MPAndroidChart——LineChart实现 XY轴、原点线的直尺刻度样式
接上文: Android图表控件MPAndroidChart--曲线图LineChart的使用(多条曲线) 其他相关文章: Android图表控件MPAndroidChart的简单介绍(MPAndro ...
- Android图表控件MPAndroidChart实现左右滑动以及联动
前言 MPAndroidChart是一个功能强大的Android图表控件库,它实现了许多常见的图表效果.关于MPAndroidChart的使用文章已经很多了,这里不再详细介绍它的使用.当数据量过多时, ...
最新文章
- codechef ANUCBC(背包)
- android 折叠与展开,android – 如何根据滚动方向折叠/展开视图?
- 单调队列板子:求滑动窗口中最大值和最小值
- http中的净荷 payload(有效载荷、有效负载)是什么?
- Nginx教程系列一:Nginx简介(反向代理、负载均衡)
- java面试常见问题
- HDFS(一) HDFS设计目标
- Mysqldump备份和恢复
- C++ map基本操作
- 动态添加内容到百度搜索框里
- python self 值自动改变,在python中对self的理解
- VS2013编译64位boost流程及若干问题
- Ubuntu用户及用户组管理命令
- Vue活动倒计时的功能
- 2023真无线蓝牙耳机怎么选?值得入手的蓝牙耳机推荐
- 机器学习之聚类算法——聚类效果评估可视化
- 听书类APP消息功能竞品分析
- mini2440----keil for AMR之IIC读写EEPROM(AT24C08)
- ~ 如何用C++自制一个日麻游戏 ~(一)大体框架构建 § 2 数据结构
- C#/WPF/.NET 第三方ddl强签名解决(xxx, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null)
热门文章
- 政策“风云突变”!新东方市值蒸发超近2000亿!俞敏洪何去何从?
- 微服务 撮合引擎 撮合微服务搭建 案例 4
- 非常漂亮的个人网站引导页HTML源码
- Tomato学习笔记-Vscode配置Makefile(使用task.jason和launch.jason)
- DHU 第一题 重排链表
- Typora开始收费了,这可咋整?
- DDR4 原理图设计、仿真和问题分析
- 很贴心的一份,适合非科班入门计算机的课程路线
- beetl模板使用场景_Java 模板引擎 Beetl 2.0 发布
- windows7 64位使用U盘进行系统安装