iis服务器助手广告广告
返回顶部
首页 > 资讯 > 移动开发 >Android UI组件AppWidget控件入门详解
  • 120
分享到

Android UI组件AppWidget控件入门详解

Android 2022-06-06 07:06:04 120人浏览 泡泡鱼
摘要

Widget引入  我们可以把Widget理解成放置在桌面上的小组件(挂件),有了Widget,我们可以很方便地直接在桌面上进行各种操作,例如播放音乐。 

Widget引入 

我们可以把Widget理解成放置在桌面上的小组件(挂件),有了Widget,我们可以很方便地直接在桌面上进行各种操作,例如播放音乐。 

当我们长按桌面时,可以看到Widget选项,如下图所示: 


点击上图中箭头处的widgets图标,会出现如下界面:(都是widget) 

长按上图中的任意一个widget,就可以将其放到桌面上。 

Widget的使用
Widget的实现思路 
(1)在AndroidManifest中声明AppWidget; 
(2)在xml目录中定义AppWidget的配置文件; 
(3)在layout目录中定义Widget的布局文件; 
(4)新建一个类,继承AppWidgetProvider类,实现具体的widget业务逻辑。 

我们需要新建一个类,继承AppWidgetProvider。点开AppWidgetProvider,发现AppWidgetProvider竟然是继承自BroadcastReceiver。 

为什么Widget是一个广播接收器呢?我们知道,BroadcastReceiver类中有一个onReceive方法,用来接收广播。当我们在桌面挂件上去做操作时,必然引起应用的改变,这就涉及到挂件和应用之间的通信,此时用广播来通信是再好不过了。 

Widget的具体使用步骤 

(1)新建一个类TestWidget.java,继承AppWidgetProvider:
 TestWidget.java: 


import android.appwidget.AppWidgetProvider;
import android.content.Context;
import android.content.Intent;

public class TestWidget extends AppWidgetProvider{
 @Override
 public void onReceive(Context context, Intent intent) {
  super.onReceive(context, intent);
 }
} 

(2)因为Widget是一个广播接收器,所以我们需要在清单文件中注册:


 <!-- 声明widget对应的AppWidgetProvider -->
  <receiver android:name=".TestWidget">
   <intent-filter>
    <action android:name="android.appwidget.action.APPWIDGET_UPDATE"/>
   </intent-filter>
   <meta-data
    android:name="android.appwidget.provider"
    android:resource="@layout/widget_setting"/>
  </receiver> 

04行:action是过滤条件,用来过滤行为,监测widget的更新。
08行:android:resource指定了widget的配置。我们知道,属性在清单文件中是用来存储数据的。 

(3)layout文件夹中新建文件widget_setting.xml:(widget的配置文件)
 setting_widget.xml: 


<?xml version="1.0" encoding="utf-8"?>
<appwidget-provider xmlns:android="Http://schemas.android.com/apk/res/android"
     android:layout_width="match_parent"
     android:layout_height="match_parent"
     android:initialLayout="@layout/layout_widget"
     android:minHeight="140dp"
     android:minWidth="140dp"
     android:previewImage="@mipmap/ic_launcher"
     android:updatePeriodMillis="20000"
     android:widgetCateGory="home_screen"
 >
</appwidget-provider> 

08行: android:initialLayout 指定了widget的布局。
09行:android:updatePeriodMillis 指定更新的时间周期
10行: android:widgetCategory="home_screen" 将widget显示在主屏幕上(也可以显示在屏上)

(4)layout文件夹中新建文件layout_widget.xml:(widget的布局)
 layout_widget.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">
 <TextView
  android:id="@+id/textView"
  android:layout_width="wrap_content"
  android:layout_height="wrap_content"
  android:layout_gravity="center_horizontal"
  android:text="Large Text"
  android:textAppearance="?android:attr/textAppearanceLarge"/>
 <Button
  android:id="@+id/button2"
  android:layout_width="wrap_content"
  android:layout_height="wrap_content"
  android:layout_gravity="center_horizontal"
  android:text="New Button"/>
</LinearLayout> 

到此,程序就可以跑起来了。运行程序之后,长按桌面,点开"Widget"按钮,可以看到我们刚刚设计出的widget: 


长按上图中的箭头处,就可以将我们设计出的widget拖放到桌面上了: 


Widget的点击和更新【重要】 

我们知道,TestWidget.java继承自AppWidgetProvider,而AppWidgetProvider在继承BroadcastReceiver之后,重写onReceive方法,然后还自定义了很多方法: 


上图中,包含了被删除时、被禁用时、被启用时、被更新时等各种方法。尤其重要的是onReceive()方法和onUpDate()方法。
 当小部件被改变时(比如被安装到桌面),系统会发送一个更新的广播(上图红框部分所示)。我们在setting_widget.xml中设置了widget的更新频率,这个也会调用更新。 

有人可能会问,我开机之后,天气等widget为何不更新了?这是因为进程被杀死了,那我们只能把这个控件先移除,然后再装上,此时应用会发update更新的广播。 

当需要做widget的点击和更新时,我们需要在需要重写onUpdate()方法,用来发送广播。当程序初始化的时候,系统就会调用onUpdate()方法。 

onUpdate()方法中的代码如下:


  @Override
 public void onUpdate(Context context, AppWidgetManager appWidgetManager, int[] appWidgetIds) {
  super.onUpdate(context, appWidgetManager, appWidgetIds);
  RemoteViews remoteViews = new RemoteViews(context.getPackageName(), R.layout.layout_widget);//需要构造一个RemoteViews
  Intent intent = new Intent();
  intent.setClass(context, TestWidget.class); //通过intent把广播发给TestWidget本身,TestWidget接受到广播之后,会调用。。进而刷新借鉴  // 。
  intent.setAction(WIDGET_BTN_ACTION);
  PendingIntent pendingIntent = PendingIntent.getBroadcast(context, 0, intent, 0);
  remoteViews.setOnClickPendingIntent(R.id.widget_btn, pendingIntent);//控件btn_widget的点击事件:点击按钮时,会发一个带action的广播。
  appWidgetManager.updateAppWidget(appWidgetIds, remoteViews); //点击完了之后,记得更新一下。
 } 

代码解释:
首先需要new一个RemoteViews,构造方法里需要传递两个参数,一个是包名(context.getPacakgeName),一个是布局文件(layout_widget)。
 然后通过remoteViews.setOnClickPendingIntent()设置按钮的点击事件。setOnClickPendingIntent()中需要传递两个参数:一个是id(比如需要被点击的button),一个是PendingIntent。PendingIntent是未来的意图。
 于是我们需要事先构造一个PendingIntent,这个需要通过 PendingIntent.getBroadcast()来构造。getBroadcast()方法中需要传递四个参数,其中有一个是Intent。
 于是我们需要构造一个Intent。在intent里发送广播,并设置Action。
 按钮点击完了之后,记得调用appWidgetManager.updateAppWidget(int[] appWidgetIds, RemoteViews views)方法更新一下,第一个参数就是onUpdate方法中的参数,代表的是所有的控件。 

在onUpdate()方法中通过intent发送按钮点击时间的广播之后,我们需要在onReceive()方法中进行广播的接收。
 onReceive()方法中的代码如下: 


 @Override
 public void onReceive(Context context, Intent intent) {
  super.onReceive(context, intent);
  if (intent != null && TextUtils.equals(intent.getAction(), WIDGET_BTN_ACTION)) { //当intent不为空,且action匹配成功时,就接收广播,然后点击事件成功
   Log.i(WIDGET_BTN_ACTION, "is clicked");
   //接下来开始做点击事件里面的内容
   RemoteViews remoteViews = new RemoteViews(context.getPackageName(), R.layout.layout_widget);//注意:需要【重新】构造一个RemoteViews
   remoteViews.setTextViewText(R.id.widget_tv, "be clicked");
   remoteViews.setTextColor(R.id.widget_tv, Color.RED);
   AppWidgetManager appWidgetManager = AppWidgetManager.getInstance(context);// 单例模式
   ComponentName componentName = new ComponentName(context, TestWidget.class);
   appWidgetManager.updateAppWidget(componentName, remoteViews);//setText之后,记得更新一下
  }
 } 

代码解释:
 当intent的action匹配成功时,开始执行做点击时间之后的setText,不过这里需要重新new 一个 RemoteViews,而不能共用onUpdate()方法中的RemoteViews(这是一个很大的坑)。
 执行完点击事件之后的setText之后,记得调用appWidgetManager.updateAppWidget(ComponentName, RemoteViews)方法,第一个参数为组件名,需要我们自己new一下,第二个参数很好解释。 

综合来说,TestWidget.java的完整版代码如下:
Testwidget.java:


 import android.app.PendingIntent;
import android.appwidget.AppWidgetManager;
import android.appwidget.AppWidgetProvider;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.graphics.Color;
import android.text.TextUtils;
import android.util.Log;
import android.widget.RemoteViews;

public class TestWidget extends AppWidgetProvider {
 public static final String WIDGET_BTN_ACTION = "widget_btn_action";
 @Override
 public void onReceive(Context context, Intent intent) {
  super.onReceive(context, intent);
  if (intent != null && TextUtils.equals(intent.getAction(), WIDGET_BTN_ACTION)) { //当intent不为空,且action匹配成功时,就接收广播,然后点击事件成功
   Log.i(WIDGET_BTN_ACTION, "is clicked");
   //接下来开始做点击事件里面的内容
   RemoteViews remoteViews = new RemoteViews(context.getPackageName(), R.layout.layout_widget);//注意:需要【重新】构造一个RemoteViews
   remoteViews.setTextViewText(R.id.widget_tv, "be clicked");
   remoteViews.setTextColor(R.id.widget_tv, Color.RED);
   AppWidgetManager appWidgetManager = AppWidgetManager.getInstance(context);// 单例模式
   ComponentName componentName = new ComponentName(context, TestWidget.class);
   appWidgetManager.updateAppWidget(componentName, remoteViews);//setText之后,记得更新一下
  }
 }
 @Override
 public void onUpdate(Context context, AppWidgetManager appWidgetManager, int[] appWidgetIds) {
  super.onUpdate(context, appWidgetManager, appWidgetIds);
  RemoteViews remoteViews = new RemoteViews(context.getPackageName(), R.layout.layout_widget);//需要构造一个RemoteViews
  Intent intent = new Intent();
  intent.setClass(context, TestWidget.class); //通过intent把广播发给TestWidget本身,TestWidget接受到广播之后,会调用。。进而刷新借鉴  // 。
  intent.setAction(WIDGET_BTN_ACTION);
  PendingIntent pendingIntent = PendingIntent.getBroadcast(context, 0, intent, 0);
  remoteViews.setOnClickPendingIntent(R.id.widget_btn, pendingIntent);//控件btn_widget的点击事件:点击按钮时,会发一个带action的广播。
  appWidgetManager.updateAppWidget(appWidgetIds, remoteViews); //点击完了之后,记得更新一下。
 }
} 

运行之后,把widget拖到桌面上,效果如下:

 

点击按钮后,效果如下:

 

工程文件:(Android Studio 2.1) 

当然,widget还有很多其他的用途。比如:
 •与Service进行通信
 •widget控件的交互方法。
 •如何做一个桌面播放器Widget

您可能感兴趣的文章:AndroidUI组件SlidingTabLayout实现ViewPager页滑动效果Android UI组件Spinner下拉列表详解Android UI组件LinearLayout线性布局详解Android UI设计系列之自定义DrawView组件实现数字签名效果(5)Android布局技巧之创建可重用的UI组件Android UI新组件学习和使用


--结束END--

本文标题: Android UI组件AppWidget控件入门详解

本文链接: https://www.lsjlt.com/news/23950.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

下载Word文档到电脑,方便收藏和打印~

下载Word文档
猜你喜欢
  • Android开发之自定义UI组件详解
    Android开发自定义UI组件实现红色小球跟随手指移动 要写实现自定义UI组件,要创建一个BallView类,继承View类,在BallView类中创建画笔,然后重写OnDraw(...
    99+
    2024-04-02
  • Android实现Neumorphism UI控件
    目录效果图第三方库支持代码示例引入第三方库黑暗模式布局明亮风格文档说明(案例)总结效果图 第三方库支持 Github:https://github.com/fornewid/n...
    99+
    2024-04-02
  • Android入门篇自定义Button控件
    在Android中,可以通过继承Button类来创建自定义Button控件。下面是一个简单的例子,演示如何创建一个带有圆角背景和自定...
    99+
    2023-09-22
    Android
  • Android入门教程之组件Activity的生命周期详解
    目录返回栈Activity 状态1. 运行状态2. 暂停状态3. 停止状态4. 销毁状态Activity 的生存期onCreate()onStart()onResume()onPau...
    99+
    2024-04-02
  • WinForm入门与基本控件使用详解
    目录一.Winform入门1.WinForm项目结构  2.窗口设计与控件布局 3.窗口事件 4.时间显示器小练习二.WinForm布局开发1...
    99+
    2024-04-02
  • Android如何实现Neumorphism UI控件
    小编给大家分享一下Android如何实现Neumorphism UI控件,相信大部分人都还不怎么了解,因此分享这篇文章给大家参考一下,希望大家阅读完这篇文章后大有收获,下面让我们一起去了解一下吧!效果图第三方库支持Github:h...
    99+
    2023-06-29
  • React受控组件与非受控组件深入讲解
    目录一、非受控组件二、受控组件三、高阶函数(函数柯里化)实现1、定义2、实现四、不用函数柯里化的实现一、非受控组件 表单中输入类DOM的值现用现取 <script type="...
    99+
    2022-12-26
    React受控组件 React非受控组件
  • Android中ContentProvider组件详解
    ContentProvider是Android中的一种组件,用于管理应用程序之间共享的数据。它提供了一种标准化的接口,使得应用程序可...
    99+
    2023-08-25
    android
  • Android入门之onTouchEvent触碰事件的示例详解
    目录简介onTouchEvent应用场景样例说明全代码前端后端后续简介 平时包括之前的例子大量是基于TouchListener如:onClick这种一类的事件。 今天给大家带来的是T...
    99+
    2022-12-08
    Android onTouchEvent触碰事件 Android onTouchEvent Android 触碰事件
  • Android中Intent组件的入门学习心得
    目录什么是 Intent ?Intent 的类型?Intent 的组成显式 Intent 的使用隐式 Intent 的使用总结什么是 Intent ? Intent是Android开...
    99+
    2024-04-02
  • 如何入门Vue 2.0的模块化前端UI 组件库
    这篇文章给大家介绍如何入门Vue 2.0的模块化前端UI 组件库,内容非常详细,感兴趣的小伙伴们可以参考借鉴,希望对大家能有所帮助。AT-UI 是一款基于 Vue.js 2.0 的轻量级、模块化前端 UI ...
    99+
    2024-04-02
  • 如何在Android UI中使用Switch控件
    这期内容当中小编将会给大家带来有关如何在Android UI中使用Switch控件,文章内容丰富且以专业的角度为大家分析和叙述,阅读完这篇文章希望大家可以有所收获。首先,在布局中添加上Switch控件:<Switch &nb...
    99+
    2023-05-30
    switch
  • Android组件化、插件化详细讲解
    目录什么是组件化(通俗易懂)反射的写法反射的⽬的关于DEX:插件化原理:动态加载问题⼀:未注册的组件(例如Activity)不能打开问题⼆:资源⽂件⽆法加载插件化有什么用?什么是组件...
    99+
    2024-04-02
  • Message组件实现发财UI 示例详解
    目录引言支持的功能使用方法实现过程如何实现不同类型的切换?如何实现Message的弹出和消失?如何实现往下排列而非堆叠?如何实现添加和移除.message-active类?如何将隐藏...
    99+
    2022-11-13
    Message组件发财UI Message组件
  • 如何在Android中自定义UI组件
    如何在Android中自定义UI组件?相信很多没有经验的人对此束手无策,为此本文总结了问题出现的原因和解决方法,通过这篇文章希望你能解决这个问题。Android开发自定义UI组件实现红色小球跟随手指移动要写实现自定义UI组件,要创建一个Ba...
    99+
    2023-06-15
  • Android控件AppWidgetProvider使用方法详解
    介绍AppWidgetProvider是Android中提供的用于实现桌面小工具的类,其本质是一个广播,即BroadcastReceiver,在实际的使用中,把AppWidgetProvider当成一个BroadcastReceiver即可...
    99+
    2023-05-30
    android appwidgetprovider pp
  • Android组件之服务的详解
    目录一、服务的概念二、Android的多线程编程2.1 线程的基本用法2.2 在子线程中更新UI更新方式一更新方式二2.3 解析异步消息处理机制2.4 使用AsyncTask三、服务...
    99+
    2024-04-02
  • Android最常用的控件ListView(详解)
    ListView是Android开发中最常用的控件之一,用于显示一个可滚动的列表,其中每个列表项都是可以点击的。ListView的使...
    99+
    2023-09-09
    Android
  • React中immutable的UI组件渲染性能详解
    目录引言UI组件渲染性能方案一:shallow compare方案二:直接对前后的对象进行deepCompare总结:引言 react 一直遵循UI = fn(state) 的原则,...
    99+
    2023-05-16
    React immutable UI组件渲染 React UI组件渲染
  • Android四大组件之BroadcastReceiver详解
    BroadcastReceiver是Android四大组件之一,用于接收和处理系统广播或者应用内发送的广播。广播是一种跨组件、跨应用的通信机制,可以用于在应用内部或者应用之间传递消息或者事件。BroadcastReceiver的主要作用...
    99+
    2023-08-09
    Android
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作