Android Widget 开发详解(二) +支持listView滑动的widget
转载请标明出处:http://blog.csdn.net/sk719887916/article/details/47027263
不少开发项目中都会有widget功能,别小瞧了它,他也是android的七大组件之一,对widget陌生的朋友可以阅读下我的上篇文章< Android Widget工作原理详解(一)>关于内部的介绍,还没掌握的同学不要担心,开发AppWidget套路很简单,今天我们就实现一个可以加入listView滑动的widget,熟悉下一个普通widget的开发步骤。
一 创建AppWidgetProvider
remoteViews)来加载或更新widget布局,也可以通过onReceive()
@Override
public void onUpdate(Context context, AppWidgetManager appWidgetManager,
int[] appWidgetIds) {
// 获取Widget的组件名
ComponentName thisWidget = new ComponentName(context,
MyAppListWidgetProvider.class);
// 创建一个RemoteView
RemoteViews remoteViews = new RemoteViews(context.getPackageName(),
R.layout.my_widget_layout);
// 把这个Widget绑定到RemoteViewsService
Intent intent = new Intent(context, MyRemoteViewsService.class);
intent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, appWidgetIds[0]);
// 设置适配器
remoteViews.setRemoteAdapter(R.id.widget_list, intent);
// 设置当显示的widget_list为空显示的View
remoteViews.setEmptyView(R.id.widget_list, R.layout.none_data);
// 点击列表触发事件
Intent clickIntent = new Intent(context, MyAppListWidgetProvider.class);
// 设置Action,方便在onReceive中区别点击事件
clickIntent.setAction(clickAction);
clickIntent.setData(Uri.parse(clickIntent.toUri(Intent.URI_INTENT_SCHEME)));
PendingIntent pendingIntentTemplate = PendingIntent.getBroadcast(
context, 0, clickIntent, PendingIntent.FLAG_UPDATE_CURRENT);
remoteViews.setPendingIntentTemplate(R.id.widget_list,
pendingIntentTemplate);
// 刷新按钮
final Intent refreshIntent = new Intent(context,
MyAppListWidgetProvider.class);
refreshIntent.setAction("refresh");
final PendingIntent refreshPendingIntent = PendingIntent.getBroadcast(
context, 0, refreshIntent, PendingIntent.FLAG_UPDATE_CURRENT);
remoteViews.setOnClickPendingIntent(R.id.button_refresh,
refreshPendingIntent);
// 更新Wdiget
appWidgetManager.updateAppWidget(thisWidget, remoteViews);
}
此方功类似广播的onReceive()用发,用开接收和处理广播,如果我们在manifest.xml注册了MyAppListWidgetProvider为一个appwidget,那么不必须为此广播加上widget标示,添加一action:<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />,下面的 <meta-data>标签用来定义widget的属性,指定一个widget描述信息,具体释义请阅读 上篇widget原理详解文章,
<!-- Widget必须添加到manifest文件中,和Broadcaset Receiver一样使用“receiver”标签 -->
<receiver android:name=".MyAppListWidgetProvider" >
<!-- 此处设置Wdiget更新动作 -->
<intent-filter>
<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
</intent-filter>
<!-- 此处设置Widget的描述资源res/xml/my_widget.xml -->
<meta-data
android:name="android.appwidget.provider"
android:resource="@xml/widget_info"
>
</meta-data>
</receiver>
onReceive里处理代码逻辑,比如我这里用来接收widget的用来更新我们在onUpdate()给刷新按钮定义的点击事件,处理刷新界面需求,
/**
* 接收Intent
*/
@Override
public void onReceive(Context context, Intent intent) {
super.onReceive(context, intent);
String action = intent.getAction();
if (action.equals("refresh")) {
// 刷新Widget
final AppWidgetManager mgr = AppWidgetManager.getInstance(context);
final ComponentName cn = new ComponentName(context,
MyAppListWidgetProvider.class);
MyRemoteViewsFactory.mList.add("音乐"+i);
// 这句话会调用RemoteViewSerivce中RemoteViewsFactory的onDataSetChanged()方法。
mgr.notifyAppWidgetViewDataChanged(mgr.getAppWidgetIds(cn),
R.id.widget_list);
} else if (action.equals(clickAction)) {
// 单击Wdiget中ListView的某一项会显示一个Toast提示。
Toast.makeText(context, intent.getStringExtra("content"),
Toast.LENGTH_SHORT).show();
}
i=i+1;
}
@Override
public void onEnabled(Context context) {
// TODO Auto-generated method stub
super.onEnabled(context);
Toast.makeText(context, "用户将widget添加桌面了",
Toast.LENGTH_SHORT).show();
}
@Override
public void onDeleted(Context context, int[] appWidgetIds) {
// TODO Auto-generated method stub。
Toast.makeText(context, "用户将widget从桌面移除了",
Toast.LENGTH_SHORT).show();
super.onDeleted(context, appWidgetIds);
}
二 创建RemoteViewsFactory
public class MyRemoteViewsFactory implements RemoteViewsFactory {
private final Context mContext;
public static List<String> mList = new ArrayList<String>();
/*
* 构造函数
*/
public MyRemoteViewsFactory(Context context, Intent intent) {
mContext = context;
}
/*
* MyRemoteViewsFactory调用时执行,这个方法执行时间超过20秒回报错。
* 如果耗时长的任务应该在onDataSetChanged或者getViewAt中处理
*/
@Override
public void onCreate() {
// 需要显示的数据
mList.add("");
for (int i = 0; i < 5; i++) {
mList.add("item"+ i);
}
}
/*
* 当调用notifyAppWidgetViewDataChanged方法时,触发这个方法
* 例如:MyRemoteViewsFactory.notifyAppWidgetViewDataChanged();
*/
@Override
public void onDataSetChanged() {
}
/*
* 这个方法不用多说了把,这里写清理资源,释放内存的操作
*/
@Override
public void onDestroy() {
mList.clear();
}
/*
* 返回集合数量
*/
@Override
public int getCount() {
return mList.size();
}
/*
* 创建并且填充,在指定索引位置显示的View,这个和BaseAdapter的getView类似
*/
@Override
public RemoteViews getViewAt(int position) {
if (position < 0 || position >= mList.size())
return null;
String content = mList.get(position);
// 创建在当前索引位置要显示的View
final RemoteViews rv = new RemoteViews(mContext.getPackageName(),
R.layout.my_widget_layout_item);
// 设置要显示的内容
rv.setTextViewText(R.id.widget_list_item_tv, content);
// 填充Intent,填充在AppWdigetProvider中创建的PendingIntent
Intent intent = new Intent();
// 传入点击行的数据
intent.putExtra("content", content);
rv.setOnClickFillInIntent(R.id.widget_list_item_tv, intent);
return rv;
}
/*
* 显示一个"加载"View。返回null的时候将使用默认的View
*/
@Override
public RemoteViews getLoadingView() {
return null;
}
/*
* 不同View定义的数量。默认为1(本人一直在使用默认值)
*/
@Override
public int getViewTypeCount() {
return 1;
}
/*
* 返回当前索引的。
*/
@Override
public long getItemId(int position) {
return position;
}
/*
* 如果每个项提供的ID是稳定的,即她们不会在运行时改变,就返回true(没用过。。。)
*/
@Override
public boolean hasStableIds() {
return true;
}
三 RemoteViewsService
具体地说,其子类RemoteViewsService是一个远程的服务适配器 可以请求RemoteViews,管理RemoteViews的服务。我们继承RemoteViewsService来获得一个视图工厂,
@TargetApi(Build.VERSION_CODES.HONEYCOMB)
public class MyRemoteViewsService extends RemoteViewsService {
@Override
public RemoteViewsFactory onGetViewFactory(Intent intent) {
return new MyRemoteViewsFactory(this.getApplicationContext(), intent);
}
}
四 增加widet基础属性配置
<?xml version="1.0" encoding="utf-8"?>
<appwidget-provider xmlns:android="http://schemas.android.com/apk/res/android"
android:initialLayout="@layout/my_widget_layout"
android:minHeight="120dp"
android:minWidth="280dp"
android:previewImage="@drawable/ic_launcher"
android:resizeMode="horizontal|vertical"
android:updatePeriodMillis="0" >
<!--
sdk1.5之后updatePeriodMillis已失效,置为0,循环执行自行在代码中实现。
至于其他属性可以查一下。在其他随笔中我也给出了
-->
</appwidget-provider>
2 新建widget资源文件xml
属性来指定。而widget描述信息我们在manifest.xml中 用<meta-data>标签用来指定。
<?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="200dp"
android:background="@android:color/white"
android:orientation="vertical" >
<Button
android:id="@+id/button_refresh"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:background="@drawable/lite_widget_item_choosed_background_icon"
android:textColor="@android:color/white"
android:layout_marginTop="2dp"
android:text="刷新" />
<ListView
android:id="@+id/widget_list"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:cacheColorHint="#00000000"
android:scrollbars="none" />
<!-- 此处的ListView 可以换成StackView或者GridView -->
</LinearLayout>
Android Widget 开发详解(二) +支持listView滑动的widget的更多相关文章
- Android WebView 开发详解(二)
转载请注明出处 http://blog.csdn.net/typename/article/details/39495409 powered by miechal zhao 概览: Androi ...
- Android USB 开发详解
Android USB 开发详解 先附上 Android USB 官方文档 Android通过两种模式支持各种 USB 外设和 Android USB 附件(实现Android附件协议的硬件):USB ...
- JMessage Android 端开发详解
目前越来越多的应用会需要集成即时通讯功能,这里就为大家详细讲一下如何通过集成 JMessage 来为你的 App 增加即时通讯功能. 首先,一个最基础的 IM 应用会需要有哪些功能? 用户注册 / 登 ...
- Android WebView 开发详解
Android WebView 开发详解 参见 http://blog.csdn.net/typename/article/details/39030091
- 《Android游戏开发详解》一1.7 控制流程第1部分——if和else语句
本节书摘来异步社区<Android游戏开发详解>一书中的第1章,第1.7节,译者: 李强 责编: 陈冀康,更多章节内容可以访问云栖社区"异步社区"公众号查看. 1.7 ...
- Android Studio 插件开发详解二:工具类
转载请标明出处:http://blog.csdn.net/zhaoyanjun6/article/details/78112856 本文出自[赵彦军的博客] 在插件开发过程中,我们按照开发一个正式的项 ...
- Android 时间日期Widget 开发详解
桌面Widget其实就是一个显示一些信息的工具(现在也有人开发了一些有实际操作功能的widget.例如相机widget,可以直接桌面拍照).不过总的来说,widget主要功能就是显示一些信息.我们今天 ...
- Android WebView 开发详解(一)
转载请注明出处 http://blog.csdn.net/typename/article/details/39030091 powered by meichal zhao 概览: Android ...
- Android WebView 开发详解(三)
转载请注明出处 http://blog.csdn.net/typename/article/details/40302351 powered by miechal zhao 概览 Android ...
随机推荐
- ACM 还是畅通工程
Problem Description 某省调查乡村交通状况,得到的统计表中列出了任意两村庄间的距离.省政府"畅通工程"的目标是使全省任何两个村庄间都可以实现公路交通(但不一定有直 ...
- Android Studio精彩案例(七)《ToolBar使用详解<一>》
转载本专栏文章,请注明出处,尊重原创 .文章博客地址:道龙的博客 本文参考博客:http://blog.csdn.net/h_zhang/article/details/51232773 http:/ ...
- vue关于数组使用的坑
关于数组使用的坑 https://vuejs.org/v2/guide/list.html#Caveats 简言之, 不要使用a[i] = v 的形式, 用a.splice(i, 1, v), 或Vu ...
- activiti监听器使用
分享牛原创(尊重原创 转载对的时候第一行请注明,转载出处来自分享牛http://blog.csdn.net/qq_30739519) activiti使用的时候,通常需要跟业务紧密的结合在一起,有些业 ...
- SpriteKit中反转Action需要注意的问题
大熊猫猪·侯佩原创或翻译作品.欢迎转载,转载请注明出处. 如果觉得写的不好请多提意见,如果觉得不错请多多支持点赞.谢谢! hopy ;) 我们知道在SpriteKit中同样有Cocos2D中类似的Ac ...
- Android Multimedia框架总结(十)Stagefright框架之音视频输出过程
转载请把头部出处链接和尾部二维码一起转载,本文出自逆流的鱼yuiop:http://blog.csdn.net/hejjunlin/article/details/52560012 前言:上篇文中最后 ...
- java的断言(assert)
概述 在C和C++语言中都有assert关键,表示断言.在Java中,同样也有assert关键字,表示断言,用法和含义都差不多.在Java中,assert关键字是从JAVA SE 1.4 引入的,为了 ...
- [ExtJS5学习笔记]第三十二节 sencha extjs 5与struts2的ajax交互配置
本文地址:http://blog.csdn.net/sushengmiyan/article/details/43487751 本文作者:sushengmiyan ------------------ ...
- EBS销售(OE)模块常用表
select * from ra_customers 客户 select * from ra_addresses_all 地址 select * from ra_site_uses_all 用户 ...
- 2.Cocos2d-x-3.2编写3d打飞机,项目代码总结
1.AppDelete中applicationDidFinishLaunching代码示范 2.当电话来了时,停止恢复游戏声音的代码(在AppDelegate中加入下面代码) boolAppDel ...