android上的一些游戏,设有方向键和功能键,当左手触摸方向键时,右手触摸功能键后仍能被系统响应。但据本人实践,屏幕处于触摸中状态时,再次触摸就不会被响应了(所有的TouchEvent、手势回调函数都不被响应,即使所触摸的点处于不同的view也一样)。请教这种异步多点触摸功能究竟是如何实现的。

解决方案 »

  1.   

     多点触摸,到底支持多少点的触摸是写在驱动里的。
    这个玩意Android系统本身可决策不了。
      

  2.   

    我试了下ipad的屏 支持10点, 我们项目中的设备支持5点。 
    你实践是什么实践在什么设备上? 呵呵...硬件驱动的过可不要怪在android头上。android在理论上是支持无限多点的,具体多少,得看硬件设备和驱动的编写。
      

  3.   


    不是点的数量的问题啦,在“触摸中”的状态下ipad还能响应之后的触摸事件吗?
    不是“同时”触摸哦。同时的话电容屏应该都支持的吧。我HTC_D_G10,整个HTC系列都支持该款游戏的,和设备关系不大的。
      

  4.   


    可以
    我说的就是这个意思
    在“触摸中”的状态下ipad还能响应之后的触摸事件
      

  5.   

    这是屏幕漂移引起的吧,并不是不响应另外一点,而是另外一点压根就不在那个位置了.
    觉得还是跟硬件驱动有关,HTC不少手机都有这问题.
      

  6.   

    TouchListner/ ClickListner/ GestureListsner 所有接口一个都不响应是不是要对view/activity进行什么设置来开启这个功能啊~
      

  7.   


    当前的问题是:上层app要通过哪个接口来捕捉这一个以上的数据包呢?
      

  8.   

    文档里面有哦
    getPointerCount()
    The number of pointers of data contained in this event.
    getPointerId(int pointerIndex)
    Return the pointer identifier associated with a particular pointer data index is this event.
    getX(int)
     for the first pointer index (may be an arbitrary pointer identifier).
    getX(int pointerIndex)
    Returns the X coordinate of this event for the given pointer index (use getPointerId(int) to find the pointer identifier for this index).等等等等  自己去看吧
      

  9.   


    这些都是MotionEvent里的吧,在onTouchEvent之类的接口里用的吧,
    但如果touch之后根本不响应onTouchEvent,又如何去调?
      

  10.   

    是不是思路要转换一下了,KeyEvent 里面要用getPointerCount来判断一下是几个点
      

  11.   


    始终是一个点,因为不是同时按下的。这么讲:
    1、在时间点A,按住屏幕上任意点PA不放。//这时候KeyEvent是响应的,getPointerCount应该是1
    2、在时间点A+n秒,在PA未放开的前提下,按屏幕上某点PB。//这时KeyEvent就没有响应了,也不存在getPointerCount一说了getPointerCount是以KeyEvent被响应为前提的。
      

  12.   

    楼主,我试过了,可以支持多点。
    模拟器是不支持多点的(没有2个鼠标去点),没有办法。
    我在我手机 I9000 上试过,最多支持5点同时触摸。我在另一个手机 moto milestone-1 上试,最多2点。
    我用 getPointerCount() 获得点数,然后用 for( int i = 0; i < getX( iCount ) ) 去取所有的点,是可以取到的。
      

  13.   


    响应的哪个函数?TouchEvent还是KeyEvent?
      

  14.   

    哥专门找了android源码里的那个PointerLocation程序源码看了一下你自己看看:
      public void addTouchEvent(MotionEvent event) {
            synchronized (mPointers) {
                int action = event.getAction();
                
                //Log.i("Pointer", "Motion: action=0x" + Integer.toHexString(action)
                //        + " pointers=" + event.getPointerCount());
                
                int NP = mPointers.size();
                
                //mRect.set(0, 0, getWidth(), mHeaderBottom+1);
                //invalidate(mRect);
                //if (mCurDown) {
                //    mRect.set(mCurX-mCurWidth-3, mCurY-mCurWidth-3,
                //            mCurX+mCurWidth+3, mCurY+mCurWidth+3);
                //} else {
                //    mRect.setEmpty();
                //}
                if (action == MotionEvent.ACTION_DOWN) {
                    for (int p=0; p<NP; p++) {
                        final PointerState ps = mPointers.get(p);
                        ps.mXs.clear();
                        ps.mYs.clear();
                        ps.mVelocity = VelocityTracker.obtain();
                        ps.mCurDown = false;
                    }
                    mPointers.get(0).mCurDown = true;
                    mMaxNumPointers = 0;
                    if (mPrintCoords) {
                        Log.i("Pointer", "Pointer 1: DOWN");
                    }
                }
                
                if ((action&MotionEvent.ACTION_MASK) == MotionEvent.ACTION_POINTER_DOWN) {
                    final int index = (action&MotionEvent.ACTION_POINTER_INDEX_MASK)
                            >> MotionEvent.ACTION_POINTER_INDEX_SHIFT;
                    final int id = event.getPointerId(index);
                    while (NP <= id) {
                        PointerState ps = new PointerState();
                        ps.mVelocity = VelocityTracker.obtain();
                        mPointers.add(ps);
                        NP++;
                    }
                    final PointerState ps = mPointers.get(id);
                    ps.mVelocity = VelocityTracker.obtain();
                    ps.mCurDown = true;
                    if (mPrintCoords) {
                        Log.i("Pointer", "Pointer " + (id+1) + ": DOWN");
                    }
                }
                
                final int NI = event.getPointerCount();
                
                mCurDown = action != MotionEvent.ACTION_UP
                        && action != MotionEvent.ACTION_CANCEL;
                mCurNumPointers = mCurDown ? NI : 0;
                if (mMaxNumPointers < mCurNumPointers) {
                    mMaxNumPointers = mCurNumPointers;
                }
                
                for (int i=0; i<NI; i++) {
                    final int id = event.getPointerId(i);
                    final PointerState ps = mPointers.get(id);
                    ps.mVelocity.addMovement(event);
                    ps.mVelocity.computeCurrentVelocity(1);
                    final int N = event.getHistorySize();
                    for (int j=0; j<N; j++) {
                        if (mPrintCoords) {
                            Log.i("Pointer", "Pointer " + (id+1) + ": ("
                                    + event.getHistoricalX(i, j)
                                    + ", " + event.getHistoricalY(i, j) + ")"
                                    + " Prs=" + event.getHistoricalPressure(i, j)
                                    + " Size=" + event.getHistoricalSize(i, j));
                        }
                        ps.mXs.add(event.getHistoricalX(i, j));
                        ps.mYs.add(event.getHistoricalY(i, j));
                    }
                    if (mPrintCoords) {
                        Log.i("Pointer", "Pointer " + (id+1) + ": ("
                                + event.getX(i) + ", " + event.getY(i) + ")"
                                + " Prs=" + event.getPressure(i)
                                + " Size=" + event.getSize(i));
                    }
                    ps.mXs.add(event.getX(i));
                    ps.mYs.add(event.getY(i));
                    ps.mCurX = (int)event.getX(i);
                    ps.mCurY = (int)event.getY(i);
                    //Log.i("Pointer", "Pointer #" + p + ": (" + ps.mCurX
                    //        + "," + ps.mCurY + ")");
                    ps.mCurPressure = event.getPressure(i);
                    ps.mCurSize = event.getSize(i);
                    ps.mCurWidth = (int)(ps.mCurSize*(getWidth()/3));
                }
                
                if ((action&MotionEvent.ACTION_MASK) == MotionEvent.ACTION_POINTER_UP) {
                    final int index = (action&MotionEvent.ACTION_POINTER_INDEX_MASK)
                            >> MotionEvent.ACTION_POINTER_INDEX_SHIFT;
                    final int id = event.getPointerId(index);
                    final PointerState ps = mPointers.get(id);
                    ps.mXs.add(Float.NaN);
                    ps.mYs.add(Float.NaN);
                    ps.mCurDown = false;
                    if (mPrintCoords) {
                        Log.i("Pointer", "Pointer " + (id+1) + ": UP");
                    }
                }
                
                if (action == MotionEvent.ACTION_UP) {
                    for (int i=0; i<NI; i++) {
                        final int id = event.getPointerId(i);
                        final PointerState ps = mPointers.get(id);
                        if (ps.mCurDown) {
                            ps.mCurDown = false;
                            if (mPrintCoords) {
                                Log.i("Pointer", "Pointer " + (id+1) + ": UP");
                            }
                        }
                    }
                }
                
                //if (mCurDown) {
                //    mRect.union(mCurX-mCurWidth-3, mCurY-mCurWidth-3,
                //            mCurX+mCurWidth+3, mCurY+mCurWidth+3);
                //}
                //invalidate(mRect);
                postInvalidate();
            }
        }
        @Override
        public boolean onTouchEvent(MotionEvent event) {
            addTouchEvent(event);
            return true;
        }
      

  15.   

    楼主,你直接在你的 Activity 里重载 onTouchEvent 函数:
    @Override public boolean onTouchEvent(MotionEvent event)
    {
       // TODO Auto-generated method stub
       super.onTouchEvent(event);   // 取触摸点
       int iCount = event.getPointerCount();   -> 总的触摸点数   int i;
       for( i = 0; i < iCount; ++i )
       {
          float x = event.getX( i );
          float y = event.getY( i );      int iPtID = event.getPointerId(i);  // 本触摸的编号 (比如你同时有3个点触摸,同时滑动,这个编号可以告诉你前后滑动的点之间的对应关系)   }   

    另外,如果你用 eclipse, 那你可以在你 Activity 代码里点右键,选择“Source”,然后选择 implements .... (我不记得具体怎么写了),然后直接勾选 onTouchEvent。
      

  16.   


    出结果了,原来第一下之后走的都是Activity里的接口,而且还要配合View::onTouchEvent的返回值。怪不得之前死活试不出。谢谢各位。俺去深入了,嘻嘻。
      

  17.   

    不用配合 View。 View 里也有 onTouchEvent, 如果你 View 里没做 onTouchEvent, 那么你应该在 Acivity 里做。总之, View 和 Acivity 里都有 onTouchEvent,都可以接收到触摸。顺序是 View -> Acivity。