title: Custom view not executing onDraw()
body: <p>I have created a custom view named CustomViewVisual1 that draws on screen objects of the class Particle. I use this custom view in a class named LayoutCanvas that extends Activity. Neither onTouch() or onProgressChanged() events in LayoutCanvas seem to cause my view to redraw even though I'm calling invalidate and have also tried postInvalidate(). The values of my objects change but I get no redraw!
  To be honest I'm new to Android and not aware of any good practises on how to design my classes and where to implement what, so if anyone has a better solution to what I'm trying to achieve, please let me know. Thanks in advance!</p>
  
  <p>This is the Particle class:</p>
  
  <pre><code>    public class Particle {
      Rect rect = new Rect();
      float similarity;
      Point p = new Point();
      float x;
      float y;
  
      float tx = 240;
      float ty = 320;
  
      Matrix transform = new Matrix();
  
      float r;
      Paint _paint = new Paint();
      Paint tempp = new Paint();
  
      Particle(){}
  
      Particle(int width, float similarity){
          this.similarity = similarity;
          x = MyMath.map(similarity, 0, 1, 0, width/2);
          //y = MyMath.myRandom(-20, 20);
          y = 0;
          //p.set((int) MyMath.map(similarity, 0, 1, 0, width/2), (int)MyMath.myRandom(0, 360));
          p.set((int)x, (int)y);
          r = MyMath.myRandom(0, 360);
          //recalculateCoordinates();
          _paint.setColor(Color.WHITE);
          tempp.setColor(Color.GREEN);
          //rotate(r);
  
      }
  
  
      public void display(Canvas canvas, Paint paint, float scale){
          //canvas.drawLine(canvas.getWidth()/2, 0, canvas.getWidth()/2, canvas.getHeight(), _paint);
          //canvas.drawLine(0, canvas.getHeight()/2, canvas.getWidth(), canvas.getHeight()/2, _paint);
          canvas.save();
          canvas.translate(canvas.getWidth()/2, canvas.getHeight()/2);
          //canvas.translate(tx, ty);
          canvas.rotate(r);
          //canvas.scale(scale, scale);
          paint.setColor(colorize());
          canvas.drawRect(-p.x, p.y, -p.x+10, p.y+10, paint);
          canvas.restore();
  
          canvas.save();
          canvas.translate(canvas.getWidth()/2, canvas.getHeight()/2);
          canvas.drawLine(0, 0, 200, 0, tempp);
          canvas.drawText("0'", 100, 8, tempp);
          canvas.restore();
  
          canvas.save();
          canvas.translate(canvas.getWidth()/2, canvas.getHeight()/2);
          canvas.rotate(45);
          canvas.drawLine(0, 0, 200, 0, tempp);
          canvas.drawText("45''", 100, 8, tempp);
          canvas.restore();
  
          canvas.save();
          canvas.translate(canvas.getWidth()/2, canvas.getHeight()/2);
          canvas.rotate(90);
          canvas.drawLine(0, 0, 200, 0, tempp);
          canvas.drawText("90'", 100, 8, tempp);
          canvas.restore();
  
          canvas.save();
          canvas.translate(canvas.getWidth()/2, canvas.getHeight()/2);
          canvas.rotate(180);
          canvas.drawLine(0, 0, 200, 0, tempp);
          canvas.drawText("180'", 100, 8, tempp);
          canvas.restore();
      }
  
      public int colorize(){
          return Color.argb(100, Math.round(255-MyMath.map(similarity, 0, 1, 0, 255)), 0, Math.round(MyMath.map(similarity, 0, 1, 0, 255)));
      }
  
      public void rotate(float degrees){
          transform.setTranslate(120, 160);
          transform.setRotate(degrees, 0, 0);
  
          // Create new float[] to hold the rotated coordinates
          float[] pts = new float[2];
  
          // Initialize the array with our Coordinate
          pts[0] = p.x;
          pts[1] = p.y;
  
          // Use the Matrix to map the points
          transform.mapPoints(pts);
  
          p.set((int)pts[0], (int)pts[1]);
          // NOTE: pts will be changed by transform.mapPoints call
          // after the call, pts will hold the new cooridnates
  
          // Now, create a new Point from our new coordinates
          //Point newPoint = new Point((int)pts[0], (int)pts[1]);
  
          // Return the new point
          //p.set(newPoint.x, newPoint.y);
          //return newPoint;
      }
  
      public void translate(int x, int y){
          tx = x;
          ty = y;
      }
  
      public void recalculateCoordinates(){
          x = (float) ( (x * android.util.FloatMath.cos(r) ) - (y * android.util.FloatMath.sin(r) ) );
          y = (float) ( (x * android.util.FloatMath.sin(r) ) - (y * android.util.FloatMath.cos(r) ) );
      }
      /**
       * @return the similarity
       */
      public float getSimilarity() {
          return similarity;
      }
  
      /**
       * @param similarity the similarity to set
       */
      public void setSimilarity(float similarity) {
          this.similarity = similarity;
      }
  
      /**
       * @return the x
       */
      public float getX() {
          return x;
      }
  
      /**
       * @param x the x to set
       */
      public void setX(float x) {
          this.x = x;
      }
  
      /**
       * @return the y
       */
      public float getY() {
          return y;
      }
  
      /**
       * @param y the y to set
       */
      public void setY(float y) {
          this.y = y;
      }
  
      /**
       * @return the r
       */
      public float getR() {
          return r;
      }
  
      /**
       * @param r the r to set
       */
      public void setR(float r) {
          this.r = r;
      }
  
      public Point getP() {
          return p;
      }
  
      public void setP(Point p) {
          this.p = p;
      }
      }
  </code></pre>
  
  <p>This is the CustomViewVisual1 class:</p>
  
  <pre><code>    public class CustomViewVisual1 extends View implements Runnable{
      int width;
      int height;
      int x = 0; 
      int y = 0;
      int canvasScale = 1;
      int countDraw = 0;
  
      Thread t = null;
      boolean isItOK = false;
  
      Paint paint;
      Particle[] p = new Particle[500];
  
      public CustomViewVisual1(Context context){
          super(context);
          initView();
      }
  
  
      public CustomViewVisual1(Context context, AttributeSet attrs) {
          super(context, attrs);
          initView();
      }
  
      private void initView() {
          // TODO Auto-generated method stub
          paint = new Paint();
  
          Random r = new Random();
          for (int i = 0; i &lt; p.length; i++) {
              p[i] = new Particle(width, r.nextFloat());
          }
      }
  
      @Override
      protected void onSizeChanged(int w, int h, int oldw, int oldh) {
          // TODO Auto-generated method stub
          super.onSizeChanged(w, h, oldw, oldh);
          width = w;
          height = h;
          x = width/2;
          y = height/2;
          initView();
      }
  
  
      @Override
      protected void onDraw(Canvas canvas) {
          super.onDraw(canvas);
          //canvas.translate(width/2, height/2);
          canvas.drawARGB(255, 0, 0, 0);
          canvas.scale(canvasScale, canvasScale);
          for (int i = 0; i &lt; p.length; i++) {
              p[i].display(canvas, paint, canvasScale);
          }
  
          paint.setColor(Color.WHITE);
          canvas.drawCircle(x, y, 20, paint);
          /*
          paint.setColor(Color.CYAN);
          canvas.drawRect(0, 0, width, 10, paint);
          paint.setColor(Color.GREEN);
          canvas.drawRect(0, height-10, width, height, paint);
          paint.setColor(Color.YELLOW);
          canvas.drawRect(0, 0, 10, height, paint);
          paint.setColor(Color.MAGENTA);
          canvas.drawRect(width-10, 0, width, height, paint);
          */
          countDraw++;
          Log.d("How many draw = ", ""+countDraw);
      }
  
  
      public float getCanvasScale() {
          return canvasScale;
      }
  
  
      public void setCanvasScale(int canvasScale) {
          this.canvasScale = canvasScale;
      }
  
      public void pause() {
          isItOK = false;
          while (true) {
              try {
                  t.join();
              } catch (InterruptedException e) {
                  e.printStackTrace();
              }
              break;
          }
          t = null;
      }
  
      public void resume() {
          isItOK = true;
          t = new Thread(this);
          t.start();
      }
  
  
      @Override
      public void run() {
          // TODO Auto-generated method stub
      }
      }
  </code></pre>
  
  <p>This is the LayoutCanvas class:</p>
  
  <pre><code>    public class LayoutCanvas extends Activity implements OnTouchListener{
  
      RelativeLayout rl;
      SeekBar sb;
      CustomViewVisual1 cView;
  
      /*
       * (non-Javadoc)
       * 
       * @see android.app.Activity#onCreate(android.os.Bundle)
       */
      @Override
      protected void onCreate(Bundle savedInstanceState) {
          // TODO Auto-generated method stub
          super.onCreate(savedInstanceState);
          requestWindowFeature(Window.FEATURE_NO_TITLE);
          getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,WindowManager.LayoutParams.FLAG_FULLSCREEN);
          setContentView(R.layout.activity_layout_canvas);
  
          cView = new CustomViewVisual1(this);
          cView.setOnTouchListener(this);
  
          rl = (RelativeLayout) findViewById(R.id.lay_canvas);
          rl.setOnTouchListener(this);
          rl.setOnLongClickListener(new OnLongClickListener(){
              @Override
              public boolean onLongClick(View v) {
                  // TODO Auto-generated method stub
                  Log.d("on long touch", "keep touching");
                  return false;
              }});
  
          sb = (SeekBar) findViewById(R.id.sb_activity_layout_canvas);
          sb.setOnSeekBarChangeListener(new OnSeekBarChangeListener(){
  
              @Override
              public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
                  Log.d("in progress changed", "before if() "+progress);
                  if(progress &gt; 0 &amp;&amp; progress &lt;=10){ 
                      Log.d("in progress changed", "in if() " + progress);
                      cView.setCanvasScale(progress);
                      cView.invalidate();
                  }
              }
  
              @Override
              public void onStartTrackingTouch(SeekBar seekBar) {
                  // TODO Auto-generated method stub
  
              }
  
              @Override
              public void onStopTrackingTouch(SeekBar seekBar) {
                  // TODO Auto-generated method stub
  
              }});
  
      }
  
      @Override
      public boolean onTouch(View v, MotionEvent event) {
          // TODO Auto-generated method stub
          Log.d("on touch", "Just touched");
          cView.x = (int) event.getX();
          cView.y = (int) event.getY();
          Log.d("cView x = ", ""+cView.x);
          Log.d("cView y = ", ""+cView.y);
          cView.invalidate();
          return false;
      }
  
  
  
      }
  </code></pre>
  
  <p>And this is the layout .xml file:</p>
  
  <pre><code>  &lt;?xml version="1.0" encoding="utf-8"?&gt;
      &lt;RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
          android:layout_width="fill_parent"
          android:layout_height="fill_parent" 
          android:id="@+id/lay_canvas"&gt;
  
          &lt;SeekBar
              android:id="@+id/sb_activity_layout_canvas"
              android:layout_width="match_parent"
              android:layout_height="wrap_content"
              android:layout_above="@+id/button1"
              android:layout_alignParentLeft="true"
              android:max="10" /&gt;
  
           &lt;Button
              android:id="@+id/button1"
              android:layout_width="wrap_content"
              android:layout_height="wrap_content"
              android:layout_alignParentBottom="true"
              android:layout_alignParentLeft="true"
              android:layout_toLeftOf="@+id/button2"
              android:text="Button" /&gt;
  
          &lt;Button
              android:id="@+id/button2"
              android:layout_width="wrap_content"
              android:layout_height="wrap_content"
              android:layout_alignParentBottom="true"
              android:layout_centerHorizontal="true"
              android:text="Button" /&gt;
  
          &lt;Button
              android:id="@+id/button3"
              android:layout_width="wrap_content"
              android:layout_height="wrap_content"
              android:layout_alignParentBottom="true"
              android:layout_alignParentRight="true"
              android:layout_toRightOf="@+id/button2"
              android:text="Button" /&gt;
  
          &lt;com.anvil.thesis.CustomViewVisual1
              android:id="@+id/myView1"
              android:layout_width="match_parent"
              android:layout_height="match_parent"
              android:layout_above="@+id/sb_activity_layout_canvas"
              android:layout_alignParentLeft="true"
              android:layout_alignParentTop="true" /&gt;
  
      &lt;/RelativeLayout&gt;
  </code></pre>