同一个自定义的更多实例的事件查看

同一个自定义的更多实例的事件查看

问题描述:

我是Android新手。 在项目中,我与后续的代码同一个自定义的更多实例的事件查看

public class MyView extends View { 

    private final Bitmap baseBitmap = BitmapFactory.decodeResource(
      getResources(), R.drawable.myImage); 
    private final Matrix matrix; 
    private boolean active = true; 

    public MyView(Context context, Matrix matrix) { 
     super(context); 
     this.matrix = matrix; 
     this.setFocusable(true); 
    } 

    @Override 
    protected void onDraw(Canvas canvas) { 
     super.onDraw(canvas); 
     if (active) { 
      System.out.println("draw "+this.getId()); 
      canvas.drawBitmap(baseBitmap, matrix, null); 
     } else { 
     ... 
     } 
    } 


    @Override 
    public boolean onTouchEvent(MotionEvent event) { 
     if (event.getAction() == MotionEvent.ACTION_DOWN) { 
      System.out.println("--------->"+this.getId()); 
     } else if (event.getAction() == MotionEvent.ACTION_MOVE) { 
      this.matrix.setTranslate(event.getX()-(baseBitmap.getWidth()/2), event.getY()-(baseBitmap.getHeight()/2)); 
      this.invalidate(); 
     } else if (event.getAction() == MotionEvent.ACTION_UP) { 

      this.active = false; 
     } 
     return true; 
    } 

在我的活动自定义视图MyView的,我实例MyView的很多次,然后将它们添加到主布局。这是它的代码:

public class MyActivity extends Activity { 
    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     Display display = getWindowManager().getDefaultDisplay(); 
     float cx = display.getWidth()/2, cy = display.getHeight()/2; 
     int radius = 80; 
     double distance = 0, distancePoint = 0; 
     final int flags = PathMeasure.POSITION_MATRIX_FLAG 
      | PathMeasure.TANGENT_MATRIX_FLAG; 
     float length = 0; 
     setContentView(R.layout.main); 
     RelativeLayout mainLayout = (RelativeLayout) findViewById(R.id.main_view); 
     Path pathCircle = new Path(); 
     pathCircle.addCircle(cx, cy, radius, Direction.CW); 
     PathMeasure meas = new PathMeasure(pathCircle, false); 
     int nObject = 10; 
     length = meas.getLength(); 
     distance = length/nObject; 
     int i = 0;   
      while(i<nObject){ 
       Matrix m = new Matrix(); 
       meas.getMatrix((float)distancePoint, m, flags); 
       MyView myView = new MyView(this, m); 
       System.out.println(myView.toString()); 
       myView.setId(i); 
       mainLayout.addView(myView,i); 
       i++; 
       distancePoint = distance*i; 
      } 
     }        
} 

在运行时,当我触摸任何MyView元素时,我总是得到最后一个。使用“​​”,我可以看到被触摸的元素的ID始终是最后一个,即使我将第一个或任何其他元素分开。实际上,我只能移动最后一个元素。
有谁知道为什么我无法获得MyView碰到的正确事件?
(我希望我的问题是清楚的)
感谢


我改变了代码添加onMeasure方法。我使用了教程的代码,尺寸不是特定于我的图像。意见是绘制和结果是相同的,不幸的是有同样的问题。我也发布了布局xml,可能会很有用。

public class MyActivity extends Activity { 
    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     Display display = getWindowManager().getDefaultDisplay(); 
     float cx = display.getWidth()/2, cy = display.getHeight()/2; 
     int radius = 80; 
     double distance = 0, distancePoint = 0; 
     final int flags = PathMeasure.POSITION_MATRIX_FLAG 
      | PathMeasure.TANGENT_MATRIX_FLAG; 
     float length = 0; 
     setContentView(R.layout.main); 
     RelativeLayout mainLayout = (RelativeLayout) findViewById(R.id.main_view); 
     Path pathCircle = new Path(); 
     pathCircle.addCircle(cx, cy, radius, Direction.CW); 
     PathMeasure meas = new PathMeasure(pathCircle, false); 
     int nObject = 10; 
     length = meas.getLength(); 
     distance = length/nObject; 
     int i = 0;   
      while(i<nObject){ 
       Matrix m = new Matrix(); 
       meas.getMatrix((float)distancePoint, m, flags); 
       MyView myView = new MyView(this, m); 
       System.out.println(myView.toString()); 
       myView.setId(i); 
       nt spec = MeasureSpec.makeMeasureSpec(MeasureSpec.UNSPECIFIED, MeasureSpec.UNSPECIFIED); 
         myView.measure(spec, spec); 
       mainLayout.addView(myView,i); 
       i++; 
       distancePoint = distance*i; 
      } 
     }        
} 


public class MyView extends View { 

    private final Bitmap baseBitmap = BitmapFactory.decodeResource(
      getResources(), R.drawable.myImage); 
    private final Matrix matrix; 
    private boolean active = true; 

    public MyView(Context context, Matrix matrix) { 
     super(context); 
     this.matrix = matrix; 
     this.setFocusable(true); 
    } 

    @Override 
    protected void onDraw(Canvas canvas) { 
     super.onDraw(canvas); 
     if (active) { 
      System.out.println("draw "+this.getId()); 
      canvas.drawBitmap(baseBitmap, matrix, null); 
     } else { 
     ... 
     } 
    } 


    @Override 
    public boolean onTouchEvent(MotionEvent event) { 
     if (event.getAction() == MotionEvent.ACTION_DOWN) { 
      System.out.println("--------->"+this.getId()); 
     } else if (event.getAction() == MotionEvent.ACTION_MOVE) { 
      this.matrix.setTranslate(event.getX()-(baseBitmap.getWidth()/2), event.getY()-(baseBitmap.getHeight()/2)); 
      this.invalidate(); 
     } else if (event.getAction() == MotionEvent.ACTION_UP) { 

      this.active = false; 
     } 
     return true; 
    } 


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

      int widthMode = MeasureSpec.getMode(widthMeasureSpec); 
      int widthSize = MeasureSpec.getSize(widthMeasureSpec); 

      int heightMode = MeasureSpec.getMode(heightMeasureSpec); 
      int heightSize = MeasureSpec.getSize(heightMeasureSpec); 

      int chosenWidth = chooseDimension(widthMode, widthSize); 
      int chosenHeight = chooseDimension(heightMode, heightSize); 

      int chosenDimension = Math.min(chosenWidth, chosenHeight); 

      setMeasuredDimension(chosenDimension, chosenDimension); 
     } 

     private int chooseDimension(int mode, int size) { 
      if (mode == MeasureSpec.AT_MOST || mode == MeasureSpec.EXACTLY) { 
       return size; 
      } else { // (mode == MeasureSpec.UNSPECIFIED) 
       return getPreferredSize(); 
      } 
     } 

     // in case there is no size specified 
     private int getPreferredSize() { 
      return 300; 
     } 
} 

main.xml中:

<?xml version="1.0" encoding="utf-8"?> 
<RelativeLayout android:id="@+id/main_view" 
    xmlns:android="http://schemas.android.com/apk/res/android" 
    android:layout_width="fill_parent" 
    android:layout_height="fill_parent" 
    android:background="#FF66FF33"> 
    </RelativeLayout> 

我敢肯定那是因为你基本上是在你RelativeLayout的左上角堆积如山的意见。所以,只有最上面的(最后一个)是可触摸的。

我认为,如果你试图将其添加到LinearLayout,作为一个测试,你会看到你的观点的作品。以编程方式为RelativeLayout设置LayoutParams不是很舒服的恕我直言。

编辑

我想你的代码。事实是,你的意见只是提出要绘制一个比其他,否则整体绘图不会来,所以我的第一个猜测是正确的(最上层覆盖了别人 - 即使在其透明部分)(顺便说一句尝试层次浏览器,你可以看到你自己)。所以,你需要做你的工作在一个单一的视图,或者处理触摸这样的:

@Override 
public boolean onTouchEvent(MotionEvent event) { 
    if (event.getAction() == MotionEvent.ACTION_DOWN) { 
     if(!isPetaloTouched()) {// check if the actual drawing was touched 
      return false; // discard the event so that it reaches 
          // the underlying view 
     } 
//...... 

的事件在Android中如何工作的说明,请参见this post

这两种方法都需要一个isPetaloTouched()逻辑以检测是否/哪些绘图必须移动,但第一个将是更有效的,当然。

另外,忘记onMeasure()的事情,我认为这可以帮助给视图大小包装,以便它不会填充它的父母,并将意见调整到一边是合理的。但是,如果视图没有堆积起来,请确保触摸可以工作。

(...每petali allora mPetali Stava的PROPRIO!)

+0

使用的LinearLayout我得到的只是第一种观点,所以我试图用RelativeLayout.LayoutParams,所以我试图用RelativeLayout.LayoutParams如下 RelativeLayout的。LayoutParams params = new RelativeLayout.LayoutParams(LayoutParams.FILL_PARENT,LayoutParams.WRAP_CONTENT);如果(i> 0){ params.addRule(RelativeLayout.ALIGN_LEFT,i-1); } myView.setLayoutParams(params); mainLayout.addView(myView,i); 但它仍然无法正常工作。 – vilandra 2011-04-06 16:04:44

+0

@vilandra:在'params.addRule()'你需要传递视图的id(你用'getId()'得到的),而不是它的索引作为布局的子元素。 LinearLayout可能没有工作,因为你忘了设置android:orientation =“vertical”。但是,如果它仍然不起作用,您是否可以使用Hierarchy Viewer来检查您的视图是否占用了所有空间?您可能需要在自定义视图中重写'onMeasure()'。 – bigstones 2011-04-06 20:03:26

+0

@bigstones:没有办法与LinearLayout和垂直方向,没有办法重写onMeasure(),没有办法保存在while内部的previuos MyView对象,并调用getId insted使用索引(这是相同的事情因为我使用索引setId , 我想)。 我真的不知道这可能是什么问题。 发布包含onMeasure方法的代码可能有用吗? – vilandra 2011-04-07 21:21:53