导航:首页 > 操作系统 > android自定义控件大小

android自定义控件大小

发布时间:2022-07-07 15:48:49

android自定义View组合控件

需要看你实现什么效果。一般自定义控件可以用2种方式:
1.
将现有的控件封装起来,作为一个通用的组件来使用,此时只能用代码的形式调用,无法再xml中引用,例如将textview和button封装为一个登录控件。
2.
继承view或者viewgroup,其实viewgroup也是继承的view。然后依次实现onmeasure()、onlayout()、ondraw(),
1.
onmeasure
--
负责测绘控件的大小
2.
onlayout
--
负责控件中子元素摆放的位置
3.
ondraw
--
负责控件和子控件的绘制,使其显示在屏幕中
4.
一些设计和实现较好的自定义view,一般还需要考虑事件的传递、动画的控制、touch事件的处理等

❷ 安卓的自定义Ratingbar控件怎么改变星星大小

RatingBar 自定义style的用法
第一步:配置ratingbar 的style
<style name="foodRatingBar" parent="@android:style/Widget.RatingBar">
<item name="android:progressDrawable">@drawable/food_ratingbar_full</item>
<item name="android:minHeight">48dip</item>
<item name="android:maxHeight">48dip</item>
</style>
第二部:配置 drawable

<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item android:id="@+android:id/background"
android:drawable="@drawable/fans_mark_gray" />
<item android:id="@+android:id/secondaryProgress"
android:drawable="@drawable/fans_mark_gray" />
<item android:id="@+android:id/progress"
android:drawable="@drawable/fans_mark_red" />
</layer-list>

第三部:引用 style

<RatingBar
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:numStars="5"//star 数量
android:stepSize="1" //如果可以交互 每次的增量
android:isIndicator="false"//true 不可交互
android:rating="2" //默认 进度2
style="@style/foodRatingBar"
/>

❸ android 如何设置view的大小

可以在activity中定义一个LinearLayout,然后再将自定义的view加到LinearLayout中:
//假设MyView是你自定义的view
MyView mView=new MyView();
LinearLayout myLinear=new LinearLayout();
//LinearLayout.LayoutParams.WRAP_CONTENT可以设定为你需要的值
LinearLayout.LayoutParams params1 = new LinearLayout.LayoutParams(
LinearLayout.LayoutParams.WRAP_CONTENT,
LinearLayout.LayoutParams.WRAP_CONTENT
);
myLinear.addView(mView,params1);
用这个方法的话还得将setContentView()设为setContentView(myLinear);
如果这个activity中还有其他的view的话,可以通过同样的方法将其加在myLinear上

❹ android自定义控件,我想做一个自定义相对布局控件中,包含两个子TextView

Android动态改变View控件大小的方法:
1、声明控件参数获取对象 LayoutParams lp;
2、获取控件参数: lp = 控件id.getLayoutParams();
3、设置控件参数:如高度。 lp.height -= 10;
4:、使设置生效:控件id.setLayoutParams(lp);
例如如要把Imageview下移200px: ImageView.setPadding( ImageView.getPaddingLeft(), ImageView.getPaddingTop()+200, ImageView.getPaddingRight(), ImageView.getPaddingBottom());

❺ android 自定义view 的高度,宽度怎么设置

Android中View是显示控件,需要用一个layout布局来装载,layout尺寸大写的设置如下:
1. 尽量使用wrap_content、match_parent、weight 来规定layout的大小。
2. 要确保布局的灵活性并适应各种尺寸的屏幕,应使用 “wrap_content” 和 “match_parent” 控制某些视图组件的宽度和高度。
3. 使用 “wrap_content”,系统就会将视图的宽度或高度设置成所需的最小尺寸以适应视图中的内容,而 “match_parent”(在低于 API 级别 8 的级别中称为“fill_parent”)则会展开组件以匹配其父视图的尺寸。
4. 如果使用 “wrap_content” 和 “match_parent” 尺寸值而不是硬编码的尺寸,视图就会相应地仅使用自身所需的空间或展开以填满可用空间。此方法可让布局正确适应各种屏幕尺寸和屏幕方向。
5. 如果某些地方必须要规定控件的大小,那么要使用dp 或者 dip单位。

❻ android自定义控件怎么用

开发自定义控件的步骤:
1、了解View的工作原理
2、 编写继承自View的子类
3、 为自定义View类增加属性
4、 绘制控件
5、 响应用户消息
6 、自定义回调函数

一、View结构原理
Android系统的视图结构的设计也采用了组合模式,即View作为所有图形的基类,Viewgroup对View继承扩展为视图容器类。
View定义了绘图的基本操作
基本操作由三个函数完成:measure()、layout()、draw(),其内部又分别包含了onMeasure()、onLayout()、onDraw()三个子方法。具体操作如下:
1、measure操作
measure操作主要用于计算视图的大小,即视图的宽度和长度。在view中定义为final类型,要求子类不能修改。measure()函数中又会调用下面的函数:
(1)onMeasure(),视图大小的将在这里最终确定,也就是说measure只是对onMeasure的一个包装,子类可以覆写onMeasure()方法实现自己的计算视图大小的方式,并通过setMeasuredDimension(width, height)保存计算结果。

2、layout操作
layout操作用于设置视图在屏幕中显示的位置。在view中定义为final类型,要求子类不能修改。layout()函数中有两个基本操作:
(1)setFrame(l,t,r,b),l,t,r,b即子视图在父视图中的具体位置,该函数用于将这些参数保存起来;
(2)onLayout(),在View中这个函数什么都不会做,提供该函数主要是为viewGroup类型布局子视图用的;

3、draw操作
draw操作利用前两部得到的参数,将视图显示在屏幕上,到这里也就完成了整个的视图绘制工作。子类也不应该修改该方法,因为其内部定义了绘图的基本操作:
(1)绘制背景;
(2)如果要视图显示渐变框,这里会做一些准备工作;
(3)绘制视图本身,即调用onDraw()函数。在view中onDraw()是个空函数,也就是说具体的视图都要覆写该函数来实现自己的显示(比如TextView在这里实现了绘制文字的过程)。而对于ViewGroup则不需要实现该函数,因为作为容器是“没有内容“的,其包含了多个子view,而子View已经实现了自己的绘制方法,因此只需要告诉子view绘制自己就可以了,也就是下面的dispatchDraw()方法;
(4)绘制子视图,即dispatchDraw()函数。在view中这是个空函数,具体的视图不需要实现该方法,它是专门为容器类准备的,也就是容器类必须实现该方法;
(5)如果需要(应用程序调用了setVerticalFadingEdge或者setHorizontalFadingEdge),开始绘制渐变框;
(6)绘制滚动条;
从上面可以看出自定义View需要最少覆写onMeasure()和onDraw()两个方法。

二、View类的构造方法
创建自定义控件的3种主要实现方式:
1)继承已有的控件来实现自定义控件: 主要是当要实现的控件和已有的控件在很多方面比较类似, 通过对已有控件的扩展来满足要求。
2)通过继承一个布局文件实现自定义控件,一般来说做组合控件时可以通过这个方式来实现。
注意此时不用onDraw方法,在构造广告中通过inflater加载自定义控件的布局文件,再addView(view),自定义控件的图形界面就加载进来了。
3)通过继承view类来实现自定义控件,使用GDI绘制出组件界面,一般无法通过上述两种方式来实现时用该方式。

三、自定义View增加属性的两种方法:
1)在View类中定义。通过构造函数中引入的AttributeSet 去查找XML布局的属性名称,然后找到它对应引用的资源ID去找值。
案例:实现一个带文字的图片(图片、文字是onDraw方法重绘实现)

public class MyView extends View {

private String mtext;
private int msrc;

public MyView(Context context) {
super(context);
}

public MyView(Context context, AttributeSet attrs) {
super(context, attrs);
int resourceId = 0;
int textId = attrs.getAttributeResourceValue(null, "Text",0);
int srcId = attrs.getAttributeResourceValue(null, "Src", 0);
mtext = context.getResources().getText(textId).toString();
msrc = srcId;
}

@Override
protected void onDraw(Canvas canvas) {
Paint paint = new Paint();
paint.setColor(Color.RED);
InputStream is = getResources().openRawResource(msrc);
Bitmap mBitmap = BitmapFactory.decodeStream(is);
int bh = mBitmap.getHeight();
int bw = mBitmap.getWidth();
canvas.drawBitmap(mBitmap, 0,0, paint);
//canvas.drawCircle(40, 90, 15, paint);
canvas.drawText(mtext, bw/2, 30, paint);
}
}

布局文件:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >

<com.example.myimageview2.MyView
android:id="@+id/myView1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
Text="@string/hello_world"
Src="@drawable/xh"/>

</LinearLayout>

属性Text, Src在自定义View类的构造方法中读取。

2)通过XML为View注册属性。与Android提供的标准属性写法一样。
案例: 实现一个带文字说明的ImageView (ImageView+TextView组合,文字说明,可在布局文件中设置位置)

public class MyImageView extends LinearLayout {

public MyImageView(Context context) {
super(context);
}

public MyImageView(Context context, AttributeSet attrs) {
super(context, attrs);
int resourceId = -1;
TypedArray typedArray = context.obtainStyledAttributes(attrs,
R.styleable.MyImageView);
ImageView iv = new ImageView(context);
TextView tv = new TextView(context);
int N = typedArray.getIndexCount();
for (int i = 0; i < N; i++) {
int attr = typedArray.getIndex(i);
switch (attr) {
case R.styleable.MyImageView_Oriental:
resourceId = typedArray.getInt(
R.styleable.MyImageView_Oriental, 0);
this.setOrientation(resourceId == 1 ? LinearLayout.HORIZONTAL
: LinearLayout.VERTICAL);
break;
case R.styleable.MyImageView_Text:
resourceId = typedArray.getResourceId(
R.styleable.MyImageView_Text, 0);
tv.setText(resourceId > 0 ? typedArray.getResources().getText(
resourceId) : typedArray
.getString(R.styleable.MyImageView_Text));
break;
case R.styleable.MyImageView_Src:
resourceId = typedArray.getResourceId(
R.styleable.MyImageView_Src, 0);
iv.setImageResource(resourceId > 0 ?resourceId:R.drawable.ic_launcher);
break;
}
}
addView(iv);
addView(tv);
typedArray.recycle();
}
}

attrs.xml进行属性声明, 文件放在values目录下

<?xml version="1.0" encoding="utf-8"?>
<resources>

<declare-styleable name="MyImageView">
<attr name="Text" format="reference|string"></attr>
<attr name="Oriental" >
<enum name="Horizontal" value="1"></enum>
<enum name="Vertical" value="0"></enum>
</attr>
<attr name="Src" format="reference|integer"></attr>
</declare-styleable>

</resources>

MainActivity的布局文件:先定义命名空间 xmlns:uview="http://schemas.android.com/apk/res/com.example.myimageview2" (com.example.myimageview2为你
在manifest中定义的包名)
然后可以像使用系统的属性一样使用:uview:Oriental="Vertical"

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:uview="http://schemas.android.com/apk/res/com.example.myimageview2"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:context=".MainActivity" >

<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/hello_world" />

<com.example.myimageview2.MyImageView
android:id="@+id/myImageView1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
uview:Text="这是一个图片说明"
uview:Src="@drawable/tw"
uview:Oriental="Vertical">
</com.example.myimageview2.MyImageView>

</LinearLayout>

四、控件绘制 onDraw()

五、
六:自定义View的方法
onFinishInflate() 回调方法,当应用从XML加载该组件并用它构建界面之后调用的方法
onMeasure() 检测View组件及其子组件的大小
onLayout() 当该组件需要分配其子组件的位置、大小时
onSizeChange() 当该组件的大小被改变时
onDraw() 当组件将要绘制它的内容时
onKeyDown 当按下某个键盘时
onKeyUp 当松开某个键盘时
onTrackballEvent 当发生轨迹球事件时
onTouchEvent 当发生触屏事件时
onWindowFocusChanged(boolean) 当该组件得到、失去焦点时
onAtrrachedToWindow() 当把该组件放入到某个窗口时
onDetachedFromWindow() 当把该组件从某个窗口上分离时触发的方法
onWindowVisibilityChanged(int): 当包含该组件的窗口的可见性发生改变时触发的方法

❼ android 自定义view 怎么设置其宽度和高度

自定义view的父类肯定是View或者View的子类。所以也是支持layout_width,layout_height属性的,如果想另外控制的话,可以重写View的onDraw方法。

❽ Android 自定义控件 动态设置高度

Android动态改变View控件大小的方法:
1、声明控件参数获取对象 LayoutParams lp;
2、获取控件参数: lp = 控件id.getLayoutParams();
3、设置控件参数:如高度。 lp.height -= 10;
4:、使设置生效:控件id.setLayoutParams(lp);
例如如要把Imageview下移200px: ImageView.setPadding( ImageView.getPaddingLeft(), ImageView.getPaddingTop()+200, ImageView.getPaddingRight(), ImageView.getPaddingBottom());

❾ Android 自定义控件开发中 onLayout如何设置里面控件的大小(Android 大神请进……)

ViewGroup在onLayout函数中通过调用其children的layout函数来设置子视图相对与父视图中的位置,具体位置由函数layout的参数决定,当我们继承ViewGroup时必须重载onLayout函数(ViewGroup中onLayout是abstract修饰),然而onMeasure并不要求必须重载,因为相对与layout来说,measure过程并不是必须的,具体后面会提到。首先我们来看下View.java中函数layout和onLayout的源码

public void layout(int l, int t, int r, int b) {
int oldL = mLeft;
int oldT = mTop;
int oldB = mBottom;
int oldR = mRight;
boolean changed = setFrame(l, t, r, b);
if (changed || (mPrivateFlags & LAYOUT_REQUIRED) == LAYOUT_REQUIRED) {
if (ViewDebug.TRACE_HIERARCHY) {
ViewDebug.trace(this, ViewDebug.HierarchyTraceType.ON_LAYOUT);
}

onLayout(changed, l, t, r, b);
mPrivateFlags &= ~LAYOUT_REQUIRED;

ListenerInfo li = mListenerInfo;
if (li != null && li.mOnLayoutChangeListeners != null) {
ArrayList<OnLayoutChangeListener> listenersCopy =
(ArrayList<OnLayoutChangeListener>)li.mOnLayoutChangeListeners.clone();
int numListeners = listenersCopy.size();
for (int i = 0; i < numListeners; ++i) {
listenersCopy.get(i).onLayoutChange(this, l, t, r, b, oldL, oldT, oldR, oldB);
}
}
}
mPrivateFlags &= ~FORCE_LAYOUT;
}

函数layout的主体过程还是很容易理解的,首先通过调用setFrame函数来对4个成员变量(mLeft,mTop,mRight,mBottom)赋值,然后回调onLayout函数,最后回调所有注册过的listener的onLayoutChange函数。
对于View来说,onLayout只是一个空实现,一般情况下我们也不需要重载该函数:
protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
}

接着我们来看下ViewGroup.java中layout的源码:

public final void layout(int l, int t, int r, int b) {
if (mTransition == null || !mTransition.isChangingLayout()) {
super.layout(l, t, r, b);
} else {
// record the fact that we noop'd it; request layout when transition finishes
mLayoutSuppressed = true;
}
}

super.layout(l, t, r, b)调用的即是View.java中的layout函数,相比之下ViewGroup增加了LayoutTransition的处理,LayoutTransition是用于处理ViewGroup增加和删除子视图的动画效果,也就是说如果当前ViewGroup未添加LayoutTransition动画,或者LayoutTransition动画此刻并未运行,那么调用super.layout(l, t, r, b),继而调用到ViewGroup中的onLayout,否则将mLayoutSuppressed设置为true,等待动画完成时再调用requestLayout()。
上面super.layout(l, t, r, b)会调用到ViewGroup.java中onLayout,其源码实现如下:

@Override
protected abstract void onLayout(boolean changed,
int l, int t, int r, int b);

和前面View.java中的onLayout实现相比,唯一的差别就是ViewGroup中多了关键字abstract的修饰,也就是说ViewGroup类只能用来被继承,无法实例化,并且其子类必须重载onLayout函数,而重载onLayout的目的就是安排其children在父视图的具体位置。重载onLayout通常做法就是起一个for循环调用每一个子视图的layout(l, t, r, b)函数,传入不同的参数l, t, r, b来确定每个子视图在父视图中的显示位置。
那layout(l, t, r, b)中的4个参数l, t, r, b如何来确定呢?联想到之前的measure过程,measure过程的最终结果就是确定了每个视图的mMeasuredWidth和mMeasuredHeight,这两个参数可以简单理解为视图期望在屏幕上显示的宽和高,而这两个参数为layout过程提供了一个很重要的依据(但不是必须的),为了说明这个过程,我们来看下LinearLayout的layout过程:

void layoutVertical() {
……
for (int i = 0; i < count; i++) {
final View child = getVirtualChildAt(i);
if (child == null) {
childTop += measureNullChild(i);
} else if (child.getVisibility() != GONE) {
final int childWidth = child.getMeasuredWidth();
final int childHeight = child.getMeasuredHeight();
……
setChildFrame(child, childLeft, childTop + getLocationOffset(child),
childWidth, childHeight);
childTop += childHeight + lp.bottomMargin + getNextLocationOffset(child);

i += getChildrenSkipCount(child, i);
}
}
}
private void setChildFrame(View child, int left, int top, int width, int height) {
child.layout(left, top, left + width, top + height);
}

从setChildFrame可以看到LinearLayout中的子视图的右边界等于left + width,下边界等于top+height,也就是说在LinearLayout中其子视图显示的宽和高由measure过程来决定的,因此measure过程的意义就是为layout过程提供视图显示范围的参考值。

layout过程必须要依靠measure计算出来的mMeasuredWidth和mMeasuredHeight来决定视图的显示大小吗?事实并非如此,layout过程中的4个参数l, t, r, b完全可以由视图设计者任意指定,而最终视图的布局位置和大小完全由这4个参数决定,measure过程得到的mMeasuredWidth和mMeasuredHeight提供了视图大小的值,但我们完全可以不使用这两个值,可见measure过程并不是必须的。\\

说到这里就不得不提getWidth()、getHeight()和getMeasuredWidth()、getMeasuredHeight()这两对函数之间的区别,getMeasuredWidth()、getMeasuredHeight()返回的是measure过程得到的mMeasuredWidth和mMeasuredHeight的值,而getWidth()和getHeight()返回的是mRight - mLeft和mBottom - mTop的值,看View.java中的源码便一清二楚了:

public final int getMeasuredWidth() {
return mMeasuredWidth & MEASURED_SIZE_MASK;
}
public final int getWidth() {
return mRight - mLeft;
}

这也解释了为什么有些情况下getWidth()和getMeasuredWidth()以及getHeight()和getMeasuredHeight()会得到不同的值。

阅读全文

与android自定义控件大小相关的资料

热点内容
大连php培训学校 浏览:979
怎么指定定向流量app的免流 浏览:900
华为云服务器有啥软件 浏览:654
礼记正义pdf 浏览:988
CorePDF 浏览:733
python多文件调用 浏览:329
linux如何用python 浏览:188
超易学的python 浏览:159
控制面板命令行 浏览:51
为什么空气难压缩是因为斥力吗 浏览:643
郭天祥单片机实验板 浏览:601
服务器有什么危害 浏览:258
饥荒怎么开新的独立服务器 浏览:753
文件夹变成了 浏览:560
linuxpython绿色版 浏览:431
怎么下载小爱同学音箱app 浏览:554
python占位符作用 浏览:76
javajdbcpdf 浏览:543
php网页模板下载 浏览:192
python试讲课pygame 浏览:409