天天看點

Android中利用畫圖類和線程畫出閃爍的心形,送給親愛的他(她)

本文講解主要涉及的知識點:

1.線程控制 

2.畫圖類 

3.心形函數

大家先看圖檔:

因為前一段時間在寫畫圖類,剛好有一個線程控制畫圖閃爍的,我就想說我能不能做一個心形閃爍的,出來的效果就如圖,先貼再講解代碼:

裡面設定兩個類,一個是我們的activity類,這個類用來顯示示圖,然後建一個繼承SurfaceView的類,我們在這裡面畫圖。先貼兩個累的代碼:

主類名:GameMainActivity,畫圖類類名:Love.

1  <b>package</b> com.cz.game.demo; 

2  

3  <b>import</b> android.app.Activity; 

4  <b>import</b> android.os.Bundle; 

5  

6  <b>public</b> <b>class</b> GameMainActivity <b>extends</b> Activity { 

7      /** Called when the activity is first created. */ 

8  

9      <b>private</b> Love love; 

10     @Override 

11     <b>public</b> <b>void</b> onCreate(Bundle savedInstanceState) { 

12         <b>super</b>.onCreate(savedInstanceState); 

13         <b>this</b>.love = <b>new</b> Love(<b>this</b>); 

14         setContentView(love); 

15     } 

16 } 

畫圖類:

1   /** 

2    *  

3    */ 

4   <b>package</b> com.cz.game.demo; 

5   

6   <b>import</b> android.content.Context; 

7   <b>import</b> android.graphics.Canvas; 

8   <b>import</b> android.graphics.Color; 

9   <b>import</b> android.graphics.Paint; 

10  <b>import</b> android.graphics.RectF; 

11  <b>import</b> android.graphics.Typeface; 

12  <b>import</b> android.view.SurfaceHolder; 

13  <b>import</b> android.view.SurfaceView; 

14  

15  /** 

16   * @author CZ 

17   *  

18   */ 

19  <b>public</b> <b>class</b> Love <b>extends</b> SurfaceView <b>implements</b> SurfaceHolder.Callback, 

20          Runnable { 

21  

22      <b>boolean</b> mbloop = <b>false</b>; 

23      SurfaceHolder mSurfaceHolder = <b>null</b>; 

24      <b>private</b> Canvas canvas; 

25      <b>int</b> miCount = <b>0</b>; 

26      <b>int</b> y = <b>50</b>; 

27  

28      /** 

29       * @param context 

30       */ 

31      <b>public</b> Love(Context context) { 

32          <b>super</b>(context); 

33          mSurfaceHolder = <b>this</b>.getHolder(); 

34          mSurfaceHolder.addCallback(<b>this</b>); 

35          <b>this</b>.setFocusable(<b>true</b>); 

36          <b>this</b>.setKeepScreenOn(<b>true</b>); 

37          mbloop = <b>true</b>; 

38      } 

39  

40      /* 

41       * (non-Javadoc) 

42       *  

43       * @see 

44       * android.view.SurfaceHolder.Callback#surfaceChanged(android.view.SurfaceHolder 

45       * , int, int, int) 

46       */ 

47      @Override 

48      <b>public</b> <b>void</b> surfaceChanged(SurfaceHolder holder, <b>int</b> format, <b>int</b> width, 

49              <b>int</b> height) { 

50          // TODO Auto-generated method stub 

51  

52      } 

53  

54      /* 

55       * (non-Javadoc) 

56       *  

57       * @see 

58       * android.view.SurfaceHolder.Callback#surfaceCreated(android.view.SurfaceHolder 

59       * ) 

60       */ 

61      @Override 

62      <b>public</b> <b>void</b> surfaceCreated(SurfaceHolder holder) { 

63          // TODO Auto-generated method stub 

64          <b>new</b> Thread(<b>this</b>).start(); 

65      } 

66  

67      /* 

68       * (non-Javadoc) 

69       *  

70       * @seeandroid.view.SurfaceHolder.Callback#surfaceDestroyed(android.view. 

71       * SurfaceHolder) 

72       */ 

73      @Override 

74      <b>public</b> <b>void</b> surfaceDestroyed(SurfaceHolder holder) { 

75          // TODO Auto-generated method stub 

76          mbloop = <b>false</b>; 

77      } 

78  

79      /* 

80       * (non-Javadoc) 

81       *  

82       * @see java.lang.Runnable#run() 

83       */ 

84      @Override 

85      <b>public</b> <b>void</b> run() { 

86          // TODO Auto-generated method stub 

87          <b>while</b> (mbloop) { 

88              <b>try</b> { 

89                  Thread.sleep(<b>200</b>); 

90              } <b>catch</b> (Exception e) { 

91                  // TODO: handle exception 

92              } 

93              <b>synchronized</b> (mSurfaceHolder) { 

94                  Draw(); 

95              } 

96          } 

97      } 

98  

99      /** 

100      *  

101      * Year:2011 Date:2011-7-27 Time:下午06:52:04 Author:CZ TODO 

102      */ 

103     <b>private</b> <b>void</b> Draw() { 

104         // TODO Auto-generated method stub 

105         canvas = mSurfaceHolder.lockCanvas(); 

106         <b>try</b> { 

107             <b>if</b> (mSurfaceHolder == <b>null</b> || canvas == <b>null</b>) { 

108                 <b>return</b>; 

109             } 

110             <b>if</b> (miCount &amp;lt; <b>100</b>) { 

111                 miCount++; 

112             } <b>else</b> { 

113                 miCount = <b>0</b>; 

114             } 

115             Paint paint = <b>new</b> Paint(); 

116             paint.setAntiAlias(<b>true</b>); 

117             paint.setColor(Color.BLACK); 

118             canvas.drawRect(<b>0</b>, <b>0</b>, <b>320</b>, <b>480</b>, paint); 

119             <b>switch</b> (miCount % <b>6</b>) { 

120             <b>case</b> <b>0</b>: 

121                 paint.setColor(Color.BLUE); 

122                 <b>break</b>; 

123             <b>case</b> <b>1</b>: 

124                 paint.setColor(Color.GREEN); 

125                 <b>break</b>; 

126             <b>case</b> <b>2</b>: 

127                 paint.setColor(Color.RED); 

128                 <b>break</b>; 

129             <b>case</b> <b>3</b>: 

130                 paint.setColor(Color.YELLOW); 

131                 <b>break</b>; 

132             <b>case</b> <b>4</b>: 

133                 paint.setColor(Color.argb(<b>255</b>, <b>255</b>, <b>181</b>, <b>216</b>)); 

134                 <b>break</b>; 

135             <b>case</b> <b>5</b>: 

136                 paint.setColor(Color.argb(<b>255</b>, <b>0</b>, <b>255</b>, <b>255</b>)); 

137                 <b>break</b>; 

138             <b>default</b>: 

139                 paint.setColor(Color.WHITE); 

140                 <b>break</b>; 

141             } 

142             <b>int</b> i, j; 

143             <b>double</b> x, y, r; 

144 

145             <b>for</b> (i = <b>0</b>; i &amp;lt;= <b>90</b>; i++) { 

146                 <b>for</b> (j = <b>0</b>; j &amp;lt;= <b>90</b>; j++) { 

147                     r = Math.PI / <b>45</b> * i * (<b>1</b> - Math.sin(Math.PI / <b>45</b> * j)) 

148                             * <b>20</b>; 

149                     x = r * Math.cos(Math.PI / <b>45</b> * j) 

150                             * Math.sin(Math.PI / <b>45</b> * i) + <b>320</b> / <b>2</b>; 

151                     y = -r * Math.sin(Math.PI / <b>45</b> * j) + <b>400</b> / <b>4</b>; 

152                     canvas.drawPoint((<b>float</b>) x, (<b>float</b>) y, paint); 

153                 } 

154             } 

155 

156             paint.setTextSize(<b>32</b>); 

157             paint.setTypeface(Typeface.create(Typeface.SERIF, Typeface.ITALIC)); 

158 

159             RectF rect = <b>new</b> RectF(<b>60</b>, <b>400</b>, <b>260</b>, <b>405</b>); 

160             canvas.drawRoundRect(rect, (<b>float</b>) <b>1</b>.<b>0</b>, (<b>float</b>) <b>1</b>.<b>0</b>, paint); 

161             canvas.drawText(<b>"</b><b>Loving</b><b> </b><b>You</b><b>"</b>, <b>75</b>, <b>400</b>, paint); 

162             mSurfaceHolder.unlockCanvasAndPost(canvas); 

163         } <b>catch</b> (Exception e) { 

164         } 

165 

166     } 

167 

168 } 

169 

關于這個程式要講解的幾點:

1. 畫圖的時候你可以繼承View,也可以繼承SurfaceView,這兩者的差別在于:surfaceView是在一個新起的單獨線程中可以重新繪制畫面而View必須在UI的主線程中更新畫面。SurfaceView可以控制表面的格式,比如大小,顯示在螢幕中的位置,最關鍵是的提供了SurfaceHolder類,使用getHolder方法擷取,還有涉及的surfaceCreated(SurfaceHolder holder),surfaceDestroyed(SurfaceHolder holder),surfaceChanged(SurfaceHolder holder, int format, int width, int height)方法,而在SurfaceHolder.Callback 接口回調中可以通過重寫來改變這些方法

2.程式其實很簡單, 既然生命了Runnable接口,就有相對應的Run方法,在surfaceCreate()的時候開啟線程,線程每隔200ms就重新整理一次,這樣我們看到的效果就是閃爍的,每200毫秒 畫一次圖,根據經過的間隔時間來設定畫筆的顔色,然後通過循環描點,畫出心形,然後設定字型大小,畫字和字下面的橫線。

3.關于心形函數,是從一個例子中看來得,關于x和y的得到,

x = r * Math.cos(Math.PI / 45 * j)  * Math.sin(Math.PI / 45 * i) + 320 / 2;  y = -r * Math.sin(Math.PI / 45 * j) + 400 / 4;

320是螢幕的寬度,本來豎屏我設定的是480,可是下面得寫字,就設定為400的了,關于畫更好看的心形還有一個函數,大家可以看下:

<a href="http://hddev.blog.51cto.com/attachment/201108/6/3365350_1312622712s1uO.jpg"></a>

有興趣的童鞋可以設定再做一下.

關于這個代碼就這麼多,是以就不放附件代碼了,把apk放上,之前就打算寫這一篇部落格,沒想到在七夕這天寫了。有興趣的童鞋可以把apk下載下傳下來給女友看哦…

本文轉自HDDevTeam 51CTO部落格,原文連結:http://blog.51cto.com/hddev/632632,如需轉載請自行聯系原作者

繼續閱讀