RelativeLayout onDraw wird nicht aufgerufen

  • 4 Antworten
  • Neuester Beitrag
Diskutiere RelativeLayout onDraw wird nicht aufgerufen im Android App Entwicklung im Bereich Betriebssysteme & Apps.
K

krackmoe

Neues Mitglied
Ich implementiere gerade Drag&Drop in einem RelativeLayout..

Jetzt möchte ich das nach dem onTouchEvent das RelativeLayout neu gezeichnet wird, bzw. nur die Views.. damit man auch sieht das sich die Drawable Shape bewegt..

Jedoch funktioniert weder invalidate() noch requestLayout() am Ende der onTouchEvent Methode.

onDraw wird einfach nicht aufgerufen...

Kann mir da bitte jemand helfen?
 
DieGoldeneMitte

DieGoldeneMitte

Experte
Bist du sicher, dass der onTouchEvent aufgerufen wird? I meine mich zu entsinnen, dass der gar keine TouchEvents empfängt, da die in den inneren Views landen.
 
K

krackmoe

Neues Mitglied
Ja onTouch wird ganz sicher aufgerufen, hab dort einige Log Meldungen eingebaut, außerdem bekomm ich die Positionen zurück..

Ich zeig euch mal meinen code...

Code:
public class DrawView extends RelativeLayout {
	private ArrayList<Rectangle> rectangles = new ArrayList<Rectangle>();
	private int rectId = 0;
	private int width;
	private int height;
	
	public DrawView(Context context) {
		super(context);		
		
		//RelativeLayout layout = new RelativeLayout(context);
		this.setLayoutParams(new RelativeLayout.LayoutParams(width, height));		
		
		Rectangle rect1 = new Rectangle(this.getContext());
		rect1.setId(1);
		rectangles.add(rect1);
		this.addView(rect1);
		
		RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
		params.setMargins(0, 10, 0, 0);
		Rectangle rect2 = new Rectangle(this.getContext());
		rect2.setId(2);
		params.addRule(RelativeLayout.BELOW, rect1.getId());    
		rect2.setLayoutParams(params);	
		rectangles.add(rect2);
		this.addView(rect2);

		
		
	}

	@Override
	protected void onDraw(Canvas canvas) {
		Log.i("ondraw","yes"+rectangles.size());
		
		for(Rectangle v: rectangles){
			Paint paint = new Paint();
			paint.setColor(Color.GREEN);
			Log.i("draw", ""+v.getTop());
			Log.i("draw", ""+v.getLeft());
			canvas.drawRect((float)v.getX(),(float) v.getY(),(float) v.getX()+150, (float)v.getY()+50, paint);
		}
	}

	@Override
	public boolean onTouchEvent(MotionEvent event) {
		
		int x = (int) event.getX();
		int y = (int) event.getY();	
		
		switch(event.getAction()){
			case MotionEvent.ACTION_DOWN:
						
				rectId = 0;
				
				for(int i=0; i < rectangles.size(); i++){
					View child = rectangles.get(i);
					if(x > child.getLeft() && x < child.getLeft()+150 && y > child.getTop() && y < child.getTop()+50){
						rectId = child.getId();
						rectangles.get(rectId-1).setTop(child.getTop());
						rectangles.get(rectId-1).setLeft(child.getLeft());
						break;
					}				
				}
				break;
			case MotionEvent.ACTION_MOVE:
				
				if(rectId > 0){
					rectangles.get(rectId-1).setBackgroundRessource(true);
					rectangles.get(rectId-1).setTop(y-25);
					rectangles.get(rectId-1).setLeft(x-25);
					Log.i("MOVE X", rectId+" "+rectangles.get(rectId-1).getX());
					Log.i("MOVE Y", rectId+" "+rectangles.get(rectId-1).getY());
				}
				
				break;
			case MotionEvent.ACTION_UP:
				Log.i("rectid Cancel", ""+rectId);
				if(rectId > 0){
					rectangles.get(rectId-1).setBackgroundRessource(true);
				}
				
				break;
		}

		invalidate();
		
		return true;
		
	}

	@Override
	protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
		super.onMeasure(widthMeasureSpec, heightMeasureSpec);

		width = View.MeasureSpec.getSize(widthMeasureSpec);
		height = View.MeasureSpec.getSize(heightMeasureSpec);
		
		setMeasuredDimension(width, height);
	}

}
 
DieGoldeneMitte

DieGoldeneMitte

Experte
Wo wird das Rectangle invalidiert?
 
K

krackmoe

Neues Mitglied
Warum muss ich das rectangle invalidaten? Wenn ich nur das invalidate dann zeichnet sich doch nur der Bereich innerhalb des rectangle neu oder?