当前位置: 首页 > news >正文

自定义view - 玩转字体变色

自定义View步骤:
1>:values__attrs.xml,定义自定义属性;
2>:在第三个构造方法中获取自定义属性;
3>:onMeasure【不是必须的】;
4>:onDraw:绘制代码全都在onDraw中写的;
这篇文章主要是结合属性动画自定义一个文字变色的view。先来看效果图。
在这里插入图片描述技术分析:
不能用TextView,因为系统的TextView只能有一种颜色,需要ColorTraceTextView,继承TextView,而不是继承View,原因是:
1>:继承TextView不用自己手动实现onMeasure、onDraw,系统已经实现了;
2>:textColor、textSize属性TextView已经实现了,不用自己实现;
3>: 自定义属性a.不变的颜色 origincolor b.变化的颜色 changcolor

1.字体颜色

自定义属性:attrs.xml

<?xml version="1.0" encoding="utf-8"?>
<resources><declare-styleable name="ColorTrackText"><attr name="originColor" format="color"/><attr name="changeColor" format="color"/></declare-styleable>
</resources>

使用属性:avtivity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<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"android:paddingBottom="16dp"android:paddingLeft="16dp"android:paddingRight="16dp"android:paddingTop="16dp"android:orientation="vertical"tools:context=".MainActivity"><com.example.view_day04.ColorTrackTextViewandroid:id="@+id/ColorTrackTextView"android:layout_width="wrap_content"android:layout_height="wrap_content"android:text="hello world"android:textSize="20sp"app:changeColor ="@color/purple_200"app:originColor = "@color/black"/><Buttonandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:text="左到右"android:onClick="leftToRight"/><Buttonandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:text="右到左"android:onClick="rightToLeft"/></LinearLayout>

2.自定义View–初始化、获取画笔、绘制、实现不同朝向

ColorTrackTextView.java

2.1.初始化、画笔、 绘制

public class ColorTrackTextView extends TextView{// 绘制不变色的画笔private Paint mOriginPaint ;// 绘制变色的画笔private Paint mChangePaint ;private float mCurrentProgress = 0.0f;private Direction mDirection;//实现不同朝向public enum Direction {LEFT_TO_RIGHT,RIGHT_TO_LEFT}public ColorTrackTextView(Context context) {this(context, null);}public ColorTrackTextView(Context context, @Nullable @org.jetbrains.annotations.Nullable AttributeSet attrs) {this(context, attrs, 0);}public ColorTrackTextView(Context context, @Nullable @org.jetbrains.annotations.Nullable AttributeSet attrs, int defStyleAttr) {super(context, attrs, defStyleAttr);initPaint(context, attrs);}private void initPaint(Context context, AttributeSet attrs){TypedArray typedArray = context.obtainStyledAttributes(attrs, R.styleable.ColorTrackText);// 此处颜色传递默认值,防止你在布局文件中没有指定颜色int originColor = typedArray.getColor(R.styleable.ColorTrackText_originColor, getTextColors().getDefaultColor());int changeColor = typedArray.getColor(R.styleable.ColorTrackText_changeColor, getTextColors().getDefaultColor());mOriginPaint = getPaintByColor(originColor);mChangePaint = getPaintByColor(changeColor);typedArray.recycle();}private Paint getPaintByColor(int color) {Paint paint = new Paint() ;// 给画笔设置颜色paint.setColor(color);// 设置抗锯齿paint.setAntiAlias(true);// 仿抖动paint.setDither(true);// 设置文字大小,拿到布局中的Textsizepaint.setTextSize(getTextSize());return paint;}//利用cliprect可以裁剪,左边用一个画笔去画,右边用另一个画笔去画 不断地改变中间值@Overrideprotected void onDraw(Canvas canvas) {//根据进度把中间值是算出来int middle = (int)(mCurrentProgress * getWidth());if (mDirection == Direction.LEFT_TO_RIGHT) {//绘制不变色的drawText(canvas,mOriginPaint,0, middle);//绘制变色的drawText(canvas,mChangePaint,middle, getWidth());} else {// 右-左:drawText(canvas , mChangePaint , getWidth()-middle , getWidth());drawText(canvas , mOriginPaint , 0 , getWidth()-middle);}}/*** 画文字*/private void drawText(Canvas canvas, Paint paint, int start, int end) {// 保存画笔canvas.save();Rect rect = new Rect(start,0,end,getHeight()) ;// 裁剪区域canvas.clipRect(rect);// 画文字套路String text = getText().toString() ;Rect bounds = new Rect() ;paint.getTextBounds(text,0,text.length(),bounds);// 获取字体宽度int x = getWidth()/2 - bounds.width()/2;// 基线计算方式Paint.FontMetricsInt fontMetricsInt = paint.getFontMetricsInt();int dy = (fontMetricsInt.bottom-fontMetricsInt.top)/2-fontMetricsInt.bottom;int baseLine = getHeight()/2+dy;canvas.drawText(text,x,baseLine,paint);// 释放画布canvas.restore();}/*** 设置朝向*/public void setDirection(Direction direction){this.mDirection = direction;}/*** 设置当前进度*/public void setCurrentProgress(float currentProgress){this.mCurrentProgress = currentProgress;// 获取到当前进度后,进行重绘invalidate();}/*** 设置改变的颜色*/public void setChangeColor(int color){this.mChangePaint.setColor(color);}}

相关文章:

自定义view - 玩转字体变色

自定义View步骤&#xff1a; 1>&#xff1a;values__attrs.xml&#xff0c;定义自定义属性&#xff1b; 2>&#xff1a;在第三个构造方法中获取自定义属性&#xff1b; 3>&#xff1a;onMeasure【不是必须的】&#xff1b; 4>&#xff1a;onDraw&#xff1a;绘制代…...

工业边缘网关HiWoo Box的4G/5G CPE功能:为现场无线设备提供网络

引言 随着工业物联网的快速发展&#xff0c;现场设备的无线连接需求越来越迫切。然而&#xff0c;在一些室外或者不方便布网的场景下&#xff0c;为现场的无线设备提供网络仍然是一个挑战。为了满足这一需求&#xff0c;工业边缘网关HiWoo Box引入了4G/5G CPE&#xff08;Cust…...

Set 和 Map 数据结构

数据结构Set ES6提供了新的数据结构Set。它类似于数组&#xff0c;但是成员的值都是唯一的&#xff0c;没有重复的值。 Set本身是一个构造函数&#xff0c;用来生成Set数据结构。 // 数组去重 const set new Set([1, 2, 3, 4, 4]); [...set] // [1, 2, 3, 4]目前个人感觉Se…...

nginx根据url参数动态代理

nginx根据url参数动态代理 请求url格式&#xff0c;其中参数proxy后面的url就是需要访问的真实地址&#xff1a; http://localhost:9388/?proxyhttp://localhost:8038/Content/layui/font/iconfont.woff?v256 http://localhost:9388/?proxyhttp://localhost:8072/article/A…...

TCP协议(收集和记录)

收集写的比较好的文章 TCP四次挥手详解 四次挥手介绍的非常详细, 重点介绍了各种异常情况下协议是如何处理的, 异常处理可以做到两点: 让连接保活, 也许只是一次连接异常让连接死掉后不影响后续的操作, 重点介绍了TIME_WAIT...

【Kafka】自动提交偏移量和手动提交偏移量的区别

区别 自动提交偏移量&#xff08;Auto Commit Offset&#xff09;和手动提交偏移量&#xff08;Manual Commit Offset&#xff09;是两种不同的消费者偏移量管理方式。 自动提交偏移量&#xff1a; 在自动提交模式下&#xff0c;消费者会定期自动将已消费的消息偏移量提交给…...

缠论线段的划分

第一种情况&#xff1a; 第二种情况&#xff1a; 第二种情况中的特例&#xff1a; 第二种情况的特例&#xff1a; 顶分型成立&#xff1a; 向上线段延续&#xff1a; 顶分型后面底分型&#xff0c;形成三段 插入一个分型的反面例子&#xff1a; dd...

【Linux】Ubuntu基本使用与配置, 以及常见问题汇总(一)

前言 大学期间&#xff0c;感觉很多时候学习课外知识都是被推着往前走&#xff0c;很多内容并没有深入去学习&#xff0c;知识的记录受限于所学比较片面&#xff0c;如今渐渐意识到似乎并没有建立起相关知识的体系架构&#xff0c;缺乏一个系统学习并整理的过程。本文将以Ubunt…...

【UE5 多人联机教程】02-开始游戏菜单控件

目录 步骤 一、完善开始游戏菜单控件 二、控件功能实现 2.1 “开始游戏”按钮切换界面 2.2 “创建房间”、“加入房间”按钮切换界面 2.3 “创建房间”按钮 步骤 一、完善开始游戏菜单控件 打开“UMG_Main” 首先在控件切换器外层包裹一个画布面板 然后调整控件切换器全…...

设计模式-工厂方法模式

基于面向对象语言开发中&#xff0c;免不得需要创建对象。前面讲解的"单例模式"也是如此&#xff0c;不过是要创建唯一的对象。本文要讲述“工厂方法模式”是要封装创建对象的过程。工厂&#xff0c;也称之为“制造厂”&#xff0c;用于创建具体的产品直接提供给外界…...

【Hammerstein模型的级联】快速估计构成一连串哈默斯坦模型的结构元素研究(Matlab代码实现)

目录 &#x1f4a5;1 概述 &#x1f4da;2 运行结果 &#x1f389;3 参考文献 &#x1f308;4 Matlab代码实现 &#x1f4a5;1 概述 在许多振动应用中&#xff0c;所研究的系统略微非线性。Hammerstein模型的级联可以方便地描述这样的系统。Hammerstein提供了一种基于指数正弦…...

「C 语言」extern关键字

在 C 语言中&#xff0c;关键字 extern 是用来告诉编译器&#xff0c;这个变量 OR 函数在其他文件中已有定义&#xff0c;可在当前文件中使用 当我们定义了一个全局变量 OR 函数时&#xff0c;它就已经具有了外部链接的属性&#xff0c;我们只需要通过在引用该变量的文件中用 …...

oracle单个用户最大连接数限制

项目经理反馈&#xff0c;现场已做了单个用户的最大连接数2000的限制&#xff0c;但数据库还是报无法连接&#xff0c;故障用户的连接数已3800多了。 查看日志报错如下 2023-07-20T13:07:57.79465308:00 Process m000 submission failed with error 20 Process m000 submiss…...

计算机网络最基础知识介绍

OSI和TCP/IP是很基础但又非常重要的知识,很多知识点都是以它们为基础去串联的,作为底层,掌握得越透彻,理解上层时会越顺畅。今天这篇网络基础科普,就是根据OSI层级去逐一展开的。 01 计算机网络基础 01 计算机网络的分类 按照网络的作用范围:广域网(WAN)、城域网(MA…...

接口测试进阶之数据模板

大家好久不见了。今天的文章将介绍jinja2模板在接口测试数据上的应用。 这几个月我在想&#xff0c;进阶系列要怎么写。 毕竟很多情况下&#xff0c;我觉得写技术文章和做培训一样&#xff0c;都会有两个结果&#xff1a; 1.是需要这些知识的人看不懂。 2.是看得懂的人不需要…...

Java中使用MySQL详解

1. 简介 在Java开发中&#xff0c;与数据库的交互是常见且重要的一部分。MySQL是一个广泛使用的关系型数据库管理系统&#xff0c;而Java作为一种强大的编程语言&#xff0c;提供了丰富的API和工具&#xff0c;使得与MySQL数据库的结合应用更加便捷和高效。 本篇博客将详细介…...

Docker安装Elasticsearch相关软件安装

Docker安装Elasticsearch相关软件安装 本文将介绍通过 Docker 的方式安装 Elasticsearch 相关的软件。 1、Docker安装Elasticsearch 1.1 搜索镜像 $ docker search elasticsearch $ docker search elasticsearch:7.12.11.2 拉取镜像 $ docker pull elasticsearch:7.12.11.…...

Ubuntu的安装与部分配置

该教程使用的虚拟机是virtuabox&#xff0c;镜像源的版本是ubuntu20.04.5桌面版 可通过下面的链接在Ubuntu官网下载&#xff1a;Alternative downloads | Ubuntu 也可直接通过下面的链接进入百度网盘下载【有Ubuntu20.04.5与hadoop3.3.2以及jdk1.8.0_162&#xff0c;该篇需要使…...

为什么 Splashtop 是更好用的 iOS 远程桌面应用

全球远程桌面软件市场最近达到19.2亿美元&#xff0c;表明使用任意设备实现随处远程控制越来越受欢迎。 近年来&#xff0c;企业的运营方式发生了重大改变&#xff0c;远程桌面软件已成为广泛使用的解决方案。Splashtop 是目前最好用的远程桌面工具之一&#xff0c;安全可靠且…...

[SQL挖掘机] - 字符串函数 - lower

介绍: lower函数是mysql中的一个字符串函数&#xff0c;其作用是将给定的字符串转换为小写形式。它接受一个字符串作为参数&#xff0c;并返回一个新的字符串&#xff0c;其中所有的字母字符均被转换为小写形式。 使用lower函数可以帮助我们在字符串处理中实现标准化和规范化…...

Leetcode 3576. Transform Array to All Equal Elements

Leetcode 3576. Transform Array to All Equal Elements 1. 解题思路2. 代码实现 题目链接&#xff1a;3576. Transform Array to All Equal Elements 1. 解题思路 这一题思路上就是分别考察一下是否能将其转化为全1或者全-1数组即可。 至于每一种情况是否可以达到&#xf…...

【WiFi帧结构】

文章目录 帧结构MAC头部管理帧 帧结构 Wi-Fi的帧分为三部分组成&#xff1a;MAC头部frame bodyFCS&#xff0c;其中MAC是固定格式的&#xff0c;frame body是可变长度。 MAC头部有frame control&#xff0c;duration&#xff0c;address1&#xff0c;address2&#xff0c;addre…...

【磁盘】每天掌握一个Linux命令 - iostat

目录 【磁盘】每天掌握一个Linux命令 - iostat工具概述安装方式核心功能基础用法进阶操作实战案例面试题场景生产场景 注意事项 【磁盘】每天掌握一个Linux命令 - iostat 工具概述 iostat&#xff08;I/O Statistics&#xff09;是Linux系统下用于监视系统输入输出设备和CPU使…...

oracle与MySQL数据库之间数据同步的技术要点

Oracle与MySQL数据库之间的数据同步是一个涉及多个技术要点的复杂任务。由于Oracle和MySQL的架构差异&#xff0c;它们的数据同步要求既要保持数据的准确性和一致性&#xff0c;又要处理好性能问题。以下是一些主要的技术要点&#xff1a; 数据结构差异 数据类型差异&#xff…...

C++ 基础特性深度解析

目录 引言 一、命名空间&#xff08;namespace&#xff09; C 中的命名空间​ 与 C 语言的对比​ 二、缺省参数​ C 中的缺省参数​ 与 C 语言的对比​ 三、引用&#xff08;reference&#xff09;​ C 中的引用​ 与 C 语言的对比​ 四、inline&#xff08;内联函数…...

Springcloud:Eureka 高可用集群搭建实战(服务注册与发现的底层原理与避坑指南)

引言&#xff1a;为什么 Eureka 依然是存量系统的核心&#xff1f; 尽管 Nacos 等新注册中心崛起&#xff0c;但金融、电力等保守行业仍有大量系统运行在 Eureka 上。理解其高可用设计与自我保护机制&#xff0c;是保障分布式系统稳定的必修课。本文将手把手带你搭建生产级 Eur…...

从零实现STL哈希容器:unordered_map/unordered_set封装详解

本篇文章是对C学习的STL哈希容器自主实现部分的学习分享 希望也能为你带来些帮助~ 那咱们废话不多说&#xff0c;直接开始吧&#xff01; 一、源码结构分析 1. SGISTL30实现剖析 // hash_set核心结构 template <class Value, class HashFcn, ...> class hash_set {ty…...

12.找到字符串中所有字母异位词

&#x1f9e0; 题目解析 题目描述&#xff1a; 给定两个字符串 s 和 p&#xff0c;找出 s 中所有 p 的字母异位词的起始索引。 返回的答案以数组形式表示。 字母异位词定义&#xff1a; 若两个字符串包含的字符种类和出现次数完全相同&#xff0c;顺序无所谓&#xff0c;则互为…...

Linux --进程控制

本文从以下五个方面来初步认识进程控制&#xff1a; 目录 进程创建 进程终止 进程等待 进程替换 模拟实现一个微型shell 进程创建 在Linux系统中我们可以在一个进程使用系统调用fork()来创建子进程&#xff0c;创建出来的进程就是子进程&#xff0c;原来的进程为父进程。…...

Mobile ALOHA全身模仿学习

一、题目 Mobile ALOHA&#xff1a;通过低成本全身远程操作学习双手移动操作 传统模仿学习&#xff08;Imitation Learning&#xff09;缺点&#xff1a;聚焦与桌面操作&#xff0c;缺乏通用任务所需的移动性和灵活性 本论文优点&#xff1a;&#xff08;1&#xff09;在ALOHA…...