Android AppWidget开发不同于普通的android应用,因为AppWidget是运行在别的进程中的程序。其使用RemoteViews更新UI。一旦系统发生变更,很容易引起AppWidget的更新。其支持的组件有限,事件类型也很少。所以一般用于更新周期较长,事件比较简单的用于桌面显示的组件。其开发流畅相对来说还是比较简单的。大致分为:
1:编写布局文件
2:编写Provider配置文件和Manifest配置文件
3:编写业务逻辑
对于第一步需要了解一下AppWidget支持的组件类型,对于桌面应用而言,其所支持的组件类型有限,原因是AppWIdget是现实在另外一个进程中的,其使用RemoteViews更新信息。而
RemoteViews支持的布局样式和组件类型有以下几种:
RrameLayout,LinearLayout,RelativeLayout
AnalogClock
,Button
,Chronometer
,ImageButton
,ImageView
,ProgressBar
,TextView
关于AppWidget的布局以及在桌面上如何划分给AppWIdget以布局的可以参考网上的一些资料,这里不再累赘。
按照我如下流程你就可以建立一个AppWidget
1:建立android项目,在res下建立一个xml文件夹,用于存放appWidget的provider配置文件。
2:在xml文件夹下新建widget_config.xml,更改其内容为:
1 <appwidget-provider 2 xmlns:android="http://schemas.android.com/apk/res/android" 3 android:minWidth="300dp" 4 android:minHeight="72dp" 5 android:updatePeriodMillis="0" 6 android:initialLayout="@layout/widget_ui" 7 > 8 appwidget-provider>
3:在layout文件夹下建立一个布局文件,正如上文提到的widget_ui.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:orientation="vertical"> <ProgressBar android:id="@+id/widget_ProgressBar" style="?android:attr/progressBarStyleHorizontal" android:layout_width="match_parent" android:layout_height="wrap_content"/> <LinearLayout android:id="@+id/linearLayout1" android:layout_width="match_parent" android:layout_height="wrap_content"> <Button android:id="@+id/widget_BT_Up" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_weight="1" android:text="Value++"/> <Button android:id="@+id/widget_BT_Down" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="Value--" android:layout_weight="1"/> LinearLayout> LinearLayout>
4:编写Manifest文件,更改内容为:
1 xml version="1.0" encoding="utf-8"?> 2 <manifest xmlns:android="http://schemas.android.com/apk/res/android" 3 package="com.jftt.cjl.widget" 4 android:versionCode="1" 5 android:versionName="1.0"> 6 7 <uses-sdk android:minSdkVersion="10"/> 8 9 <application 10 android:icon="@drawable/ic_launcher" 11 android:label="@string/app_name"> 12 13 <receiver android:name=".MyWidgetProvider" android:label="myWIdget" 14 android:icon="@drawable/ic_launcher"> 15 <intent-filter> 16 <action android:name="android.appwidget.action.APPWIDGET_UPDATE"/> 17 <action android:name="zyf.test.widget.UP"/> 18 <action android:name="zyf.test.widget.DOWN"/> 19 intent-filter> 20 <meta-data android:name="android.appwidget.provider" 21 android:resource="@xml/widget_config"/> 22 receiver> 23 application> 24 25 manifest>
到此为止,我们的配置文件告一段落,下面看看代码吧:
5:新建一个java类 MyWidgetProvider 继承自AppWidgetProvider
1 package com.jftt.cjl.widget; 2 3 import android.app.PendingIntent; 4 import android.appwidget.AppWidgetManager; 5 import android.appwidget.AppWidgetProvider; 6 import android.content.ComponentName; 7 import android.content.Context; 8 import android.content.Intent; 9 import android.media.AudioManager; 10 import android.util.Log; 11 import android.widget.RemoteViews; 12 13 public class MyWidgetProvider extends AppWidgetProvider { 14 public static int Tag; 15 public int max; 16 public int current; 17 18 @Override 19 public void onEnabled(Context context) { 20 // TODO Auto-generated method stub 21 22 super.onEnabled(context); 23 } 24 25 @Override 26 public void onReceive(Context context, Intent intent) { 27 // TODO Auto-generated method stub 28 super.onReceive(context, intent); 29 30 ComponentName thisWidget = new ComponentName(context, 31 MyWidgetProvider.class); 32 RemoteViews views = new RemoteViews(context.getPackageName(), 33 R.layout.widget_ui); 34 AppWidgetManager appmanager = AppWidgetManager.getInstance(context); 35 Log.d("UPUP", intent.getAction()); 36 auc(context, 0); 37 views.setProgressBar(R.id.widget_ProgressBar, max, current, false); 38 appmanager.updateAppWidget(thisWidget, views); 39 Tag = current; 40 if (intent.getAction().equals("zyf.test.widget.UP")) { 41 42 Tag += 1; 43 Log.d("tagdd", Integer.toString(Tag)); 44 45 if (Tag > max) { 46 Tag = max; 47 } 48 auc(context, 1); 49 views.setProgressBar(R.id.widget_ProgressBar, max, Tag, false); 50 appmanager.updateAppWidget(thisWidget, views); 51 } 52 if (intent.getAction().equals("zyf.test.widget.DOWN")) { 53 Tag -= 1; 54 if (Tag < 0) { 55 Tag = 0; 56 } 57 auc(context, -1); 58 views.setProgressBar(R.id.widget_ProgressBar, max, Tag, false); 59 appmanager.updateAppWidget(thisWidget, views); 60 } 61 } 62 63 @Override 64 public void onUpdate(Context context, AppWidgetManager appWidgetManager, 65 int[] appWidgetIds) { 66 // TODO Auto-generated method stub 67 final int N = appWidgetIds.length; 68 auc(context, 0); 69 Log.d("UPUP", "2222222"); 70 // Perform this loop procedure for each App Widget that belongs to this 71 // provider 72 for (int i = 0; i < N; i++) { 73 int appWidgetId = appWidgetIds[i]; 74 RemoteViews views = new RemoteViews(context.getPackageName(), 75 R.layout.widget_ui); 76 Intent UPintent = new Intent("zyf.test.widget.UP"); 77 Intent DOWNintent = new Intent("zyf.test.widget.DOWN"); 78 // 实例化两个带有Action 的Intent 79 PendingIntent pendingIntentUp = PendingIntent.getBroadcast(context, 80 0, UPintent, 0); 81 PendingIntent pendingIntentDown = PendingIntent.getBroadcast( 82 context, 0, DOWNintent, 0); 83 // 实例化两个以Intent 来构造的PendingIntent 84 views.setOnClickPendingIntent(R.id.widget_BT_Up, pendingIntentUp); 85 views.setOnClickPendingIntent(R.id.widget_BT_Down, 86 pendingIntentDown); 87 // 给View 上的两个按钮绑定事件,这里是广播消息的发送 88 appWidgetManager.updateAppWidget(appWidgetId, views); 89 } 90 } 91 92 public void auc(Context context, int i) { 93 // TODO Auto-generated method stub 94 // ---开始音量处理,i=0 仅查询,i=其他的进行操作 95 AudioManager am = null; 96 am = (AudioManager) context.getSystemService(Context.AUDIO_SERVICE); 97 max = am.getStreamMaxVolume(AudioManager.STREAM_MUSIC); 98 current = am.getStreamVolume(AudioManager.STREAM_MUSIC); 99 Log.d("MUSIC", "max : " + max + "current : " + current); 100 current = current + i; 101 am.setStreamVolume(AudioManager.STREAM_MUSIC, current, 0); 102 } 103 }
这样我们的AppWIdget的创建就完成了,可以试试看在桌面上长按,选择Widget,选择我们开发的桌面Widget,显示出来看看效果吧