0
点赞
收藏
分享

微信扫一扫

Android Launcher桌面3D实现和原理分析


Android Launcher桌面3D实现和原理分析_java

 

 

 

 

1,概述:

Launcher桌面由Workspace.java包含Celllayout.java构成,一个celllayout就是一个桌面,默认5个。 Workspace和celllayout都继承于viewgroup。

 

2,获得Touch坐标:

Launcher.java为activity,workspace是viewgroup。所以在activity中会注册一个scroller来记录滑动状态,scroller start后workspace中的computeScroll() 会接收到scroller的状态。这里获取到 mTouchX = mScrollX = mScroller.getCurrX();。Launcher会对滑动事件进行管理使得每次都能切屏或返回,而不会出现滑动到一半的状态。

 

3,重绘view:

scroller start的时候会不断重绘view直到scroller结束(mScroller.computeScrollOffset()返回false),所以要实现效果只需直接修改dispathDraw函数。dispathDraw和onDraw的区别是一个是画自己一个是画子view,dispathDraw在onDraw之后执行。

这里我们要实现伪3D效果,所以不用opengl,根据上面得到的mTouchX直接用camera和matrix配合就可以实现了。根据上面得到的mTouchX计算出子view需要旋转的角度,隐藏childview后,1)用drawchild画子view;2)直接抓取子view的bitmap(getChildAt(0).buildDrawingCache();Bitmap bitmap

 

4,实现代码:

上面大概的讲了下原理,下面给出实现代码,其实很简单,只需要修改Launcher2中的workspace.java就可以实现了。

 

 



1. @Override  
2. protected void dispatchDraw(Canvas canvas) {  
3. boolean restore = false;  
4. int restoreCount = 0;  
5.   
6. // ViewGroup.dispatchDraw() supports many features we don't need:  
7. // clip to padding, layout animation, animation listener, disappearing  
8. // children, etc. The following implementation attempts to fast-track  
9. // the drawing dispatch by drawing only what we know needs to be drawn.  
10.   
11. boolean fastDraw = mTouchState != TOUCH_STATE_SCROLLING && mNextScreen == INVALID_SCREEN;  
12. // If we are not scrolling or flinging, draw only the current screen  
13. if (fastDraw) {  
14. //add by andy.xie 20120831  
15. class="s1">mCurrentScreen</span>).setBackgroundResource(android.R.color.transparent);  
16.             drawChild(canvas, getChildAt(mCurrentScreen), getDrawingTime());  
17. else {  
18. final long drawingTime = getDrawingTime();  
19. final float scrollPos = (float) mScrollX / getWidth();  
20. final int leftScreen = (int) scrollPos;  
21. final int rightScreen = leftScreen + 1;  
22. //edit by andy.xie 20120831  
23. //            if (leftScreen >= 0) {  
24. //                drawChild(canvas, getChildAt(leftScreen), drawingTime);  
25. //            }  
26. //            if (scrollPos != leftScreen && rightScreen < getChildCount()) {  
27. //                drawChild(canvas, getChildAt(rightScreen), drawingTime);  
28. //            }  
29. //add by andy.xie 20120831  
30. new Camera();  
31. new Matrix();  
32. int width = getWidth();  
33. int height = getHeight();  
34.   
35. float rotateY = ((float)(mTouchX % width) / width) * 90;  
36. if(rotateY < 0) rotateY = 0;  
37. if(rotateY > 90) rotateY = 90;  
38. if(rotateY > 90) rotateY = 90;  
39.   
40. //  
41. "xxh", "x=" + mTouchX + " rotateY=" + rotateY + " scrollPos=" + scrollPos);  
42.   
43. if (leftScreen >= 0) {  
44. //  
45.                         canvas.save();  
46.                         camera.save();  
47. //camera.translate(0, 0, mWidth/2);  
48.                         camera.rotateY(-rotateY);  
49.                         camera.getMatrix(matrix);  
50.                         camera.restore();  
51. int)scrollPos + 1), -height/2);  
52. int)scrollPos + 1), height/2);  
53. //  
54.                         canvas.concat(matrix);  
55.                 getChildAt(leftScreen).setBackgroundResource(android.R.drawable.screen_background_dark_transparent);  
56.                         drawChild(canvas, getChildAt(leftScreen), drawingTime);  
57. getChildAt(leftScreen).setBackgroundResource(android.R.drawable.screen_background_dark_transparent);  
58.                         drawChild(canvas, getChildAt(leftScreen), drawingTime);  
59.                         canvas.restore();  
60.             }  
61.   
62.   
63. if (scrollPos != leftScreen && rightScreen < getChildCount()) {  
64. new Matrix();  
65.                 canvas.save();  
66.                         camera.save();  
67. //camera.translate(0, 0, mWidth/2);  
68. 90-rotateY);  
69.                         camera.getMatrix(matrix2);  
70.                         camera.restore();  
71. int)scrollPos + 1), -height/2);  
72. int)scrollPos + 1), height/2);  
73. //  
74.                         canvas.concat(matrix2);  
75.                 getChildAt(rightScreen).setBackgroundResource(android.R.drawable.screen_background_dark_transparent);  
76. canvas.concat(matrix2);  
77.                 getChildAt(rightScreen).setBackgroundResource(android.R.drawable.screen_background_dark_transparent);  
78.                 drawChild(canvas, getChildAt(rightScreen), drawingTime);  
79.                 canvas.restore();  
80.             }  
81.         }  
82.   
83. if (restore) {  
84.             canvas.restoreToCount(restoreCount);  
85.         }  
86.     }

举报

相关推荐

0 条评论