首页 > 代码库 > App Widget

App Widget

开发APP Widget的步骤


1、继承AppWidgetProvider类,

public class MyWidget extends AppWidgetProvider{
<!-- 每一个Widget放置到桌面上时调用,每一次updatePeriodMillis时间到了之后也会被调用-->    
public void onUpdate(Context context, AppWidgetManager appWidgetManager,int[] appWidgetIds)
<!-- 移除widget时调用-->
public void onDeleted(Context context, int[] appWidgetIds)
<!-- 不管添加多少个widget,都只会调用一次 -->
public void onEnabled(Context context)
<!-- 当最后一个widget从桌面删除的时候调用-->
public void onDisabled(Context context)

<!-- 可用做Widget上的按键响应处理-->
public void onReceive(Context context, Intent intent)
    
}

一般在onUpdate中进行widget中按键的事件处理,和初始化值。



2、AppWidgetProvider是一个Broadcast,需要在Mainfest.xml中注册。

 <receiver android:name="继承AppWidgetProvider的类">
           <intent-filter >
               <action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
           </intent-filter>
           <meta-data android:name="android.appwidget.provider"
               android:resource="@xml/widget_config"/>
 </receiver

   3、 <meta-data>中的android:resource引用的是Widget的配置文件,需要在res/xml下新建,如果xml目录不存在,也需要新建。

 widget_config文件

<?xml version="1.0" encoding="UTF-8"?>
<appwidget-provider xmlns:android="http://schemas.android.com/apk/res/android"
    android:minWidth="40dp"  <!-- 显示在桌面上最小的的宽,高,不能大于4*4的格子-->
    android:minHeight="20dp" 
    android:updatePeriodMillis="1000000"  <!-- widget的更新间隔时间-->
    android:previewImage="@drawable/l7"  <!-- 预览图-->
    android:initialLayout="@layout/my_widgets_layout" <!-- 在桌面的显示布局,在3.0版本之后可以使用,默认以应用图标显示。-->
    android:resizeMode="horizontal|vertical"  <!-- 在桌面可调整的方向-->
     android:configure="cn.fly.widgets.MyWidgetsConfigActivity"> <!-- 当widget在拖到桌面上时,显示的配置文件-->
     
    <!--在4.2版本可以放到锁屏界面上 加上,4.2以下的版本默认是放主屏幕
    android:widgetCategory ="home_screen|keyguard" 
    android:initialKeyguardLayout="" 在锁屏界面上显示的布局
     -->
</appwidget-provider>

设置了updatePeriodMillis后,就算手机处于待机状态,也会唤醒手机去执行更新操作,如果widget更新频繁,这会对手机电池寿命造成影响,所以针对这种情况,可以使用AlarmManager来执行定时更新操作,将AlarmManager的Type设置为 ELAPSED_REALTIME orRTC,就可以保证手机在唤醒的状态下执行更新,updatePeriodMillis则需要设置为0。


在桌面显示的布局文件的跟节点必须是常用布局例如:Framelayout,linearLayout,viewStub等,不能使用自定义布局。


在4.0以后的版本,widget放置到桌面上是可以根据其他的widget或者快捷图标来扩充边距,使添加的widget能够在桌面视觉上达到协调,但是4.0以下的版本需要自己来设置Padding,使widget能和其他桌面图标达到视觉协调。


做完以上的操作,一个简单的widget的就完成了,根据应用需求我们会遇到以下的一些情况。

一、相应widget的按键事件

    因为widget不是运行在自身的应用的进程中,所以是通过以下方式来处理事件。

  RemoteView 进行布局引用。

   PendingIntent  进行事件分发。

//这段代码一般写在onUpdate中,所处理的事情是按button更改Textview的显示
final int N = appWidgetIds.length;
for(int i = 0;i< N;i++){
    Intent intent = new Intent("自定义action用来标示这个intent");
    intent.setClass(context, MyWidgets.class);
    //发送广播,在onReceive()中进行处理PendingIntent也可以启动Activity,也可以//启动Service
    PendingIntent mPendingIntent = PendingIntent.getBroadcast(context, 
					0, intent, 0);
    RemoteViews remoteViews = new RemoteViews(context.getPackageName(),
					"widget布局引用");
    //button按键处理
    remoteViews.setOnClickPendingIntent(R.id.btn_click, mPendingIntent);
    appWidgetManager.updateAppWidget(appWidgetIds[i], remoteViews);
}

  在onReceive()的处理

String action = intent.getAction();
if(action.equals("比较发送的action")){
    RemoteViews remoteViews  = new RemoteViews(context.getPackageName(),"widget布局引用");
    //更改文本显示
    remoteViews.setTextViewText(R.id.tv, "测试");
    AppWidgetManager appWidgetManager = AppWidgetManager.getInstance(context); 
    ComponentName componentName = new ComponentName(context,MyWidgets.class);
    appWidgetManager.updateAppWidget(componentName, remoteViews); 
		}

二、widget添加上桌面上时的配置页面

这个配置页面是一个activity,所以需要在mainfest.xml中进行配置

在启动这个配置页面的时候,需要在oncreate()方法里面写上setResult(RESULT_CANCELED);这样做是为了防止配置页面还没有显示出来,用户就按了返回键,

setResult(RESULT_CANCELED);
super.onCreate(savedInstanceState);


本文出自 “fly” 博客,请务必保留此出处http://fujian0910.blog.51cto.com/1706151/1546112

App Widget