android 创建桌面小部件widget

1. 创建自定义widget的广播类,继承自 AppWidgetProvider(有了这个广播就会在widgets中能够选择了吗?)这个广播的生命周期主要有五个,在第一个widget拖动到桌面和最后一个widget删除和已经有widget时拖动到桌面的生命周期是不同的

根据对生命周期的分析,在onUpdate中进行初始化,在onDisabled中进行销毁(关闭服务)。

public class ProcessWidgetReceiver extends AppWidgetProvider {

    private Intent intent;

    @Override
    public void onReceive(Context context, Intent intent) {
        Log.e("John", "ProcessWidgetReceiver" + " # " + "onReceive");
        super.onReceive(context, intent);
    }

    @Override
    public void onUpdate(Context context, AppWidgetManager appWidgetManager, int[] appWidgetIds) {
        Log.e("John", "ProcessWidgetReceiver" + " # " + "onUpdate");
        // 初始化的相关工作,开启一个服务,
        intent = new Intent(context, ProcessWidgetService.class);
        context.startService(intent);
    }

    @Override
    public void onDeleted(Context context, int[] appWidgetIds) {
        Log.e("John", "ProcessWidgetReceiver" + " # " + "onDeleted");
        super.onDeleted(context, appWidgetIds);
    }

    @Override
    public void onEnabled(Context context) {
        Log.e("John", "ProcessWidgetReceiver" + " # " + "onEnabled");
        super.onEnabled(context);
    }

    @Override
    public void onDisabled(Context context) {
        Log.e("John", "ProcessWidgetReceiver" + " # " + "onDisabled");
        // 销毁的相关工作
        context.stopService(intent);
        super.onDisabled(context);
    }
}

2. 注册widget广播在Manifest中,并且初始化他的布局

        <receiver android:name=".receiver.ProcessWidgetReceiver">
            <intent-filter>
                <action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
            </intent-filter>
            <meta-data android:name="android.appwidget.provider"
                android:resource="@xml/process_clean_widget" /> // 这个是widget的布局文件
        </receiver>
"@xml/process_clean_widget"描述了widget的基本布局信息,主要的参数是下面四个
<?xml version="1.0" encoding="utf-8"?>
<appwidget-provider xmlns:android="http://schemas.android.com/apk/res/android"
    android:initialLayout="@layout/process_widget"
    android:minHeight="72.0dip"
    android:minWidth="294.0dip"
    android:updatePeriodMillis="0" />
"@layout/process_widget" 具体的布局,和其他的控件布局形式相同

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="wrap_content"
    android:background="@drawable/widget_bg_portrait"
    android:gravity="center_vertical">

    <LinearLayout
        android:layout_width="0.0dip"
        android:layout_height="fill_parent"
        android:layout_marginLeft="5.0dip"
        android:layout_weight="1.0"
        android:background="@drawable/widget_bg_portrait_child"
        android:gravity="center_vertical"
        android:orientation="vertical"
        android:paddingBottom="3.0dip"
        android:paddingTop="3.0dip">

        <TextView
            android:id="@+id/process_count"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_marginLeft="10.0dip"
            android:textAppearance="@style/widget_text" />

        <ImageView
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:layout_marginBottom="1.0dip"
            android:layout_marginTop="1.0dip"
            android:background="@drawable/widget_bg_portrait_child_divider" />

        <TextView
            android:id="@+id/process_memory"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_marginLeft="10.0dip"
            android:textAppearance="@style/widget_text" />
    </LinearLayout>

    <LinearLayout
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:gravity="center_horizontal"
        android:orientation="vertical">

        <LinearLayout
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:gravity="center_vertical">

            <ImageView
                android:layout_width="20.0dip"
                android:layout_height="20.0dip"
                android:src="@drawable/main_icon" />

            <TextView
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="@string/app_name"
                android:textColor="@color/textColorPrimary" />
        </LinearLayout>

        <Button
            android:id="@+id/btn_clear"
            android:layout_width="90.0dip"
            android:layout_height="wrap_content"
            android:layout_centerVertical="true"
            android:layout_marginTop="5.0dip"
            android:background="@drawable/function_greenbutton_selector"
            android:text="一键清理"
            android:textColor="@color/function_greenbutton_textcolor_selector" />
    </LinearLayout>
</LinearLayout>

3. 实现这个widget的界面更新和按钮的点击事件,注意的是widget是相当于创建在桌面应用中的所以界面的更新和点击事件的实现和普通的不一样,因为widget的操作在一个单独注册的服务中

public class ProcessWidgetService extends Service {

    private Timer timer;

    @Nullable
    @Override
    public IBinder onBind(Intent intent) {
        return null;
    }

    @Override
    public void onCreate() {
        final AppWidgetManager awm = AppWidgetManager.getInstance(getApplicationContext());
        // 创建定时器,定时刷新widget
        timer = new Timer();
        timer.schedule(new TimerTask() {
            @Override
            public void run() {
                Log.e("John", "ProcessWidgetService" + " # " + "更新widget");
                // 不停更新widget文本内容
                ComponentName provider = new ComponentName(getApplicationContext(), ProcessWidgetReceiver.class);
                RemoteViews views = new RemoteViews(getPackageName(), R.layout.process_widget);
                views.setTextViewText(R.id.process_count, "正在运行的软件:" +
                        ProcessUtil.getRunningProcess(getApplicationContext(),
                                ProcessUtil.ProcessType.ALL).size() + "个");
                long availMem = ProcessUtil.getMemoryInfo(getApplicationContext(), ProcessUtil.MemoryType.AVAILABLE);
                String memStr = Formatter.formatFileSize(getApplicationContext(), availMem);
                views.setTextViewText(R.id.process_memory, "可用内存 :" + memStr);

                // 点击清理内存,通过发出一个广播在另一个广播中进行清理
                Intent intent = new Intent();
                intent.setAction("com.john.kill_process");
                PendingIntent pendingIntent = PendingIntent.getBroadcast(getApplicationContext(), 0, intent, PendingIntent.FLAG_UPDATE_CURRENT);
                views.setOnClickPendingIntent(R.id.btn_clear, pendingIntent);

                awm.updateAppWidget(provider, views);   // 更新widget
            }
        }, 0, 5000);
    }

    @Override
    public void onDestroy() {
        timer.cancel();
        timer = null;
        super.onDestroy();
    }
}

通过点击按钮,是发出了一个广播,这个广播在程序中进行注册了,当点击发生后程序接受到广播然后在广播里进行清理进程

        <receiver android:name=".receiver.ProcessCleanReceiver">
            <intent-filter>
                <action android:name="com.john.kill_process"/>
            </intent-filter>
        </receiver>

清理的广播

public class ProcessCleanReceiver extends BroadcastReceiver{

    @Override
    public void onReceive(Context context, Intent intent) {
        List<ProcessInfo> runningProcess = ProcessUtil.getRunningProcess(context, ProcessUtil.ProcessType.ALL);
        Log.e("John", "ProcessCleanReceiver" + " # " + "广播,清理进程 #" + runningProcess.size());
        ProcessUtil.killProcesses(context, runningProcess);
    }

}

总结:

  1. 初始化widget的广播

    1.1 自定义widget的类继承自AppWidgetReceiver

    1.2 在Manifest中注册widget

  2. 根据Manifest中注册时定义的widget的基本布局文件去定义widget的基本布局参数

  3. 根据widget的基本参数文件中定义的layout文件在layout文件夹下面去创建这个layout文件,这个layout文件按照一般的控件布局去定义

  4. 在widget广播中开启一个服务,这个服务中开启一个定时器用来更新运行的进程数据(这里是以这个Demo为例,每隔5秒去获取正在运行的进程)

  4.1 widget中点击事件是通过点击了然后发出一个广播由当前程序去监听这个广播然后在收到广播后清理进程的操作

时间: 2024-11-04 17:08:34

android 创建桌面小部件widget的相关文章

Android开发中实现桌面小部件

在Android开发中,有时候我们的App设计的功能比较多的时候,需要根据需要更简洁的为用户提供清晰已用的某些功能的时候,用桌面小部件就是一个很好的选择,即App Widget,下面我们就用Android studio来创建一个简单的桌面小部件: 选择New->Widget->App Wight                                                                 接下来设置App Widget的一些信息               

Android桌面小部件AppWidget开发

什么是AppWidget AppWidget 即桌面小部件,也叫桌面控件,就是能直接显示在Android系统桌面上的小程序,先看图: 图中我用×××箭头指示的即为AppWidget,一些用户使用比较频繁的程序,可以做成AppWidget,这样能方便地使用.典型的程序有时钟.天气.音乐播放器等.AppWidget 是Android 系统应用开发层面的一部分,有着特殊用途,使用得当的化,的确会为app 增色不少,它的工作原理是把一个进程的控件嵌入到别外一个进程的窗口里的一种方法.长按桌面空白处,会出

Android 桌面小部件(AppWidgetProvider)的应用

根据应用的需要,有的APP中内嵌了桌面小部件代码,以至于我们可以通过长按手机屏幕-->小部件-->选择你需要添加的应用小部件.这样可以给用户提过了较好的.快捷的使用体验方式,这边是Android桌面小部件的实际意义. 下图是有道词典的一个桌面小部件的实例(另外红日的icon便是红日APP的一个简单的桌面小部件): AppWidgetProvider是Android提供的用于实现桌面小部件的类,其本质是一个广播.另外也用到了RemoteViews这个类,这是一个跨进程的远程类,使用场景有两种:通

Android 之窗口小部件高级篇--App Widget 之 RemoteViews - 跨到对岸去

在之前的一篇博文( Android 之窗口小部件详解--App Widge t)中,已经介绍了App Widget的基本用法和简单实例.这篇主要讲解 App Widget 的高级内容,即通过 RemoteViews 去管理Widget的中GridView.ListView.StackView等内容.在学习本篇之前,建议读者先掌握 App Widget 的基本知识. 1 RemoteViews等相关类的介绍 下面先简单介绍RemoteViews.RemoteViewsService.RemoteV

桌面小部件AppWidgetProvider简单分析

1.一般桌面小部件涉及到的类 AppWidgetProvider :BroadcastRecevier子类,用于接收更新,删除通知 AppWidgetProvderInfo:AppWidget相关信息(大小,更新频率等),xml形式 AppWidgetManger:AppWidget管理类,用于向provider发送消息 RemoteViews:可以在其他进程中运行的类,用于向provider发送通知. RemoteViewsService : 是一个远程的服务适配器 可以请求RemoteVie

android创建桌面快捷键shortcut

有很多人也写过创建桌面快捷键的blog,但是大部分都只讲了怎么用,其实技术使用起来都很简单,但是你使用后下次还知道吗? 根本原因还是不清楚原理,今天我就来讲讲shortcut创建过程. 过程: home键-->点击添加-->弹出一个Dialog对话框-->Dialog对话框中的数据,是一个系统级专门用来查找的Activity启动 --->查找出数据显示能添加的快捷方式--->然后保存数据,退出dialog-->桌面launcher操作-->完成 原理: 查看源码,

解决 三星Note3 桌面小部件不实时更新/不刷新 的问题

机型及问题描述:我的是三星note3 (国行 SM-N9008V),已ROOT,安装了LBE安全大师.在桌面小部件中,有些不会实时更新.比如有 滴答清单(办过的事项无法勾选),百度云音乐(歌曲播放更新不及时),系统自带健走计步器(走路数量不更新)等. 问题原因:经测试,原因应该出在LBE安全大师会自动清理RAM,导致负责桌面小部件的进行被杀掉了,致使无法顺利更新小部件. 解决方法:打开LBE安全大师--"手机加速"--"任务管理"--上方的"白名单任务&q

Android 之窗口小部件详解--App Widget

1 App Widget简介 App Widget是应用程序窗口小部件(Widget)是微型的应用程序视图,它可以被嵌入到其它应用程序中(比如桌面)并接收周期性的更新.你可以通过一个App Widget Provider来发布一个Widget. 本文参考Android官方文本,先介绍App Widget的主要组件,然后再以示例来详细说明. 2 App Widget主要的相关类介绍 2.1 AppWidgetProvider AppWidgetProvider 继承自 BroadcastRecei

【Android】AppWidget桌面小部件

什么是App Widget? AppWidget是应用程序窗口小部件,是微型的应用程序视图,它可以被嵌入到桌面应用程序中,并接收周期的更新. 如何实现AppWidget? 1. 新建一个AppWidget类继承AppWidgetProvider(AppWidgetProvider继承BroadcastReceiver),并实现相关生命周期方法. onUpdate() 当widget更新时被执行. 注意:用户首次添加widget时,onUpdate()也会被调用.但是如果定义了widget的con