自定义视图的简单应用
来源:互联网 发布:广东人吃福建人 知乎 编辑:程序博客网 时间:2024/05/19 17:06
1、在res/values目录下新建attrs.xml文件:
<resources> <declare-styleable name="myStyleable"> <attr name="max" format="integer"/> <attr name="progress" format="integer"/> <attr name="textSize" format="dimension"/> <attr name="smallBgColor" format="color"/> <attr name="progressColor" format="color"/> </declare-styleable></resources>
format(自定义属性的格式)可选内容有integer、dimension(尺寸)、color、boolean、enum(枚举值)、flag(位或运算)、float、fraction(百分数)、reference(参考某一ID、默认)、string.
<declare-styleable name ="名称">
<attr name = "background" format = "reference" />
</declare-styleable>
eg:
<ImageView
android:layout_width = "42dip"
android:layout_height = "42dip"
android:background = "@drawable/图片ID"
/>
2、自定义视图:
public class XykjProgressBar extends View { //进度条的半径 private int radius; //圆心 private int cx, cy; //画笔 private Paint paint; //进度的最大值 private int max = 100; //进度值 private int progress; //文本大小 private int textSize; //内部小圆的背景色 private int smallBgColor = 0xff3F51B5; //进度条的颜色 private int progressColor = 0xffFF4081; public XykjProgressBar(Context context) { super(context); init(); } public XykjProgressBar(Context context, @Nullable AttributeSet attrs) { super(context, attrs); //解析自定义属性 TypedArray ta = context.obtainStyledAttributes(attrs, R.styleable.myStyleable); textSize = ta.getDimensionPixelSize(R.styleable.myStyleable_textSize, 0); //sp dp dip max = ta.getInteger(R.styleable.myStyleable_max,100); progress = ta.getInteger(R.styleable.myStyleable_progress,0); smallBgColor = ta.getColor(R.styleable.myStyleable_smallBgColor,0xff3F51B5); progressColor = ta.getColor(R.styleable.myStyleable_progressColor,0xffFF4081); //释放资源 ta.recycle(); init(); } private void init() { paint = new Paint(); paint.setAntiAlias(true); } @Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); paint.setStyle(Paint.Style.FILL); paint.setColor(smallBgColor); //画中间的小圆 canvas.drawCircle(cx, cy, radius - 10, paint); //文本 int num = 100 * progress / max; //50 100 -->50% String str = num + "%"; //获取文本的边框 Rect bound = new Rect(); paint.setTextSize(textSize); paint.getTextBounds(str, 0, str.length(), bound); int x = cx - bound.centerX(); int y = cy - bound.centerY(); paint.setColor(Color.WHITE); //画进度文本 canvas.drawText(str, x, y, paint); //进度的弧线 paint.setStyle(Paint.Style.STROKE); paint.setStrokeWidth(10); paint.setColor(progressColor); //计算所跨越的弧度 int degree = 360 * progress / max; RectF rect = new RectF(cx - radius, cy - radius, cx + radius, cy + radius); //画弧线 canvas.drawArc(rect, -90, degree, false, paint); } @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { int width = getSize(widthMeasureSpec); int height = getSize(heightMeasureSpec); //初始化圆心 cx = width / 2; cy = height / 2; //取最短的边的一半作为进度半径 radius = width < height ? cx : cy; radius -= 10; //如果没有默认值则,初始化文本大小 if (textSize == 0) { textSize = radius / 2; } setMeasuredDimension(width, height); } //获取尺寸方法(自定义的根据模式获取,wrap_content时设置默认值为80) private int getSize(int measureSpec) { //获取测量模式 int mode = MeasureSpec.getMode(measureSpec); int size = 80; if (mode == MeasureSpec.EXACTLY) { //精确的,固定的值,match_parent或者100 200 size = MeasureSpec.getSize(measureSpec); }/*else if(mode == MeasureSpec.AT_MOST){ //不确定,如wrap_content size = 80; }*/ return size; } public int getMax() { return max; } public void setMax(int max) { this.max = max; } public int getProgress() { return progress; } public void setProgress(int progress) { if (this.progress != progress && progress <= max) { this.progress = progress; invalidate(); } } public int getTextSize() { return textSize; } public void setTextSize(int textSize) { this.textSize = textSize; } public int getSmallBgColor() { return smallBgColor; } public void setSmallBgColor(int smallBgColor) { this.smallBgColor = smallBgColor; } public int getProgressColor() { return progressColor; } public void setProgressColor(int progressColor) { this.progressColor = progressColor; }}
3、在主界面中引用:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" tools:context="com.xykj.myprogressbar.MainActivity"> <com.xykj.myprogressbar.XykjProgressBar android:id="@+id/progress_bar" android:layout_width="200dp" android:layout_height="200dp" app:textSize="30sp" app:smallBgColor="#ff000000"/> <Button android:id="@+id/btn" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="Click" /></LinearLayout>
java代码:
public class MainActivity extends AppCompatActivity implements View.OnClickListener{ XykjProgressBar pBar; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); pBar = (XykjProgressBar) findViewById(R.id.progress_bar); pBar.setMax(100); pBar.setProgress(10); pBar.setTextSize(50); findViewById(R.id.btn).setOnClickListener(this); } @Override public void onClick(View v) { int p = pBar.getProgress(); p+=5; pBar.setProgress(p); }}
结果如下图:
面试题:介绍下实现一个自定义View的基本流程:
1、自定义view属性,编写attrs.xml文件
2、在layout布局中引用,同时引用命名空间
3、在view的构造方法中获得我们自定义的属性,在自定义的控件中进行读取
4、重写onMeasure()方法
5、重写onDraw()方法
阅读全文
0 0
- 自定义视图的简单应用
- 简单的完全自定义视图(同心圆)
- 编写简单的视图切换应用
- 自定义事件的简单应用
- 自定义View的简单尝试——自定义日历视图
- iOS自定义弹出视图,以及简单的手势讲解
- iOS开发-------自定义简单的表情键盘(UICollectionView 集合视图)
- android 自定义视图之简单的轮播
- Swift 自定义视图:简单的数量选择控件
- Spinner自定义样式的简单应用
- JSP中自定义标签的简单应用
- 简单类型视图状态应用
- IOS研究院之滚动视图UIScrollView的简单应用
- IOS 滚动视图UIScrollView的简单应用(九)
- iOS中的UINavigationController导航栏视图控制器的简单应用
- 自定义视图的绘制
- 自定义的照相机视图
- 视图的应用
- 20170816
- HDU 6127 Hard challenge【几何】
- 分布式系统事务一致性解决方案
- 中线交易——股票程序化交易模型鉴赏
- 原型设计模式
- 自定义视图的简单应用
- 数据指标 | 移动应用数据分析体系
- Linux指令ps,top
- OpenGL ES着色器语言之变量和数据类型(一)(官方文档第四章)
- JMS消息平台FioranoMQ更新v10.3.0,改进共享HA功能
- 理解javascript原型链
- Relation Network笔记
- Ubuntu 更改文件夹权限及chmod详细用法
- JAVA 单列集合总结