亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb

首頁 > 學院 > 開發設計 > 正文

widget開發之helloworld(基礎篇)

2019-11-09 14:36:44
字體:
來源:轉載
供稿:網友

widget開發之helloworld

由于工作需求,上周剛開始接觸widget。經過一周的開發和了解,對widget的一些基礎點做一下整理。

什么是widget:

widget也叫小部件,在launcher中點擊menu鍵,會出現小部件選項,進入后會顯示所以手機上已經安裝的widget。長按或者單擊(launcher決定)后,可添加到手機桌面上。

從功能上,widget功能比較簡單,專注于某一件事情。比如時鐘、天氣、音樂等等。

widget也可以和響應的普通應用聯系起來,點擊之后進入應用界面。這時候widget更像是一個應用的快捷入口。

下面來具體介紹一下widget的開發步驟:

1、注冊widget處理器

在manifest中,注冊一個receiver,用來接收系統發來的widget的廣播。

<!-- receiver的 android:name指向的是widget的請求處理器或者說請求接收者 -->		<receiver			android:label="@string/app_name"			android:name="com.cooee.phenix.widget.WidgetPRovider">			<intent-filter>			    <!-- 點擊事件對應的廣播字符串 -->                <action android:name="com.cooee.phenix.widget.click.clock_layout"/>                <action android:name="com.cooee.phenix.widget.click.weather_layout"/>                <action android:name="com.cooee.phenix.widget.click.date_layout"/>				<!-- widget默認的事件action -->				<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />			</intent-filter>			<!-- widget元數據,name是寫死的,resource指的是widget的配置文件 -->			<meta-data				android:name="android.appwidget.provider"				android:resource="@layout/widgetinfo" />		</receiver>

2、WidgetProvider處理器

WidgetProvider是我們自己創建的類,繼承AppWidgetProvider,AppWidgetProvider extends BroadcastReceiver,用來處理widget的各種請求。

widget中的事件都是通過廣播進行傳遞的:

widget的添加、刪除、更新等操作,都會收到相應的廣播。在AppWidgetProvider的public void onReceive(方法中可以看到

AppWidgetProvider類中:

public void onUpdate:widget更新時回調

public void onDeleted:一個widget從桌面刪除時回調

public void onEnabled:第一個widget被放到桌面時回調

public void onDisabled:最后一個widget從桌面刪除時回調

public void onReceive:用來接收廣播,處理widget的消息。

如果我們需要在這些時刻做一下自己的邏輯處理,WidgetProvider可以重寫這幾個方法。

3、widgetinfo和widget布局

widget的界面和widget寬高等信息在哪里定義呢?

在上面代碼的注釋中可以看到,widgetinfo是關聯在receiver里的mete-data中。(把這部分代碼單獨貼出來方便大家看)

<!-- widget元數據,name是寫死的,resource指的是widget的配置文件 -->			<meta-data				android:name="android.appwidget.provider"				android:resource="@layout/widgetinfo" />那么,widgetinfo中究竟定義了什么東西,我們來具體看一下這個xml文件:

<?xml version="1.0" encoding="utf-8"?><!-- appwidget-provider Widget的配置文件 --><!-- android:minWidth 最小寬度 --><!-- android:minHeight 最小高度 --><!-- android:updatePeriodMillis 組件更新頻率(毫秒) --><!-- android:initialLayout 用來關聯widget的布局文件 --><!-- android:configure Widget設置用Activity ??? --><appwidget-provider	android:layout_width="wrap_content"	android:layout_height="wrap_content"	xmlns:android="http://schemas.android.com/apk/res/android"	android:initialLayout="@layout/widget_layout"	android:minWidth="@dimen/widget_width"	android:minHeight="@dimen/widget_height"	android:updatePeriodMillis="86400000" />關于android:configure屬性,這次并沒有用到,具體我也不懂這是干嘛用的。在這里,我最關心的是布局文件,畢竟,它是要顯示的東西。

由于布局文件比較長這里就不貼代碼了。(布局文件就像我們app里的一樣布局就ok啦)

4、widget點擊事件(action的意義)

說道點擊事件,我們得先來說一下widget中的view。

remoteview:

上面講到widget關聯布局的方式,和我們寫app有點不同。那么 我們想對顯示的布局做一些動態的改變(改變文字或者背景之類),該怎么辦呢?

按照寫app的思考方式,我們需要獲取到一個view,它里面填充的整個布局,然后最好有個findviewbyid獲取到布局里每一個控件,然后,嘎嘎嘎,我們就能為所欲為了。

設置點擊監聽、改變文字、設置圖片背景神馬的還不是灑灑水???!??!

想法,是很美好的。但是百度了一番之后我才發現并沒有想象中辣么簡單。。。。。。

下面來介紹widget如何獲取我們想要的view:

rv = new RemoteViews( mContext.getPackageName() , R.layout.widget_layout );得到view之后,悲劇的事情發生了,它居然沒有findviewbyid方法?。。。。∫簿褪钦f我得不到布局里每一個具體的view

一番網上搜索之后,設置點擊事件監聽和改變文字之類的找到了對應的方法,不過,動畫好像就與我們絕緣了。。。

點擊事件:

//日期Intent intentDateClick = new Intent( WidgetProvider.CLICK_DATE_LAYOUT );//intent的action用來區分具體點擊的是哪一個viewPendingIntent pendingDateIntent = PendingIntent.getBroadcast( mContext , 0 , intentDateClick , 0 );rv.setOnClickPendingIntent( R.id.date_textview , pendingDateIntent );//設置點擊事件監聽//時鐘if( showClockVeiw ){	Intent intentClockClick = new Intent( WidgetProvider.CLICK_CLOCK_LAYOUT );	PendingIntent pendingClockIntent = PendingIntent.getBroadcast( mContext , 0 , intentClockClick , 0 );	rv.setOnClickPendingIntent( R.id.clock_layout , pendingClockIntent );}visibility = showClockVeiw ? View.VISIBLE : View.GONE;rv.setViewVisibility( R.id.clock_layout , visibility );//天氣if( showWeatherVeiw ){	Intent intentWeatherClick = new Intent( WidgetProvider.CLICK_WEATHER_LAYOUT );	PendingIntent pendingWeatherIntent = PendingIntent.getBroadcast( mContext , 0 , intentWeatherClick , 0 );	rv.setOnClickPendingIntent( R.id.city_textview , pendingWeatherIntent );	rv.setOnClickPendingIntent( R.id.weather_city , pendingWeatherIntent );	rv.setOnClickPendingIntent( R.id.temperature_current , pendingWeatherIntent );	rv.setOnClickPendingIntent( R.id.temperature_range , pendingWeatherIntent );}visibility = showWeatherVeiw ? View.VISIBLE : View.GONE;setWeatherVisibility( visibility );上面代碼可以看到。我們的關鍵點在于:

rv.setOnClickPendingIntent( R.id.date_textview , pendingDateIntent );就是這個方法設置了點擊事件的監聽。第一個參數是rv這個view中,布局里面的某一個view的id,第二個參數是PendingIntent是具體的廣播意圖。里面包含了如果點擊這個view,WidgetProvider將受到的廣播。

widget中,點擊事件是通過廣播傳遞的。intent的action就是我們在manifest里看到的三個action。所以我們用三個action來區分三種view的點擊事件。

下面貼出來三個action的變量值,方便大家邏輯跟蹤。這三個值都是WidgetProvider中的:

public static final String CLICK_CLOCK_LAYOUT = "com.cooee.phenix.widget.click.clock_layout";public static final String CLICK_WEATHER_LAYOUT = "com.cooee.phenix.widget.click.weather_layout";public static final String CLICK_DATE_LAYOUT = "com.cooee.phenix.widget.click.date_layout";	

通過點擊事件的啟發,我發現雖然我們不能具體拿到布局里的每一個view,但是我們可以通過remoteview來改變它。

比如這句:rv.setViewVisibility( R.id.clock_layout , visibility );//設置view是否可見,我似乎找到了某種規律。至此,我們已經設置好了widget中view的點擊事件。

當我們點擊view時,WidgetProvider就會收到廣播,我們通過區分intent的action來處理不同view的點擊:

public void onClick(		String action ){	//點擊時鐘布局	if( action.equals( WidgetProvider.CLICK_CLOCK_LAYOUT ) )	{		ClockCalendarManager.getInstance( mContext ).onClickClock();	}	//點擊日期	else if( action.equals( WidgetProvider.CLICK_DATE_LAYOUT ) )	{		ClockCalendarManager.getInstance( mContext ).onclickDate();	}	//點擊天氣	else if( action.equals( WidgetProvider.CLICK_WEATHER_LAYOUT ) )	{		WeatherManager.getInstance( mContext ).onClick();	}	else	{		Log.d( TAG , "其他" );	}}

5、widget修改后更新顯示

以上我們講了widget的manifest注冊、widgetinfo、widget布局、如何獲取view、如何設置點擊事件、如何響應點擊事件。

下面我們來看看如何更新一個view顯示的內容、如何更新我們的widget。

以我們的時鐘為例,當我們需要更新view時:

TwinkleClockwidgetManager instance = TwinkleClockwidgetManager.getInstance( mContext );RemoteViews rv = instance.getRv();if( instance.showClockVeiw ){	rv.setImageViewResource( R.id.clock_minute_tens , timeNumbers[mCurrentMinute / 10] );	rv.setImageViewResource( R.id.clock_minute_ones , timeNumbers[mCurrentMinute % 10] );}哈哈,果然跟想的一樣,都是通過remoteview來設置,第一個參數是要改變的view的id,第二個是要設置的值。

改變完view之后,我們需要更新一下widget,就能改變桌面上widget的顯示了:

//更新插件AppWidgetManager appWidgetManger = AppWidgetManager.getInstance( mContext );//第一步,通過context拿到appwidgetManagerint[] appIds = appWidgetManger.getAppWidgetIds( new ComponentName( mContext , WidgetProvider.class ) );//第二步,通過widgetManager和包類名拿到widgetIdappWidgetManger.updateAppWidget( appIds , rv );//第三步,更新widget的顯示

總結:

以上就是這一周多時間對widget的了解,貼一張widget的圖展示小成果:嘿嘿嘿

其中還有些坑無法解惑:

1、widget如何做動畫?(好像在哪看到過別的桌面的widget,日歷時鐘,過一天,日歷更新時是帶一個旋轉的動畫的)

2、widget如何可拉伸?(launcher上顯示widget時,有的widget長按松手之后可以改變widget在桌面上顯示的大小,目前還不確定這部分是桌面做?還是需要widget這邊協助。。。)

以上僅代表個人觀點,如有理解不到位的地方,還請指正。歡迎留言,歡迎私信。


發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb
日韩在线视频播放| www.xxxx欧美| 欧美日韩999| 欧美在线视频一区| 欧洲亚洲在线视频| 亚洲国产女人aaa毛片在线| 午夜免费日韩视频| 亚洲色图第三页| 91天堂在线观看| 亚洲人成人99网站| 国产精品私拍pans大尺度在线| 欧美亚洲第一区| 亚洲国产一区二区三区在线观看| 亚洲精品少妇网址| 国产美女精品免费电影| 欧洲成人在线观看| 一本色道久久88精品综合| 午夜精品久久久久久久白皮肤| 91视频国产精品| 成人信息集中地欧美| 中文字幕精品国产| 亚洲香蕉成人av网站在线观看| 中文字幕不卡在线视频极品| 国产精品一区二区三区毛片淫片| 亚洲天天在线日亚洲洲精| 亚洲国产日韩欧美在线99| 欧美另类老女人| 成人国产精品av| 国产成人在线播放| 欧美激情久久久| 国产精品视频白浆免费视频| 2019中文字幕全在线观看| 日韩av中文字幕在线| 久久影院模特热| 欧美又大粗又爽又黄大片视频| 久久久天堂国产精品女人| 国产精品一久久香蕉国产线看观看| 日韩毛片在线看| 日韩av在线直播| 亚洲图片欧美午夜| 日韩精品在线电影| wwwwwwww亚洲| 色无极影院亚洲| 4438全国亚洲精品在线观看视频| 欧美激情久久久久久| 91深夜福利视频| 欧美日韩久久久久| 欧日韩在线观看| 精品国产91久久久| 亚洲人成在线播放| 亚洲精品久久久久中文字幕二区| 亚洲国产成人精品久久| 日韩激情av在线免费观看| 久久久免费观看| 日韩大片免费观看视频播放| 国产999精品久久久| 2021久久精品国产99国产精品| 亚洲精品99久久久久中文字幕| 国产欧美一区二区三区久久| 中文.日本.精品| 亚洲成人精品av| 亚洲国产精品成人一区二区| 久久久久久免费精品| 国产精品jizz在线观看麻豆| 中文字幕亚洲欧美| 亚洲女人初尝黑人巨大| 伊人久久久久久久久久久久久| 久久高清视频免费| 成人免费大片黄在线播放| 亚洲视频在线观看免费| 成人午夜在线观看| 午夜精品久久久久久99热软件| 97视频在线观看成人| 日韩av一区在线| 亚洲一区二区三区乱码aⅴ| 91免费精品视频| 91热福利电影| 中文字幕亚洲欧美日韩在线不卡| 91av免费观看91av精品在线| 久久综合国产精品台湾中文娱乐网| 精品亚洲一区二区三区四区五区| 久久影视电视剧免费网站| 亚洲成年网站在线观看| 国产精品美女久久| 九九热99久久久国产盗摄| 91精品久久久久久久久不口人| 国产在线视频2019最新视频| 亚洲美女性视频| 亚洲国产成人精品一区二区| 国产精品丝袜一区二区三区| 国产精品久久久久久久久影视| 国产成人91久久精品| 欧美日产国产成人免费图片| 亚洲性av在线| 日韩美女免费观看| 成人欧美一区二区三区黑人孕妇| 欧美日韩国产中文字幕| 欧美电影在线观看完整版| 欧美怡春院一区二区三区| 2020国产精品视频| 精品亚洲aⅴ在线观看| 国产精品中文字幕久久久| 久久国产精品偷| 亚洲精品国偷自产在线99热| 成人情趣片在线观看免费| 亚洲xxxxx电影| 欧美日韩成人在线视频| 亚洲精品成人久久电影| 午夜精品一区二区三区在线| 亚洲欧美激情精品一区二区| 成人免费网站在线看| 久久精品免费播放| 日韩欧美999| 日韩在线视频网| 欧美刺激性大交免费视频| 欧美在线欧美在线| 欧美激情免费观看| 韩剧1988免费观看全集| 欧洲成人在线视频| 日韩免费视频在线观看| 亚洲肉体裸体xxxx137| 国产午夜精品理论片a级探花| 亚洲男人av在线| 日韩欧美第一页| 亚洲天堂开心观看| 日韩精品视频在线播放| 美女扒开尿口让男人操亚洲视频网站| 日韩精品一二三四区| 91精品成人久久| 亚洲欧美色婷婷| 91av国产在线| 亲子乱一区二区三区电影| 亚洲综合社区网| 色噜噜狠狠色综合网图区| 久久天天躁夜夜躁狠狠躁2022| 亚洲自拍av在线| 一本色道久久88亚洲综合88| 国产成人精品免费视频| 国产在线视频不卡| 亚洲欧美在线一区二区| 91精品国产乱码久久久久久久久| 亚洲精品国精品久久99热| 日本精品免费观看| 4444欧美成人kkkk| 国产国产精品人在线视| 亚洲淫片在线视频| 正在播放欧美视频| 欧美三级欧美成人高清www| 国产成人欧美在线观看| 日韩精品在线观看网站| 68精品国产免费久久久久久婷婷| 国产伦精品一区二区三区精品视频| 亚洲白虎美女被爆操| 一区二区三区高清国产| 久久久精品2019中文字幕神马| 欧美一区深夜视频| 国产精品第一页在线| 欧美亚洲视频一区二区| 日韩av理论片| 人人澡人人澡人人看欧美| 国产精品久久网| 精品久久久久久| 日韩中文字在线| 日韩一级裸体免费视频|