2012-12-27 3 views
3

onDraw() 메서드를 사용하여 일부 상자를 그리는 뷰 유형 클래스를 만들었습니다. 내가 성공하지 못한다는 것은, 나는 3-5 초 후에이 박스들을 사라지기를 원한다는 것이다. 이를 위해 저는 timer와 timerTask를 사용하고 있습니다. TimerTask에서는 Paint 객체의 색상을 흰색으로 변경하는 run 메서드를 재정의했습니다. 배경색도 흰색이므로 상자를 지우는 효과가 있습니다. 너희들이 나를 도와 줄 수 있니?Timer 클래스를 사용하여 캔버스 업데이트 지연

public class PlayView extends View 
{ 
private float width,height; 
private int touchatX, touchatY; 
private boolean isanyBox, clearCanvas; 
private Point points[]; 
private Paint box; 
Timer timer; 
TimerTask task; 


    // Set the number of points to be generated so we print that number of boxes on the board 
public void nPoints(int n) 
{ 
    points = new Point[n]; 
    box = new Paint(); 
    box.setColor(Color.BLUE); 
} 

public void init() 
{ 
     isanyBox = false; 
     clearCanvas = true; 
     timer = new Timer(); 
     task = new TimerTask() 
     { 
      @Override 
      public void run() 
      { 
       box.setColor(Color.WHITE); 
      } 
     }; 
} 


     @Override 
    protected void onSizeChanged(int w, int h, int oldw, int oldh) 
{ 
// TODO Auto-generated method stub 

    width = w/6f; 
    height = h/6f; 

    Log.d("playview", getWidth()+" "+getHeight()); 
    super.onSizeChanged(w, h, oldw, oldh); 
} 

public PlayView(Context context) 
    { 
     super(context); 
     setFocusable(true); 
     setFocusableInTouchMode(true); 
     init(); 
    } 


// Randomly generate the points and draw boxes on these points 
public void generatePoints(int np) 
{ 
    Time sec = new Time(); 

    Random random_Xpoints = new Random(); 
    Random random_Ypoints = new Random(); 

    random_Xpoints.setSeed(sec.second); 
    random_Ypoints.setSeed(sec.second); 
    nPoints(np); // set the number of points to be generated 

    for(int i=0; i<np; i++) 
    { 
     points[i] = new Point(); 

     points[i].setX(((random_Xpoints.nextInt(getWidth())/(int)width)*(int)width)); 
     points[i].setY(((random_Ypoints.nextInt(getHeight())/(int)height)*(int)height)); 

     Log.d("Point "+1, points[i].getX()+" "+points[i].getY()); 
    } 
} 




    @Override 
    public boolean onTouchEvent(MotionEvent event) 
    { 
     // TODO Auto-generated method stub 

    invalidate(); 
    isanyBox = true; 
    touchatX = (int) ((int) (event.getX()/width)*width); 
    touchatY = (int) ((int) (event.getY()/height)*height); 
    Log.d("onTouchEvent", event.getX()+" "+event.getY()+" "+touchatX+" "+touchatY); 
     invalidate(); 
    return super.onTouchEvent(event); 
} 


    public void onDraw(Canvas canvas) 
    { 
    Paint lineColor = new Paint(); 
    lineColor.setColor(Color.BLACK); 

    //Box property 
    Paint boxColor = new Paint(); 
    boxColor.setColor(Color.BLUE); 

    //Draw horizontal lines 
    for(int i=0; i<6; i++) 
    { 
     canvas.drawLine(0, i*height, getWidth(), i*height, lineColor); 
    } 

    //Draw vertical lines 
    for(int j=0; j<6; j++) 
    { 
     canvas.drawLine(j*width, 0, j*width, getHeight(), lineColor); 
    } 

    if(isanyBox) 
    { 
    canvas.drawRect(touchatX+2, touchatY+2, touchatX+width-1, touchatY+height-2, boxColor); 
    } 


     generatePoints(5); 
     for(int j=0; j<5; j++) 
     { 
      canvas.drawRect(points[j].getX()+2, points[j].getY()+2, points[j].getX()+width-1, points[j].getY()+height-2, box); 
      Log.d("BoxColor", ""+box); 
     } 

     if(clearCanvas) 
     { 

      timer.schedule(task, 3000); 
      clearCanvas = false; 
      invalidate(); 
     } 

    } 
} 
+0

및 전화해야 귀하의 질문은 무엇인가? – Budius

+0

@Budius 나는 몇 초 후에 박스 디 서퍼를 만들려고 노력하고 있지만 이것은 일어나지 않습니다. – umerk44

답변

1

색상을 변경 한 후 invalidate();으로 전화하십시오. 그러면 시스템에서 onDraw()에 다시 전화를 겁니다.

 @Override 
     public void run() 
     { 
      box.setColor(Color.WHITE); 
      invalidate(); 
     } 

편집 :

내가 타이머를 좋아 한 적이

지금 나는 지금 이유가 여기에 읽을 수 있으며 어떤 이유로 안드로이드 팀은 사람들이 사용하지 않는 제안 그 이유는 : http://developer.android.com/reference/java/util/Timer.html

당신이보기를 확장하는 클래스에이기 때문에, 당신은 단지 postDelayed();

if(clearCanvas) 
    { 
     clearCanvas = false; 
     postDelayed(new Runnable{ 
     @Override 
     public void run(){ 
      box.setColor(Color.WHITE); 
      invalidate(); 
     } 
     }, 3000); 
    } 
+0

사실, 나는 타이머를 예약 한 후에 invalidate()를 호출하지만, "run 메서드에서 무효화 (move)"라고 말한 것처럼 했습니까? 활동이 추락했습니다. – umerk44

+0

Logcat이 있습니까? – Budius

+0

UI 스레드에서 invalidate를 호출해야하기 때문에 문제가 발생했을 수 있습니다. Timer 대신에'postDelayed()'를 사용하도록 답변을 업데이트했습니다. – Budius

관련 문제