本文主要是介绍Toast实现原理分析,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
Toast
是 Android 中用于短暂显示提示信息的一种 UI 组件。它通常用于向用户展示一些简短的信息,例如操作结果或状态更新。下面我将结合源码来分析 Toast
的实现原理。
1. Toast 类定义
Toast
类定义如下:
1public class Toast {
2 // ...
3 private static final String TAG = "Toast";
4 private static final int MAX_SHOW_TIME = 7000;
5 private static final int MIN_SHOW_TIME = 1000;
6 // ...
7}
2. 构造函数
Toast
没有公开的构造函数,而是通过 makeText
或者 makeCustom
方法来创建实例。
1public static Toast makeText(Context context, CharSequence text, int duration) {
2 return makeText(context, text, duration, null);
3}
4
5public static Toast makeText(Context context, int resId, int duration) {
6 return makeText(context, context.getText(resId), duration, null);
7}
8
9public static Toast makeText(Context context, CharSequence text, int duration,
10 @Nullable RemoteCallback callback) {
11 return makeText(context, text, duration, callback, false /* useTextForAccessibility */);
12}
13
14public static Toast makeText(Context context, CharSequence text, int duration,
15 @Nullable RemoteCallback callback, boolean useTextForAccessibility) {
16 // ...
17 // 创建一个新的 Toast 实例
18 // ...
19 return new Toast(context, text, duration, callback, useTextForAccessibility);
20}
3. 创建 Toast 实例
Toast
实例通过私有的构造函数创建,并且通常会使用默认的 LayoutInflater
来创建视图。
1private Toast(Context context, CharSequence text, int duration,
2 @Nullable RemoteCallback callback, boolean useTextForAccessibility) {
3 mTN = new ToastRecord();
4 mTN.text = text;
5 mTN.duration = duration;
6 mTN.callback = callback;
7 mTN.useTextForAccessibility = useTextForAccessibility;
8 mTN.view = LayoutInflater.from(context).inflate(com.android.internal.R.layout.toast, null);
9 mTN.view.setImportantForAccessibility(useTextForAccessibility ?
10 View.IMPORTANT_FOR_ACCESSIBILITY_YES : View.IMPORTANT_FOR_ACCESSIBILITY_NO_HIDE_DESCENDANTS);
11 // ...
12 // 设置文本
13 ((TextView) mTN.view.findViewById(com.android.internal.R.id.message)).setText(text);
14 // ...
15}
4. 显示 Toast
Toast
通过 show()
方法来显示。
1public void show() {
2 synchronized (this) {
3 if (mTN == null) {
4 throw new RuntimeException("This toast was not created with Toast.makeText()");
5 }
6 if (mTN.view == null) {
7 throw new RuntimeException("The toast view is null.");
8 }
9 if (mShown) {
10 return;
11 }
12 // ...
13 // 创建 ToastManager 并显示视图
14 ToastManager tm = ToastManager.sInstance;
15 if (tm == null) {
16 tm = new ToastManager();
17 ToastManager.sInstance = tm;
18 Context appContext = mTN.view.getContext().getApplicationContext();
19 if (appContext == null) {
20 appContext = mTN.view.getContext();
21 }
22 tm.mContext = appContext;
23 }
24 // ...
25 // 显示 Toast
26 tm.show(this, mTN);
27 mShown = true;
28 }
29}
5. ToastManager
ToastManager
负责管理 Toast
的显示和隐藏。
1public class ToastManager {
2 // ...
3 private Context mContext;
4 private WindowManager mWM;
5 private Handler mHandler;
6 private ToastRecord mCurrent;
7 private ToastRecord mNext;
8 private long mNextFirstShow;
9 private int mNextDuration;
10 // ...
11 public void show(Toast t, ToastRecord record) {
12 // ...
13 // 显示 Toast 视图
14 // ...
15 showView(record, t);
16 // ...
17 }
18}
6. 显示视图
ToastManager
通过 showView
方法来显示视图。
1private void showView(ToastRecord record, Toast t) {
2 // ...
3 // 设置视图的参数
4 WindowManager.LayoutParams lp = record.view.getLayoutParams();
5 if (lp == null) {
6 lp = new WindowManager.LayoutParams(
7 WindowManager.LayoutParams.WRAP_CONTENT,
8 WindowManager.LayoutParams.WRAP_CONTENT,
9 WindowManager.LayoutParams.TYPE_TOAST,
10 WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON |
11 WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE |
12 WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE,
13 PixelFormat.TRANSLUCENT);
14 // ...
15 // 设置动画
16 // ...
17 // 添加视图到 WindowManager
18 mWM.addView(record.view, lp);
19 }
20 // ...
21}
7. 移除视图
ToastManager
也负责移除视图。
1private void removeView(ToastRecord record) {
2 // ...
3 // 从 WindowManager 中移除视图
4 mWM.removeViewImmediate(record.view);
5 // ...
6}
8. 隐藏 Toast
Toast
通过 cancel()
方法来隐藏。
1public void cancel() {
2 synchronized (this) {
3 if (mTN == null) {
4 throw new RuntimeException("This toast was not created with Toast.makeText()");
5 }
6 if (!mShown) {
7 return;
8 }
9 // ...
10 // 移除视图
11 // ...
12 ToastManager tm = ToastManager.sInstance;
13 if (tm != null) {
14 tm.cancel(this, mTN);
15 }
16 mShown = false;
17 }
18}
9. 生命周期管理
Toast
的显示和隐藏通过 Handler
来控制。
1public void cancel(Toast t, ToastRecord record) {
2 // ...
3 // 移除视图
4 removeView(record);
5 // ...
6 // 清理记录
7 // ...
8}
10. 结合源码总结
Toast
通过静态方法makeText
来创建实例。Toast
的显示和隐藏是通过ToastManager
来管理的。Toast
的视图是通过LayoutInflater
来创建的。Toast
的视图添加到了WindowManager
中,并且设置了特定的参数,如位置和透明度。Toast
的显示时间是通过Handler
来控制的。
这篇关于Toast实现原理分析的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!