How to resize 2 images in android , as one image which remain constant ( .png image in drawable folder) should be equal to the size of input image (image enter from the user from mobile gallery) . I use resize(src, dst) function in opencv for resizing two images , don't have any idea of this kind of function in java end as I check this post as well but it look some kind of extra loaded work to me.
I know some method about image operation in android.
Transform Drawable to Bitmap:
public static Bitmap drawableToBitmap(Drawable drawable) {
int width = drawable.getIntrinsicWidth();
int height = drawable.getIntrinsicHeight();
Bitmap bitmap = Bitmap.createBitmap(width, height, drawable
.getOpacity() != PixelFormat.OPAQUE ? Bitmap.Config.ARGB_8888
: Bitmap.Config.RGB_565);
Canvas canvas = new Canvas(bitmap);
drawable.setBounds(0, 0, width, height);
drawable.draw(canvas);
return bitmap;
}
Resize Bitmap:
public static Bitmap zoomBitmap(Bitmap bitmap, int w, int h) {
int width = bitmap.getWidth();
int height = bitmap.getHeight();
Matrix matrix = new Matrix();
float scaleWidht = ((float) w / width);
float scaleHeight = ((float) h / height);
matrix.postScale(scaleWidht, scaleHeight);
Bitmap newbmp = Bitmap.createBitmap(bitmap, 0, 0, width, height,
matrix, true);
return newbmp;
}
You can transform your first Drawable image to Bitmap, then resize it with the second method. Use getWidth() and getHeight() to get parameters of the image.
I don't know whether this is the best solution. If I didn't understand your intent well, make a comment and I can edit my answer.
Edit:
You can get Uri or the path of the image right?
If you get Uri, use String path = uri.getPath(); to get the path.
Then
Decode Bitmap from file:
public static Bitmap getBitmap(String path) {
return BitmapFactory.decodeFile(String path);
}
If the size of image is not too big, load it directly wouldn't cause memory leaks, everything is OK.
But if you don't know the size, I recommend the next method.
Decode BitmapDrawable from path:
public static BitmapDrawable getScaledDrawable(Activity a, String path) {
Display display = a.getWindowManager().getDefaultDisplay();
float destWidth = display.getWidth();
float destHeight = display.getHeight();
BitmapFactory.Options options = new BitmapFactory.Options();
options.inJustDecodeBounds = true;
BitmapFactory.decodeFile(path, options);
float srcWidth = options.outWidth;
float srcHeight = options.outHeight;
int inSampleSize = 1;
if (srcHeight > destHeight || srcWidth > destWidth) {
if (srcWidth > srcHeight) {
inSampleSize = Math.round(srcHeight / destHeight);
} else {
inSampleSize = Math.round(srcWidth / destWidth);
}
}
options = new BitmapFactory.Options();
options.inSampleSize = inSampleSize;
Bitmap bitmap = BitmapFactory.decodeFile(path, options);
return new BitmapDrawable(a.getResources(), bitmap);
}
This method will return a scaled BitmapDrawable object to prevent memory leaks.
If you need Bitmap not BitmapDrawable , just return bitmap.
Edit2:
ThirdActivity.java :
public class ThirdActivity extends ActionBarActivity {
private static final int REQUEST_IMAGE = 0;
private Bitmap bitmapToResize;
private Button mGetImageButton;
private Button mResizeButton;
private ImageView mImageViewForGallery;
private ImageView mImageVIewForDrable;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_third);
mGetImageButton = (Button) findViewById(R.id.button_getImage);
mGetImageButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
// SET action AND miniType
Intent intent = new Intent();
intent.setAction(Intent.ACTION_PICK);
intent.setType("image/*");
// REQUEST Uri of image
startActivityForResult(intent, REQUEST_IMAGE);
}
});
mResizeButton = (Button) findViewById(R.id.button_resize);
mResizeButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
resize();
}
});
mImageViewForGallery = (ImageView) findViewById(R.id.imageView);
mImageVIewForDrable = (ImageView) findViewById(R.id.imageViewFromDrable);
mImageVIewForDrable.setImageDrawable(getResources().getDrawable(R.drawable.ic_launcher));
}
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (resultCode != Activity.RESULT_OK) {return;}
if (requestCode == REQUEST_IMAGE) {
Uri uri = data.getData();
// SET image
mImageViewForGallery.setImageURI(uri);
Drawable drawable = mImageViewForGallery.getDrawable();
Log.e("asd", "Height:" + drawable.getIntrinsicHeight());
Log.e("asd", "Width:" + drawable.getIntrinsicWidth());
}
}
private void resize() {
if (mImageViewForGallery.getDrawable() != null) {
bitmapToResize = drawableToBitmap(mImageVIewForDrable.getDrawable());
int width = mImageViewForGallery.getDrawable().getIntrinsicWidth();
int height = mImageViewForGallery.getDrawable().getIntrinsicHeight();
bitmapToResize = zoomBitmap(bitmapToResize, width, height);
mImageVIewForDrable.setImageBitmap(bitmapToResize);
} else {
Log.e("asd", "setImageFirst");
}
}
public static Bitmap zoomBitmap(Bitmap bitmap, int w, int h) {
int width = bitmap.getWidth();
int height = bitmap.getHeight();
Matrix matrix = new Matrix();
float scaleWidht = ((float) w / width);
float scaleHeight = ((float) h / height);
matrix.postScale(scaleWidht, scaleHeight);
Bitmap newbmp = Bitmap.createBitmap(bitmap, 0, 0, width, height,
matrix, true);
return newbmp;
}
public static Bitmap drawableToBitmap(Drawable drawable) {
int width = drawable.getIntrinsicWidth();
int height = drawable.getIntrinsicHeight();
Bitmap bitmap = Bitmap.createBitmap(width, height, drawable
.getOpacity() != PixelFormat.OPAQUE ? Bitmap.Config.ARGB_8888
: Bitmap.Config.RGB_565);
Canvas canvas = new Canvas(bitmap);
drawable.setBounds(0, 0, width, height);
drawable.draw(canvas);
return bitmap;
}
}
activity_third.xml:
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingLeft="#dimen/activity_horizontal_margin"
android:paddingRight="#dimen/activity_horizontal_margin"
android:paddingTop="#dimen/activity_vertical_margin"
android:paddingBottom="#dimen/activity_vertical_margin"
android:background="#android:color/darker_gray"
tools:context="com.ch.summerrunner.ThirdActivity">
<ScrollView
android:layout_width="match_parent"
android:layout_height="match_parent">
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#android:color/darker_gray">
<Button
android:id="#+id/button_getImage"
android:text="#string/gallery"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<Button
android:id="#+id/button_resize"
android:text="#string/resize"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginLeft="16dp"
android:layout_toRightOf="#id/button_getImage"/>
<ImageView
android:id="#+id/imageView"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="8dp"
android:background="#android:color/white"
android:layout_below="#id/button_getImage"/>
<ImageView
android:id="#+id/imageViewFromDrable"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="#android:color/white"
android:layout_below="#id/imageView"/>
</RelativeLayout>
</ScrollView>
</RelativeLayout>
Bitmap bmpIn = BitmapFactory.decodeResource(view.getResources(), R.drawable.image);
BitMap bmpOut = Bitmap.createScaledBitmap(bmpIn, width, height, false);
Related
Is it possible to change the settings of an Intent for taking a picture to set the size or resolution of the resulting Image?
So right now I take a picture and the resulting Image was taken with 16MP and 4608x2304.
I'd like to know if its possible to get a resulting image such as (for example):
2MP and 460x230...
I know there is this way:
intent.putExtra("outputX", 460);
intent.putExtra("outputY", 230);
But I'm looking for something that works with all devices (cause of course they all don't have the same image sizes and if I crop them with hard coded values it'll suck)...
Hope you can understand what my issue is..
You need to take a photo without saving it in a file:
static final int REQUEST_IMAGE_CAPTURE = 1;
private void dispatchTakePictureIntent() {
Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
if (takePictureIntent.resolveActivity(getPackageManager()) != null) {
startActivityForResult(takePictureIntent, REQUEST_IMAGE_CAPTURE);
}
}
After that you need to scale a result Bitmap with saving of aspect ratio:
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == REQUEST_IMAGE_CAPTURE && resultCode == RESULT_OK) {
Bundle extras = data.getExtras();
Bitmap imageBitmap = (Bitmap) extras.get("data");
Bitmap scaledImage = scaleBitmap(imageBitmap , 460, 230);
mImageView.setImageBitmap(scaledImage);
}
}
private Bitmap scaleBitmap(Bitmap bm, int maxWidth, int maxHeight) {
int width = bm.getWidth();
int height = bm.getHeight();
if (width > height) {
// landscape
int ratio = width / maxWidth;
width = maxWidth;
height = height / ratio;
} else if (height > width) {
// portrait
int ratio = height / maxHeight;
height = maxHeight;
width = width / ratio;
} else {
// square
height = maxHeight;
width = maxWidth;
}
bm = Bitmap.createScaledBitmap(bm, width, height, true);
return bm;
}
so i am trying now for about a week to get this thing working but to no avail....
i want the user to pick an image from his gallery and then crop that image into a nice circle profile photo i get the photo to crop but the background is still square.... i found this question and tried implementing the answer he gave but still the background is square Cropping circular area from bitmap in Android
i googled and just found more ways to do it but still gets the square background.... any help will be appreciated
public class RegisterActivity extends Fragment {
// TODO: Rename parameter arguments, choose names that match
// the fragment initialization parameters, e.g. ARG_ITEM_NUMBER
private static final String ARG_PARAM1 = "param1";
private static final String ARG_PARAM2 = "param2";
private String mParam1;
private String mParam2;
RoundedImageView roundImageView ;
String numberToPass = "1";//default 1 for male
String selectedImagePath;
EditText etNickname, etAge;
Button btnNext;
ImageView profilePhoto, imageview;
Bitmap bitmap;
private OnRegisterListener mListener;
public RegisterActivity() {
// Required empty public constructor
}
public static RegisterActivity newInstance(String param1, String param2) {
RegisterActivity fragment = new RegisterActivity();
Bundle args = new Bundle();
args.putString(ARG_PARAM1, param1);
args.putString(ARG_PARAM2, param2);
fragment.setArguments(args);
return fragment;
}
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
if (getArguments() != null) {
mParam1 = getArguments().getString(ARG_PARAM1);
mParam2 = getArguments().getString(ARG_PARAM2);
}
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_register, container, false);
etNickname = (EditText) view.findViewById(R.id.etNickName);
btnNext = (Button) view.findViewById(R.id.btnNextRegister);
profilePhoto = (ImageView) view.findViewById(R.id.imageButton);
bitmap = BitmapFactory.decodeResource(getResources(),
R.drawable.blender);
// profilePhoto.setImageBitmap(bitmap);
/* Bitmap bitmap2 = BitmapFactory.decodeResource(this.getResources(),R.drawable.blender);
Bitmap circularBitmap = ImageConverter.getRoundedCornerBitmap(bitmap2, 100);
ImageView circularImageView = (ImageView)view.findViewById(R.id.imageButton);
circularImageView.setImageBitmap(circularBitmap); */
profilePhoto.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
openGallery();
}
});
return view;
}
// TODO: Rename method, update argument and hook method into UI event
public void onButtonPressed(Uri uri) {
if (mListener != null) {
mListener.onFragmentInteraction(uri);
}
}
#Override
public void onAttach(Context context) {
super.onAttach(context);
if (context instanceof OnRegisterListener) {
mListener = (OnRegisterListener) context;
} else {
throw new RuntimeException(context.toString()
+ " must implement OnRegisterListener");
}
}
#Override
public void onDetach() {
super.onDetach();
mListener = null;
}
public interface OnRegisterListener {
// TODO: Update argument type and name
void onFragmentInteraction(Uri uri);
}
//this allows the uset to select one image from openGallery
public void openGallery() {
Intent gallery = new Intent(Intent.ACTION_PICK, MediaStore.Images.Media.INTERNAL_CONTENT_URI);
startActivityForResult(gallery, 1);
}
//when starting activity for result and choose an image, the code will automatically continue here
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (resultCode == RESULT_OK && requestCode == 1 && null != data) {
if (requestCode == 1) {
Uri current_ImageURI = data.getData();
/* String[] filePathColumn = { MediaStore.Images.Media.DATA };
Cursor cursor = getActivity().getContentResolver().query(current_ImageURI,
filePathColumn, null, null, null);
cursor.moveToFirst();
int columnIndex = cursor.getColumnIndex(filePathColumn[0]);
String picturePath = cursor.getString(columnIndex);
cursor.close();*/
selectedImagePath = getPath(current_ImageURI);
profilePhoto.setImageBitmap(circleBitmap(decodeSampledBitmap(new File(selectedImagePath), 250, 250)));
}
}
}
public String getPath(Uri contentUri) {
// we have to check for sdk version because from lollipop the retrieval of path is different
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
// can post image
String[] proj = {MediaStore.Images.Media.DATA};
Cursor cursor = getActivity().getApplicationContext().getContentResolver().query(contentUri, proj, null, null, null);
int column_index = cursor.getColumnIndexOrThrow(MediaStore.Images.Media.DATA);
cursor.moveToFirst();
return cursor.getString(column_index);
} else {
String filePath = "";
String wholeID = DocumentsContract.getDocumentId(contentUri);
// Split at colon, use second item in the array
String id = wholeID.split(":")[1];
String[] column = {MediaStore.Images.Media.DATA};
// where id is equal to
String sel = MediaStore.Images.Media._ID + "=?";
Cursor cursor = getActivity().getContentResolver().query(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, column, sel, new String[]{id}, null);
int columnIndex = cursor.getColumnIndex(column[0]);
if (cursor.moveToFirst()) {
filePath = cursor.getString(columnIndex);
}
cursor.close();
return filePath;
}
}
public Bitmap decodeSampledBitmap(File res, int reqWidth, int reqHeight) {
if (res != null) {
// First decode with inJustDecodeBounds=true to check dimensions
final BitmapFactory.Options options = new BitmapFactory.Options();
options.inJustDecodeBounds = true;
try {
FileInputStream stream2 = null;
try {
stream2 = new FileInputStream(res);
} catch (FileNotFoundException e) {
e.printStackTrace();
}
BitmapFactory.decodeStream(stream2, null, options);
stream2.close();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
// Calculate inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = calculateInSampleSize(options, reqWidth, reqHeight);
o2.inJustDecodeBounds = false;
FileInputStream stream = null;
try {
stream = new FileInputStream(res);
} catch (FileNotFoundException e) {
e.printStackTrace();
}
Bitmap bitmap = BitmapFactory.decodeStream(stream, null, o2);
try {
stream.close();
} catch (IOException e) {
e.printStackTrace();
}
return bitmap;
} else
return null;
}
public int calculateInSampleSize(BitmapFactory.Options options, int reqWidth, int reqHeight) {
// Raw height and width of image
final int height = options.outHeight;
final int width = options.outWidth;
int inSampleSize = 1;
if (height > reqHeight || width > reqWidth) {
final int halfHeight = height / 2;
final int halfWidth = width / 2;
// Calculate the largest inSampleSize value that is a power of 2 and keeps both
// height and width larger than the requested height and width.
while ((halfHeight / inSampleSize) > reqHeight && (halfWidth / inSampleSize) > reqWidth) {
inSampleSize *= 2;
}
}
return inSampleSize;
}
//-----------------------------------------------------------------
private Bitmap circleBitmap(Bitmap bitmap) {
final Bitmap output = Bitmap.createBitmap(bitmap.getWidth(),
bitmap.getHeight(), Bitmap.Config.ARGB_8888);
int squareBitmapWidth = Math.min(bitmap.getWidth(), bitmap.getHeight());
/* Canvas
The Canvas class holds the "draw" calls. To draw something, you need 4 basic
components: A Bitmap to hold the pixels, a Canvas to host the draw calls (writing
into the bitmap), a drawing primitive (e.g. Rect, Path, text, Bitmap), and a paint
(to describe the colors and styles for the drawing). */
final Canvas canvas = new Canvas(output);
final int color = Color.RED;
final Paint paint = new Paint();
final Rect rect = new Rect(0, 0, bitmap.getWidth(), bitmap.getHeight());
// final Rect rect = new Rect(0, 0, squareBitmapWidth, squareBitmapWidth);
final RectF rectF = new RectF(rect);
paint.setAntiAlias(true);
canvas.drawARGB(0, 0, 0, 0);
paint.setColor(color);
canvas.drawCircle(bitmap.getWidth() / 2, bitmap.getHeight() / 2, bitmap.getWidth() / 2, paint);
//canvas.drawOval(rectF, paint);
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));
//float left = (squareBitmapWidth - bitmap.getWidth()) / 2;
//float top = (squareBitmapWidth - bitmap.getHeight()) / 2;
//canvas.drawBitmap(bitmap, left, top, paint);
canvas.drawBitmap(bitmap, rect, rect, paint);
//bitmap.recycle();
return output;
}
//---------------------------------------------------------------------------------------------
//end img upload
I use this code and it works perfectly:
public static Bitmap getCircularBitmap(Bitmap bitmap) {
Bitmap output;
if (bitmap.getWidth() > bitmap.getHeight()) {
output = Bitmap.createBitmap(bitmap.getHeight(), bitmap.getHeight(), Bitmap.Config.ARGB_8888);
} else {
output = Bitmap.createBitmap(bitmap.getWidth(), bitmap.getWidth(), Bitmap.Config.ARGB_8888);
}
Canvas canvas = new Canvas(output);
final int color = 0xff424242;
final Paint paint = new Paint();
final Rect rect = new Rect(0, 0, bitmap.getWidth(), bitmap.getHeight());
float r = 0;
if (bitmap.getWidth() > bitmap.getHeight()) {
r = bitmap.getHeight() / 2;
} else {
r = bitmap.getWidth() / 2;
}
paint.setAntiAlias(true);
canvas.drawARGB(0, 0, 0, 0);
paint.setColor(color);
canvas.drawCircle(r, r, r, paint);
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));
canvas.drawBitmap(bitmap, rect, rect, paint);
return output;
}
You can custom ImageView to make its all drawing things circular. Here is my implementation(not the best solution for performance-eager application but good enough for condition that don't invalidate ImageView much):
class CircleImageView extends ImageView {
private Paint mPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
public CircleImageView(Context context) {
super(context);
}
#Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
int radiusMeasureSpec = widthMeasureSpec;
super.onMeasure(radiusMeasureSpec, radiusMeasureSpec);
int radiusMeasureSize = MeasureSpec.getSize(widthMeasureSpec);
setMeasuredDimension(radiusMeasureSize, radiusMeasureSize);
}
#Override
public void draw(Canvas viewCanvas) {
final int EDGE_SIZE = viewCanvas.getWidth();
// Draw this View's things.
Bitmap fgBm = Bitmap.createBitmap(EDGE_SIZE, EDGE_SIZE, Bitmap.Config.ARGB_8888);
Canvas fgCanvas = new Canvas(fgBm);
super.draw(fgCanvas);
// Transfer to a special shape.
Bitmap shapedBm = Bitmap.createBitmap(EDGE_SIZE, EDGE_SIZE, Bitmap.Config.ARGB_8888);
Canvas shapedCanvas = new Canvas(shapedBm);
shapedCanvas.drawCircle(EDGE_SIZE/2, EDGE_SIZE/2, EDGE_SIZE/2, mPaint);
mPaint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));
shapedCanvas.drawBitmap(fgBm, 0, 0, mPaint);
mPaint.setXfermode(null);
// Move drawn things to View's canvas.
viewCanvas.drawBitmap(shapedBm, 0, 0, mPaint);
fgBm.recycle();
shapedBm.recycle();
}
}
There's someone who customizes ImageView using BitmapShader in an SO post without Xfermode and create extra Bitmap instances. Here's his implementation.
you can use trusted library like This one
Adding circle image adding border to your image and some other feature
I'm trying to draw grid (just 8x8 lines) in background, but my drawing view covers it and grid doesn't show up. My DrawingView handles touches and draws circles. Grid must draw grids in background (it does when DrawingView is gone).
MainActivity.java:
public class MainActivity extends AppCompatActivity {
private RelativeLayout layout;
private DrawingView drawingView;
private FloatingActionButton pickPhoto;
private final int SELECT_PHOTO = 1;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
layout = (RelativeLayout) findViewById(R.id.layout);
pickPhoto = (FloatingActionButton) findViewById(R.id.insertPhoto);
drawingView = (DrawingView) findViewById(R.id.drawingView);
assert drawingView != null;
drawingView.getHolder().setFormat(PixelFormat.TRANSLUCENT);
pickPhoto.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
Intent photoPickerIntent = new Intent(Intent.ACTION_PICK);
photoPickerIntent.setType("image/*");
startActivityForResult(photoPickerIntent, SELECT_PHOTO);
}
});
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
menu.add(0, 0, 0, "Save")
.setIcon(R.drawable.ic_save)
.setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() {
#Override
public boolean onMenuItemClick(MenuItem item) {
FloatingActionMenu fab = (FloatingActionMenu) findViewById(R.id.fab);
assert fab != null;
fab.setVisibility(View.GONE);
Bitmap bitmap = getBitmap(layout);
saveChart(bitmap, layout.getMeasuredHeight(), layout.getMeasuredWidth());
fab.setVisibility(View.VISIBLE);
return false;
}
})
.setShowAsAction(
MenuItem.SHOW_AS_ACTION_ALWAYS
| MenuItem.SHOW_AS_ACTION_WITH_TEXT);
return super.onCreateOptionsMenu(menu);
}
public void saveChart(Bitmap getbitmap, float height, float width) {
File folder = new File(Environment
.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES),
"My drawings");
if (!folder.exists()) {
folder.mkdirs();
}
String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss",
Locale.getDefault()).format(new Date());
File file = new File(folder.getPath() + File.separator + "/" + timeStamp + ".png");
if (!file.exists()) {
try {
file.createNewFile();
} catch (IOException e) {
e.printStackTrace();
}
}
FileOutputStream ostream;
try {
ostream = new FileOutputStream(file);
Bitmap save = Bitmap.createBitmap((int) width, (int) height, Bitmap.Config.ARGB_8888);
Paint paint = new Paint();
paint.setColor(Color.WHITE);
Canvas now = new Canvas(save);
now.drawRect(new Rect(0, 0, (int) width, (int) height), paint);
now.drawBitmap(getbitmap,
new Rect(0, 0, getbitmap.getWidth(), getbitmap.getHeight()),
new Rect(0, 0, (int) width, (int) height), null);
save.compress(Bitmap.CompressFormat.PNG, 100, ostream);
} catch (NullPointerException | FileNotFoundException e) {
e.printStackTrace();
}
}
public Bitmap getBitmap(RelativeLayout layout) {
layout.setDrawingCacheEnabled(true);
layout.buildDrawingCache();
Bitmap bmp = Bitmap.createBitmap(layout.getDrawingCache());
layout.setDrawingCacheEnabled(false);
return bmp;
}
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent imageReturnedIntent) {
super.onActivityResult(requestCode, resultCode, imageReturnedIntent);
switch (requestCode) {
case SELECT_PHOTO:
if (resultCode == RESULT_OK) {
try {
final Uri imageUri = imageReturnedIntent.getData();
final InputStream imageStream = getContentResolver().openInputStream(imageUri);
final Bitmap selectedImage = BitmapFactory.decodeStream(imageStream);
drawingView.setImage(selectedImage);
} catch (FileNotFoundException e) {
e.printStackTrace();
}
}
}
}
}
DrawingView.java:
class DrawingView extends SurfaceView {
private final Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);
private ArrayList<Point> points;
private Bitmap mBitmap;
public DrawingView(Context context, AttributeSet attrs) {
super(context, attrs);
paint.setColor(Color.RED);
paint.setStyle(Paint.Style.FILL);
setFocusable(true);
setFocusableInTouchMode(true);
points = new ArrayList<>();
setBackgroundColor(Color.WHITE);
}
#Override
protected void onDraw(Canvas canvas) {
if (mBitmap != null)
canvas.drawBitmap(mBitmap, 0, 0, paint);
for (Point p : points)
canvas.drawCircle(p.x, p.y, 50, paint);
}
#Override
public boolean onTouchEvent(MotionEvent event) {
points.add(new Point((int) event.getX(), (int) event.getY()));
invalidate();
return false;
}
public void setImage(Bitmap bitmap) {
mBitmap = bitmap;
invalidate();
}
}
Grid.java:
public class Grid extends View{
private int rowsCount = 8;
private int columnsCount = 8;
private Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);
public Grid(Context context, AttributeSet attrs) {
super(context, attrs);
paint.setColor(Color.BLACK);
}
#Override
protected void onDraw(Canvas canvas) {
int height = getHeight();
int width = getWidth();
for (int i = 0; i < rowsCount; ++i) {
canvas.drawLine(0, height / rowsCount * (i + 1), width, height / rowsCount * (i + 1), paint);
}
for (int i = 0; i < columnsCount; ++i) {
canvas.drawLine(width / columnsCount * (i + 1), 0, width / columnsCount * (i + 1), height, paint);
}
super.onDraw(canvas);
}
}
activity_main.xml:
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
xmlns:fab="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/layout"
tools:context=".MainActivity"
android:orientation="vertical">
<reminder.com.paint.Grid
android:id="#+id/grid"
android:layout_width="match_parent"
android:layout_height="match_parent" />
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<reminder.com.paint.DrawingView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/drawingView"
android:background="#00FFFFFF"
android:layout_alignParentEnd="true" />
</RelativeLayout>
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<com.github.clans.fab.FloatingActionMenu
android:id="#+id/fab"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginRight="10dp"
android:layout_marginLeft="10dp"
fab:menu_fab_size="normal"
fab:menu_showShadow="true"
fab:menu_shadowColor="#66000000"
fab:menu_shadowRadius="4dp"
fab:menu_shadowXOffset="1dp"
fab:menu_shadowYOffset="3dp"
fab:menu_colorNormal="#DA4336"
fab:menu_colorPressed="#E75043"
fab:menu_colorRipple="#99f47070"
fab:menu_animationDelayPerItem="50"
fab:menu_icon="#drawable/fab_add"
fab:menu_buttonSpacing="0dp"
fab:menu_labels_margin="0dp"
fab:menu_labels_showAnimation="#anim/fab_slide_in_from_right"
fab:menu_labels_hideAnimation="#anim/fab_slide_out_to_right"
fab:menu_labels_paddingTop="4dp"
fab:menu_labels_paddingRight="8dp"
fab:menu_labels_paddingBottom="4dp"
fab:menu_labels_paddingLeft="8dp"
fab:menu_labels_padding="8dp"
fab:menu_labels_textColor="#FFFFFF"
fab:menu_labels_textSize="14sp"
fab:menu_labels_cornerRadius="3dp"
fab:menu_labels_colorNormal="#333333"
fab:menu_labels_colorPressed="#444444"
fab:menu_labels_colorRipple="#66FFFFFF"
fab:menu_labels_showShadow="true"
fab:menu_labels_singleLine="false"
fab:menu_labels_ellipsize="none"
fab:menu_labels_maxLines="-1"
fab:menu_labels_position="left"
fab:menu_openDirection="up"
fab:menu_backgroundColor="#android:color/transparent"
android:layout_alignParentBottom="true"
android:layout_alignParentEnd="true"
android:layout_gravity="end">
<com.github.clans.fab.FloatingActionButton
android:id="#+id/insertPhoto"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="#drawable/ic_insert_photo_24dp"
fab:fab_size="mini"
fab:fab_label="Add photos" />
<com.github.clans.fab.FloatingActionButton
android:id="#+id/addCircle"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="#drawable/ic_brightness_1_24dp"
fab:fab_size="mini"
fab:fab_label="Add circles" />
</com.github.clans.fab.FloatingActionMenu>
</RelativeLayout>
private Paint mPaintGridLine;
...
mPaintGridLine = new Paint();
mPaintGridLine.setColor(Color.WHITE);
mPaintGridLine.setStyle(Paint.Style.STROKE);
mPaintGridLine.setStrokeWidth(1);
...
#Override
protected void onDraw(Canvas canvas)
{
super.onDraw(canvas);
final int w = getWidth();
final int h = getHeight();
final int colCount = 10;
final int rowCount = 10;
// vertical lines
final int vLinesCount = colCount - 1;
for (int i=0; i<vLinesCount; i++)
{
float pos = (w / colCount) * (i + 1);
canvas.drawLine(pos, 0, pos, h, mPaintGridLine);
}
// horizontal lines
final int hLinesCount = rowCount - 1;
for (int i=0; i<hLinesCount; i++)
{
float pos = (h / rowCount) * (i + 1);
canvas.drawLine(0, pos, w, pos, mPaintGridLine);
}
}
I am trying to display images from a specified directory on an android device in a gallery type activity. i was following (at least trying to) the guide on displaying images on the android developers site but kept getting lost http://developer.android.com/training/displaying-bitmaps/load-bitmap.html . I currently have a downsampled version of the image and am loading it into an image view in the layout.xml file. but this would require me to know the amount of images that will be present which i wont and i fear it is wasteful.
I need to Know how to create the image views depending on how many images are in the directory. and display the thumbnails or downsampled images in the created imageViews.
layout.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent"
android:layout_height="match_parent" android:paddingLeft="#dimen/activity_horizontal_margin"
android:paddingRight="#dimen/activity_horizontal_margin"
android:paddingTop="#dimen/activity_vertical_margin"
android:paddingBottom="#dimen/activity_vertical_margin"
tools:context=".MainActivity">
<TextView android:text="Hello World!" android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/textView" />
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/mImageView0"
android:layout_centerHorizontal="true"
android:layout_alignParentEnd="true" />
............
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/mImageView5"
android:layout_below="#id/mImageView4"
android:layout_centerHorizontal="true"
android:layout_alignParentEnd="true" />
</RelativeLayout>
MainActivity.java
public class MainActivity extends Activity {
private final String TAG = "MainActivity Class";
public ImageView mImageView;
public ListView listView;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
String fileDir = Environment.getExternalStorageDirectory().toString()+ File.separator +"Camera-App-Images"+ File.separator;
File f = new File(fileDir);
Log.d(TAG, fileDir);
File file[] = f.listFiles();
ImageView[] imgViews = new ImageView[file.length];
for (int i=0; i < file.length; i++) {
mImageView = (ImageView)findViewById(R.id.mImageView0 + i);
listView = (ListView)findViewById(R.id.listView);
loadBitmap(fileDir + file[i].getName(), mImageView);
}
}
public void loadBitmap(String fileLoc, ImageView imageView) {
BitmapWorkerTask task = new BitmapWorkerTask(fileLoc ,imageView);
task.execute();
}
}
BitmapWorkerTask
class BitmapWorkerTask extends AsyncTask<Integer, Void, Bitmap> {
private final WeakReference<ImageView> imageViewReference;
private int data = 0;
private String imagePath = "";
private final String TAG = "BitmapWorkerTask";
public BitmapWorkerTask(String imgPath, ImageView imageView) {
imagePath = imgPath;
// Use a WeakReference to ensure the ImageView can be garbage collected
imageViewReference = new WeakReference<ImageView>(imageView);
Log.d(TAG,"Constructor");
}
// Decode image in background.
#Override
protected Bitmap doInBackground(Integer... params) {
//data = params[0];
return decodeSampledBitmapFromFile(imagePath, 100, 100);
}
// Once complete, see if ImageView is still around and set bitmap.
#Override
protected void onPostExecute(Bitmap bitmap) {
if (imageViewReference != null && bitmap != null) {
final ImageView imageView = imageViewReference.get();
if (imageView != null) {
imageView.setImageBitmap(bitmap);
}
}
}
public static Bitmap decodeSampledBitmapFromFile(String filePath, int reqWidth, int reqHeight) {
// First decode with inJustDecodeBounds=true to check dimensions
final BitmapFactory.Options options = new BitmapFactory.Options();
options.inJustDecodeBounds = true;
BitmapFactory.decodeFile(filePath, options);
// Calculate inSampleSize
options.inSampleSize = calculateInSampleSize(options, reqWidth, reqHeight);
// Decode bitmap with inSampleSize set
options.inJustDecodeBounds = false;
return BitmapFactory.decodeFile(filePath, options);
}
public static int calculateInSampleSize(
BitmapFactory.Options options, int reqWidth, int reqHeight) {
// Raw height and width of image
final int height = options.outHeight;
final int width = options.outWidth;
int inSampleSize = 1;
if (height > reqHeight || width > reqWidth) {
final int halfHeight = height / 2;
final int halfWidth = width / 2;
while ((halfHeight / inSampleSize) > reqHeight
&& (halfWidth / inSampleSize) > reqWidth) {
inSampleSize *= 2;
}
}
return inSampleSize;
}
}
(JAVA FILE 1)
public class CropActivity extends Activity implements OnTouchListener {
public static final String RETURN_DATA = "return-data";
public static final String RETURN_DATA_AS_BITMAP = "data";
public static final String ACTION_INLINE_DATA = "inline-data";
private ImageView mImg;
private ImageView mTemplateImg;
// private static ProgressDialog mProgressDialog;
private Matrix mMatrix = new Matrix();
private float mScaleFactor = 0.8f;
private float mRotationDegrees = 0.f;
private float mFocusX = 0.f;
private float mFocusY = 0.f;
private int mImageHeight, mImageWidth;
private ScaleGestureDetector mScaleDetector;
private MoveGestureDetector mMoveDetector;
// Constants
public static final int MEDIA_GALLERY = 1;
public static final int TEMPLATE_SELECTION = 2;
public static final int DISPLAY_IMAGE = 3;
Bitmap profilePic;
String userImageLink;
int cropImageWidth;
int cropImageHeight;
int width, height, w1;
#SuppressLint("NewApi")
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.crop_activity_layout);
Resources r = getResources();
DisplayMetrics dm = new DisplayMetrics();
getWindowManager().getDefaultDisplay().getMetrics(dm);
width = dm.widthPixels;
height = dm.heightPixels;
double fWidth = width * (0.70);
Log.d("Width is:- ", ">>>>>>>>>>>>>>>>" + fWidth);
w1 = (int) Math.round(fWidth);
Log.d("Width after roundin is:- ", ">>>>>>>>>>>>>>>>" + width);
cropImageWidth = (int) TypedValue.applyDimension(
TypedValue.COMPLEX_UNIT_DIP, w1, r.getDisplayMetrics());
// etc...
cropImageHeight = (int) TypedValue.applyDimension(
TypedValue.COMPLEX_UNIT_DIP, w1, r.getDisplayMetrics());
int actionBarHeight = (int) TypedValue.applyDimension(
TypedValue.COMPLEX_UNIT_DIP, 40, r.getDisplayMetrics());
userImageLink = getIntent().getStringExtra("path");
mImg = (ImageView) findViewById(R.id.cp_img);
mTemplateImg = (ImageView) findViewById(R.id.cp_face_template);
mImg.setOnTouchListener(this);
// Get screen size in pixels.
// DisplayMetrics metrics = new DisplayMetrics();
// getWindowManager().getDefaultDisplay().getMetrics(metrics);
// mScreenWidth = metrics.widthPixels;
Display display = getWindowManager().getDefaultDisplay();
Point size = new Point();
display.getSize(size);
int statusBarHeight = (int) Math.ceil(25 * (getResources()
.getDisplayMetrics().density));
Log.e("size.x", "" + size.x);
Log.e("size.y", "" + (size.y - statusBarHeight - actionBarHeight));
// Set template image accordingly to device screen size.
Bitmap faceTemplate = BitmapFactory.decodeResource(getResources(),
R.drawable.four);
faceTemplate = Bitmap.createScaledBitmap(faceTemplate, cropImageWidth,
cropImageHeight, true);
mTemplateImg.setImageBitmap(faceTemplate);
// cropImageWidth = faceTemplate.getWidth();
// cropImageHeight = faceTemplate.getHeight();
// Log.e("getWidth", "" + faceTemplate.getWidth());
// Log.e("getHeight", "" + faceTemplate.getHeight());
File imgFile = new File("" + userImageLink);
if (imgFile.exists()) {
Bitmap myBitmap = BitmapFactory.decodeFile(imgFile
.getAbsolutePath());
// Drawable d = new BitmapDrawable(getResources(), myBitmap);
mImg.setImageBitmap(myBitmap);
mImageHeight = myBitmap.getHeight();
mImageWidth = myBitmap.getWidth();
}
// View is scaled by matrix, so scale initially
mMatrix.postScale(mScaleFactor, mScaleFactor);
mImg.setImageMatrix(mMatrix);
// Setup Gesture Detectors
mScaleDetector = new ScaleGestureDetector(getApplicationContext(),
new ScaleListener());
mMoveDetector = new MoveGestureDetector(getApplicationContext(),
new MoveListener());
// Instantiate Thread Handler.
// mCropHandler = new CropHandler(this);
}
public void onCancelImageButton(View v) {
Intent intent = new Intent();
setResult(RESULT_CANCELED, intent);
finish();
}
public void onCropImageButton(View v) {
// Create progress dialog and display it.
// mProgressDialog = new ProgressDialog(v.getContext());
// mProgressDialog.setCancelable(false);
// mProgressDialog.setProgressStyle(ProgressDialog.STYLE_SPINNER);
// mProgressDialog.setMessage("Please wait...");
// mProgressDialog.show();
// Setting values so that we can retrive the image from
// ImageView multiple times.
mImg.buildDrawingCache(true);
mImg.setDrawingCacheEnabled(true);
mTemplateImg.buildDrawingCache(true);
mTemplateImg.setDrawingCacheEnabled(true);
// Create new thread to crop.
new Thread(new Runnable() {
#Override
public void run() {
Bitmap croppedImg = null;
croppedImg = ImageProcess.cropImage(mImg.getDrawingCache(true),
mTemplateImg.getDrawingCache(true), cropImageWidth,
cropImageHeight);
mImg.setDrawingCacheEnabled(false);
mTemplateImg.setDrawingCacheEnabled(false);
if (croppedImg != null) {
// mProgressDialog.dismiss();
Utils.storeImage(croppedImg, "temp" + Const.ImageExtension);
Intent intent = new Intent();
setResult(RESULT_OK, intent);
finish();
} else {
// mProgressDialog.dismiss();
Intent intent = new Intent();
setResult(RESULT_CANCELED, intent);
finish();
}
}
}).start();
}
#SuppressLint("ClickableViewAccessibility")
public boolean onTouch(View v, MotionEvent event) {
mScaleDetector.onTouchEvent(event);
mMoveDetector.onTouchEvent(event);
float scaledImageCenterX = (mImageWidth * mScaleFactor) / 2;
float scaledImageCenterY = (mImageHeight * mScaleFactor) / 2;
mMatrix.reset();
mMatrix.postScale(mScaleFactor, mScaleFactor);
mMatrix.postRotate(mRotationDegrees, scaledImageCenterX,
scaledImageCenterY);
mMatrix.postTranslate(mFocusX - scaledImageCenterX, mFocusY
- scaledImageCenterY);
ImageView view = (ImageView) v;
view.setImageMatrix(mMatrix);
return true;
}
private class ScaleListener extends
ScaleGestureDetector.SimpleOnScaleGestureListener {
#Override
public boolean onScale(ScaleGestureDetector detector) {
mScaleFactor *= detector.getScaleFactor();
mScaleFactor = Math.max(0.1f, Math.min(mScaleFactor, 10.0f));
return true;
}
}
private class MoveListener extends
MoveGestureDetector.SimpleOnMoveGestureListener {
#Override
public boolean onMove(MoveGestureDetector detector) {
PointF d = detector.getFocusDelta();
mFocusX += d.x;
mFocusY += d.y;
return true;
}
}
}
(JAVA FILE 2)
public class ImageProcess {
public static Bitmap cropImage(Bitmap img, Bitmap templateImage, int width,
int height) {
// Merge two images together.
Bitmap bm = Bitmap.createBitmap(img.getWidth(), img.getHeight(),
Bitmap.Config.ARGB_8888);
Canvas combineImg = new Canvas(bm);
combineImg.drawBitmap(img, 0f, 0f, null);
// Create new blank ARGB bitmap.
Bitmap finalBm = Bitmap.createBitmap(width, height,
Bitmap.Config.ARGB_8888);
// Get the coordinates for the middle of combineImg.
int hMid = bm.getHeight() / 2;
int wMid = bm.getWidth() / 2;
int hfMid = finalBm.getHeight() / 2;
int wfMid = finalBm.getWidth() / 2;
finalBm = Bitmap.createBitmap(bm, (wMid - wfMid), (hMid - hfMid),
width, height);
// Get rid of images that we finished with to save memory.
img.recycle();
templateImage.recycle();
bm.recycle();
return finalBm;
}
}
(XML FILE 1)
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical" >
<innovify.hustl.library.CustomTextView
android:id="#+id/fcp_info_text"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="#string/cp_info_text"
android:textAppearance="?android:attr/textAppearanceMedium"
android:visibility="gone" />
<FrameLayout
android:layout_width="fill_parent"
android:layout_height="0dp"
android:layout_weight="1.0" >
<ImageView
android:id="#+id/cp_img"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:layout_gravity="center"
android:contentDescription="#string/cp_image_contentDesc"
android:scaleType="matrix" />
<ImageView
android:id="#+id/cp_face_template"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:layout_gravity="center"
android:contentDescription="#string/cp_template_contentDesc"
android:scaleType="centerInside"
android:src="#drawable/four" />
</FrameLayout>
<LinearLayout
style="?android:attr/buttonBarStyle"
android:layout_width="fill_parent"
android:layout_height="40dp"
android:orientation="horizontal" >
<innovify.hustl.library.CustomButton
style="?android:attr/buttonBarButtonStyle"
android:layout_width="0dp"
android:layout_height="40dp"
android:layout_gravity="center"
android:layout_marginLeft="5dp"
android:layout_marginRight="5dp"
android:layout_weight="1"
android:background="#e2e2e2"
android:gravity="center"
android:onClick="onCancelImageButton"
android:text="#string/cancel" />
<innovify.hustl.library.CustomButton
style="?android:attr/buttonBarButtonStyle"
android:layout_width="0dp"
android:layout_height="40dp"
android:layout_gravity="center"
android:layout_marginLeft="5dp"
android:layout_marginRight="5dp"
android:layout_weight="1"
android:background="#e2e2e2"
android:gravity="center"
android:onClick="onCropImageButton"
android:text="#string/cp_crop_button" />
</LinearLayout>
Output:
Got This Error:-
12-08 13:35:38.108: E/AndroidRuntime(15191): FATAL EXCEPTION: Thread-1317
12-08 13:35:38.108: E/AndroidRuntime(15191): java.lang.IllegalArgumentException: x must be >= 0
12-08 13:35:38.108: E/AndroidRuntime(15191): at android.graphics.Bitmap.checkXYSign(Bitmap.java:280)
12-08 13:35:38.108:
for custom shape in imageview,
you can use this lib
https://github.com/siyamed/android-shape-imageview
https://github.com/MostafaGazar/CustomShapeImageView