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

android 支持自定义布局、线程安全、避免内存泄漏的 Toast 工具类

支持自定义布局:可以灵活地显示自定义样式的 Toast。

线程安全:确保在主线程中显示 Toast,避免崩溃。

避免内存泄漏:使用 ApplicationContext 和取消机制,防止内存泄漏问题。

工具类:作为一个通用的工具类,方便在项目中复用。

ToastUtil

import android.content.Context;
import android.os.Handler;
import android.os.Looper;
import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.View;
import android.widget.TextView;
import android.widget.Toast;public class ToastUtil {private static Toast toast; // 全局Toast对象,避免重复创建private static final int DEFAULT_GRAVITY = Gravity.BOTTOM | Gravity.CENTER_HORIZONTAL; // 默认显示位置private static final int DEFAULT_Y_OFFSET = 100; // 默认Y轴偏移量private static final Handler mainHandler = new Handler(Looper.getMainLooper()); // 主线程Handler/*** 显示短时间的Toast** @param context 上下文* @param message 要显示的消息*/public static void showShort(Context context, String message) {showToast(context, message, Toast.LENGTH_SHORT, DEFAULT_GRAVITY, 0, DEFAULT_Y_OFFSET);}/*** 显示长时间的Toast** @param context 上下文* @param message 要显示的消息*/public static void showLong(Context context, String message) {showToast(context, message, Toast.LENGTH_LONG, DEFAULT_GRAVITY, 0, DEFAULT_Y_OFFSET);}/*** 显示短时间的Toast(使用字符串资源ID)** @param context 上下文* @param resId   字符串资源ID*/public static void showShort(Context context, int resId) {showShort(context, context.getString(resId));}/*** 显示长时间的Toast(使用字符串资源ID)** @param context 上下文* @param resId   字符串资源ID*/public static void showLong(Context context, int resId) {showLong(context, context.getString(resId));}/*** 显示自定义位置的Toast** @param context  上下文* @param message  要显示的消息* @param gravity  显示位置(例如 Gravity.TOP)* @param xOffset  X轴偏移量* @param yOffset  Y轴偏移量*/public static void showAtPosition(Context context, String message, int gravity, int xOffset, int yOffset) {showToast(context, message, Toast.LENGTH_SHORT, gravity, xOffset, yOffset);}/*** 显示自定义布局的Toast** @param context     上下文* @param layoutResId 自定义布局资源ID* @param message     要显示的消息*/public static void showCustom(Context context, int layoutResId, String message) {runOnUiThread(() -> {if (toast != null) {toast.cancel(); // 取消之前的Toast}// 使用ApplicationContext,避免内存泄漏Context appContext = context.getApplicationContext();LayoutInflater inflater = (LayoutInflater) appContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);View layout = inflater.inflate(layoutResId, null);// 查找布局中的TextView(假设id为text)TextView textView = layout.findViewById(R.id.text);if (textView != null) {textView.setText(message);}toast = new Toast(appContext);toast.setDuration(Toast.LENGTH_SHORT);toast.setView(layout);toast.show();});}/*** 显示自定义布局的Toast(支持自定义显示时长)** @param context     上下文* @param layoutResId 自定义布局资源ID* @param message     要显示的消息* @param duration    显示时长(Toast.LENGTH_SHORT 或 Toast.LENGTH_LONG)*/public static void showCustom(Context context, int layoutResId, String message, int duration) {runOnUiThread(() -> {if (toast != null) {toast.cancel(); // 取消之前的Toast}// 使用ApplicationContext,避免内存泄漏Context appContext = context.getApplicationContext();LayoutInflater inflater = (LayoutInflater) appContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);View layout = inflater.inflate(layoutResId, null);// 查找布局中的TextView(假设id为text)TextView textView = layout.findViewById(R.id.text);if (textView != null) {textView.setText(message);}toast = new Toast(appContext);toast.setDuration(duration);toast.setView(layout);toast.show();});}/*** 核心方法:显示Toast** @param context  上下文* @param message  要显示的消息* @param duration 显示时长(Toast.LENGTH_SHORT 或 Toast.LENGTH_LONG)* @param gravity  显示位置* @param xOffset  X轴偏移量* @param yOffset  Y轴偏移量*/private static void showToast(Context context, String message, int duration, int gravity, int xOffset, int yOffset) {runOnUiThread(() -> {if (toast != null) {toast.cancel(); // 取消之前的Toast}// 使用ApplicationContext,避免内存泄漏Context appContext = context.getApplicationContext();toast = Toast.makeText(appContext, message, duration);toast.setGravity(gravity, xOffset, yOffset); // 设置显示位置toast.show();});}/*** 取消Toast*/public static void cancelToast() {if (toast != null) {toast.cancel();toast = null; // 释放引用}}/*** 确保在主线程中运行** @param runnable 需要执行的任务*/private static void runOnUiThread(Runnable runnable) {if (Looper.myLooper() == Looper.getMainLooper()) {runnable.run(); // 当前是主线程,直接运行} else {mainHandler.post(runnable); // 当前是子线程,切换到主线程运行}}
}

使用示例

  1. 显示自定义布局的 Toast
ToastUtil.showCustom(MainActivity.this, R.layout.custom_toast, "这是一个自定义Toast");

在子线程中调用:

new Thread(() -> {// 在子线程中调用ToastUtil.showCustom(MainActivity.this, R.layout.custom_toast, "子线程中的自定义Toast");
}).start();

自定义布局示例:
假设 res/layout/custom_toast.xml 是一个自定义布局文件,例如:

<!-- res/layout/custom_toast.xml -->
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"android:layout_width="wrap_content"android:layout_height="wrap_content"android:background="@drawable/toast_background"android:padding="16dp"android:orientation="horizontal"><ImageViewandroid:id="@+id/icon"android:layout_width="24dp"android:layout_height="24dp"android:src="@drawable/ic_toast_icon"android:layout_marginEnd="8dp"/><TextViewandroid:id="@+id/text"android:layout_width="wrap_content"android:layout_height="wrap_content"android:textColor="@android:color/white"android:textSize="16sp"/>
</LinearLayout>

相关文章:

android 支持自定义布局、线程安全、避免内存泄漏的 Toast 工具类

支持自定义布局&#xff1a;可以灵活地显示自定义样式的 Toast。 线程安全&#xff1a;确保在主线程中显示 Toast&#xff0c;避免崩溃。 避免内存泄漏&#xff1a;使用 ApplicationContext 和取消机制&#xff0c;防止内存泄漏问题。 工具类&#xff1a;作为一个通用的工具…...

景联文科技:以精准数据标注赋能AI进化,构筑智能时代数据基石

在人工智能技术席卷全球的浪潮中&#xff0c;高质量数据已成为驱动AI模型进化的核心燃料。作为全球领先的AI数据服务解决方案提供商&#xff0c;景联文科技深耕数据标注领域多年&#xff0c;以技术为基、以专业为本&#xff0c;致力于为全球客户提供全场景、高精度、多模态的数…...

Mysql的卸载安装配置以及简单使用

MySQL其它问题已经更新在&#xff1a;MySQL完善配置---可视化-CSDN博客 一、卸载 ①控制面板卸载 ②C盘隐藏项目>ProgramData>mysql相关文件夹&#xff0c;还有Program file下的MySQL文件夹 ③开始菜单栏搜索>服务&#xff0c;找到MySQL相关服务删除&#xff0c;如果再…...

使用 ResponseBodyEmitter 实现异步响应式数据流处理

1. 概述 1.1 什么是 ResponseBodyEmitter ResponseBodyEmitter 是 Spring MVC 提供的一个接口,用于支持异步返回响应数据流。它允许在控制器方法中逐步发送数据给客户端,而无需一次性生成完整的响应。 1.2 使用场景 实时数据推送(如股票行情、聊天消息等)。大量数据分批…...

Uniapp项目运行到微信小程序、H5、APP等多个平台教程

摘要&#xff1a;Uniapp作为一款基于Vue.js的跨平台开发框架&#xff0c;支持“一次开发&#xff0c;多端部署”。本文将手把手教你如何将Uniapp项目运行到微信小程序、H5、APP等多个平台&#xff0c;并解析常见问题。 一、环境准备 在开始前&#xff0c;请确保已安装以下工具…...

Ubuntu 下 nginx-1.24.0 源码分析 - cycle->modules[i]->type

Nginx 中主要有以下几种模块类型 类型 含义 NGX_CORE_MODULE 核心模块&#xff08;如进程管理、错误日志、配置解析&#xff09;。 NGX_EVENT_MODULE 事件模块&#xff08;如 epoll、kqueue 等 IO 多路复用机制的实现&#xff09;。 NGX_HTTP_MODULE HTTP 模块&#xf…...

基于SpringBoot的“文物管理系统”的设计与实现(源码+数据库+文档+PPT)

基于SpringBoot的“文物管理系统”的设计与实现&#xff08;源码数据库文档PPT) 开发语言&#xff1a;Java 数据库&#xff1a;MySQL 技术&#xff1a;SpringBoot 工具&#xff1a;IDEA/Ecilpse、Navicat、Maven 系统展示 系统总体功能模块图 E-R实体图 系统首页界面 系统…...

dify + ollama + deepseek-r1+ stable-diffusion 构建绘画智能体

故事背景 stable-diffusion 集成进 dify 后&#xff0c;我们搭建一个小智能体&#xff0c;验证下文生图功能 业务流程 #mermaid-svg-6nSwwp69eMizP6bt {font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}#mermaid-svg-6nSwwp69eMiz…...

Android原生gif动图加载AnimatedImageDrawable

Android原生gif动图加载AnimatedImageDrawable 从Android P&#xff08;9.0&#xff09;开始&#xff0c;Android系统支持gif动图的原生控件AnimatedImageDrawable&#xff0c;可以播放加载gif动图。 AnimatedImageDrawable官方文档链接&#xff1a; https://developer.andro…...

Windows 系统 Docker Desktop 入门教程:从零开始掌握容器化技术

文章目录 前言一、Docker 简介二、Docker Desktop 安装2.1 系统要求2.2 安装步骤 三、Docker 基本概念四、Docker 常用命令五、实战&#xff1a;运行你的第一个容器5.1 拉取并运行 Nginx 容器5.2 查看容器日志5.3 停止并删除容器 六、总结 前言 随着云计算和微服务架构的普及&…...

记录小白使用 Cursor 开发第一个微信小程序(二):创建项目、编译、预览、发布(250308)

文章目录 记录小白使用 Cursor 开发第一个微信小程序&#xff08;二&#xff09;&#xff1a;创建项目、编译、预览、发布&#xff08;250308&#xff09;一、创建项目1.1 生成提示词1.2 生成代码 二、编译预览2.1 导入项目2.2 编译预览 三、发布3.1 在微信开发者工具进行上传3…...

实战 - 使用 AutoAWQ 进行量化

文章目录 一、准备1、安装 autoawq2、模型准备 二、量化config.json 文件变化 三、加载量化后模型量化后的输出原始输出对比 四、查看模型的精度1、查看模型卡2、查看 config.json 中的 torch_dtype3、打印模型信息4、model.dtype 未必是模型精度 一、准备 1、安装 autoawq p…...

C++20 格式化库:强大的字符串格式化工具

文章目录 格式化语法常见用法1. 填充和对齐2. 数值格式化3. 进制格式化4. 自定义类型 示例代码注意事项 C20 的格式化库是一个强大的工具&#xff0c;用于处理字符串的格式化操作。它提供了类似于 Python 中 str.format() 的功能&#xff0c;但语法和用法更符合 C 的风格。以下…...

【一文学会 HTML5】

目录 HTML概述基本概念HTML 发展历程HTML 基本结构 网页基本标签标题标签&#xff08;<h1> - <h6>&#xff09;段落标签&#xff08;<p>&#xff09;换行标签&#xff08;<br>&#xff09;水平线标签&#xff08;<hr>&#xff09;注释&#xff0…...

如何在WPS中接入DeepSeek并使用OfficeAI助手(超细!成功版本)

目录 第一步&#xff1a;下载并安装OfficeAI助手 第二步&#xff1a;申请API Key 第三步:两种方式导入WPS 第一种:本地大模型Ollama 第二种APIKey接入 第四步&#xff1a;探索OfficeAI的创作功能 工作进展汇报 PPT大纲设计 第五步&#xff1a;我的使用体验(体验建议) …...

蓝耘智算 + 通义万相 2.1:为 AIGC 装上 “智能翅膀”,翱翔创作新天空

1. 引言&#xff1a;AIGC 的崛起与挑战 在过去几年中&#xff0c;人工智能生成内容&#xff08;AIGC&#xff09;技术突飞猛进。AIGC 涉及了文本生成、图像创作、音乐创作、视频制作等多个领域&#xff0c;并逐渐渗透到日常生活的方方面面。传统的内容创作方式已经被许多人类创…...

电脑如何在系统默认的壁纸中切换自己喜欢的

1、声明&#xff1a;该切换壁纸仅支持win10。 当你想去切换系统默认的壁纸&#xff0c;但是不知道该怎么切换&#xff0c;别慌&#xff0c;小亦教你几招帮你快速切换自定义壁纸。 我们平常使用的win10桌面壁纸大部分都是 简单、朴素的壁纸&#xff0c;但如果你想要切换自己喜…...

【大模型安全】安全解决方案

【大模型安全】安全解决方案 1.技术层面2.数据层面数据收集阶段训练阶段模型推理阶段 1.技术层面 在使用大语言模型时&#xff0c;通常有几种选择&#xff1a;一种是采用封装好的大语言模型SaaS云服务&#xff1b;另一种是在公有云上部署自有的大语言模型&#xff0c;并通过权…...

Windows编译环境搭建(MSYS2\MinGW\cmake)

我的音视频/流媒体开源项目(github) 一、基础环境搭建 1.1 MSYS2\MinGW 参考&#xff1a;1. 基于MSYS2的Mingw-w64 GCC搭建Windows下C开发环境_msys2使用mingw64编译 在Widndows系统上&#xff0c;使用gcc工具链&#xff08;g&#xff09;进行C程序开发&#xff1f;可以的&a…...

云曦春季开学考复现(2025)

Crypto 划水的dp和dq 下载附件后是简单的RSA算法题&#xff0c;之所以说简单是因为给了公钥e 趁热打铁&#xff0c;昨天刚学的RSA&#xff0c;既然有p有q&#xff0c;也有e&#xff0c;而np*q&#xff0c;可以算出欧拉函数值phi&#xff08;p-1&#xff09;*&#xff08;q-1&…...

2025年能源电力系统与流体力学国际会议 (EPSFD 2025)

2025年能源电力系统与流体力学国际会议&#xff08;EPSFD 2025&#xff09;将于本年度在美丽的杭州盛大召开。作为全球能源、电力系统以及流体力学领域的顶级盛会&#xff0c;EPSFD 2025旨在为来自世界各地的科学家、工程师和研究人员提供一个展示最新研究成果、分享实践经验及…...

23-Oracle 23 ai 区块链表(Blockchain Table)

小伙伴有没有在金融强合规的领域中遇见&#xff0c;必须要保持数据不可变&#xff0c;管理员都无法修改和留痕的要求。比如医疗的电子病历中&#xff0c;影像检查检验结果不可篡改行的&#xff0c;药品追溯过程中数据只可插入无法删除的特性需求&#xff1b;登录日志、修改日志…...

LeetCode - 394. 字符串解码

题目 394. 字符串解码 - 力扣&#xff08;LeetCode&#xff09; 思路 使用两个栈&#xff1a;一个存储重复次数&#xff0c;一个存储字符串 遍历输入字符串&#xff1a; 数字处理&#xff1a;遇到数字时&#xff0c;累积计算重复次数左括号处理&#xff1a;保存当前状态&a…...

JUC笔记(上)-复习 涉及死锁 volatile synchronized CAS 原子操作

一、上下文切换 即使单核CPU也可以进行多线程执行代码&#xff0c;CPU会给每个线程分配CPU时间片来实现这个机制。时间片非常短&#xff0c;所以CPU会不断地切换线程执行&#xff0c;从而让我们感觉多个线程是同时执行的。时间片一般是十几毫秒(ms)。通过时间片分配算法执行。…...

如何在网页里填写 PDF 表格?

有时候&#xff0c;你可能希望用户能在你的网站上填写 PDF 表单。然而&#xff0c;这件事并不简单&#xff0c;因为 PDF 并不是一种原生的网页格式。虽然浏览器可以显示 PDF 文件&#xff0c;但原生并不支持编辑或填写它们。更糟的是&#xff0c;如果你想收集表单数据&#xff…...

Redis的发布订阅模式与专业的 MQ(如 Kafka, RabbitMQ)相比,优缺点是什么?适用于哪些场景?

Redis 的发布订阅&#xff08;Pub/Sub&#xff09;模式与专业的 MQ&#xff08;Message Queue&#xff09;如 Kafka、RabbitMQ 进行比较&#xff0c;核心的权衡点在于&#xff1a;简单与速度 vs. 可靠与功能。 下面我们详细展开对比。 Redis Pub/Sub 的核心特点 它是一个发后…...

【Go语言基础【13】】函数、闭包、方法

文章目录 零、概述一、函数基础1、函数基础概念2、参数传递机制3、返回值特性3.1. 多返回值3.2. 命名返回值3.3. 错误处理 二、函数类型与高阶函数1. 函数类型定义2. 高阶函数&#xff08;函数作为参数、返回值&#xff09; 三、匿名函数与闭包1. 匿名函数&#xff08;Lambda函…...

CVE-2020-17519源码分析与漏洞复现(Flink 任意文件读取)

漏洞概览 漏洞名称&#xff1a;Apache Flink REST API 任意文件读取漏洞CVE编号&#xff1a;CVE-2020-17519CVSS评分&#xff1a;7.5影响版本&#xff1a;Apache Flink 1.11.0、1.11.1、1.11.2修复版本&#xff1a;≥ 1.11.3 或 ≥ 1.12.0漏洞类型&#xff1a;路径遍历&#x…...

Caliper 配置文件解析:fisco-bcos.json

config.yaml 文件 config.yaml 是 Caliper 的主配置文件,通常包含以下内容: test:name: fisco-bcos-test # 测试名称description: Performance test of FISCO-BCOS # 测试描述workers:type: local # 工作进程类型number: 5 # 工作进程数量monitor:type: - docker- pro…...

PostgreSQL——环境搭建

一、Linux # 安装 PostgreSQL 15 仓库 sudo dnf install -y https://download.postgresql.org/pub/repos/yum/reporpms/EL-$(rpm -E %{rhel})-x86_64/pgdg-redhat-repo-latest.noarch.rpm# 安装之前先确认是否已经存在PostgreSQL rpm -qa | grep postgres# 如果存在&#xff0…...