Android 8.1 Launcher3实现动态指针时钟功能
作者:_Shawn_ 发布时间:2023-09-27 18:53:09
标签:android,动态,指针,时钟
本文主要实现功能,可能有不合理的地方
首先创建一个实现功能的工具里,直接上代码:
import android.content.Context;
import android.graphics.Bitmap;
import android.os.Handler;
import android.os.Message;
import com.android.launcher3.ItemInfo;
import com.android.launcher3.LauncherSettings;
import com.android.launcher3.ShortcutInfo;
import com.android.launcher3.util.LogUtil;
public class DeskClockUtil {
private OnDeskClockIconChangeListener mListener;
private ItemInfo mItemInfo;
private boolean mIsResume;
private Handler mHandler = new Handler() {
@Override
public void handleMessage(Message msg) {
super.handleMessage(msg);
if (msg.what == 100) {
Message msg1 = new Message();
msg1.what = 100;
msg1.obj = msg.obj;
mHandler.sendMessageDelayed(msg1, 60000);
if (mListener != null && mItemInfo != null) {
mListener.onChange(IconUtil.getDeskClockIcon((Context) msg.obj), mItemInfo);
}
}
}
};
private static DeskClockUtil sInstance;
private DeskClockUtil() {
}
public static DeskClockUtil getInstance() {
if (sInstance == null) {
sInstance = new DeskClockUtil();
}
return sInstance;
}
private void refresh(Context context) {
if (mListener != null && mItemInfo != null) {
mListener.onChange(IconUtil.getDeskClockIcon(context), mItemInfo);
}
if (mHandler.hasMessages(100)) {
mHandler.removeMessages(100);
}
Message msg = new Message();
msg.what = 100;
msg.obj = context;
mHandler.sendMessageDelayed(msg,
1000 * (60 - Integer.parseInt(DateUtils.getCurrentSecond())));
}
public void onResume(Context context) {
mIsResume = true;
refresh(context);
}
public void onPause() {
mIsResume = false;
mHandler.removeMessages(100);
}
public void setListener(OnDeskClockIconChangeListener listener, ItemInfo info, Context context) {
if (!(info instanceof ShortcutInfo)) {
return;
}
String pkg = null;
if (info.getIntent() != null && info.getIntent().getComponent() != null) {
pkg = info.getIntent().getComponent().getPackageName();
}
if (!"com.android.deskclock".equals(pkg) || info.itemType == LauncherSettings.Favorites.ITEM_TYPE_DEEP_SHORTCUT) {
return;
}
mListener = listener;
mItemInfo = info;
if (mIsResume) {
refresh(context);
}
}
public interface OnDeskClockIconChangeListener {
void onChange(Bitmap icon, ItemInfo info);
}
}
画出动态时钟
import android.content.Context;
import android.graphics.*;
import com.android.launcher3.R;
public class IconUtil {
private static final String TAG = "IconUtil";
private static Bitmap getBitmap(Context context, int res) {
BitmapFactory.Options options = new BitmapFactory.Options();
options.inPreferredConfig = Bitmap.Config.ARGB_4444;
return BitmapFactory.decodeResource(context.getResources(), res, options);
}
public static Bitmap getDeskClockIcon(Context context) {
// 添加一个带表盘的背景图
Bitmap empty = getBitmap(context, R.drawable.icon_time);
int x = empty.getWidth();
int y = empty.getHeight();
Bitmap deskClock = Bitmap.createBitmap(x, y, Bitmap.Config.ARGB_4444);
Canvas canvas = new Canvas(deskClock);
Paint paint = new Paint();
paint.setAntiAlias(true);
canvas.drawBitmap(empty, 0, 0, paint);
//设置圆角
paint.setStrokeCap(Paint.Cap.ROUND);
paint.setStrokeWidth(5);
paint.setColor(context.getResources().getColor(R.color.deskclock_time));
// 时针的长度
int radius = 35;
// 圆心的x y 坐标
int cx = x / 2;
int cy = y / 2;
int hour = Integer.parseInt(DateUtils.getCurrentHour());
int min = Integer.parseInt(DateUtils.getCurrentMin());
//时针的角度,这里是整点的角度。因为0°是从3点开始,所以这里减90°,从9点开始计算角度
int drgeeHour = hour * 30 - 90;
if (drgeeHour < 0) {
drgeeHour += 360;
}
// 加上时针在两个整点之间的角度,一分钟在分针上是6°,在时针上是min * 6 / 12
drgeeHour += min * 6 / 12;
//时针 针尖的x y坐标,相当于已知圆心坐标和半径,求圆上任意一点的坐标
int xHour = (int) (cx + radius * Math.cos(drgeeHour * 3.14 / 180));
int yHour = (int) (cy + radius * Math.sin(drgeeHour * 3.14 / 180));
canvas.drawLine(xHour, yHour, cx, cy, paint);
//分针的长度
radius = 45;
paint.setStrokeWidth(3);
paint.setColor(Color.RED);
//分针的角度
int drgeeMin = min * 6 - 90;
if (drgeeMin < 0) {
drgeeMin += 360;
}
//分针 针尖的x y坐标
int x1 = (int) (cx + radius * Math.cos(drgeeMin * Math.PI / 180));
int y1 = (int) (cy + radius * Math.sin(drgeeMin * Math.PI / 180));
canvas.drawLine(x1, y1, cx, cy, paint);
return deskClock;
}
}
时间工具类
import java.text.SimpleDateFormat;
public class DateUtils {
public static String getCurrentDay() {
SimpleDateFormat format = new SimpleDateFormat("dd");
Long t = new Long(System.currentTimeMillis());
String d = format.format(t);
return d;
}
public static String getCurrentSecond() {
SimpleDateFormat format = new SimpleDateFormat("ss");
Long t = new Long(System.currentTimeMillis());
String d = format.format(t);
return d;
}
public static String getCurrentMin() {
SimpleDateFormat format = new SimpleDateFormat("mm");
Long t = new Long(System.currentTimeMillis());
String d = format.format(t);
return d;
}
public static String getCurrentHour() {
SimpleDateFormat format = new SimpleDateFormat("HH");
Long t = new Long(System.currentTimeMillis());
String d = format.format(t);
return d;
}
}
下面就比较简单了,我是在BubbleTextView.java中添加listener,我这里偷懒了,应该给时钟单独创建一个view,继承BubbleTextView。
private void applyIconAndLabel(Bitmap icon, ItemInfo info) {
/* begin */
setDeskClockIcon(info);
/* end */
applyIcon(icon, info);
setText(info.title);
if (info.contentDescription != null) {
setContentDescription(info.isDisabled()
? getContext().getString(R.string.disabled_app_label, info.contentDescription)
: info.contentDescription);
}
}
private void setDeskClockIcon(ItemInfo info) {
DeskClockUtil.getInstance().setListener(new DeskClockUtil.OnDeskClockIconChangeListener() {
@Override
public void onChange(Bitmap icon, ItemInfo info) {
applyIcon(icon, info);
}
}, info, getContext());
}
private void applyIcon(Bitmap icon, ItemInfo info) {
FastBitmapDrawable iconDrawable = DrawableFactory.get(getContext()).newIcon(icon, info);
iconDrawable.setIsDisabled(info.isDisabled());
setIcon(iconDrawable);
}
在Launcher.java的onResume()和onPause()中分别开始和暂停
@Override protected void onResume() {
......
/* begin */
DeskClockUtil.getInstance().onResume(this);
/* end */
if (mLauncherCallbacks != null) {
mLauncherCallbacks.onResume();
}
}
@Override
protected void onPause() {
// Ensure that items added to Launcher are queued until Launcher returns
InstallShortcutReceiver.enableInstallQueue(InstallShortcutReceiver.FLAG_ACTIVITY_PAUSED);
super.onPause();
mPaused = true;
mDragController.cancelDrag();
mDragController.resetLastGestureUpTime();
// We call onHide() aggressively. The custom content callbacks should be able to
// debounce excess onHide calls.
if (mWorkspace.getCustomContentCallbacks() != null) {
mWorkspace.getCustomContentCallbacks().onHide();
}
if (mLauncherCallbacks != null) {
mLauncherCallbacks.onPause();
}
/* begin */
DeskClockUtil.getInstance().onPause();
/* end */
}
这样就可以了,如果想要加秒针,在IconUtil中再把秒针画出来就行。
还有日历的动态图标也可以用同样的方法实现
总结
以上所述是小编给大家介绍的Android 8.1 Launcher3实现动态指针时钟功能网站的支持!
来源:https://blog.csdn.net/qq_30552095/article/details/81021625


猜你喜欢
- 1. 效果图展示2. 工程目录结构注意: webapp下的resources目录放置easyui和js(jQuery文件是另外的) 
- 本文实例讲述了spring mvc 实现获取后端传递的值。分享给大家供大家参考,具体如下:jsp页面怎么获取从后端传递过来的值?JSTL 方
- mybatis foreach嵌套if标签代码实现:Mapper.java文件List<Map<String, Object&g
- 一、引言Good Good Study,Day Day UpMP自带的条件构造器虽然很强大,有时候也避免不了写稍微复杂一点业务的sql,那么
- 1、什么是keyWidget中有个可选属性key,顾名思义,它是组件的标识符,当设置了key,组件更新时会根据新老组件的key是否相等来进行
- 关键点:将List内存储的对象实现Comparable类,重写它的compareTo()方法即可Bean:package chc;publi
- 前言大家都知道MySQL数据库很好用,但数据量到了千万以上了,想增加字段是非常痛苦的,这个在MongoDB里就不存在,字段想怎么加就怎么加,
- WebMvcConfigurer配置类其实是Spring内部的一种配置方式,采用JavaBean的形式来代替传统的xml配置文件形式进行针对
- 介绍本文介绍在Java程序中如何添加图片到excel表格,添加图片时可设置图片大小、位置、旋转、超链接、可选文本等,以及如何读取、删除exc
- 前言现如今几乎大多数Java应用,例如我们耳熟能详的tomcat, struts2, netty...等等数都数不过来的软件,要满足通用性,
- 本文句句走心,希望老铁们用心阅读并实战,一定会有收获的。摘要:本文主要讨论生产环境中枚举类的使用。首先会通过对枚举类概念进行简单的介绍,引入
- JAVA IDEA 打开assert 设置概念(此处为借鉴前辈们的讲解)断言(Assertion)是Java中一条语句,包含一个布尔表达式,
- 1. 网络爬虫是一个自动提取网页的程序,它为搜索引擎从万维网上下载网页,是搜索引擎的重要组成。传统爬虫从一个或若干初始网页的URL开始,获得
- 从功能上说,可以分为两部分,分布式功能和数据功能。分布式功能主要是节点集群及集群附属功能如restful借口、集群性能检测功能等,数据功能主
- 相关文章android popwindow实现左侧弹出菜单层https://www.jb51.net/article/33533.htm移动
- 本文讲述了在Java中如何创建和结束线程的最基本方法,只针对于Java初学者。一些高级知识如线程同步、调度、线程池等内容将会在后续章节中逐步
- 本文实例讲述了C#实现TCP连接信息统计的方法。分享给大家供大家参考。具体实现方法如下:using System;using System.
- 程序的最主要的功能在于对数据进行操作,通过对数据进行操作来实现某个功能。而数据库就是很重要的一个方面的,Android中内置了小巧轻便,功能
- 什么是Java类库在编写程序的时候,通常有很多功能是通用的,或者是很基础的,可以用这些功能来组成更发杂的功能代码。比如文件操作,不同程序对文
- 一、CAS(Compare And Set)Compare And Set(或Compare And Swap),CAS是解决多线程并行情况