下面列出了android.graphics.Matrix#preTranslate ( ) 实例代码,或者点击链接到github查看源代码,也可以在右侧发表评论。
/**
* Sets a matrix such that given a rotation, it transforms that rotation's logical coordinates
* to physical coordinates.
*
* @param rotation the rotation to which the matrix should transform
* @param out the matrix to be set
*/
public static void transformLogicalToPhysicalCoordinates(@Rotation int rotation,
@Dimension int physicalWidth, @Dimension int physicalHeight, Matrix out) {
switch (rotation) {
case ROTATION_0:
out.reset();
break;
case ROTATION_90:
out.setRotate(90);
out.preTranslate(0, -physicalWidth);
break;
case ROTATION_180:
out.setRotate(180);
out.preTranslate(-physicalWidth, -physicalHeight);
break;
case ROTATION_270:
out.setRotate(270);
out.preTranslate(-physicalHeight, 0);
break;
default:
throw new IllegalArgumentException("Unknown rotation: " + rotation);
}
}
static void offsetDescendantMatrix(ViewParent target, View view, Matrix m) {
final ViewParent parent = view.getParent();
if (parent instanceof View && parent != target) {
final View vp = (View) parent;
offsetDescendantMatrix(target, vp, m);
m.preTranslate(-vp.getScrollX(), -vp.getScrollY());
}
m.preTranslate(view.getLeft(), view.getTop());
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB) {
if (!view.getMatrix().isIdentity()) {
m.preConcat(view.getMatrix());
}
}
}
public static Bitmap rotate(Bitmap original, final int angle) {
if ((angle % 360) == 0) {
return original;
}
final boolean dimensionsChanged = angle == 90 || angle == 270;
final int oldWidth = original.getWidth();
final int oldHeight = original.getHeight();
final int newWidth = dimensionsChanged ? oldHeight : oldWidth;
final int newHeight = dimensionsChanged ? oldWidth : oldHeight;
Bitmap bitmap = Bitmap.createBitmap(newWidth, newHeight, original.getConfig());
Canvas canvas = new Canvas(bitmap);
Matrix matrix = new Matrix();
matrix.preTranslate((newWidth - oldWidth) / 2f, (newHeight - oldHeight) / 2f);
matrix.postRotate(angle, bitmap.getWidth() / 2f, bitmap.getHeight() / 2);
canvas.drawBitmap(original, matrix, null);
original.recycle();
return bitmap;
}
@Override
protected void applyTransformation(float interpolatedTime, Transformation t) {
final float fromDegrees = mFromDegrees;
float degrees = fromDegrees + ((mToDegrees - fromDegrees) * interpolatedTime);
final float centerX = mCenterX;
final float centerY = mCenterY;
final Camera camera = mCamera;
final Matrix matrix = t.getMatrix();
camera.save();
if (mReverse) {
camera.translate(0.0f, 0.0f, mDepthZ * interpolatedTime);
} else {
camera.translate(0.0f, 0.0f, mDepthZ * (1.0f - interpolatedTime));
}
camera.rotateY(degrees);
camera.getMatrix(matrix);
camera.restore();
matrix.preTranslate(-centerX, -centerY);
matrix.postTranslate(centerX, centerY);
}
/**
* 旋转Bitmap为一定的角度并四周暗化处理.
*
* @param bitmap the bitmap
* @param degrees the degrees
* @return the bitmap
*/
public static Bitmap rotateBitmapTranslate(Bitmap bitmap, float degrees) {
Bitmap mBitmap = null;
int width;
int height;
try {
Matrix matrix = new Matrix();
if ((degrees / 90) % 2 != 0) {
width = bitmap.getWidth();
height = bitmap.getHeight();
}
else {
width = bitmap.getHeight();
height = bitmap.getWidth();
}
int cx = width / 2;
int cy = height / 2;
matrix.preTranslate(-cx, -cy);
matrix.postRotate(degrees);
matrix.postTranslate(cx, cy);
} catch (Exception e) {
e.printStackTrace();
}
return mBitmap;
}
public Matrix getRotateMatrix() {
// By default this is an identity matrix.
Matrix matrix = new Matrix();
if (mRotation != 0) {
// We want to do the rotation at origin, but since the bounding
// rectangle will be changed after rotation, so the delta values
// are based on old & new width/height respectively.
int cx = mBitmap.getWidth() / 2;
int cy = mBitmap.getHeight() / 2;
matrix.preTranslate(-cx, -cy);
matrix.postRotate(mRotation);
matrix.postTranslate(getWidth() / 2, getHeight() / 2);
}
return matrix;
}
@Override
protected boolean getChildStaticTransformation(View child, Transformation t) {
int topCenterView = mHeightCenter - mChildrenHeightMiddle;
int childTop = Math.max(0,child.getTop());
float offset = (-childTop + topCenterView)/ (float) mSpaceBetweenViews;
final Matrix matrix = t.getMatrix();
if (offset != 0) {
float absOffset = Math.abs(offset);
t.clear();
t.setTransformationType(Transformation.TYPE_MATRIX);
float px = child.getLeft() + (child.getWidth()) / 2;
float py = child.getTop() + (child.getHeight()) / 2;
if (mTranslatateEnbabled){
matrix.setTranslate(mTranslate * absOffset, 0);
}
if (offset > 0) {
matrix.preTranslate(-px,0);
matrix.postTranslate(px,0);
} else {
matrix.preTranslate(-px, -py);
matrix.postTranslate(px, py);
}
}
return true;
}
static void offsetDescendantMatrix(ViewParent target, View view, Matrix m) {
final ViewParent parent = view.getParent();
if (parent instanceof View && parent != target) {
final View vp = (View) parent;
offsetDescendantMatrix(target, vp, m);
m.preTranslate(-vp.getScrollX(), -vp.getScrollY());
}
m.preTranslate(view.getLeft(), view.getTop());
if (!view.getMatrix().isIdentity()) {
m.preConcat(view.getMatrix());
}
}
public Matrix getRotateMatrix() {
// By default this is an identity matrix.
Matrix matrix = new Matrix();
if (mRotation != 0) {
// We want to do the rotation at origin, but since the bounding
// rectangle will be changed after rotation, so the delta values
// are based on old & new width/height respectively.
int cx = mBitmap.getWidth() / 2;
int cy = mBitmap.getHeight() / 2;
matrix.preTranslate(-cx, -cy);
matrix.postRotate(mRotation);
matrix.postTranslate(getWidth() / 2, getHeight() / 2);
}
return matrix;
}
public Matrix getRotateMatrix() {
// By default this is an identity matrix.
Matrix matrix = new Matrix();
if (mRotation != 0) {
// We want to do the rotation at origin, but since the bounding
// rectangle will be changed after rotation, so the delta values
// are based on old & new width/height respectively.
int cx = mBitmap.getWidth() / 2;
int cy = mBitmap.getHeight() / 2;
matrix.preTranslate(-cx, -cy);
matrix.postRotate(mRotation);
matrix.postTranslate(getWidth() / 2, getHeight() / 2);
}
return matrix;
}
@Override
protected void applyTransformation(float interpolatedTime, Transformation t) {
// Angle around the y-axis of the rotation at the given time
// calculated both in radians and degrees.
final double radians = Math.PI * interpolatedTime;
float degrees = (float) (180.0 * radians / Math.PI);
// Once we reach the midpoint in the animation, we need to hide the
// source view and show the destination view. We also need to change
// the angle by 180 degrees so that the destination does not come in
// flipped around
if (interpolatedTime >= 0.5f) {
degrees -= 180.f;
fromView.setVisibility(View.GONE);
toView.setVisibility(View.VISIBLE);
}
if (forward)
degrees = -degrees; // determines direction of rotation when
// flip begins
final Matrix matrix = t.getMatrix();
camera.save();
camera.rotateY(degrees);
camera.getMatrix(matrix);
camera.restore();
matrix.preTranslate(-centerX, -centerY);
matrix.postTranslate(centerX, centerY);
}
@Override
protected void applyTransformation(float interpolatedTime, Transformation t) {
super.applyTransformation(interpolatedTime, t);
Matrix matrix = t.getMatrix();
Camera camera = new Camera();
camera.save();
camera.rotateY(-180 * interpolatedTime);
camera.getMatrix(matrix);
camera.restore();
matrix.preTranslate(-mcenterX,-mcenterY);
matrix.postTranslate(mcenterX,mcenterY);
}
private void drawSun(Canvas canvas) {
Matrix matrix = mMatrix;
matrix.reset();
float dragPercent = mPercent;
if (dragPercent > 1.0f) { // Slow down if pulling over set height
dragPercent = (dragPercent + 9.0f) / 10;
}
float sunRadius = (float) mSunSize / 2.0f;
float sunRotateGrowth = SUN_INITIAL_ROTATE_GROWTH;
float offsetX = mSunLeftOffset;
float offsetY = mSunTopOffset + (mParent.getTotalDragDistance() / 2) * (1.0f - dragPercent)
// Move the sun up
- mTop; // Depending on Canvas position
float scalePercentDelta = dragPercent - SCALE_START_PERCENT;
if (scalePercentDelta > 0) {
float scalePercent = scalePercentDelta / (1.0f - SCALE_START_PERCENT);
float sunScale = 1.0f - (1.0f - SUN_FINAL_SCALE) * scalePercent;
sunRotateGrowth += (SUN_FINAL_ROTATE_GROWTH - SUN_INITIAL_ROTATE_GROWTH) * scalePercent;
matrix.preTranslate(offsetX + (sunRadius - sunRadius * sunScale),
offsetY * (2.0f - sunScale));
matrix.preScale(sunScale, sunScale);
offsetX += sunRadius;
offsetY = offsetY * (2.0f - sunScale) + sunRadius * sunScale;
} else {
matrix.postTranslate(offsetX, offsetY);
offsetX += sunRadius;
offsetY += sunRadius;
}
matrix.postRotate((isRefreshing ? -360 : 360) * mRotate * (isRefreshing ? 1 : sunRotateGrowth),
offsetX, offsetY);
canvas.drawBitmap(mSun, matrix, null);
}
public static void setRectToRect(Matrix matrix, RectF src, RectF dst, int rotation, Matrix.ScaleToFit align)
{
float tx, sx;
float ty, sy;
if (rotation == 90 || rotation == 270)
{
sx = dst.height() / src.width();
sy = dst.width() / src.height();
}
else
{
sx = dst.width() / src.width();
sy = dst.height() / src.height();
}
if (align != Matrix.ScaleToFit.FILL)
{
if (sx > sy)
{
sx = sy;
}
else
{
sy = sx;
}
}
tx = -src.left * sx;
ty = -src.top * sy;
matrix.setTranslate(dst.left, dst.top);
if (rotation == 90)
{
matrix.preRotate(90);
matrix.preTranslate(0, -dst.width());
}
else if (rotation == 180)
{
matrix.preRotate(180);
matrix.preTranslate(-dst.width(), -dst.height());
}
else if (rotation == 270)
{
matrix.preRotate(270);
matrix.preTranslate(-dst.height(), 0);
}
matrix.preScale(sx, sy);
matrix.preTranslate(tx, ty);
}
@Override
protected void applyTransformation(float interpolatedTime, Transformation t) {
final float fromDegrees = mFromDegrees;
float degrees = fromDegrees + ((mToDegrees - fromDegrees) * interpolatedTime);
final float centerX = mCenterX;
final float centerY = mCenterY;
final Camera camera = mCamera;
final Matrix matrix = t.getMatrix();
camera.save();
camera.rotateY(degrees);
camera.getMatrix(matrix);
camera.restore();
matrix.preTranslate(-centerX, -centerY);
matrix.postTranslate(centerX, centerY);
}
private void testGetMatrix(Canvas canvas) {
Path path = new Path();
path.addCircle(0, 0, 200, Path.Direction.CW); // 添加大矩形
PathMeasure measure = new PathMeasure(path, false);
Matrix matrix = new Matrix();
measure.getMatrix(measure.getLength() * currentValue, matrix, PathMeasure.TANGENT_MATRIX_FLAG | PathMeasure.POSITION_MATRIX_FLAG);
//考虑的时候 把角度先放到0度在考虑; 图片默认在左上角移动到该点 应该在该点之下;
matrix.preTranslate(-arraw.getWidth(), -arraw.getHeight() / 2);
canvas.drawBitmap(arraw, matrix, null);
canvas.drawPath(path, mDeafultPaint); // 绘制 Path
}
public PaintingData getPaintingData(RectF rect, boolean undo) {
int minX = (int) rect.left;
int minY = (int) rect.top;
int width = (int) rect.width();
int height = (int) rect.height();
GLES20.glGenFramebuffers(1, buffers, 0);
int framebuffer = buffers[0];
GLES20.glBindFramebuffer(GLES20.GL_FRAMEBUFFER, framebuffer);
GLES20.glGenTextures(1, buffers, 0);
int texture = buffers[0];
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, texture);
GLES20.glTexParameteri(GL10.GL_TEXTURE_2D, GL10.GL_TEXTURE_MIN_FILTER, GL10.GL_LINEAR);
GLES20.glTexParameteri(GL10.GL_TEXTURE_2D, GL10.GL_TEXTURE_MAG_FILTER, GL10.GL_LINEAR);
GLES20.glTexParameteri(GL10.GL_TEXTURE_2D, GL10.GL_TEXTURE_WRAP_S, GL10.GL_CLAMP_TO_EDGE);
GLES20.glTexParameteri(GL10.GL_TEXTURE_2D, GL10.GL_TEXTURE_WRAP_T, GL10.GL_CLAMP_TO_EDGE);
GLES20.glTexImage2D(GLES20.GL_TEXTURE_2D, 0, GLES20.GL_RGBA, width, height, 0, GLES20.GL_RGBA, GLES20.GL_UNSIGNED_BYTE, null);
GLES20.glFramebufferTexture2D(GLES20.GL_FRAMEBUFFER, GLES20.GL_COLOR_ATTACHMENT0, GLES20.GL_TEXTURE_2D, texture, 0);
GLES20.glViewport(0, 0, (int) size.width, (int) size.height);
if (shaders == null) {
return null;
}
Shader shader = shaders.get(undo ? "nonPremultipliedBlit" : "blit");
if (shader == null) {
return null;
}
GLES20.glUseProgram(shader.program);
Matrix translate = new Matrix();
translate.preTranslate(-minX, -minY);
float effective[] = GLMatrix.LoadGraphicsMatrix(translate);
float finalProjection[] = GLMatrix.MultiplyMat4f(projection, effective);
GLES20.glUniformMatrix4fv(shader.getUniform("mvpMatrix"), 1, false, FloatBuffer.wrap(finalProjection));
if (undo) {
GLES20.glUniform1i(shader.getUniform("texture"), 0);
GLES20.glActiveTexture(GLES20.GL_TEXTURE0);
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, getTexture());
} else {
GLES20.glUniform1i(shader.getUniform("texture"), 0);
GLES20.glActiveTexture(GLES20.GL_TEXTURE0);
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, bitmapTexture.texture());
GLES20.glActiveTexture(GLES20.GL_TEXTURE0);
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, getTexture());
}
GLES20.glClearColor(0, 0, 0, 0);
GLES20.glClear(GLES20.GL_COLOR_BUFFER_BIT);
GLES20.glBlendFunc(GLES20.GL_ONE, GLES20.GL_ONE_MINUS_SRC_ALPHA);
GLES20.glVertexAttribPointer(0, 2, GLES20.GL_FLOAT, false, 8, vertexBuffer);
GLES20.glEnableVertexAttribArray(0);
GLES20.glVertexAttribPointer(1, 2, GLES20.GL_FLOAT, false, 8, textureBuffer);
GLES20.glEnableVertexAttribArray(1);
GLES20.glDrawArrays(GLES20.GL_TRIANGLE_STRIP, 0, 4);
dataBuffer.limit(width * height * 4);
GLES20.glReadPixels(0, 0, width, height, GLES20.GL_RGBA, GLES20.GL_UNSIGNED_BYTE, dataBuffer);
PaintingData data;
if (undo) {
data = new PaintingData(null, dataBuffer);
} else {
Bitmap bitmap = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
bitmap.copyPixelsFromBuffer(dataBuffer);
data = new PaintingData(bitmap, null);
}
buffers[0] = framebuffer;
GLES20.glDeleteFramebuffers(1, buffers, 0);
buffers[0] = texture;
GLES20.glDeleteTextures(1, buffers, 0);
return data;
}
public PaintingData getPaintingData(RectF rect, boolean undo) {
int minX = (int) rect.left;
int minY = (int) rect.top;
int width = (int) rect.width();
int height = (int) rect.height();
GLES20.glGenFramebuffers(1, buffers, 0);
int framebuffer = buffers[0];
GLES20.glBindFramebuffer(GLES20.GL_FRAMEBUFFER, framebuffer);
GLES20.glGenTextures(1, buffers, 0);
int texture = buffers[0];
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, texture);
GLES20.glTexParameteri(GL10.GL_TEXTURE_2D, GL10.GL_TEXTURE_WRAP_S, GL10.GL_CLAMP_TO_EDGE);
GLES20.glTexParameteri(GL10.GL_TEXTURE_2D, GL10.GL_TEXTURE_WRAP_T, GL10.GL_CLAMP_TO_EDGE);
GLES20.glTexParameteri(GL10.GL_TEXTURE_2D, GL10.GL_TEXTURE_MIN_FILTER, GL10.GL_LINEAR);
GLES20.glTexParameteri(GL10.GL_TEXTURE_2D, GL10.GL_TEXTURE_MAG_FILTER, GL10.GL_NEAREST);
GLES20.glTexImage2D(GLES20.GL_TEXTURE_2D, 0, GLES20.GL_RGBA, width, height, 0, GLES20.GL_RGBA, GLES20.GL_UNSIGNED_BYTE, null);
GLES20.glFramebufferTexture2D(GLES20.GL_FRAMEBUFFER, GLES20.GL_COLOR_ATTACHMENT0, GLES20.GL_TEXTURE_2D, texture, 0);
GLES20.glViewport(0, 0, (int) size.width, (int) size.height);
if (shaders == null) {
return null;
}
Shader shader = shaders.get(undo ? "nonPremultipliedBlit" : "blit");
if (shader == null) {
return null;
}
GLES20.glUseProgram(shader.program);
Matrix translate = new Matrix();
translate.preTranslate(-minX, -minY);
float[] effective = GLMatrix.LoadGraphicsMatrix(translate);
float[] finalProjection = GLMatrix.MultiplyMat4f(projection, effective);
GLES20.glUniformMatrix4fv(shader.getUniform("mvpMatrix"), 1, false, FloatBuffer.wrap(finalProjection));
GLES20.glUniform1i(shader.getUniform("texture"), 0);
GLES20.glActiveTexture(GLES20.GL_TEXTURE0);
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, getTexture());
GLES20.glClearColor(0, 0, 0, 0);
GLES20.glClear(GLES20.GL_COLOR_BUFFER_BIT);
GLES20.glBlendFunc(GLES20.GL_ONE, GLES20.GL_ZERO);
GLES20.glVertexAttribPointer(0, 2, GLES20.GL_FLOAT, false, 8, vertexBuffer);
GLES20.glEnableVertexAttribArray(0);
GLES20.glVertexAttribPointer(1, 2, GLES20.GL_FLOAT, false, 8, textureBuffer);
GLES20.glEnableVertexAttribArray(1);
GLES20.glDrawArrays(GLES20.GL_TRIANGLE_STRIP, 0, 4);
dataBuffer.limit(width * height * 4);
GLES20.glReadPixels(0, 0, width, height, GLES20.GL_RGBA, GLES20.GL_UNSIGNED_BYTE, dataBuffer);
PaintingData data;
if (undo) {
data = new PaintingData(null, dataBuffer);
} else {
Bitmap bitmap = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
bitmap.copyPixelsFromBuffer(dataBuffer);
data = new PaintingData(bitmap, null);
}
buffers[0] = framebuffer;
GLES20.glDeleteFramebuffers(1, buffers, 0);
buffers[0] = texture;
GLES20.glDeleteTextures(1, buffers, 0);
return data;
}
@Override
protected boolean getChildStaticTransformation(View child, Transformation t) {
// We can cast here because FancyCoverFlowAdapter only creates wrappers.
FancyCoverFlowItemWrapper item = (FancyCoverFlowItemWrapper) child;
// Since Jelly Bean childs won't get invalidated automatically, needs to be added for the smooth coverflow animation
if (android.os.Build.VERSION.SDK_INT >= 16) {
item.invalidate();
}
final int coverFlowWidth = this.getWidth();
final int coverFlowCenter = coverFlowWidth / 2;
final int childWidth = item.getWidth();
final int childHeight = item.getHeight();
final int childCenter = item.getLeft() + childWidth / 2;
// Use coverflow width when its defined as automatic.
final int actionDistance = (this.actionDistance == ACTION_DISTANCE_AUTO) ? (int) ((coverFlowWidth + childWidth) / 2.0f) : this.actionDistance;
// Calculate the abstract amount for all effects.
final float effectsAmount = Math.min(1.0f, Math.max(-1.0f, (1.0f / actionDistance) * (childCenter - coverFlowCenter)));
// Clear previous transformations and set transformation type (matrix + alpha).
t.clear();
t.setTransformationType(Transformation.TYPE_BOTH);
// Alpha
if (this.unselectedAlpha != 1) {
final float alphaAmount = (this.unselectedAlpha - 1) * Math.abs(effectsAmount) + 1;
t.setAlpha(alphaAmount);
}
// Saturation
if (this.unselectedSaturation != 1) {
// Pass over saturation to the wrapper.
final float saturationAmount = (this.unselectedSaturation - 1) * Math.abs(effectsAmount) + 1;
item.setSaturation(saturationAmount);
}
final Matrix imageMatrix = t.getMatrix();
// Apply rotation.
if (this.maxRotation != 0) {
final int rotationAngle = (int) (-effectsAmount * this.maxRotation);
this.transformationCamera.save();
this.transformationCamera.rotateY(rotationAngle);
this.transformationCamera.getMatrix(imageMatrix);
this.transformationCamera.restore();
}
// Zoom.
if (this.unselectedScale != 1) {
final float zoomAmount = (this.unselectedScale - 1) * Math.abs(effectsAmount) + 1;
// Calculate the scale anchor (y anchor can be altered)
final float translateX = childWidth / 2.0f;
final float translateY = childHeight * this.scaleDownGravity;
imageMatrix.preTranslate(-translateX, -translateY);
imageMatrix.postScale(zoomAmount, zoomAmount);
imageMatrix.postTranslate(translateX, translateY);
}
return true;
}
private void a(Matrix matrix, View view)
{
float f1 = view.getWidth();
float f2 = view.getHeight();
boolean flag = d;
float f3;
float f4;
float f5;
float f6;
float f7;
float f8;
float f9;
if (flag)
{
f3 = f;
} else
{
f3 = f1 / 2.0F;
}
if (flag)
{
f4 = g;
} else
{
f4 = f2 / 2.0F;
}
f5 = h;
f6 = i;
f7 = j;
if (f5 != 0.0F || f6 != 0.0F || f7 != 0.0F)
{
Camera camera = c;
camera.save();
camera.rotateX(f5);
camera.rotateY(f6);
camera.rotateZ(-f7);
camera.getMatrix(matrix);
camera.restore();
matrix.preTranslate(-f3, -f4);
matrix.postTranslate(f3, f4);
}
f8 = k;
f9 = l;
if (f8 != 1.0F || f9 != 1.0F)
{
matrix.postScale(f8, f9);
matrix.postTranslate(-(f3 / f1) * (f8 * f1 - f1), -(f4 / f2) * (f9 * f2 - f2));
}
matrix.postTranslate(m, n);
}