简体   繁体   English

获取视图的边界/矩形

[英]Get draw bounds/rect of a view

I'm developing an app where a lot of views can be rotated - it's something like a map of physical objects. 我正在开发一个可以旋转许多视图的应用程序-有点像物理对象的地图。 I have to detect when 2 objects (all objects are rectangles/squares) are overlapping and if a user has performed a single/double/long tap on an object. 我必须检测2个对象(所有对象均为矩形/正方形)何时重叠以及用户是否对某个对象执行了单次/双击/长按。 For this reason I need to know the drawing bounds of a view. 因此,我需要知道视图的绘图范围。

Let's look at the example image bellow - the green rectangle is rotated 45 degrees. 让我们看下面的示例图像-绿色矩形旋转了45度。 I need to get the coordinates of the 4 corners of the green rectangle. 我需要获取绿色矩形的4个角的坐标。 If I use view.getHitRect() it returns the bounding box (marked in red) of the view, which is of no use to me. 如果我使用view.getHitRect(),它将返回视图的边界框(标记为红色),这对我没有用。

Do you know how could I get the coordinates of the edges of a view? 您知道如何获取视图边缘的坐标吗?

The only solution I could think of is to subclass a View, manually store the initial coordinates of the corners and calculate their new values on every modification to the view - translation, scale and rotation but I was wondering if there is a better method. 我能想到的唯一解决方案是对View进行子类化,手动存储拐角的初始坐标,并在对视图的每次修改(平移,缩放和旋转)上计算其新值,但我想知道是否有更好的方法。

PS The app should be working on Android 2.3 but 4.0+ solutions are also welcomed. PS该应用程序应可在Android 2.3上运行,但也欢迎4.0+解决方案。

情况示例

Thanks to pskink I explored again the Matrix.mapPoints method and managed to get the proper coordinates of the corners of the rectangle. 多亏了pskink,我再次探索了Matrix.mapPoints方法,并设法获得了矩形角的正确坐标。

If you are running on Android 3.0+ you can easily get the view's matrix by calling myView.getMatrix() and map the points of interest. 如果您在Android 3.0+上运行,则可以通过调用myView.getMatrix()并映射兴趣点来轻松获取视图的矩阵。 I had to use 0,0 for the upper left corner and getWidth(),getHeight() for the bottom right corner and map these coordinates to the matrix. 我必须对左上角使用0,0,对右下角使用getWidth(),getHeight()并将这些坐标映射到矩阵。 After that add view's X and Y values to get the real values of the corners. 之后,添加视图的X和Y值以获取角的真实值。

Something like: 就像是:

float points[] = new float[2];
        points[0] = myView.getWidth();
        points[1] = myView.getHeight();
        myView.getViewMatrix().mapPoints(points);

        Paint p = new Paint();
        p.setColor(Color.RED);
        //offset the point and draw it on the screen
        canvas.drawCircle(center.getX() + points[0], center.getY() + points[1], 5f, p);

If you have to support lower versions of Android you can use NineOldAndroids . 如果必须支持较低版本的Android,则可以使用NineOldAndroids Then I've copied and modified one of its internal methods to get the view's matrix: 然后,我复制并修改了其内部方法之一,以获取视图的矩阵:

public Matrix getViewMatrix()
{
    Matrix m = new Matrix();
    Camera mCamera = new Camera();

    final float w = this.getWidth();
    final float h = this.getHeight();
    final float pX = ViewHelper.getPivotX(this);
    final float pY = ViewHelper.getPivotY(this);

    final float rX = ViewHelper.getRotationX(this);;
    final float rY = ViewHelper.getRotationY(this);
    final float rZ = ViewHelper.getRotation(this);
    if ((rX != 0) || (rY != 0) || (rZ != 0)) 
    {
        final Camera camera = mCamera;
        camera.save();
        camera.rotateX(rX);
        camera.rotateY(rY);
        camera.rotateZ(-rZ);
        camera.getMatrix(m);
        camera.restore();
        m.preTranslate(-pX, -pY);
        m.postTranslate(pX, pY);
    }

    final float sX = ViewHelper.getScaleX(this);
    final float sY = ViewHelper.getScaleY(this);;
    if ((sX != 1.0f) || (sY != 1.0f)) {
        m.postScale(sX, sY);
        final float sPX = -(pX / w) * ((sX * w) - w);
        final float sPY = -(pY / h) * ((sY * h) - h);
        m.postTranslate(sPX, sPY);
    }

    m.postTranslate(ViewHelper.getTranslationX(this), ViewHelper.getTranslationY(this));

    return m;
}

I've put this method in an overloaded class of a view (in my case - extending TextView). 我已经将此方法放在视图的重载类中(在我的情况下是扩展TextView)。 From there on it's the same as in Android 3.0+ but instead of calling myView.getMatrix() you call myView.getViewMatrix(). 从那里开始,它与Android 3.0+中的相同,但是不调用myView.getMatrix(),而是调用myView.getViewMatrix()。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM