因为工作需求,所以自己研究了自定义Toast,这里做出总结:

在此之前有一点需要提前说明:Toast与其他组件一样,都属于UI界面中的内容,因此在子线程中无法使用Toast弹出提示内容,如果强行在子线程中增加会导致错误。本例子使用异步任务来说明,原理跟子线程一样。

主界面:

自定义Toast弹出的样式:

MainActivity:

 public class MainActivity extends AppCompatActivity implements View.OnClickListener {
Button btn_define; //自定义Toast
Button btn_thread; //线程中的Toast @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
requestWindowFeature(Window.FEATURE_NO_TITLE);
setContentView(R.layout.activity_main);
initButton();
btn_define.setOnClickListener(this);
btn_thread.setOnClickListener(this);
} private void initButton() {
btn_define = (Button) findViewById(R.id.btn_all_define);
btn_thread = (Button) findViewById(R.id.btn_other_thread);
} @Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.btn_all_define:
ToastMessage("自定义Toast", "这是我自定义的Toast");
break;
case R.id.btn_other_thread:
//异步任务
new AsyncTask<String, Void, Object>() {
@Override
protected void onPreExecute() {
super.onPreExecute();
} protected Object doInBackground(String... strings) {
//线程中无法使用Toast,需要将Toast发送至主线程中才能使用
Message msg = new Message();
msg.what = 1;//标记位,标记是哪个线程传数据
msg.obj = "这是线程的toast";
mHandler.sendMessage(msg);
return null;
} @Override
protected void onPostExecute(Object o) {
super.onPostExecute(o);
}
}.execute(); break;
}
} Handler mHandler = new MyHandler(); private class MyHandler extends Handler {
@Override
public void handleMessage(Message msg) {
super.handleMessage(msg);
switch (msg.what) {
case 1:
String str = (String) msg.obj;
Toast.makeText(getApplicationContext(), str, Toast.LENGTH_LONG).show();
break;
}
}
} /**
* 将Toast封装在一个方法中,在其它地方使用时直接输入要弹出的内容即可
*/
private void ToastMessage(String titles, String messages) {
//LayoutInflater的作用:对于一个没有被载入或者想要动态载入的界面,都需要LayoutInflater.inflate()来载入,LayoutInflater是用来找res/layout/下的xml布局文件,并且实例化
LayoutInflater inflater = getLayoutInflater();//调用Activity的getLayoutInflater()
View view = inflater.inflate(R.layout.toast_style, null); //加載layout下的布局
ImageView iv = view.findViewById(R.id.tvImageToast);
iv.setImageResource(R.mipmap.atm);//显示的图片
TextView title = view.findViewById(R.id.tvTitleToast);
title.setText(titles); //toast的标题
TextView text = view.findViewById(R.id.tvTextToast);
text.setText(messages); //toast内容
Toast toast = new Toast(getApplicationContext());
toast.setGravity(Gravity.CENTER, 12, 20);//setGravity用来设置Toast显示的位置,相当于xml中的android:gravity或android:layout_gravity
toast.setDuration(Toast.LENGTH_LONG);//setDuration方法:设置持续时间,以毫秒为单位。该方法是设置补间动画时间长度的主要方法
toast.setView(view); //添加视图文件
toast.show();
}
}

activity的布局文件:activity_main.xml

 <?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:gravity="center_horizontal"
android:orientation="vertical"> <Button
android:id="@+id/btn_all_define"
android:text="自定义Toast"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center_horizontal"/> <Button
android:id="@+id/btn_other_thread"
android:text="线程中Toast的使用"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center_horizontal"/>
</LinearLayout>

toast的样式:toast_style.xml

我这里是比较简单的样式,如果想要其他形式的可以根据自身的需求更改界面即可实现。

 <?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/llToast"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="#ffffffff"
android:orientation="vertical" > <TextView
android:id="@+id/tvTitleToast"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_margin="1dip"
android:background="#bb000000"
android:gravity="center"
android:textColor="#ffffffff" /> <LinearLayout
android:id="@+id/llToastContent"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginBottom="1dip"
android:layout_marginLeft="1dip"
android:layout_marginRight="1dip"
android:background="#44000000"
android:orientation="vertical"
android:padding="15dip" > <ImageView
android:id="@+id/tvImageToast"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center" /> <TextView
android:id="@+id/tvTextToast"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center"
android:paddingLeft="10dip"
android:paddingRight="10dip"
android:textColor="#ff000000" />
</LinearLayout> </LinearLayout>

以上就是今天上午研究的自定义的Toast。以后开发直接拿来用就OK!

补充:上面的形式总归上不了大雅之堂,现在补充一个新的完全自定义的Toast,可以根据自身需求随意设置:

import com.example.myproject.R;
import android.content.Context;
import android.view.View;
import android.widget.LinearLayout;
import android.widget.TextView;
import android.widget.Toast; public class ToastUtils {
private Toast toast;
private LinearLayout toastView; /**
* 完全自定义布局Toast
*/
public ToastUtils(Context context, View view, int duration) {
toast = new Toast(context);
toast.setView(view);
toast.setDuration(duration);
} /**
* 向Toast中添加自定义View
*/
public ToastUtils addView(View view, int position) {
toastView = (LinearLayout) toast.getView();
toastView.addView(view, position);
return this;
} /**
* 设置Toast字体及背景
*/
public ToastUtils setToastBackground(int messageColor, int background) {
View view = toast.getView();
if (view != null) {
TextView message = (TextView) view.findViewById(R.id.message);
message.setBackgroundResource(background);
message.setTextColor(messageColor);
} return this;
} /**
* 短时间显示Toast
*/
public ToastUtils Short(Context context, CharSequence message) {
if (toast == null
|| (toastView != null && toastView.getChildCount() > 1)) {
toast = Toast.makeText(context, message, Toast.LENGTH_SHORT);
toastView = null;
} else {
toast.setText(message);
toast.setDuration(Toast.LENGTH_SHORT);
}
return this;
} /**
* 长时间显示toast
*/
public ToastUtils Long(Context context, CharSequence message) {
if (toast == null
|| (toastView != null && toastView.getChildCount() > 1)) {
toast = Toast.makeText(context, message, Toast.LENGTH_LONG);
toastView = null;
} else {
toast.setText(message);
toast.setDuration(Toast.LENGTH_LONG);
}
return this;
} /**
* 自定义显示Toast的时长
*/
public ToastUtils Indefinite(Context context, CharSequence message,
int duration) {
if (toast == null
|| (toastView != null && toastView.getChildCount() > 1)) {
toast = Toast.makeText(context, message, duration);
toastView = null;
} else {
toast.setText(message);
toast.setDuration(duration);
} return this;
} /**
* 显示Toast
*/
public ToastUtils show() {
toast.show();
return this;
} /**
* 获取Toast
*/
public Toast getToast() {
return toast;
}
}

Android开发之自定义Toast(带详细注释)的更多相关文章

  1. Android开发之自定义的ListView(UITableViewController)

    Android开发中的ListView, 顾名方法思义,就是表视图.表示图在iOS开发中就是TableView.两者虽然名称不一样,但是其使用方法,使用场景以及该控件的功能都极为相似,都是用来展示大量 ...

  2. android开发之自定义组件

    android开发之自定义组件 一:自定义组件: 我认为,自定义组件就是android给我们提供的的一个空白的可以编辑的图片,它帮助我们实现的我们想要的界面,也就是通过自定义组件我们可以把我们要登入的 ...

  3. C#/WPF/WinForm/.NET程序代码实现软件程序开机自动启动的两种常用方法的示例与源码下载带详细注释-源码代码-注册表方式-启动目录快捷方式

    C#/WPF/WinForm/.NET程序代码实现软件程序开机自动启动的两种常用方法的示例与源码下载带详细注释-源码代码-注册表方式-启动目录快捷方式 C#实现自动启动的方法-两种方法 源码下载地址: ...

  4. android开发中系统自带语音模块的使用

    android开发中系统自带语音模块的使用需求:项目中需要添加语音搜索模块,增加用户体验解决过程:在网上搜到语音搜索例子,参考网上代码,加入到了自己的项目,完成产品要求.这个问题很好解决,网上能找到很 ...

  5. Light OJ - 1026 - Critical Links(图论-Tarjan算法求无向图的桥数) - 带详细注释

     原题链接   无向连通图中,如果删除某边后,图变成不连通,则称该边为桥. 也可以先用Tajan()进行dfs算出所有点 的low和dfn值,并记录dfs过程中每个 点的父节点:然后再把所有点遍历一遍 ...

  6. Android开发之自定义组件和接口回调

    说到自定义控件不得不提的就是接口回调,在Android开发中接口回调用的还是蛮多的.在这篇博客开始的时候呢,我想聊一下iOS的自定义控件.在iOS中自定义控件的思路是继承自UIView, 在UIVie ...

  7. Android开发之自定义局部导航菜单

    如今,要实现导航功能方案有很多.比如: 1.用3.0+自带的Toolbar + Fragment导航. 2.用Tabhost实现导航.小弟学浅,就只用过这两种方案实现导航. 但是这两种方案都有一个很明 ...

  8. Android开发UI之Toast的使用

    Toast,A toast provides simple feedback about an operation in a small popup. 对于操作提供一个简单反馈信息. 官网链接:htt ...

  9. Android开发进阶——自定义View的使用及其原理探索

    在Android开发中,系统提供给我们的UI控件是有限的,当我们需要使用一些特殊的控件的时候,只靠系统提供的控件,可能无法达到我们想要的效果,这时,就需要我们自定义一些控件,来完成我们想要的效果了.下 ...

随机推荐

  1. SQL Server Assembly (SQL CLR) 还原数据库后的问题

    最近弄项目迁移的时候遇到还原数据库(SQL Server 2008)后遇到的一个问题: 消息 10314,级别 16,状态 11,第 1 行 在尝试加载程序集 ID 65536 时 Microsoft ...

  2. 阿里云栖大会 所有ppt

    https://github.com/Alimei/hangzhouYunQi2017ppt

  3. Oracle监听程序未启动或数据库服务未注册到该监听

    oracle新建数据库的时候提示Could not find appropriate listener for this database要做的操作如下: 1.查看netmanager里面的liste ...

  4. apache安装配置

    因为个人是在docker上面做实验的,所以可以多少会有些出入. 1.先启动一个docker,配置好基本的工具,网络啊,ssh啊是,tar啊,wget啊,vim等等. 其次去官网获取自己想要的压缩文件的 ...

  5. 重启虚拟机后,再次重启nginx会报错:[emerg] open() "/var/run/nginx/nginx.pid" failed (2: No such file or directory)

    问题: 重启虚拟机后,再次重启nginx会报错: open() "/var/run/nginx/nginx.pid" failed (2: No such file or dire ...

  6. Activity 与 Task

    [Activity 与 Task] A task is a collection of activities that users interact with when performing a ce ...

  7. day13 多个装饰器叠加 生成式

    1.装饰器剩余 from functions import wraps @wrap(func) 会把func内的自带方法赋给wrapper,这样wrapper装饰函数就和原函数一模一样 多个装饰器叠加 ...

  8. Android学习路-UI控件

  9. hdu 2089 数位dp

    链接:https://vjudge.net/problem/23625/origin 中文,题目不用说了. 其实这题的数据很小,所以直接暴力也可以过,但是还是要学会数位dp,因为并不是每一题的数据都会 ...

  10. HDU_1024.MaxSumPlusPlus(基础DP + 滚动数组优化讲解)

    这道题打破了我常规的做题思路,因为这是我刚开始训练DP,感觉这道题目好晕眼呀,emm其实就是感觉自己是真的菜...... 为什么说打破了我的做题思路呢,因为我平时看题解都是在已经AC或者完全不懂的情况 ...