2010-11-19 26 views
8

Vì vậy, tôi đang phát triển một ứng dụng phải xử lý cảm ứng đa điểm. Về cơ bản tôi muốn liên lạc duy nhất để quay (điều này là không có vấn đề). Và cảm ứng đa điểm để cuộn.Cách mã cho multitouch

Tôi có mã cơ bản, nhưng tôi gặp sự cố khi thay đổi từ đơn sang cảm ứng đa điểm và ngược lại, xảy ra. Về cơ bản, chuyển động sẽ nổi lên vì vị trí trung bình của cảm ứng đa điểm (hai ngón tay) và vị trí tuyệt đối của ngón tay đơn lẻ ở khoảng cách xa. Vì vậy, nếu tôi có hai ngón tay trên màn hình, chúng tạo thành một vị trí trung bình, và sau đó nhấc một ngón tay, nó sẽ giống như một chuyển động nhanh từ vị trí trung bình đó đến vị trí ngón tay duy nhất tuyệt đối. Đây sẽ là phong trào mà tôi không muốn.

Đây là mã của tôi:

@Override 
public boolean onTouchEvent(MotionEvent event) { 
    float xEvent[] = new float[ 2 ]; 
    float yEvent[] = new float[ 2 ]; 
    switch(event.getPointerCount()) { 
     case 1: 
      xEvent[ 0 ] = event.getX(0); 
      yEvent[ 0 ] = event.getY(0); 
      switch(event.getAction()) { 
       case MotionEvent.ACTION_DOWN: 
        camera.onTouchDown(xEvent[ 0 ], yEvent[ 0 ]); 
        return true; 
       case MotionEvent.ACTION_MOVE: 
        camera.onTouchRotate(xEvent[ 0 ], yEvent[ 0 ]); 
        return true; 
       default: return super.onTouchEvent(event); 
      } 
     case 2: 
      xEvent[ 0 ] = event.getX(0); 
      yEvent[ 0 ] = event.getY(0); 
      xEvent[ 1 ] = event.getX(1); 
      yEvent[ 1 ] = event.getY(1); 
      switch(event.getAction()) { 
       case MotionEvent.ACTION_DOWN: 
        camera.onTouchDown(((xEvent[ 0 ] + xEvent[ 1 ])/2), ((yEvent[ 0 ] + yEvent[ 1 ])/2)); 
        return true; 
       case MotionEvent.ACTION_MOVE: 
        camera.onTouchSlide(((xEvent[ 0 ] + xEvent[ 1 ])/2), ((yEvent[ 0 ] + yEvent[ 1 ])/2)); 
        return true; 
       case MotionEvent.ACTION_POINTER_1_UP: 
        camera.onTouchDown(xEvent[ 1 ], yEvent[ 1 ]); 
        return true; 
       case MotionEvent.ACTION_POINTER_2_UP: 
        camera.onTouchDown(xEvent[ 0 ], yEvent[ 0 ]); 
        return true; 
       default: return super.onTouchEvent(event); 
      } 
     default: return false; 
    } 
} 

Các onTouchDown chức năng của máy ảnh chỉ đặt giá trị đầu tiên của di chuyển cảm ứng. Đó là lý do tại sao tôi cũng sử dụng nó trong phong trào lên để thiết lập một giá trị mới bắt đầu cho các phong trào cảm ứng duy nhất khi đến từ một cảm ứng đa điểm.

Tôi hy vọng ai đó biết vấn đề của tôi là gì và có thể giúp tôi nhiều hơn nữa.

Trả lời

10

Bắt đầu ở đây nếu bạn chưa đọc nó rồi, nó đi qua một số điều đối phó với cảm ứng đa điểm trong Android: http://android-developers.blogspot.com/2010/06/making-sense-of-multitouch.html

Một vài điều về mã mà bạn đã viết:

  1. Bạn sẽ không bao giờ thấy ACTION_DOWN với số lượng con trỏ là 2. ACTION_DOWN chỉ được gửi cho con trỏ đầu tiên đi xuống. Tất cả các ngón tay chạm vào màn hình sau lần đầu tiên sẽ gửi ACTION_POINTER_DOWN.
  2. Đừng cho phép chạm tới 2 ngón tay, có thể dễ dàng hơn.
  3. Đó là dễ dàng hơn nhiều để làm việc với các hành động đeo mặt nạ (sử dụng MotionEvent#getActionMasked()) hơn là mã cho mỗi chỉ số trỏ riêng.
  4. Cuối cùng, chỉ số chỉ vấn đề để kéo dữ liệu ra khỏi một MotionEvent. Nếu bạn đang theo dõi chuyển động của con trỏ theo thời gian, hãy sử dụng ID con trỏ.
  5. ID con trỏ chỉ là số. Đừng đưa ra các giả định về giá trị mà chúng sẽ có khác hơn là chúng sẽ là số nguyên từ 0 trở lên.
+0

Thanx! Tôi vừa hoàn thành một triển khai hoạt động 80%. Nhưng sau khi đọc liên kết đó, tôi nghĩ rằng tôi có thể làm tốt hơn bằng cách sử dụng mặt nạ và id. – Espen

2

Bạn có thể giải quyết việc này với toán học đơn giản, mặc dù có thể có một cách tốt hơn đã được xây dựng trong.

Chỉ cần tạo một đối tượng chứa vị trí của mỗi ngón tay khi sự kiện cháy .ACTION_POINTER_X_UP và một đối tượng boolean chứa loại touchmode bạn sử dụng lần cuối.

case MotionEvent.ACTION_POINTER_1_UP: 
     camera.onTouchDown(xEvent[ 1 ], yEvent[ 1 ]); 
     boolean usedMultiTouch = true; 
     int x = event.getX(1); 
     int y = event.getY(1); 
     return true; 

Tiếp theo, câu lệnh ACTION_MOVE (bên trong case = 1) sẽ di chuyển khi người dùng di chuyển ngón tay khi họ chạm từ nhiều lần.

Bây giờ, tùy thuộc vào những gì bạn muốn làm, bạn có thể bỏ qua các động thái duy nhất (boolean là séc của bạn) cho đến khi sự kiện cháy .ACTION_UP và bạn đặt boolean trở lại sai

hoặc

bạn gọi phương thức thực hiện một số phép tính dựa trên giá trị vị trí đã lưu và ngón tay vẫn còn trên màn hình. Toán học khá dễ, nhưng tôi không biết bạn thực sự muốn làm gì.

Các vấn đề liên quan