У меня есть следующий метод Draw:
@Override
protected void onDraw(Canvas canvas) {
// super.onDraw(canvas);
canvas.drawBitmap(bitmap, 0, 0, mBitmapPaint); //Deseneaza Bitmapul mutabil
if (PaintActivity.isPic == 1) {
rect = new Rect((int)mX, (int)mY, ((int)mX+bitmaps.get(lastBitmap).bitmap.getWidth()), ((int)mY+bitmaps.get(lastBitmap).bitmap.getHeight()));
rectscale = new Rect((int)mX-20, (int)mY-20, (int)mX+20, (int)mY+20);
rectrotate = new Rect((int)((mX+bitmaps.get(lastBitmap).bitmap.getWidth())-20), (int)mY-20, (int)(mX+bitmaps.get(lastBitmap).bitmap.getHeight()+20), (int)mY+20);
for(int i=0;i<bitmaps.size();i++){
if((lastBitmap != i)&& (bitmaps.get(i)!= null) ){
if(bitmaps.get(i).isRotate){
matrixRotate.setRotate(bitmaps.get(i).rectrotateVal, bitmaps.get(i).pX+(bitmaps.get(i).bitmap.getWidth() / 2), bitmaps.get(i).pY+(bitmaps.get(i).bitmap.getHeight() / 2)); //rotate it
}else{
matrixRotate.setRotate(0, bitmaps.get(i).pX+(bitmaps.get(i).bitmap.getWidth() / 2), bitmaps.get(i).pY+(bitmaps.get(i).bitmap.getHeight() / 2)); //rotate it
}
canvas.setMatrix(matrixRotate);
canvas.drawBitmap(bitmaps.get(i).bitmap, bitmaps.get(i).pX, bitmaps.get(i).pY, mBitmapPaint);
canvas.setMatrix(null);
canvas.drawCircle(bitmaps.get(i).pX, bitmaps.get(i).pY, 10, cPaint);
canvas.drawCircle(bitmaps.get(i).pX+bitmaps.get(i).bitmap.getWidth(), bitmaps.get(i).pY, 10, cPaint);
}
}
if (bitmaps.get(lastBitmap).bitmap != null) {
bitmaps.get(lastBitmap).rectscale = rectscale;
bitmaps.get(lastBitmap).rectrotate = rectrotate;
if(isScalling){
rect = new Rect((int)mX,(int) mY, (int)tempx, (int)tempy);
int w = Math.abs(rect.width());
int h = Math.abs(rect.height());
canvas.drawRect(rect, rPaint);
if((w!=0)&&(h!=0)){
bitmaps.get(lastBitmap).bitmap = getResizedBitmap(bitmaps.get(lastBitmap).bitmap2, h, w, bitmaps.get(lastBitmap).bitmap.getConfig());
}
}
if(isRotating){
rotateVal = (float) 45;
bitmaps.get(lastBitmap).rectrotateVal = rotateVal;
bitmaps.get(lastBitmap).isRotate = isRotating;
matrixRotate.setRotate(rotateVal, mX+(bitmaps.get(lastBitmap).bitmap.getWidth() / 2), mY+(bitmaps.get(lastBitmap).bitmap.getHeight() / 2)); //rotate it
canvas.setMatrix(matrixRotate);
canvas.drawBitmap(bitmaps.get(lastBitmap).bitmap, mX, mY, mBitmapPaint);
canvas.setMatrix(null);
canvas.drawCircle(bitmaps.get(lastBitmap).pX+bitmaps.get(lastBitmap).bitmap.getWidth(), bitmaps.get(lastBitmap).pY, 10, cPaint);
canvas.drawRect(bitmaps.get(lastBitmap).rect, rPaint);
}else{
canvas.drawBitmap(bitmaps.get(lastBitmap).bitmap, mX, mY, mBitmapPaint);
canvas.drawCircle(mX, mY, 10, cPaint);
canvas.drawCircle(mX+bitmaps.get(lastBitmap).bitmap.getWidth(), mY, 10, cPaint);
}
bitmaps.get(lastBitmap).pX = mX;
bitmaps.get(lastBitmap).pY = mY;
bitmaps.get(lastBitmap).rect = rect;
bitmaps.get(lastBitmap).rectscale = rectscale;
bitmaps.get(lastBitmap).rectrotate = rectrotate;
}
for(int j=0;j<textArray.size();j++){
if (textArray.get(j) != null) {
canvas.drawText(textArray.get(j), tXArray.get(j), tYArray.get(j), textPaintArray.get(j));
}
}
}
У меня есть несколько растровых изображений, прямоугольный прямоугольник имеет ту же ширину и высоту, что и изображение, поэтому, если я нажимаю изображение, оно устанавливает меня на него, чтобы переместить его. rectscale = это прямоугольник, расположенный в левом верхнем углу изображения, где я рисую круг, если я нажму на круг, я могу масштабировать свое изображение. rectrotate = то же самое, но в правом верхнем углу изображения. я нажимаю на нее, моя картинка поворачивается на 45 градусов. У меня есть следующие события касания:
private void touch_start(float x, float y) {
mPath.reset();
mPath.moveTo(x, y);
canvas.drawPoint(x, y, paint);
mX = x;
mY = y;
if(PaintActivity.isPic == 1){
if(bitmaps.size() > 0){
for(int i = 0;i<(bitmaps.size()-1);i++){
if(bitmaps.get(i).rect.contains((int)mX,(int) mY)){
lastBitmap = i;
}
}
}
if(bitmaps.size() > 0){
for(int i = 0;i<(bitmaps.size());i++){
if(bitmaps.get(i).rectscale.contains((int)mX,(int) mY)){
lastBitmap = i;
isScalling = true;
tempx = mX+bitmaps.get(lastBitmap).bitmap.getWidth();
tempy = mY+bitmaps.get(lastBitmap).bitmap.getHeight();
}
}
}
if(bitmaps.size() > 0){
for(int i = 0;i<(bitmaps.size());i++){
if(bitmaps.get(i).rectrotate.contains((int)mX,(int) mY)){
lastBitmap = i;
isRotating = true;
}
}
}
}
}
private void touch_move(float x, float y) {
float dx = Math.abs(x - mX);
float dy = Math.abs(y - mY);
if ((dx >= TOUCH_TOLERANCE) || (dy >= TOUCH_TOLERANCE)) {
mPath.quadTo(mX, mY, (x + mX) / 2, (y + mY) / 2);
mX = x;
mY = y;
Log.d("move", "mx, my=" + mX + " " + mY);
// mPath.moveTo(mX, mY);
}
// invalidate();
}
private void touch_up() {
mPath.lineTo(mX, mY);
mPath.moveTo(mX, mY);
// commit the path to our offscreen
canvas.drawPath(mPath, paint);
// canvas.save();
// kill this so we don't double draw
mPath.reset();
if(PaintActivity.isPic == 1){
if(isScalling){
isScalling = false;
}
if(isRotating){
isRotating = false;
}
lastBitmap = bitmaps.size()-1;
mX= bitmaps.get(lastBitmap).pX;
mY= bitmaps.get(lastBitmap).pY;
}
}
@Override
public boolean onTouchEvent(MotionEvent event) {
float x = event.getX();
float y = event.getY();
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
touch_start(x, y);
invalidate();
break;
case MotionEvent.ACTION_MOVE:
touch_move(x, y);
invalidate();
break;
case MotionEvent.ACTION_UP:
touch_up();
invalidate();
break;
}
return true;
}
Если я прокомментирую следующие строки:
canvas.setMatrix(matrixRotate);
А ТАКЖЕ:
canvas.setMatrix(null);
Все работает, кроме вращения. Но если я их не комментирую, вращение работает, первая картинка в порядке, но на остальных картинках прямоугольники немного перепутались. Они не начинаются в левом верхнем углу растрового изображения (там, где находится мой масштабный круг), вместо этого они начинаются где-то ниже, почти на половине растрового изображения. Таким образом, я могу использовать свои функции масштабирования и поворота, но мне нужно угадать, куда поставить палец, потому что точка, в которой нарисован круг, не содержится в прямоугольниках. Любые идеи, как я могу это исправить?
РЕДАКТИРОВАТЬ: я пробовал: перед установкой матрицы на вращение матрицы:
origMatrix = canvas.getMatrix();
и вместо:
canvas.setMatrix(null);
Я старался:
canvas.setMatrix(origMatrix);
Он по-прежнему искажал мои прямоугольники, но, по крайней мере, теперь он рисует круги для вращения и масштабирования там, где находятся прямоугольники (обычно где-то в середине растрового изображения).