自定义View之利用组合View实现复用

android自定义view复用UI *前言:*项目搭建UI中,我们总会遇到很多都是地方重复样式,比如:现在来学习一下如何自定义一个UI模块,重复利用提高开发效率以及避免代码冗余。自定义UI模块步骤:一、先贴出一个案例: 1.自定义view类public class ServiceView extends LinearLayout { private TextView tv_content; //右边显示的内容 priv 阅读详情

需求:很多UI界面中有相同的View单位,比如每个UI有相同的TitleBar。
利用androidannotations注入注解框架。

androidannotations框架的依赖导入:

//在app的build.gradle中加入
apply plugin: 'com.android.application'

apply plugin: 'android-apt'
def AAVersion = '3.3.2'

dependencies {
    compile fileTree(include: ['*.jar'], dir: 'libs')
    testCompile 'junit:junit:4.12'
    compile 'com.android.support:appcompat-v7:23.1.0'
    apt "org.androidannotations:androidannotations:$AAVersion"
    compile "org.androidannotations:androidannotations-api:$AAVersion"
    }
    apt {
    arguments {
        androidManifestFile variant.outputs[0].processResources.manifestFile
        // if you have multiple outputs (when using splits), you may want to have other index than 0
        // you should set your package name here if you are using different application IDs
        // resourcePackageName "your.package.name".
        // You can set optional annotation processing options here, like these commented options:
        // logLevel 'INFO'
        // logFile '/var/log/aa.log'
    }
}

//在整个project的build.gradle中加入
 dependencies {
        classpath 'com.android.tools.build:gradle:2.1.2'
        classpath 'com.neenbedankt.gradle.plugins:android-apt:1.4'

        // NOTE: Do not place your application dependencies here; they belong
        // in the individual module build.gradle files
    }

至此,androidannotations添加依赖完成

一个常用的需求布局,左边返回,中间一个标题,右边一个显示更多

先自定一个布局
一个线性布局,左边一个 TextView,中间一个TextView,右边一个TextView,(R.layout.custom)

<?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">
    <TextView
        android:id="@+id/tv_left"
        android:layout_weight="2"
        android:layout_width="0dp"
        android:layout_height="match_parent" />

    <TextView
        android:id="@+id/tv_middle"
        android:layout_weight="6"
        android:layout_width="0dp"
        android:layout_height="match_parent"
        android:gravity="center_horizontal"/>

    <TextView
        android:id="@+id/tv_right"
        android:layout_weight="2"
        android:layout_width="0dp"
        android:layout_height="match_parent"
        android:gravity="right"/>
</LinearLayout>

在value文件夹下建立attrs.xml文件进行属性的自定义,这里只进行字体颜色和内容的定义,可以根据需求自行添加其他需要的(命名完全自定义,只是 作为中介承接,format代表此属性的 属性)

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

    <declare-styleable name="TitleBar" >
        <!-- 此属性用来表示右边TextView的内容 -->
        <attr name="text_right" format="string"/>
        <!-- 此属性用来表示左边TextView的内容 -->
        <attr name="text_lfet" format="string"/>
        !-- 此属性用来表示中间TextView的内容 -->
        <attr name="text_title" format="string"/>
        <!-- 此属性用来表示右边TextView的颜色 -->
        <attr name="color_right" format="color"/>
        <!-- 此属性用来表示左边TextView的颜色 -->
        <attr name="color_left" format="color"/>
        <!-- 此属性用来表示中间TextView的颜色 -->
        <attr name="color_title" format="color"/>
    </declare-styleable>
</resources>

然后自定义一个类继承刚才布局的根ViewGroup,这里就用到了annotations进行简洁代码了

package yidianlingzj.com.viewdemo;

import android.content.Context;
import android.content.res.TypedArray;
import android.util.AttributeSet;
import android.view.View;
import android.widget.LinearLayout;
import android.widget.TextView;

import org.androidannotations.annotations.AfterViews;
import org.androidannotations.annotations.EViewGroup;
import org.androidannotations.annotations.ViewById;


@EViewGroup(R.layout.ui_custom)
public class TitleBar extends LinearLayout {
    @ViewById
    TextView tv_left,tv_middle,tv_right;

    String mTitle, mLeft, mRight;

    int mTitle_color, mLeft_color, mRight_color;

    //回调监听
    TitleBarListener mLeftListener,mMiddleListener,mRightListener;

    public TitleBar(Context context) {
        super(context);
        initRoot(null,0);
    }

    public TitleBar(Context context, AttributeSet attrs) {
        super(context, attrs);
        initRoot(attrs,0);
    }

    public TitleBar(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        initRoot(attrs, defStyleAttr);
    }

    void initRoot(AttributeSet attrs, int defStyleAttr) {
        final TypedArray typedArray=getContext().obtainStyledAttributes(
                attrs,R.styleable.TitleBar,defStyleAttr,0
        );

        //获得对应的内容
        mTitle=typedArray.getString(R.styleable.TitleBar_text_title);
        mLeft=typedArray.getString(R.styleable.TitleBar_text_lfet);
        mRight=typedArray.getString(R.styleable.TitleBar_text_right);

        //获得对应的颜色值,默认为黑色
        mTitle_color=typedArray.getColor(R.styleable.TitleBar_color_title,0xff000000);
        mLeft_color=typedArray.getColor(R.styleable.TitleBar_color_left,0xff000000);
        mRight_color=typedArray.getColor(R.styleable.TitleBar_color_right,0xff000000);

        typedArray.recycle();
    }

    @AfterViews
    void setupView(){
        tv_left.setText(mLeft);
        tv_middle.setText(mTitle);
        tv_right.setText(mRight);

        tv_left.setTextColor(mLeft_color);
        tv_middle.setTextColor(mTitle_color);
        tv_right.setTextColor(mRight_color);

        setListener();
    }

    private void setListener(){
        tv_left.setOnClickListener(new OnClickListener() {
            @Override
            public void onClick(View view) {
                if(mLeftListener!=null){
                    mLeftListener.click(view);
                }
            }
        });

        tv_middle.setOnClickListener(new OnClickListener() {
            @Override
            public void onClick(View view) {
                if(mMiddleListener!=null){
                    mMiddleListener.click(view);
                }
            }
        });

        tv_right.setOnClickListener(new OnClickListener() {
            @Override
            public void onClick(View view) {
                if(mRightListener!=null){
                    mRightListener.click(view);
                }
            }
        });

    }

    public void setmLeftListener(TitleBarListener mLeftListener){
        this.mLeftListener=mLeftListener;
    }

    public void setmMiddleListener(TitleBarListener mMiddleListener){
        this.mMiddleListener=mMiddleListener;
    }

    public void setmRightListener(TitleBarListener mRightListener){
        this.mRightListener=mRightListener;
    }

    //监听回调
    interface TitleBarListener{
        void click(View view);
    }
}

然后就可以进行复用了,有个地方要注意,用annotations进行注解的类,annotations会自动生成一个以”“结尾的类,比如上面的TitleBar,我们使用的是注释注解生成的TitleBar
在需要用到复用这个布局
(R.layout.activity_main)

<?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"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:orientation="vertical">
<yidianlingzj.com.viewdemo.TitleBar_
    android:id="@+id/main_tb"
    android:layout_width="match_parent"
    android:layout_height="65dp"
    app:text_lfet="left,红色"
    app:text_title="middle,默认给的是黑色"
    app:text_right="right,蓝色"
    app:color_left="#ff0000"
    app:color_right="#0000ff"/>
</LinearLayout>

都这个TitleBar就是一个组合的View的复用了,现在可以在需要的地方直接用而不需要每个地方写那么长一段布局代码了

然后可以给其设置监听

@EActivity(R.layout.activity_main)
public class MainActivity extends AppCompatActivity {

    @ViewById
    TitleBar main_tb;

    @AfterViews
    void setListener(){
        main_tb.setmLeftListener(new TitleBar.TitleBarListener() {
            @Override
            public void click(View view) {
                Toast.makeText(MainActivity.this, "点击了left", Toast.LENGTH_SHORT).show();
            }
        });

        main_tb.setmMiddleListener(new TitleBar.TitleBarListener() {
            @Override
            public void click(View view) {
                Toast.makeText(MainActivity.this, "点击了middle", Toast.LENGTH_SHORT).show();
            }
        });

        main_tb.setmRightListener(new TitleBar.TitleBarListener() {
            @Override
            public void click(View view) {
                Toast.makeText(MainActivity.this, "点击了right", Toast.LENGTH_SHORT).show();
            }
        });
    }
}

效果图:
这里写图片描述

其实这种方式颇有一番自定义View的风味了,只是在原有的view的基础上进行排列组合,虽然没有完全继承View进行各种方法的重写来的高大上和酷炫,但是也是很使用的一个小技巧.

新技能GET√
打造高级Android自定义组合View 自定义View是指开发者根据特定需求,在Android框架提供的基础View之上,通过继承现有的View类或实现View接口,来自定义的组件。这种做法在Android应用开发中非常重要,因为它可以提高用户界面的灵活性和应用的个性化程度。通过自定义View,开发者可以创建完全符合应用风格的UI组件,避免了重复造轮子的工作,并且有助于保持项目代码的整洁与模块化。增强用户交互体验:自定义View可以实现丰富的交互效果和流畅的动画效果,提升用户体验。 阅读详情

相关推荐

Android通过view复用优化ViewFlipper用法

增加ViewFlipper中view的复用,完成ViewFlipper的优化使用

Android入门之路 - Include(复用layout)的使用方式

本篇文章主要讲解的是之前文章的不足之处,因为之前的第一种方式并不完善,所以固在此篇文章为大家带入更清晰的使用方式。第一篇文章地址:http://blog.csdn.net/qq_20451879/article/details/54288317简单结构组成: 1.MainAcitivity与其XML 2.复用的Layout XMLMainActivity code:package com.exa

Android、前端、小程序、后端 1万+

ubuntu安装FSL

1.下载fslinstaller.py 官网下载地址:https://fsl.fmrib.ox.ac.uk/fsldownloads_registration 或者去我的百度网盘取: 链接:https://pan.baidu.com/s/1d5eHm48oamFdYdKm84nifw 提取码:6ff9 2.将base环境改成python2.0版本 本来想在服务器安装,服务器没有sudo权限,网上很多教程都装不了,于是就自己安装虚拟机再装了一个ubuntu,然后安装了python2环境,再开始装fsl,fsl

qq_36421001的博客 4098

Android基础--ListView的复用机制

RecycleBin 机制 RecycleBin 缓存机制如图: RecycleBin 代码实现:其实就是BaseAdapter中的getView方法的第二个参数convertView复用代码如下:这是两种样式的item的复用 @Override public View getView(int position, View convertView, ViewGroup viewGroup...

yanwenyuan0304的专栏 1128

基于云平台的ATS系统微服务架构方案研究

在当前智慧地铁的升级转型过程中,城市轨道交通ATS系统面临着稳定性差、运维方 式繁琐和故障应急处理效率低等问题。为此,提出一种基于云平台的ATS系统微服务架构方案; 研究了ATS系统在云平台上的微服务总体架构、ATS应用的微服务划分和设计、容器部署方式 及通信交互模式,可实现系统松耦合和易扩展,达到节约计算资源、提高系统稳定性和运营效 率的目的

mi_lan1的博客 966

振动分析中相位的确定

更是定位不平衡量角度的关键。是确定振动信号与转子旋转位置之间时间关系的核心步骤,而。以内,以确保校正配重安装角度的有效性。在实际动平衡中,相位角的误差需控制在。在振动分析和动平衡中,

轩辕霸天L 2735

Android自定义组合View

将几个基础 view 组合成一个新的可复用的 view

DAI_JICHEN的博客 1523

从零开始:用RFSOC XCZU47DR搭建软件无线电开发环境(2023最新版)

本文详细介绍了如何使用Xilinx RFSoC XCZU47DR搭建高性能软件无线电(SDR)开发环境,涵盖硬件选型、开发环境配置、射频子系统校准及实战应用开发。特别针对2023年最新技术需求,提供从基础配置到高级优化的完整指南,助力科研人员和工程师快速掌握RFSoC开发技术。

weixin_42525005的博客 512

Android 自定义View 代码复用

前言在写程序的时候,我们很多时候士想着怎么去尽量的少写代码,那么代码的复用就显着尤为重要,在一个地方写了之后,其他地方也能够复用是更好的事情,那么今天我们就简单的介绍代码的复用。那么我们就以一个登陆界面为例,来简单的演示代码的复用。实例项目就是一个简单的登录和注册的界面,实现代码复用,修改的时候简单的修改布局就可以实现。首先我们先创建一个继承LinearLayout为基类的View,名字我们命名为L

向着太阳迎着光 1361

Windows 11 安装 JDK 11:下载、安装、配置环境变量、验证

本文详细介绍了在 Windows 11 系统中安装 JDK 11 的完整流程,包括从 Oracle 官网下载压缩包、解压到自定义目录、配置 JAVA_HOME 与 Path 环境变量,并验证安装是否成功。文章还包含一个专为 JDK 11 新特性设计的测试程序,涵盖 Lambda 表达式 var 语法、HTTP 客户端 API、字符串增强方法等,帮助读者确认安装版本正确无误,适合初学者和需要多版本 JDK 共存的开发者参考。

寒水馨 · 轻量级技术文档 · hanshuixin.org 2782

Android 15.0 Launcher3中去掉Hotseat功能实现

在15.0系统产品定制化开发中,在Launcher3的定制化需求也是特别多的,由产品是小屏幕的产品,所以产品需求Launcher3 页面布局的原因,要求Launcher3 需要去掉Hotseat 不显示Hotseat下面几个图标,而做满屏app的显示,从而达到美观的效果,下面就来分析去掉Hotseat从而实现这个功能

安卓兼职framework和app工程师的博客 555

利用组合控件实现布局文件抽取复用--自定义view属性抽取

布局文件的复用,和抽取。

NELA的博客 1556

以 Joule 驱动的生成式开发:把需求文档直接变成可运行的 SAP 应用

摘要:SAP BTP的AI助手Joule正在改变开发方式,支持从自然语言描述自动生成数据模型、服务、UI及测试代码。在SAP Business Application Studio中,Joule能根据业务需求生成结构化代码,并提供代码补全、重构、解释等功能。开发者需注意避免上传敏感数据,并对AI生成的代码进行人工审核。Joule特别针对ABAP开发进行了优化,提供符合SAP规范的代码建议,帮助迁移遗留系统。此外,它还能快速生成CAP项目原型,但所有AI生成内容都需经过严格测试验证。

2007 年 ~ 2025 年,深耕 SAP 技术 18 年 342

android自定义view

组合控件就是将多个控件组合成一个新的控件,可以重复使用应用场景:在项目中经常会遇到一些比较复杂的UI块需要用在多处使用,那么我们就可以通过五大布局 和基本控件组合成一个新的布局View,这样就可以方便的将该UI用在项目的不同页面中,比如一个标题栏。这种方式比较简单,只要通过布局文件实现相应的UI,然后将该UI加到适合的五大布局中即可。2.自动定义组合控件的使用步骤1.首先先创建一个.xml文件,编写布局/>......

xubo667的博客 1018

基于STM32设计的智能手环(ESP8266+华为云IOT)_178

为了满足用户对健康监测的需求,手环项目集成了血氧检测、心率检测、体温检测等功能。这些功能采用了专门的传感器模块,如MAX30102、DS18B20等,确保了测量数据的准确性和可靠性。同时,为了方便用户了解自己的运动情况,项目还加入了行走步数统计功能,通过MPU6050模块实现精确计步。

2402

WINCC7.3破解文件

WINCC7.3硬件够破解文件,有需要的下载!WINCC7.3硬件够破解文件,有需要的下载!

View 自定义 - 不同的实现方式

无论是改造现有的控件(如继承ImageView)还是直接继承View,都需要对构造函数进行重写。onMeasure()、onLayout() 中用到的全局变量不能在构造中初始化(要在他们自己中),因为构造只走一次,而他们可能会执行很多次。//创建实例的时候调用//xml中使用时调用(xml转java代码的时候反射)//使用主题的时候调用= null= null= null= null= null= null//改成this调用2个参数的构造//改成this调用3个参数的构造。

HugMua的博客 315

汉书HE8,好用的汇编代码编写工具

汉书HE8,好用的汇编代码编写工具早期编写汇编代码所用功能强大

【Android API指南】自定义组件

http://blog.csdn.net/lixiang0522/article/details/7993452 Android基于View和ViewGroup基础类提供了复杂和强大的组件模型来创建UI。比如一些小部件和布局。 小部件包括Button,TextView,EditText等,布局包括LinearLayout,FrameLayout等。 如

joe 523

jre9下载 jdk9

(Java SE Runtime Environment 9.0) 9.0u175 官方最新版 【x86|x64】

Outlook Express 6 (OE6) for Win7/Win8/Win10

英文版 Outlook Express6.0, 兼容Win7/Win10/WinXP,解压就可用。

android自定义view之---组合view

最近工作比较轻松,没有什么事情干,于是进入高产模式(呃。。。。高产似xx)。 应该很多童鞋对自定义view这个东西比较抵触,可能是听网上说view比较难吧,其实自定义view并没有很难 自定义view分为三种 1.自绘view 2.组合控件view 3.重写系统view 今天我们就来以一个小例子讲一下自定义view中的组合控件view,所谓的组合控件view就是使用系统预设的view来

旋转 跳跃 然后 团灭 3113

自定义View的三种实现方式及自定义属性使用介绍

这里写目录标题一 前言二 三种自定义控件的方法2.1 组合控件2.2 继承控件2.2.1 继承View类系统控件2.2.2 继承ViewGroup类系统控件2.3 自绘控件2.3.1 自绘叶子View控件2.3.2 自绘ViewGroup控件三 在自定义View中使用自定义属性四 自定义属性格式汇总 一 前言 尽管Android系统提供了不少控件,但是有很多酷炫效果仍然是系统原生控件无法实现的。好在Android允许自定义控件,来弥补原生控件的不足。但是在很多初学者看来,自定义View似乎很难掌握。其中

qq_39431405的博客 4080

自定义View之组合控件

一、简要介绍之前写过自定义view与viewgroup但是那里阐述的是写一个可以设置多属性的可以设置响应事件的view,但是很多场景下又有很多不同,比如下图所示的由几个控件组合起来一个自定义控件来实现布局代码复用、逻辑清晰等作用二、组合控件优势一般,我们在布局的时候,如果出来多个类似的样式,比如上图的ImagVIew+TextVIew+ImagVIew会出现多次,我们可以有多种写法,比如使用线性布局

firesmog的博客 963

Android自定义View使用详细分析与绘制流程全解

目录 目录.png 1. 自定义View基础 1.1 分类 自定义View的实现方式有以下几种 类型 定义 自定义组合控件 多个控件组合成为一个新的控件,方便多处复用 继承系统View控件 继承自TextView等系统控件,在系统控件的基础功能上进行扩展 继承View 不复用系统控件逻辑,继承View进行功能定义 继承系统ViewGroup 继承自LinearLayout等系统控件,在系统控件的基础功能上进行扩展 继承ViewViewGro

yzwfeng的专栏 7554

一步一步实现Android自定义组合View

Android自定义View之组合ViewAndroid自定义View之组合View 前序 设计图UI效果 实现思路 动手实现 继承LinearLayout实现外部轮廓 定义各种需要的属性 初始化View 添加一些必要的接口方法 自定义View完成 自定义View的引用 实现效果图前序最近在开发一款电商类B端APP,比较忙,现在最新版本要上线了。刚好年底才有时间停下来梳理一下自己写过的东西,顺便分享

凌风_冷暖的专栏 1767

【安卓笔记】自定义view之组合控件

组合控件即将若干个系统已有的控件组合到一块形成一个组合控件,比如带返回按钮的标题栏就是一个最简单的组合控件。 使用组合控件的好处是提高代码的复用性,一处定义多处使用。 下面我们将使用组合控件实现这样的效果: 首先,我们需要自定义一个view: package com.example.widgets; import android.app.Activity; import

RowandJJ 2688
上一篇: Dagger2最简单注入使用
下一篇: ImageView定宽,高度等比例放大
Wi1ls
博客等级 码龄11年 2粉丝 16原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值