生活随笔
收集整理的這篇文章主要介紹了
android 动态壁纸
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
引用:http://www.ophonesdn.com/article/show/278
http://developer.android.com/resources/samples/CubeLiveWallpaper/src/com/example/android/livecubes/cube1/CubeWallpaper1.html
標簽 :?動態壁紙?Live?Wallpapers?時間壁紙?TimeWall
?
隨著三星Oscar的上市,流暢的操作,華麗的界面,OPhone 2.0的不俗表現不禁讓人眼前一亮。作為OPhone 2.0一個新特性,動態壁紙(Live Wallpapers)為用戶帶來了更炫體驗。本文主要通過一個完整的時間壁紙(TimeWall)為大家介紹如何開發 Live Wallpapers。還沒開發環境?趕緊去下載OPhone SDK 2.0吧!
1、 Live Wallpapers是什么? 在oscar上有一個動態壁紙叫“天空草地”,用過一段時間,可以發現,隨著時間的變化,壁紙的天空就會由藍藍青天變成繁星滿天。看看效果: 為什么壁紙還有這么神奇的變化,這中間到底是什么在起作用?其實,一個Live Wallpaper就是一個apk!也就是說,動態壁紙的實質是一個apk在后臺不斷地重繪壁紙,所以我們可以讓小草長高,小鳥飛翔。 來看一下我們TimeWall的AndoridManifest.xml: view plaincopy to clipboardprint?
<?xml?version="1.0"?encoding="utf-8"?>??<manifest?xmlns:android="http://schemas.android.com/apk/res/android"??????package="com.oms.LiveWall"?android:versionCode="1"??????android:versionName="1.0">??????<application?android:icon="@drawable/icon"?android:label="@string/app_name">??????????<service?android:label="@string/app_name"?android:name=".TimeWall"??????????????android:permission="android.permission.BIND_WALLPAPER">??????????????<intent-filter>??????????????????<action?android:name="android.service.wallpaper.WallpaperService"?/>??????????????</intent-filter>??????????????<meta-data?android:name="android.service.wallpaper"??????????????????android:resource="@xml/alive_wall"?/>??????????</service>??????</application>??????<uses-sdk?android:minSdkVersion="7"?/>??</manifest>?? 原來如此簡單,動態壁紙僅僅有一個service就夠了。其中 android:permission="android.permission.BIND_WALLPAPER" 是讓該service有能設置為壁紙的權限,沒有的話該壁紙只能被預覽。 <uses-sdk?android:minSdkVersion="7"?/> 告訴我們,如果你想開發一個live wallpaper,必須是OPhone 2.0或者更高的版本。當然這也需要手機硬件的支持。
2、怎樣實現WallpaperService? WallpaperService與其他的service唯一的不同就是,你必須要增加一個方法onCreateEngine(),它會返回一個WallpaperService.Engine,這個engine才是負責繪制壁紙以及響應與用戶交互事件的核心部件。這個service代碼結構如下: view plaincopy to clipboardprint?
public?class?TimeWall?extends?WallpaperService?{?????????public?Engine?onCreateEngine()?{??????????return?new?TimeEngine();??????}?????????public?class?TimeEngine?extends?Engine?{????????????????}??}?? 類TimeEngine才是處理壁紙的核心類,我們會在類TimeEngine中加上自己的邏輯以完成壁紙的繪制、變化以及銷毀。Engine的生命周期與大多數OPhone應用程序組件,比如activity類似,都是從onCreate()開始,在銷毀時調用onDestory()方法。不同的是WallpaperService會提供一個surface用來繪制壁紙,所以在生命周期中多一個onSurfaceCreated與onSurfaceDestroyed的過程。下面是一個最簡生命周期: 也就是說只要我們實現上面四個方法,一個基本的LiveWallpaper就可以完成了。讓我們逐個看一下這幾個方法的實現。 view plaincopy to clipboardprint?
@Override??public?void?onCreate(SurfaceHolder?surfaceHolder)?{??????super.onCreate(surfaceHolder);??????setTouchEventsEnabled(true);??}????@Override??public?void?onDestroy()?{??????super.onDestroy();??????mHandler.removeMessages(DRAW);??}????@Override??public?void?onSurfaceCreated(SurfaceHolder?holder)?{??????super.onSurfaceCreated(holder);??????mHandler.sendEmptyMessage(DRAW);??}????@Override??public?void?onSurfaceDestroyed(SurfaceHolder?holder)?{??????super.onSurfaceDestroyed(holder);??????mHandler.removeMessages(DRAW);??}?? 在onCreate方法里,我們 setTouchEventsEnabled(
true); 作用是使壁紙能響應touch event,默認是false。TimeWall會在用戶點擊屏幕的時候畫一個十字架,所以我們需要設置其為true。 可以看到我們在這四個方法里面做的事情非常簡單,就是在create時候發一個message,執行畫面的繪制,在destory時remove這個消息。看一下mHandler的代碼: view plaincopy to clipboardprint?
private?Handler?mHandler?=?new?Handler()?{????????public?void?handleMessage(Message?msg)?{????????????switch?(msg.what)?{????????????case?DRAW:????????????????drawWall();????????????????break;????????????}????????}????};?? 方法drawWall(): view plaincopy to clipboardprint?
private?void?drawWall()?{??????????????SurfaceHolder?holder?=?getSurfaceHolder();??????????????Canvas?canvas?=?holder.lockCanvas();??????????????drawTime(canvas);??????????????drawCross(canvas);??????????????holder.unlockCanvasAndPost(canvas);?????????????????mHandler.removeMessages(DRAW);??????????????mHandler.sendEmptyMessageDelayed(DRAW,?50);??????????}?? 從上面可以看出,動態壁紙實際上就是不斷刷新的靜態壁紙,越華麗越流暢,CPU就消耗越大,對于現在的本來電量就不怎么地的智能機來說,耗電也是很可觀的。但是偶爾向朋友們炫一下還是絕對可行的。drawTime()與drawCross()的內容可以由家自己實現,在TimeWall里,它們比較簡單。drawTime()是計算下一處Time String應該移動到的坐標,以及畫出這個String。drawCross()的作用是在用戶觸發onTouchEvent時畫一個十字架。因為TimeWall比較簡單,如果大家自己實現的畫圖比較復雜,可以另外開啟一個線程來刷新UI,否則有可能主線程被阻塞掉。(代碼見附件) 看看TimeWall的效果:
附件代碼:
?
?
view plaincopy to clipboardprint?
package?com.OPhonesdn.timewall;?????import?java.text.SimpleDateFormat;??import?java.util.Date;?????import?android.graphics.Canvas;??import?android.graphics.Color;??import?android.graphics.Paint;??import?android.os.Handler;??import?android.os.Message;??import?android.service.wallpaper.WallpaperService;??import?android.view.MotionEvent;??import?android.view.SurfaceHolder;?????public?class?TimeWall?extends?WallpaperService?{?????????public?Engine?onCreateEngine()?{??????????return?new?TimeEngine();??????}?????????public?class?TimeEngine?extends?Engine?{?????????????private?final?float?STEP_X?=?2f;??????????private?final?float?STEP_Y?=?7f;??????????private?final?float?SCOPE_LEFT?=?10f;??????????private?final?float?SCOPE_RIGHT?=?110f;??????????private?final?float?SCOPE_TOP?=?250f;??????????private?final?float?SCOPE_BOTTOM?=?600f;??????????private?final?float?RADIUS?=?20f;??????????private?final?int?DIRECTION_1?=?1;???????????private?final?int?DIRECTION_2?=?2;???????????private?final?int?DIRECTION_3?=?3;???????????private?final?int?DIRECTION_4?=?4;???????????private?final?int?DRAW?=?1;??????????private?float?mTouchX?=?-1f;??????????private?float?mTouchY?=?-1f;??????????private?float?mLocationX?=?0f;??????????private?float?mLocationY?=?400f;??????????private?int?mDirection?=?1;?????????????private?Paint?mPaint?=?new?Paint();??????????private?Handler?mHandler?=?new?Handler()?{??????????????public?void?handleMessage(Message?msg)?{??????????????????switch?(msg.what)?{??????????????????case?DRAW:??????????????????????drawWall();??????????????????????break;??????????????????}??????????????}??????????};?????????????public?TimeEngine()?{??????????????mPaint.setColor(Color.RED);??????????????mPaint.setAntiAlias(true);??????????????mPaint.setStrokeWidth(4);??????????????mPaint.setStrokeCap(Paint.Cap.BUTT);??????????????mPaint.setStyle(Paint.Style.STROKE);??????????????mPaint.setTextSize(40);??????????}?????????????@Override??????????public?void?onCreate(SurfaceHolder?surfaceHolder)?{??????????????super.onCreate(surfaceHolder);??????????????setTouchEventsEnabled(true);??????????}?????????????@Override??????????public?void?onDestroy()?{??????????????super.onDestroy();??????????????mHandler.removeMessages(DRAW);??????????}?????????????@Override??????????public?void?onSurfaceCreated(SurfaceHolder?holder)?{??????????????super.onSurfaceCreated(holder);??????????????mHandler.sendEmptyMessage(DRAW);??????????}?????????????@Override??????????public?void?onSurfaceDestroyed(SurfaceHolder?holder)?{??????????????super.onSurfaceDestroyed(holder);??????????????mHandler.removeMessages(DRAW);??????????}?????????????@Override??????????public?void?onTouchEvent(MotionEvent?event)?{??????????????if?(event.getAction()?==?MotionEvent.ACTION_MOVE??????????????????????||?event.getAction()?==?MotionEvent.ACTION_DOWN)?{??????????????????mTouchX?=?event.getX();??????????????????mTouchY?=?event.getY();??????????????}?else?{??????????????????mTouchX?=?-1;??????????????????mTouchY?=?-1;??????????????}??????????????super.onTouchEvent(event);??????????}?????????????private?void?drawWall()?{??????????????SurfaceHolder?holder?=?getSurfaceHolder();??????????????Canvas?canvas?=?holder.lockCanvas();??????????????drawTime(canvas);??????????????drawCross(canvas);??????????????holder.unlockCanvasAndPost(canvas);?????????????????mHandler.removeMessages(DRAW);??????????????mHandler.sendEmptyMessageDelayed(DRAW,?50);??????????}?????????????private?void?drawTime(Canvas?c)?{??????????????Date?date?=?new?Date(System.currentTimeMillis());??????????????SimpleDateFormat?sdf?=?new?SimpleDateFormat("yyyy-MM-dd?HH:mm:ss");??????????????String?strDate?=?sdf.format(date);??????????????c.save();??????????????c.drawColor(0xff000000);??????????????c.drawText(strDate,?mLocationX,?mLocationY,?mPaint);??????????????switch?(mDirection)?{??????????????case?DIRECTION_1:??????????????????mLocationX?=?mLocationX?+?STEP_X;??????????????????mLocationY?=?mLocationY?-?STEP_Y;??????????????????if?(mLocationY?<=?SCOPE_TOP)?{??????????????????????mDirection?=?DIRECTION_2;??????????????????}??????????????????break;??????????????case?DIRECTION_2:??????????????????mLocationX?=?mLocationX?+?STEP_X;??????????????????mLocationY?=?mLocationY?+?STEP_Y;??????????????????if?(mLocationX?>=?SCOPE_RIGHT)?{??????????????????????mDirection?=?DIRECTION_3;??????????????????}??????????????????break;??????????????case?DIRECTION_3:??????????????????mLocationX?=?mLocationX?-?STEP_X;??????????????????mLocationY?=?mLocationY?+?STEP_Y;??????????????????if?(mLocationY?>=?SCOPE_BOTTOM)?{??????????????????????mDirection?=?DIRECTION_4;??????????????????}??????????????????break;??????????????case?DIRECTION_4:??????????????????mLocationX?=?mLocationX?-?STEP_X;??????????????????mLocationY?=?mLocationY?-?STEP_Y;??????????????????if?(mLocationX?<=?SCOPE_LEFT)?{??????????????????????mDirection?=?DIRECTION_1;??????????????????}??????????????????break;??????????????}??????????????c.restore();??????????}?????????????private?void?drawCross(Canvas?c)?{??????????????if?(mTouchX?>=?0?&&?mTouchY?>=?0)?{??????????????????c.drawLine(mTouchX?-?RADIUS,?mTouchY,?mTouchX?+?RADIUS,??????????????????????????mTouchY,?mPaint);??????????????????c.drawLine(mTouchX,?mTouchY?-?RADIUS,?mTouchX,??????????????????????????mTouchY?+?RADIUS,?mPaint);??????????????}??????????}??????}??}????? ?
總結
以上是生活随笔為你收集整理的android 动态壁纸的全部內容,希望文章能夠幫你解決所遇到的問題。
如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。