裁剪后的位图不适合中心。 (免提裁剪。)
Cropped Bitmap not fitting to the center. (Hand free cropping.)
我正在尝试使用绘图裁剪图像。并且按预期进行裁剪,但我认为不会将裁剪部分缩放到新位图的中心。你可以看到 2 图片 1. 图片是我现在拥有的。 2.图片是我所期望的。
原始图像。
我有什么
我需要什么
我在 SomeView 上裁剪并将点发送到 CropActivity,然后 CropActivity 裁剪图像并将其发送到 MainActivity。
这是我的CropActivity.Java
public class CropActivity extends Activity {
ImageView compositeImageView;
boolean crop;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.cropview);
Bundle extras = getIntent().getExtras();
if (extras != null) {
crop = extras.getBoolean("crop");
}
int widthOfscreen = 512;
int heightOfScreen = 512;
DisplayMetrics dm = new DisplayMetrics();
try {
getWindowManager().getDefaultDisplay().getMetrics(dm);
} catch (Exception ex) {
}
widthOfscreen = dm.widthPixels;
heightOfScreen = dm.heightPixels;
compositeImageView = (ImageView) findViewById(R.id.our_imageview);
Bitmap bitmap2 = SomeView.bitmap;
Bitmap resultingImage = Bitmap.createBitmap(widthOfscreen,
heightOfScreen, bitmap2.getConfig());
Canvas canvas = new Canvas(resultingImage);
Paint paint = new Paint();
paint.setAntiAlias(true);
Path path = new Path();
for (int i = 0; i < SomeView.points.size(); i++) {
path.lineTo(SomeView.points.get(i).x, SomeView.points.get(i).y);
}
canvas.drawPath(path, paint);
if (crop) {
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));
} else {
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_OUT));
}
canvas.drawBitmap(bitmap2, 0, 0, paint);
compositeImageView.setImageBitmap(resultingImage);
Button donb = findViewById(R.id.donb);
donb.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent returnIntent = new Intent();
ByteArrayOutputStream bStream = new ByteArrayOutputStream();
resultingImage.compress(Bitmap.CompressFormat.PNG, 100, bStream);
byte[] byteArray = bStream.toByteArray();
returnIntent.putExtra("result",byteArray);
setResult(2,returnIntent);
finish();
// donb.setText("Dondum");
}
});
}
}
这是我的SomeView.Java
public class SomeView extends View implements View.OnTouchListener {
private Paint paint;
public static List<Point> points;
int DIST = 2;
boolean flgPathDraw = true;
public static final int PICK_IMAGE = 1;
Point mfirstpoint = null;
boolean bfirstpoint = false;
Point mlastpoint = null;
public static Bitmap bitmap;
Context mContext;
public SomeView(Context c, Bitmap b) {
super(c);
bitmap = b;
mContext = c;
setFocusable(true);
setFocusableInTouchMode(true);
paint = new Paint(Paint.ANTI_ALIAS_FLAG);
paint.setStyle(Paint.Style.STROKE);
paint.setPathEffect(new DashPathEffect(new float[] { 10, 20 }, 0));
paint.setStrokeWidth(15);
paint.setColor(Color.GREEN);
this.setOnTouchListener(this);
points = new ArrayList<Point>();
bfirstpoint = false;
}
public SomeView(Context context, AttributeSet attrs) {
super(context, attrs);
mContext = context;
setFocusable(true);
setFocusableInTouchMode(true);
paint = new Paint(Paint.ANTI_ALIAS_FLAG);
paint.setStyle(Paint.Style.STROKE);
paint.setStrokeWidth(2);
paint.setColor(Color.WHITE);
this.setOnTouchListener(this);
points = new ArrayList<Point>();
bfirstpoint = false;
}
public void onDraw(Canvas canvas) {
canvas.drawBitmap(bitmap, 0, 0, null);
Path path = new Path();
boolean first = true;
for (int i = 0; i < points.size(); i += 2) {
Point point = points.get(i);
if (first) {
first = false;
path.moveTo(point.x, point.y);
} else if (i < points.size() - 1) {
Point next = points.get(i + 1);
path.quadTo(point.x, point.y, next.x, next.y);
} else {
mlastpoint = points.get(i);
path.lineTo(point.x, point.y);
}
}
canvas.drawPath(path, paint);
}
public boolean onTouch(View view, MotionEvent event) {
// if(event.getAction() != MotionEvent.ACTION_DOWN)
// return super.onTouchEvent(event);
Point point = new Point();
point.x = (int) event.getX();
point.y = (int) event.getY();
if (flgPathDraw) {
if (bfirstpoint) {
if (comparepoint(mfirstpoint, point)) {
// points.add(point);
points.add(mfirstpoint);
flgPathDraw = false;
showcropdialog();
} else {
points.add(point);
}
} else {
points.add(point);
}
if (!(bfirstpoint)) {
mfirstpoint = point;
bfirstpoint = true;
}
}
invalidate();
Log.e("Hi ==>", "Size: " + point.x + " " + point.y);
if (event.getAction() == MotionEvent.ACTION_UP) {
mlastpoint = point;
if (flgPathDraw) {
if (points.size() > 12) {
if (!comparepoint(mfirstpoint, mlastpoint)) {
flgPathDraw = false;
points.add(mfirstpoint);
showcropdialog();
}
}
}
}
return true;
}
private boolean comparepoint(Point first, Point current) {
int left_range_x = (int) (current.x - 3);
int left_range_y = (int) (current.y - 3);
int right_range_x = (int) (current.x + 3);
int right_range_y = (int) (current.y + 3);
if ((left_range_x < first.x && first.x < right_range_x)
&& (left_range_y < first.y && first.y < right_range_y)) {
if (points.size() < 10) {
return false;
} else {
return true;
}
} else {
return false;
}
}
public void fillinPartofPath() {
Point point = new Point();
point.x = points.get(0).x;
point.y = points.get(0).y;
points.add(point);
invalidate();
}
public void resetView() {
points.clear();
paint.setColor(Color.WHITE);
paint.setStyle(Paint.Style.STROKE);
flgPathDraw = true;
invalidate();
}
private void showcropdialog() {
DialogInterface.OnClickListener dialogClickListener = new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
Intent intent;
switch (which) {
case DialogInterface.BUTTON_POSITIVE:
// Yes button clicked
// bfirstpoint = false;
intent = new Intent(mContext, CropActivity.class);
intent.putExtra("crop", true);
((Activity)mContext).startActivityForResult(intent,1);
break;
case DialogInterface.BUTTON_NEGATIVE:
// No button clicked
intent = new Intent(mContext, CropActivity.class);
intent.putExtra("crop", false);
((Activity)mContext).startActivityForResult(intent,1);
bfirstpoint = false;
// resetView();
break;
}
}
};
AlertDialog.Builder builder = new AlertDialog.Builder(mContext);
builder.setMessage("Do you Want to save Crop or Non-crop image?")
.setPositiveButton("Crop", dialogClickListener)
.setNegativeButton("Non-crop", dialogClickListener).show()
.setCancelable(false);
}
}
class Point {
public float dy;
public float dx;
float x, y;
@Override
public String toString() {
return x + ", " + y;
}
}
我真的很感谢你给我答案。
我花了 2 天时间寻找解决方案。我查看了 Whosebug 中的所有裁剪答案,但没有找到任何解决方案使其居中。并修剪额外的空间。所以我找到了避免裁剪图像上出现额外空间的解决方案....
使用此功能正在制作没有额外空间的新位图。在 resultingImage.
之前使用函数
static Bitmap trim(Bitmap source) {
int firstX = 0, firstY = 0;
int lastX = source.getWidth();
int lastY = source.getHeight();
int[] pixels = new int[source.getWidth() * source.getHeight()];
source.getPixels(pixels, 0, source.getWidth(), 0, 0, source.getWidth(), source.getHeight());
loop:
for (int x = 0; x < source.getWidth(); x++) {
for (int y = 0; y < source.getHeight(); y++) {
if (pixels[x + (y * source.getWidth())] != Color.TRANSPARENT) {
firstX = x;
break loop;
}
}
}
loop:
for (int y = 0; y < source.getHeight(); y++) {
for (int x = firstX; x < source.getWidth(); x++) {
if (pixels[x + (y * source.getWidth())] != Color.TRANSPARENT) {
firstY = y;
break loop;
}
}
}
loop:
for (int x = source.getWidth() - 1; x >= firstX; x--) {
for (int y = source.getHeight() - 1; y >= firstY; y--) {
if (pixels[x + (y * source.getWidth())] != Color.TRANSPARENT) {
lastX = x;
break loop;
}
}
}
loop:
for (int y = source.getHeight() - 1; y >= firstY; y--) {
for (int x = source.getWidth() - 1; x >= firstX; x--) {
if (pixels[x + (y * source.getWidth())] != Color.TRANSPARENT) {
lastY = y;
break loop;
}
}
}
return Bitmap.createBitmap(source, firstX, firstY, lastX - firstX, lastY - firstY);
}
我正在尝试使用绘图裁剪图像。并且按预期进行裁剪,但我认为不会将裁剪部分缩放到新位图的中心。你可以看到 2 图片 1. 图片是我现在拥有的。 2.图片是我所期望的。
原始图像。
我有什么
我需要什么
我在 SomeView 上裁剪并将点发送到 CropActivity,然后 CropActivity 裁剪图像并将其发送到 MainActivity。
这是我的CropActivity.Java
public class CropActivity extends Activity {
ImageView compositeImageView;
boolean crop;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.cropview);
Bundle extras = getIntent().getExtras();
if (extras != null) {
crop = extras.getBoolean("crop");
}
int widthOfscreen = 512;
int heightOfScreen = 512;
DisplayMetrics dm = new DisplayMetrics();
try {
getWindowManager().getDefaultDisplay().getMetrics(dm);
} catch (Exception ex) {
}
widthOfscreen = dm.widthPixels;
heightOfScreen = dm.heightPixels;
compositeImageView = (ImageView) findViewById(R.id.our_imageview);
Bitmap bitmap2 = SomeView.bitmap;
Bitmap resultingImage = Bitmap.createBitmap(widthOfscreen,
heightOfScreen, bitmap2.getConfig());
Canvas canvas = new Canvas(resultingImage);
Paint paint = new Paint();
paint.setAntiAlias(true);
Path path = new Path();
for (int i = 0; i < SomeView.points.size(); i++) {
path.lineTo(SomeView.points.get(i).x, SomeView.points.get(i).y);
}
canvas.drawPath(path, paint);
if (crop) {
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));
} else {
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_OUT));
}
canvas.drawBitmap(bitmap2, 0, 0, paint);
compositeImageView.setImageBitmap(resultingImage);
Button donb = findViewById(R.id.donb);
donb.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent returnIntent = new Intent();
ByteArrayOutputStream bStream = new ByteArrayOutputStream();
resultingImage.compress(Bitmap.CompressFormat.PNG, 100, bStream);
byte[] byteArray = bStream.toByteArray();
returnIntent.putExtra("result",byteArray);
setResult(2,returnIntent);
finish();
// donb.setText("Dondum");
}
});
}
}
这是我的SomeView.Java
public class SomeView extends View implements View.OnTouchListener {
private Paint paint;
public static List<Point> points;
int DIST = 2;
boolean flgPathDraw = true;
public static final int PICK_IMAGE = 1;
Point mfirstpoint = null;
boolean bfirstpoint = false;
Point mlastpoint = null;
public static Bitmap bitmap;
Context mContext;
public SomeView(Context c, Bitmap b) {
super(c);
bitmap = b;
mContext = c;
setFocusable(true);
setFocusableInTouchMode(true);
paint = new Paint(Paint.ANTI_ALIAS_FLAG);
paint.setStyle(Paint.Style.STROKE);
paint.setPathEffect(new DashPathEffect(new float[] { 10, 20 }, 0));
paint.setStrokeWidth(15);
paint.setColor(Color.GREEN);
this.setOnTouchListener(this);
points = new ArrayList<Point>();
bfirstpoint = false;
}
public SomeView(Context context, AttributeSet attrs) {
super(context, attrs);
mContext = context;
setFocusable(true);
setFocusableInTouchMode(true);
paint = new Paint(Paint.ANTI_ALIAS_FLAG);
paint.setStyle(Paint.Style.STROKE);
paint.setStrokeWidth(2);
paint.setColor(Color.WHITE);
this.setOnTouchListener(this);
points = new ArrayList<Point>();
bfirstpoint = false;
}
public void onDraw(Canvas canvas) {
canvas.drawBitmap(bitmap, 0, 0, null);
Path path = new Path();
boolean first = true;
for (int i = 0; i < points.size(); i += 2) {
Point point = points.get(i);
if (first) {
first = false;
path.moveTo(point.x, point.y);
} else if (i < points.size() - 1) {
Point next = points.get(i + 1);
path.quadTo(point.x, point.y, next.x, next.y);
} else {
mlastpoint = points.get(i);
path.lineTo(point.x, point.y);
}
}
canvas.drawPath(path, paint);
}
public boolean onTouch(View view, MotionEvent event) {
// if(event.getAction() != MotionEvent.ACTION_DOWN)
// return super.onTouchEvent(event);
Point point = new Point();
point.x = (int) event.getX();
point.y = (int) event.getY();
if (flgPathDraw) {
if (bfirstpoint) {
if (comparepoint(mfirstpoint, point)) {
// points.add(point);
points.add(mfirstpoint);
flgPathDraw = false;
showcropdialog();
} else {
points.add(point);
}
} else {
points.add(point);
}
if (!(bfirstpoint)) {
mfirstpoint = point;
bfirstpoint = true;
}
}
invalidate();
Log.e("Hi ==>", "Size: " + point.x + " " + point.y);
if (event.getAction() == MotionEvent.ACTION_UP) {
mlastpoint = point;
if (flgPathDraw) {
if (points.size() > 12) {
if (!comparepoint(mfirstpoint, mlastpoint)) {
flgPathDraw = false;
points.add(mfirstpoint);
showcropdialog();
}
}
}
}
return true;
}
private boolean comparepoint(Point first, Point current) {
int left_range_x = (int) (current.x - 3);
int left_range_y = (int) (current.y - 3);
int right_range_x = (int) (current.x + 3);
int right_range_y = (int) (current.y + 3);
if ((left_range_x < first.x && first.x < right_range_x)
&& (left_range_y < first.y && first.y < right_range_y)) {
if (points.size() < 10) {
return false;
} else {
return true;
}
} else {
return false;
}
}
public void fillinPartofPath() {
Point point = new Point();
point.x = points.get(0).x;
point.y = points.get(0).y;
points.add(point);
invalidate();
}
public void resetView() {
points.clear();
paint.setColor(Color.WHITE);
paint.setStyle(Paint.Style.STROKE);
flgPathDraw = true;
invalidate();
}
private void showcropdialog() {
DialogInterface.OnClickListener dialogClickListener = new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
Intent intent;
switch (which) {
case DialogInterface.BUTTON_POSITIVE:
// Yes button clicked
// bfirstpoint = false;
intent = new Intent(mContext, CropActivity.class);
intent.putExtra("crop", true);
((Activity)mContext).startActivityForResult(intent,1);
break;
case DialogInterface.BUTTON_NEGATIVE:
// No button clicked
intent = new Intent(mContext, CropActivity.class);
intent.putExtra("crop", false);
((Activity)mContext).startActivityForResult(intent,1);
bfirstpoint = false;
// resetView();
break;
}
}
};
AlertDialog.Builder builder = new AlertDialog.Builder(mContext);
builder.setMessage("Do you Want to save Crop or Non-crop image?")
.setPositiveButton("Crop", dialogClickListener)
.setNegativeButton("Non-crop", dialogClickListener).show()
.setCancelable(false);
}
}
class Point {
public float dy;
public float dx;
float x, y;
@Override
public String toString() {
return x + ", " + y;
}
}
我真的很感谢你给我答案。
我花了 2 天时间寻找解决方案。我查看了 Whosebug 中的所有裁剪答案,但没有找到任何解决方案使其居中。并修剪额外的空间。所以我找到了避免裁剪图像上出现额外空间的解决方案....
使用此功能正在制作没有额外空间的新位图。在 resultingImage.
static Bitmap trim(Bitmap source) {
int firstX = 0, firstY = 0;
int lastX = source.getWidth();
int lastY = source.getHeight();
int[] pixels = new int[source.getWidth() * source.getHeight()];
source.getPixels(pixels, 0, source.getWidth(), 0, 0, source.getWidth(), source.getHeight());
loop:
for (int x = 0; x < source.getWidth(); x++) {
for (int y = 0; y < source.getHeight(); y++) {
if (pixels[x + (y * source.getWidth())] != Color.TRANSPARENT) {
firstX = x;
break loop;
}
}
}
loop:
for (int y = 0; y < source.getHeight(); y++) {
for (int x = firstX; x < source.getWidth(); x++) {
if (pixels[x + (y * source.getWidth())] != Color.TRANSPARENT) {
firstY = y;
break loop;
}
}
}
loop:
for (int x = source.getWidth() - 1; x >= firstX; x--) {
for (int y = source.getHeight() - 1; y >= firstY; y--) {
if (pixels[x + (y * source.getWidth())] != Color.TRANSPARENT) {
lastX = x;
break loop;
}
}
}
loop:
for (int y = source.getHeight() - 1; y >= firstY; y--) {
for (int x = source.getWidth() - 1; x >= firstX; x--) {
if (pixels[x + (y * source.getWidth())] != Color.TRANSPARENT) {
lastY = y;
break loop;
}
}
}
return Bitmap.createBitmap(source, firstX, firstY, lastX - firstX, lastY - firstY);
}