溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務(wù)條款》

Android開發(fā)中如何使用線程Bezier曲線

發(fā)布時間:2021-11-26 16:16:33 來源:億速云 閱讀:161 作者:柒染 欄目:移動開發(fā)

Android開發(fā)中如何使用線程Bezier曲線,相信很多沒有經(jīng)驗的人對此束手無策,為此本文總結(jié)了問題出現(xiàn)的原因和解決方法,通過這篇文章希望你能解決這個問題。

Android中使用線程Thread的方法和Java SE相同。和大多數(shù)OS系統(tǒng)一樣,Android中也有稱為UI  Thread的主線程。UI Thread 主要用來給相應(yīng)的Widget分發(fā)消息,包括繪制(Drawing)事件。UI Thread  也是用來處理用戶交互事件的線程。比如:如果你按下屏幕上某個按鈕,UI 線程則將Touch 事件通知對應(yīng)的控件(Widgets),Widget  則將其狀態(tài)設(shè)置成“按下”,并把“重繪”(Invalidate)事件發(fā)到Event Queue中去。 UI線程從Event  Queue中讀取事件后通知Widgets重畫自身。

如果你的應(yīng)用設(shè)計不好的話, UI線程的這種單線程模式就會導(dǎo)致非常差的用戶響應(yīng)性能。特別是你將一些費時的操作如網(wǎng)絡(luò)訪問或數(shù)據(jù)庫訪問也放在UI線程中,這些操作會造成用戶界面無反應(yīng),最糟糕的是,如果UI線程阻塞超過幾秒(5秒),著名的ANR對話框就會出現(xiàn):

Android開發(fā)中如何使用線程Bezier曲線

所以在設(shè)計應(yīng)用時,需要把一些費時的任務(wù)使用單獨的工作線程來運行避免阻塞UI線程,但是如果在工作線程中想更新UI線程的話,不能直接在工作線程 中更新UI,這是因為UI線程不是“Thread Safe”。因此所有UI相關(guān)的操作一般必須在UI Thread中進(jìn)行。

Android OS提供了多種方法可以用在非UI線程訪問UI線程。

  • Activity.runOnUiThread(Runnable)

  • View.post(Runnable)

  • View.postDelayed(Runnable, long)

  • Handler

Bezier 示例動態(tài)顯示Bezier曲線,使用了Activity.runOnUiThread 來更新屏幕,完整代碼如下:

1   public class Bezier extends Graphics2DActivity 2   implements OnClickListener,Runnable{  3     4    /** 5        * The animation thread. 6        */ 7       private Thread thread; 8       private volatile boolean stopThread=false; 9       private boolean stopOrNot=false; 10      boolean drawn; 11      /** 12       * The random number generator. 13       */ 14      static java.util.Random random = new java.util.Random(); 15      /** 16       * The animated path 17       */ 18      Path path = new Path(); 19      /** 20       * Red brush used to fill the path. 21       */ 22      SolidBrush brush = new SolidBrush(Color.RED); 23      private static final int NUMPTS = 6; 24      private int animpts[] = new int[NUMPTS * 2]; 25      private int deltas[] = new int[NUMPTS * 2]; 26      long startt, endt; 27       28   private Button btnOptions; 29   @Override 30   protected void drawImage() { 31     drawDemo(100, 100); 32      33   } 34     35   public void onCreate(Bundle savedInstanceState) { 36    super.onCreate(savedInstanceState); 37    setContentView(R.layout.beziers); 38    graphic2dView 39       = (GuidebeeGraphics2DView) findViewById(R.id.graphics2dview); 40    btnOptions = (Button) findViewById(R.id.btnStopStart); 41    btnOptions.setOnClickListener(this); 42    reset(100,100); 43    if (thread == null) { 44              thread = new Thread(this); 45              thread.start(); 46          } 47      48   }  49    50   @Override 51   public void onClick(View view) { 52      53    if(!stopOrNot){ 54     btnOptions.setText("Start"); 55        stopThread=true; 56    } 57    else{ 58     stopThread=false; 59     btnOptions.setText("Stop"); 60     if (thread == null) { 61               thread = new Thread(this); 62               thread.start(); 63           } 64    } 65    stopOrNot=!stopOrNot; 66      67   }  68      /** 69       * Generates new points for the path. 70       */ 71      private void animate(int[] pts, int[] deltas, 72        int i, int limit) { 73          int newpt = pts[i] + deltas[i]; 74          if (newpt <= 0) { 75              newpt = -newpt; 76              deltas[i] = (random.nextInt() & 0x00000003) 77              + 2; 78          } else if (newpt >= limit) { 79              newpt = 2 * limit - newpt; 80              deltas[i] = -((random.nextInt() & 0x00000003) 81                + 2); 82          } 83          pts[i] = newpt; 84      }  85    86      /** 87       * Resets the animation data. 88       */ 89      private void reset(int w, int h) { 90          for (int i = 0; i < animpts.length; i += 2) { 91              animpts[i + 0] 92                      = (random.nextInt() & 0x00000003) 93                      * w / 2; 94              animpts[i + 1] 95                      = (random.nextInt() & 0x00000003) 96                      * h / 2; 97              deltas[i + 0] 98                     = (random.nextInt() & 0x00000003) 99                     * 6 + 4; 100             deltas[i + 1] 101                    = (random.nextInt() & 0x00000003) 102                    * 6 + 4; 103             if (animpts[i + 0] > w / 2) { 104                 deltas[i + 0] = -deltas[i + 0]; 105             } 106             if (animpts[i + 1] > h / 2) { 107                 deltas[i + 1] = -deltas[i + 1]; 108             } 109         } 110     }  111   112     final Runnable updateCanvas = new Runnable() { 113   public void run() { 114    int offsetX = (graphic2dView.getWidth() - 115      SharedGraphics2DInstance.CANVAS_WIDTH) / 2; 116    int offsetY = (graphic2dView.getHeight() 117      - SharedGraphics2DInstance.CANVAS_HEIGHT) / 2; 118    graphic2dView.invalidate(offsetX,offsetY, 119      offsetX+100,offsetY+100); 120   } 121  }; 122     /** 123      * Sets the points of the path and draws and fills the path. 124      */ 125     private void drawDemo(int w, int h) { 126         for (int i = 0; i < animpts.length; i += 2) { 127             animate(animpts, deltas, i + 0, w); 128             animate(animpts, deltas, i + 1, h); 129         } 130         //Generates the new pata data. 131         path.reset(); 132         int[] ctrlpts = animpts; 133         int len = ctrlpts.length; 134         int prevx = ctrlpts[len - 2]; 135         int prevy = ctrlpts[len - 1]; 136         int curx = ctrlpts[0]; 137         int cury = ctrlpts[1]; 138         int midx = (curx + prevx) / 2; 139         int midy = (cury + prevy) / 2; 140         path.moveTo(midx, midy); 141         for (int i = 2; i <= ctrlpts.length; i += 2) { 142             int x1 = (curx + midx) / 2; 143             int y1 = (cury + midy) / 2; 144             prevx = curx; 145             prevy = cury; 146             if (i < ctrlpts.length) { 147                 curx = ctrlpts[i + 0]; 148                 cury = ctrlpts[i + 1]; 149             } else { 150                 curx = ctrlpts[0]; 151                 cury = ctrlpts[1]; 152             } 153             midx = (curx + prevx) / 2; 154             midy = (cury + prevy) / 2; 155             int x2 = (prevx + midx) / 2; 156             int y2 = (prevy + midy) / 2; 157             path.curveTo(x1, y1, x2, y2, midx, midy); 158         } 159         path.closePath(); 160         // clear the clipRect area before production  161   162         graphics2D.clear(Color.WHITE); 163         graphics2D.fill(brush, path);  164   165         this.runOnUiThread(updateCanvas);  166     } 167      168       169   170     public void run() { 171         Thread me = Thread.currentThread();  172   173         if (!drawn) { 174             synchronized (this) { 175                 graphics2D.clear(Color.WHITE); 176                 graphics2D.fill(brush, path); 177                 graphic2dView.refreshCanvas(); 178                 drawn = true; 179             } 180         } 181         while (thread == me && !stopThread) { 182             drawDemo(100,100); 183         } 184         thread = null; 185     } 186 }

Android開發(fā)中如何使用線程Bezier曲線

除了上述的方法外,Android還提供了AsyncTask類以簡化工作線程與UI線程之間的通信。此外,上面Bezier曲線動畫在屏幕上顯示時有閃爍的現(xiàn)象,這是動態(tài)顯示圖像的一個常見問題。

看完上述內(nèi)容,你們掌握Android開發(fā)中如何使用線程Bezier曲線的方法了嗎?如果還想學(xué)到更多技能或想了解更多相關(guān)內(nèi)容,歡迎關(guān)注億速云行業(yè)資訊頻道,感謝各位的閱讀!

向AI問一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點不代表本網(wǎng)站立場,如果涉及侵權(quán)請聯(lián)系站長郵箱:is@yisu.com進(jìn)行舉報,并提供相關(guān)證據(jù),一經(jīng)查實,將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI