Android图像视图矩阵比例+翻译

Vin*_*rat 30 android transformation matrix imageview

我试图手动获取图像视图内部的图像并适合屏幕.我需要用矩阵来做(我稍后会动态地改变矩阵变换).

问题是我无法将图像置于视图中心(比例尺是合适的).这是代码:

// Compute the scale to choose (this works)
float scaleX = (float) displayWidth / (float) imageWidth;
float scaleY = (float) displayHeight / (float) imageHeight;
float minScale = Math.min(scaleX, scaleY);

// tx, ty should be the translation to take the image back to the screen center
float tx = Math.max(0, 
        0.5f * ((float) displayWidth - (minScale * imageWidth)));
float ty = Math.max(0, 
        0.5f * ((float) displayHeight - (minScale * imageHeight)));

// Compute the matrix
Matrix m = new Matrix();
m.reset();

// Middle of the image should be the scale pivot
m.postScale(minScale, imageWidth/2, imageHeight/2);

// Translate
m.postTranslate(tx, ty);

imageView.setImageMatrix(m);
Run Code Online (Sandbox Code Playgroud)

上面的代码可以工作,如果我没有将比例放在图像中心上(但我需要稍后再做,所以我现在需要弄清楚公式).

我认为执行以下操作可以解决问题,但图像仍然偏移(朝向底部和右侧).

tx += 0.5*imageWidth*minScale;
ty += 0.5*imageHeight*minScale;
Run Code Online (Sandbox Code Playgroud)

我有一些值: - 图像:200x133 - 显示:800x480 - minScale:2.4 - 图像的最后左上角:100,67(应为17,1)

Joa*_*elt 67

有一个方便的方法叫做Matrix.setRectToRect(RectF,RectF,ScaleToFit)来帮助你.

Matrix m = imageView.getImageMatrix();
RectF drawableRect = new RectF(0, 0, imageWidth, imageHeight);
RectF viewRect = new RectF(0, 0, imageView.getWidth(), imageView.getHeight());
m.setRectToRect(drawableRect, viewRect, Matrix.ScaleToFit.CENTER);
imageView.setImageMatrix(m);
Run Code Online (Sandbox Code Playgroud)

这应该将矩阵设置m为具有缩放和组合所需的值的组合,以显示可绘制的居中并适合ImageView小部件.

  • 仔细考虑上述情况,getImageMatrix()docs声明"不要在适当的位置更改此矩阵.如果要将不同的矩阵应用于drawable,请务必调用setImageMatrix()".但是,如果局部矩阵mMatrix.equals(传入矩阵),setImageMatrix()会进行检查并且不会使视图无效.因此我建议:Matrix m = new Matrix(); m.reset(); 在这个实例中的getImageMatrix(). (6认同)
  • @joakime图像不显示.然后,当我点击图像一次时,它将显示但不会居中并与其视图相匹配.我正在使用TouchImageView(源代码在这里https://github.com/gabu/AndroidSDK-RecipeBook/blob/master/Recipe060/src/com/example/android/recipe060/TouchImageView.java) (2认同)

Vin*_*rat 5

以下是我使用矩阵解决问题的方法(joakime在另一个答案中请求):

private void setImageTransformation(float tx, float ty, float scale) {
    savedMatrix.reset();
    savedMatrix.postTranslate(-imageWidth / 2f, -imageHeight / 2f);
    savedMatrix.postScale(scale, scale);
    savedMatrix.postTranslate(tx, ty);
    imageView.setImageMatrix(savedMatrix);
}

public void resetImageMatrix() {
    if (!isImageLoaded()) return;

    imageWidth = imageView.getDrawable().getIntrinsicWidth();
    imageHeight = imageView.getDrawable().getIntrinsicHeight();

    float scaleX = (float) displayWidth / (float) imageWidth;
    float scaleY = (float) displayHeight / (float) imageHeight;
    minScale = Math.min(scaleX, scaleY);
    maxScale = 2.5f * minScale;

    initialTranslation.set(
              Math.max(0, 
                minScale * imageWidth / 2f 
                + 0.5f * (displayWidth - (minScale * imageWidth))), 
              Math.max(0, 
                minScale * imageHeight / 2f
                + 0.5f * (displayHeight - (minScale * imageHeight))));

    currentScale = minScale;
    currentTranslation.set(initialTranslation);
    initialImageRect.set(0, 0, imageWidth, imageHeight);

    setImageTransformation(initialTranslation.x, initialTranslation.y, 
                minScale);
}
Run Code Online (Sandbox Code Playgroud)

我在这里作弊有点因为捏不是用户手指之间的中心,这在我的情况下是可以接受的.

  • 什么是initialTranslation,savedMatrix,displayWidth,displayHeight? (4认同)