Live Wallpaper动态壁纸开发

作者: Android开发网原创 时间: 2011-04-12

对于Android 2.1来说Live Wallpapers动态壁纸的加入为Android桌面加入了更好的动态效果。如何开发一个Android动态桌面呢? 下面Android123给大家一个详细的步骤创建属于你自己的Live Wallpaper吧。

1. 首先我使用Eclipse创建一个标准的Android工程这里package name我们使用cn.com.android123.cwj,然后进入工程的/res/文件夹,删除layout这个文件夹,当然里面的main.xml也会被删除的,对于Live Wallpaper来说传统的布局文件是不需要的。

2. 类似AppWidget一样,我们可以加入动态壁纸的设置界面,我们在/res/文件夹中新建一个名为xml的文件夹,新建一个utf8编码的xml文件,名为livewallpaper.xml,内容为

<?xml version="1.0" encoding="utf-8"?><wallpaper xmlns:android="http://schemas.android.com/apk/res/android"android:settingsActivity="cn.com.android123.cwj.LiveWallpaperSettings"android:thumbnail="@drawable/icon"/>

这里我们可以看到上面的节点名为wallpaper,而设置的界面为 cn.com.android123.cwj.LiveWallpaperSettings  这个Activity,而在添加动态壁纸时显示图标为/res/drawable/icon 这个文件,同时我们再创建一个xml文件用于LiveWallpaperSettings这个Activity的布局,我们起名为livewallpaper_settings.xml内容为

  <?xml version="1.0" encoding="utf-8"?>
<PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android"android:title="@string/livewallpaper_settings"android:key="livewallpaper_settings"><ListPreferenceandroid:key="livewallpaper_testpattern"android:title="标题"android:summary="简单描述"android:entries="@array/livewallpaper_testpattern_names"android:entryValues="@array/livewallpaper_testpattern_prefix"/><CheckBoxPreference android:key="livewallpaper_movement"android:summary="动态描述"android:title="动态标题"android:summaryOn="动态测试"android:summaryOff="静止测试"/>
</PreferenceScreen>

3. 创建一个名为LiveWallpaper的类作为动态壁纸的主类,从WallpaperService父类继承,这里我们可以像写标准Android服务那样开发,代码为

public class LiveWallpaper extends WallpaperService {public static final String SHARED_PREFS_NAME = "livewallpapersettings";@Overridepublic void onCreate() {super.onCreate();}@Overridepublic void onDestroy() {super.onDestroy();}@Overridepublic Engine onCreateEngine() {return new TestPatternEngine();}class TestPatternEngine extends Engine implementsSharedPreferences.OnSharedPreferenceChangeListener {private final Handler mHandler = new Handler();private float mTouchX = -1;private float mTouchY = -1;private final Paint mPaint = new Paint();private final Runnable mDrawPattern = new Runnable() {public void run() {drawFrame();}};private boolean mVisible;private SharedPreferences mPreferences;private Rect mRectFrame;private Rect[] mColorRectangles;private int[] rectColor;private int mRectCount;// privateprivate Rect mGradientRect;GradientDrawable mGradient;private boolean mHorizontal = false;private int mFrameCounter = 0;private boolean mMotion = true;private String mShape = "smpte";TestPatternEngine() {final Paint paint = mPaint;paint.setColor(0xffffffff);paint.setAntiAlias(true);paint.setStrokeWidth(2);paint.setStrokeCap(Paint.Cap.ROUND);paint.setStyle(Paint.Style.STROKE);mPreferences = LiveWallpaper.this.getSharedPreferences(SHARED_PREFS_NAME, 0);mPreferences.registerOnSharedPreferenceChangeListener(this);onSharedPreferenceChanged(mPreferences, null);}public void onSharedPreferenceChanged(SharedPreferences prefs,String key) {mShape = prefs.getString("livewallpaper_testpattern", "smpte");mMotion = prefs.getBoolean("livewallpaper_movement", true);readColors();}private void readColors() {int pid = getResources().getIdentifier(mShape + "colors", "array",getPackageName());rectColor = getResources().getIntArray(pid);mRectCount = rectColor.length;mColorRectangles = new Rect[mRectCount];System.out.println("mRectCount " + mRectCount);initFrameParams();}@Overridepublic void onCreate(SurfaceHolder surfaceHolder) {super.onCreate(surfaceHolder);setTouchEventsEnabled(true);}@Overridepublic void onDestroy() {super.onDestroy();mHandler.removeCallbacks(mDrawPattern);}@Overridepublic void onVisibilityChanged(boolean visible) {mVisible = visible;if (visible) {drawFrame();} else {mHandler.removeCallbacks(mDrawPattern);}}@Overridepublic void onSurfaceChanged(SurfaceHolder holder, int format,int width, int height) {super.onSurfaceChanged(holder, format, width, height);initFrameParams();drawFrame();}@Overridepublic void onSurfaceCreated(SurfaceHolder holder) {super.onSurfaceCreated(holder);}@Overridepublic void onSurfaceDestroyed(SurfaceHolder holder) {super.onSurfaceDestroyed(holder);mVisible = false;mHandler.removeCallbacks(mDrawPattern);}@Overridepublic void onOffsetsChanged(float xOffset, float yOffset, float xStep,float yStep, int xPixels, int yPixels) {drawFrame();}@Overridepublic void onTouchEvent(MotionEvent event) {if (event.getAction() == MotionEvent.ACTION_MOVE) {mTouchX = event.getX();mTouchY = event.getY();} else {mTouchX = -1;mTouchY = -1;}super.onTouchEvent(event);}void drawFrame() {final SurfaceHolder holder = getSurfaceHolder();Canvas c = null;try {c = holder.lockCanvas();if (c != null) {// draw somethingdrawPattern(c);drawTouchPoint(c);}} finally {if (c != null)holder.unlockCanvasAndPost(c);}mHandler.removeCallbacks(mDrawPattern);if (mVisible) {mHandler.postDelayed(mDrawPattern, 1000 / 25);}}void drawPattern(Canvas c) {c.save();c.drawColor(0xff000000);Paint paint = new Paint();if (mMotion) {mFrameCounter++;if (mHorizontal) {int right;int left;if (mFrameCounter > mRectFrame.right)mFrameCounter = 0;for (int i = 0; i < mRectCount; i++) {paint.setColor(rectColor[i]);right = mColorRectangles[i].right + mFrameCounter;left = mColorRectangles[i].left + mFrameCounter;if (right > mRectFrame.right) {c.drawRect(left - mRectFrame.right,mColorRectangles[i].top, right- mRectFrame.right,mColorRectangles[i].bottom, paint);}if (left < mRectFrame.right) {c.drawRect(left, mColorRectangles[i].top, right,mColorRectangles[i].bottom, paint);}}if (mShape.compareToIgnoreCase("smpte") == 0) {right = mGradientRect.right + mFrameCounter;left = mGradientRect.left + mFrameCounter;if (right > mRectFrame.right) {mGradient.setBounds(left - mRectFrame.right,mGradientRect.top,right - mRectFrame.right,mGradientRect.bottom);mGradient.draw(c);}if (left < mRectFrame.right) {mGradient.setBounds(left, mGradientRect.top, right,mGradientRect.bottom);mGradient.draw(c);}}} else {int top;int bottom;if (mFrameCounter > mRectFrame.bottom)mFrameCounter = 0;for (int i = 0; i < mRectCount; i++) {paint.setColor(rectColor[i]);top = mColorRectangles[i].top + mFrameCounter;bottom = mColorRectangles[i].bottom + mFrameCounter;if (bottom > mRectFrame.bottom) {c.drawRect(mColorRectangles[i].left, top- mRectFrame.bottom,mColorRectangles[i].right, bottom- mRectFrame.bottom, paint);}if (top < mRectFrame.bottom) {c.drawRect(mColorRectangles[i].left, top,mColorRectangles[i].right, bottom, paint);}}if (mShape.compareToIgnoreCase("smpte") == 0) {top = mGradientRect.top + mFrameCounter;bottom = mGradientRect.bottom + mFrameCounter;if (bottom > mRectFrame.bottom) {mGradient.setBounds(mGradientRect.left, top- mRectFrame.bottom, mGradientRect.right,bottom - mRectFrame.bottom);mGradient.draw(c);}if (top < mRectFrame.bottom) {mGradient.setBounds(mGradientRect.left, top,mGradientRect.right, bottom);mGradient.draw(c);}}}} else {for (int i = 0; i < mRectCount; i++) {paint.setColor(rectColor[i]);c.drawRect(mColorRectangles[i], paint);}if (mShape.compareToIgnoreCase("smpte") == 0) {mGradient.setBounds(mGradientRect);mGradient.draw(c);}}c.restore();}void drawTouchPoint(Canvas c) {if (mTouchX >= 0 && mTouchY >= 0) {c.drawCircle(mTouchX, mTouchY, 80, mPaint);}}void initFrameParams() {DisplayMetrics metrics = new DisplayMetrics();Display display = ((WindowManager) getSystemService(WINDOW_SERVICE)).getDefaultDisplay();display.getMetrics(metrics);mRectFrame = new Rect(0, 0, metrics.widthPixels,metrics.heightPixels);int rotation = display.getOrientation();if (rotation == Surface.ROTATION_0|| rotation == Surface.ROTATION_180)mHorizontal = false;elsemHorizontal = true;System.out.println("mHorizontal " + mHorizontal);System.out.println("mShape " + mShape);if (mShape.compareToIgnoreCase("smpte") == 0) {System.out.println("mShape == smpte");CreateSmpte();} else if (mShape.compareToIgnoreCase("bars") == 0) {System.out.println("mShape == bars");CreateBars();} else {System.out.println("mShape == ebu");CreateEbu();}}private void CreateSmpte() {if (mHorizontal) {int topHeight = mRectFrame.bottom * 7 / 12;int bottomHeight = mRectFrame.bottom * 3 / 4;int wideColumnWidth = mRectFrame.right / 8;int narrowColumnWidth = mRectFrame.right * 3 / 28;mColorRectangles[0] = new Rect(0, 0, wideColumnWidth, topHeight);for (int i = 1; i < 8; i++) {mColorRectangles[i] = new Rect(mColorRectangles[i - 1].right, 0,mColorRectangles[i - 1].right + narrowColumnWidth,topHeight);}mColorRectangles[8] = new Rect(mColorRectangles[7].right, 0,mRectFrame.right, topHeight);for (int i = 0; i < 2; i++) {int middleTop = mRectFrame.bottom * (7 + i) / 12;int middleBottom = mRectFrame.bottom * (8 + i) / 12;mColorRectangles[i + 9] = new Rect(0, middleTop,wideColumnWidth, middleBottom);mColorRectangles[i + 11] = new Rect(wideColumnWidth,middleTop, narrowColumnWidth + wideColumnWidth,middleBottom);mColorRectangles[i + 13] = new Rect(narrowColumnWidth * 7+ wideColumnWidth, middleTop, mRectFrame.right,middleBottom);}mColorRectangles[15] = new Rect(narrowColumnWidth+ wideColumnWidth, topHeight, narrowColumnWidth * 7+ wideColumnWidth, mRectFrame.bottom * 8 / 12);mGradientRect = new Rect(mColorRectangles[15].left,mColorRectangles[15].bottom,mColorRectangles[15].right, mRectFrame.bottom * 9 / 12);mGradient = new GradientDrawable(Orientation.LEFT_RIGHT,new int[] { 0xff050505, 0xfffdfdfd });mGradient.setBounds(mGradientRect);mColorRectangles[16] = new Rect(0, bottomHeight,wideColumnWidth, mRectFrame.right);mColorRectangles[17] = new Rect(mColorRectangles[16].right,bottomHeight, mRectFrame.right * 9 / 56+ mColorRectangles[16].right, mRectFrame.bottom);mColorRectangles[18] = new Rect(mColorRectangles[17].right,bottomHeight, mRectFrame.right * 3 / 14+ mColorRectangles[17].right, mRectFrame.bottom);mColorRectangles[19] = new Rect(mColorRectangles[18].right,bottomHeight, mRectFrame.right * 45 / 448+ mColorRectangles[18].right, mRectFrame.bottom);for (int i = 20; i < 25; i++) {mColorRectangles[i] = new Rect(mColorRectangles[i - 1].right, bottomHeight,mRectFrame.right * 15 / 448+ mColorRectangles[i - 1].right,mRectFrame.right);}mColorRectangles[25] = new Rect(mColorRectangles[24].right,bottomHeight, narrowColumnWidth+ mColorRectangles[24].right, mRectFrame.bottom);mColorRectangles[26] = new Rect(mColorRectangles[25].right,bottomHeight, mRectFrame.right, mRectFrame.bottom);} else {int topHeight = mRectFrame.right * 5 / 12;int bottomHeight = mRectFrame.right / 4;int wideColumnWidth = mRectFrame.bottom / 8;int narrowColumnWidth = mRectFrame.bottom * 3 / 28;mColorRectangles[0] = new Rect(topHeight, 0, mRectFrame.bottom,wideColumnWidth);for (int i = 1; i < 8; i++) {mColorRectangles[i] = new Rect(topHeight,mColorRectangles[i - 1].bottom, mRectFrame.right,narrowColumnWidth + mColorRectangles[i - 1].bottom);}mColorRectangles[8] = new Rect(topHeight,mColorRectangles[7].bottom, mRectFrame.right,mRectFrame.bottom);for (int i = 0; i < 2; i++) {int middleLeft = mRectFrame.right * (4 - i) / 12;int middleRight = mRectFrame.right * (5 - i) / 12;mColorRectangles[i + 9] = new Rect(middleLeft, 0,middleRight, wideColumnWidth);mColorRectangles[i + 11] = new Rect(middleLeft,wideColumnWidth, middleRight, narrowColumnWidth+ wideColumnWidth);mColorRectangles[i + 13] = new Rect(middleLeft,narrowColumnWidth * 7 + wideColumnWidth,middleRight, mRectFrame.bottom);}mColorRectangles[15] = new Rect(mRectFrame.right * 4 / 12,narrowColumnWidth + wideColumnWidth,mRectFrame.right * 5 / 12, narrowColumnWidth * 7+ wideColumnWidth);mGradientRect = new Rect(mRectFrame.right * 3 / 12,mColorRectangles[15].top, mColorRectangles[15].left,mColorRectangles[15].bottom);mGradient = new GradientDrawable(Orientation.TOP_BOTTOM,new int[] { 0xff050505, 0xfffdfdfd });mGradient.setBounds(mGradientRect);mColorRectangles[16] = new Rect(0, 0, bottomHeight,wideColumnWidth);mColorRectangles[17] = new Rect(0, mColorRectangles[16].bottom,bottomHeight, mRectFrame.bottom * 9 / 56+ mColorRectangles[16].bottom);mColorRectangles[18] = new Rect(0, mColorRectangles[17].bottom,bottomHeight, mRectFrame.bottom * 3 / 14+ mColorRectangles[17].bottom);mColorRectangles[19] = new Rect(0, mColorRectangles[18].bottom,bottomHeight, mRectFrame.bottom * 45 / 448+ mColorRectangles[18].bottom);for (int i = 20; i < 25; i++) {mColorRectangles[i] = new Rect(0,mColorRectangles[i - 1].bottom, bottomHeight,mRectFrame.bottom * 15 / 448+ mColorRectangles[i - 1].bottom);}mColorRectangles[25] = new Rect(0, mColorRectangles[24].bottom,bottomHeight, narrowColumnWidth+ mColorRectangles[24].bottom);mColorRectangles[26] = new Rect(0, mColorRectangles[25].bottom,bottomHeight, mRectFrame.bottom);}}private void CreateBars() {if (mHorizontal) {int narrowColumnWidth = mRectFrame.right / 7;int wideColumnWidth = mRectFrame.right * 5 / 28;int narrowestColumnWidth = mRectFrame.right / 21;int topColumnHeight = mRectFrame.bottom * 2 / 3;int middleColumnHeight = mRectFrame.bottom / 12;mColorRectangles[0] = new Rect(0, 0, narrowColumnWidth,topColumnHeight);for (int i = 1; i < 7; i++) {mColorRectangles[i] = new Rect(mColorRectangles[i - 1].right, 0,mColorRectangles[i - 1].right + narrowColumnWidth,topColumnHeight);}mColorRectangles[7] = new Rect(0, mColorRectangles[0].bottom,narrowColumnWidth, mColorRectangles[0].bottom+ middleColumnHeight);for (int i = 8; i < 14; i++) {mColorRectangles[i] = new Rect(mColorRectangles[i - 1].right,mColorRectangles[7].top,mColorRectangles[i - 1].right + narrowColumnWidth,mColorRectangles[7].bottom);}mColorRectangles[14] = new Rect(0, mColorRectangles[7].bottom,wideColumnWidth, mRectFrame.bottom);for (int i = 15; i < 18; i++) {mColorRectangles[i] = new Rect(mColorRectangles[i - 1].right,mColorRectangles[14].top,mColorRectangles[i - 1].right + wideColumnWidth,mRectFrame.bottom);}mColorRectangles[18] = new Rect(mColorRectangles[17].right,mColorRectangles[17].top, mColorRectangles[17].right+ narrowestColumnWidth, mRectFrame.bottom);for (int i = 19; i < 21; i++) {mColorRectangles[i] = new Rect(mColorRectangles[i - 1].right,mColorRectangles[14].top,mColorRectangles[i - 1].right+ narrowestColumnWidth, mRectFrame.bottom);}mColorRectangles[21] = new Rect(mColorRectangles[20].right,mColorRectangles[17].top, mColorRectangles[6].right,mRectFrame.bottom);} else {int narrowColumnWidth = mRectFrame.bottom / 7;int wideColumnWidth = mRectFrame.bottom * 5 / 28;int narrowestColumnWidth = mRectFrame.bottom / 21;int topColumnHeight = mRectFrame.right / 3;int middleColumnHeight = mRectFrame.right / 12;mColorRectangles[0] = new Rect(topColumnHeight, 0,mRectFrame.right, narrowColumnWidth);for (int i = 1; i < 7; i++) {mColorRectangles[i] = new Rect(topColumnHeight,mColorRectangles[i - 1].bottom, mRectFrame.right,mColorRectangles[i - 1].bottom + narrowColumnWidth);}mColorRectangles[7] = new Rect(mColorRectangles[0].left+ middleColumnHeight, 0, mColorRectangles[0].left,narrowColumnWidth);for (int i = 8; i < 14; i++) {mColorRectangles[i] = new Rect(mColorRectangles[7].left,mColorRectangles[i - 1].bottom,mColorRectangles[7].right,mColorRectangles[i - 1].bottom + narrowColumnWidth);}mColorRectangles[14] = new Rect(0, 0,mColorRectangles[7].right, wideColumnWidth);for (int i = 15; i < 18; i++) {mColorRectangles[i] = new Rect(0,mColorRectangles[i - 1].bottom,mColorRectangles[7].right,mColorRectangles[i - 1].bottom + wideColumnWidth);}mColorRectangles[18] = new Rect(0, mColorRectangles[17].bottom,mColorRectangles[7].right, mColorRectangles[17].bottom+ narrowestColumnWidth);for (int i = 19; i < 21; i++) {mColorRectangles[i] = new Rect(0,mColorRectangles[i - 1].bottom,mColorRectangles[7].right,mColorRectangles[i - 1].bottom+ narrowestColumnWidth);}mColorRectangles[21] = new Rect(0, mColorRectangles[20].bottom,mColorRectangles[7].right, mRectFrame.bottom);}}private void CreateEbu() {if (mHorizontal) {int narrowColumnWidth = mRectFrame.right / 8;mColorRectangles[0] = new Rect(0, 0, narrowColumnWidth,mRectFrame.bottom);for (int i = 1; i < 8; i++) {mColorRectangles[i] = new Rect(mColorRectangles[i - 1].right, 0,mColorRectangles[i - 1].right + narrowColumnWidth,mRectFrame.bottom);}} else {int narrowColumnWidth = mRectFrame.bottom / 8;mColorRectangles[0] = new Rect(0, 0, mRectFrame.right,narrowColumnWidth);for (int i = 1; i < 8; i++) {mColorRectangles[i] = new Rect(0,mColorRectangles[i - 1].bottom, mRectFrame.right,narrowColumnWidth + mColorRectangles[i - 1].bottom);}}}}
}

这里需要注意的是在androidmanifest.xml文件中加入

<service android:name=".LiveWallpaper" android:label="@string/app_name"  android:icon="@drawable/icon"><intent-filter><action android:name="android.service.wallpaper.WallpaperService" /></intent-filter><meta-data android:name="android.service.wallpaper" android:resource="@xml/livewallpaper" />
</service>

4.   新建类LiveWallpaperSettings从 PreferenceActivity 继承实现我们的设置界面,代码如下

public class LiveWallpaperSettings extends PreferenceActivity implementsSharedPreferences.OnSharedPreferenceChangeListener {@Overrideprotected void onCreate(Bundle icicle) {super.onCreate(icicle);getPreferenceManager().setSharedPreferencesName(LiveWallpaper.SHARED_PREFS_NAME);addPreferencesFromResource(R.xml.livewallpaper_settings);getPreferenceManager().getSharedPreferences().registerOnSharedPreferenceChangeListener(this);}@Overrideprotected void onResume() {super.onResume();}@Overrideprotected void onDestroy() {getPreferenceManager().getSharedPreferences().unregisterOnSharedPreferenceChangeListener(this);super.onDestroy();}public void onSharedPreferenceChanged(SharedPreferences sharedPreferences,String key) {}
}

同时仍然在androidmanifest.xml中加入 下面的代码。

<activity android:label="@string/livewallpaper_settings"android:name=".LiveWallpaperSettings"android:theme="@android:style/Theme.Light.WallpaperSettings"android:exported="true"android:icon="@drawable/icon"></activity>

5. 由于Android动态壁纸是2.1 API Level为7才加入的,所以设置好minSDK以及需要设备支持动态壁纸,我们在androidmanifest.xml中加入

 <uses-sdk android:minSdkVersion="7" /><uses-feature android:name="android.software.live_wallpaper" />

6. 对于文中ListPreference用到的数组,及代码中涉及的颜色数组,我们在/res/values/ 文件夹中创建一个名为testpatterns.xml 的文件,内容为

<?xml version="1.0" encoding="utf-8"?>
<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"><string-array name="livewallpaper_testpattern_names"><item>"Color Bars 16x9"</item><item>"Color Bars 4x3"</item><item>"EBU Color Bars"</item></string-array><string-array name="livewallpaper_testpattern_prefix"><item>"smpte"</item><item>"bars"</item><item>"ebu"</item></string-array><integer-array name="smptecolors"><item>0xFF696969</item><item>0xFFC1C1C1</item><item>0xFFC1C100</item><item>0xFF00C1C1</item><item>0xFF00C100</item><item>0xFFC100C1</item><item>0xFFC10000</item><item>0xFF0000C1</item><item>0xFF696969</item><item>0xFF00FFFF</item><item>0xFFFFFF00</item><item>0xFF052550</item><item>0xFF36056D</item><item>0xFF0000FF</item><item>0xFFFF0000</item><item>0xFFC1C1C1</item><item>0xFF2B2B2B</item><item>0xFF050505</item><item>0xFFFFFFFF</item><item>0xFF050505</item><item>0xFF000000</item><item>0xFF050505</item><item>0xFF0A0A0A</item><item>0xFF050505</item><item>0xFF0D0D0D</item><item>0xFF050505</item><item>0xFF2b2b2b</item></integer-array><integer-array name="barscolors"><item>0xFFC0C0C0</item><item>0xFFC0C000</item><item>0xFF00C0C0</item><item>0xFF00C000</item><item>0xFFC000C0</item><item>0xFFC00000</item><item>0xFF0000C0</item><item>0xFF0000C0</item><item>0xFF131313</item><item>0xFFC000C0</item><item>0xFF131313</item><item>0xFF00C0C0</item><item>0xFF131313</item><item>0xFFC0C0C0</item><item>0xFF00214C</item><item>0xFFFFFFFF</item><item>0xFF32006A</item><item>0xFF131313</item><item>0xFF090909</item><item>0xFF131313</item><item>0xFF1D1D1D</item><item>0xFF131313</item></integer-array><integer-array name="ebucolors"><item>0xFFBFBFBF</item><item>0xFFBFBF00</item><item>0xFF00BFBF</item><item>0xFF00BF00</item><item>0xFFBF00BF</item><item>0xFFBF0000</item><item>0xFF0000BF</item><item>0xFF000000</item></integer-array>
</resources>

Live Wallpaper动态壁纸开发相关推荐

  1. android 动态壁纸开发

    转:http://www.eoeandroid.com/thread-100389-1-1.html android 动态壁纸开发 参考:http://www.ophonesdn.com/articl ...

  2. Android自定义壁纸预览界面,Android自定义动态壁纸开发(时钟)

    看到有些手机酷炫的动态壁纸,有没有好奇过他们是如何实现的,其实我们自己也可以实现. 先看效果 上图是动态壁纸钟的一个时钟. 我们先来看看 Livewallpaper(即动态墙纸)的实现,Android ...

  3. Android 动态壁纸开发(时钟)

    Android 动态壁纸开发(时钟) 这是我人生第一篇文章,希望大家不喜无喷啊!有兴趣的可以看看玩,因为语言组织能力有限,就废话不多说直接进入重点! 先看效果 上图是动态壁纸钟的一个时钟. 我们先来看 ...

  4. wallpaper动态壁纸软件

    对于长期烦恼找不到好看的动态壁纸的小伙伴们来说,wallpaper动态壁纸(软件下载地址)绝对是救命仙丹,这是由吾爱论坛网友自制分享的一款超好用的动态壁纸软件,内置Steam和bilibili解析,可 ...

  5. Android自定义动态壁纸开发

    看到有些手机酷炫的动态壁纸,有没有好奇过他们是如何实现的,其实我们自己也可以实现. 一.动态壁纸原理 如果你了解使用过SurfaceView的话,那么开发一款动态壁纸对你来说其实非常简单. 动态壁纸的 ...

  6. Android自定义动态壁纸,Android自定义动态壁纸开发详解

    看到有些手机酷炫的动态壁纸,有没有好奇过他们是如何实现的,其实我们自己也可以实现. 一.动态壁纸原理 如果你了解使用过SurfaceView的话,那么开发一款动态壁纸对你来说其实非常简单. 动态壁纸的 ...

  7. android动态壁纸引擎,Android动态壁纸开发

    新建一个Android项目: 完成下面步骤后,安装到手机,并设置动态壁纸才能看到效果. res/xml/cube1.xml AndroidManifest.xml CubeWallpaper1.jav ...

  8. 使用C++实现的仿Wallpaper动态壁纸软件(含源文件)

    在上一篇博客中,已经介绍了wallpaper的实现原理,并用C#实现,本文将使用C++和Qt框架实现,由于之前已经介绍过具体思路,本文将跳过分析过程,直接上代码. 新建Qt项目,系统自动生成widge ...

  9. 开源规则引擎比较_Lively Wallpaper - 免费开源的动态壁纸桌面软件 (Wallpaper Engine 替代品)...

    说到动态壁纸 / 视频动画桌面,大家可能都会听过 Wallpaper Engine 这款神器!它可以说是动态桌面软件中的王者,素材资源最为丰富,唯一可惜的是它是一款付费软件. 如果你不想花钱,又希望体 ...

最新文章

  1. 不是我放弃AI,是AI放弃了我!!
  2. 如何设置chrome谷歌浏览器不显示图片
  3. python资料书-《Python数据分析与应用》——图书配套资料下载
  4. mysql 时间函数多了8小时_MySQL时间函数了解
  5. 全球通吃的九大黄金专业
  6. Leetcode--12. 整数转罗马数字
  7. exoplayer 纯java,Exoplayer不播放任何视频
  8. 拥有这个证书的医务人员恭喜了,国家正式通知……
  9. NOIP2015普及组第1题 45 金币 方法三(python3实现)
  10. 深入掌握JMS(三):MessageListener
  11. Java 约瑟夫环(循环链表解决)
  12. mysql升级mysql5.7.22记录
  13. 篇章级关系抽取(Doc-RE)论文列表整理
  14. SSM汽车维修中心管理系统
  15. 计算机高一教案,《计算机系统的基本组成》高一信息技术课教案
  16. Vue跨域问题解决方案
  17. Openstack 高可用部署(Ocata版)
  18. 首届广西网络安全技术大赛初赛通关攻略
  19. Facebook批量养号分享
  20. markdown表格内如何进行换行

热门文章

  1. F1V3.0-图形-前端绘图库简介
  2. 我国电信业市场秩序现状分析(转)
  3. 荣耀手机在哪升级鸿蒙系统,4部荣耀手机可升级至华为鸿蒙系统
  4. 微软GPT-4 Office王炸来袭,10亿打工人被革命
  5. javax 包是什么
  6. Golang单元测试覆盖率统计
  7. “亚北极生存训练”---哈佛人的不同
  8. c语言递归函数头文件,C语言函数,递归,功能模块头文件(习题)
  9. 头疼Android APP 抓包?看这一篇就够了!(不是)
  10. Python后端开发面经