I am trying to rename an image in Gallery taken from Camera to give a new name. When I renamed the file the original image disappears showing 2 black squares . Can any one help me in sorting this issue by telling me procedure to rename Gallery Image.
Path is as follows : /mnt/sdcard/DCIM/Camera
I tried to update the Image title through content provider as below:
ContentValues val = new ContentValues();
val.put(Images.Media.TITLE, "ImageTitle23");
getContentResolver().update(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, val, null, null);
The image title is changed in Gallery.
But when I try to query the updated image as below I am getting the name same as previous one :
final String[] imageColumns = { MediaStore.Images.Media._ID, MediaStore.Images.Media.DATA };
final String imageOrderBy = MediaStore.Images.Media._ID+" DESC";
Cursor imageCursor = managedQuery(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, imageColumns, MediaStore.Images.Media._ID+"="+id, null, imageOrderBy);
if(imageCursor.moveToFirst()){
int idd = imageCursor.getInt(imageCursor.getColumnIndex(MediaStore.Images.Media._ID));
String fullPath = imageCursor.getString(imageCursor.getColumnIndex(MediaStore.Images.Media.DATA));
Can anyone help me in sorting out this issue?
The MediaStore looks for changes in your pictures BUT it will not react to all changes in real time. Each time you do such a modification, you should ask the MediaScanner to scan this file:
MediaScannerConnection.scanFile(
getApplicationContext(),
new String[]{file.getAbsolutePath()},
null,
new OnScanCompletedListener() {
#Override
public void onScanCompleted(String path, Uri uri) {
Log.v("grokkingandroid",
"file " + path + " was scanned seccessfully: " + uri);
}
});
Also, you should check this blog post that gives a lot of useful informations on this usecase.
The Gallery is interacting with the MediaStore content provider. If you change the name of the image file you probably need to update the field in the content provider.
You can read up on it in the MediaStore reference : http://developer.android.com/reference/android/provider/MediaStore.Images.Media.html
Potentially you can just trigger a refresh of the MediaStore. Look at this thread : How can I refresh MediaStore on Android?
Related
I use MediaStore to get all Images from Android device. Then after I delete some of the Images from File Manager. Followed I use MediaStore again to get Images, and I get all deleted files which is problem.
Why MediaStore returns files that are no longer are on the device(Deleted from device) ?
Code which I am using to retrieve image from MediaStore.
Uri uri = android.provider.MediaStore.Images.Media.EXTERNAL_CONTENT_URI;
String[] projection = {MediaStore.MediaColumns.DATA, MediaStore.Images.Media.BUCKET_DISPLAY_NAME};
Cursor cursor = activity.getContentResolver().query(uri, projection, null, null, MediaStore.MediaColumns.DATE_ADDED + " DESC");
String ImagePath = cursor.getString(cursor.getColumnIndexOrThrow(MediaStore.MediaColumns.DATA));
Help to resolve this issue.
Why MediaStore returns files that are no longer are on the device(Deleted from device) ?
Because whatever file manager you used did not do anything to inform the MediaStore about the deletion of the files. MediaStore will find out eventually, but it may be several hours.
You can rescan Media using below code
MediaScannerConnection.scanFile(context, new String[]{imagePath}, null, new MediaScannerConnection.OnScanCompletedListener() {
public void onScanCompleted(String path, Uri uri) {
//something that you want to do
}
});
I am querying the Images table to get all pictures in the MediaStore.Images.Media.EXTERNAL_CONTENT_URI directory.
See the following query:
String[] what = new String[]{ MediaStore.Images.ImageColumns.DATE_TAKEN,
MediaStore.Images.ImageColumns._ID,
MediaStore.Images.ImageColumns.MIME_TYPE,
MediaStore.Images.ImageColumns.DATA };
String where = MediaStore.Images.Media.MIME_TYPE + "='image/jpeg'" +
" OR " + MediaStore.Images.Media.MIME_TYPE + "='image/png’";
Cursor cursor = getContext().getContentResolver()
.query(MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
what,
where,
null,
MediaStore.Images.ImageColumns.DATE_TAKEN + " DESC”);
Now, I’d like to have an Uri pointing to each of the result.
This is what I am doing right now:
int dataIndex = cursor.getColumnIndex(MediaStore.Images.ImageColumns.DATA);
String path = cursor.getString(dataIndex);
final Uri uri = Uri.fromFile(new File(path));
E.g., I take the path from the DATA column, create a file and use Uri.fromFile. I have two questions.
Is this guaranteed to work? Is the query above guaranteed to return paths in the data column? It works for all the pictures in my phone: path is always a path, like /storage/0/whatever.jpg, and uri.toString() is the same but with the file scheme. Still, pictures can very well be defined by content:// uris, but I fail to see how (and if) these are represented in the images table.
If not, what should I expect in the DATA column, and how to get an Uri from it?
Is the query above guaranteed to return paths in the data column?
It should return something. That "something" may not be usable. For example, the image might be on removable storage, and you cannot access it directly.
how to get an Uri from it?
You don't. You construct a Uri from the _ID:
Uri imageUri=
ContentUris
.withAppendedId(MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
cursor.getInt(cursor.getColumnIndex(MediaStore.Images.ImageColumns._ID)));
I'm searching a way to find and load images from Pictures folder depending on creation date. For example I want to load all pictures took in the last month, but I don't know their name.
I already read about Picasso library, but as written in the documentation, the url is required.
So instead of scan the entire folder and then check creation date, does it exist a quicker way to accomplish this task?
Thanks
Maybe this could work for you. You may add selection clauses to query as well, to filter files by date for example.
Uri uri = MediaStore.Images.Media.EXTERNAL_CONTENT_URI;
Cursor cursor = getContentResolver().query(uri, new String[] {MediaStore.Images.Media.DATA}, null, null, MediaStore.Images.Media.DATE_ADDED + " ASC");
if (cursor != null) {
while (cursor.moveToNext()) {
Uri imageUri = Uri.parse(cursor.getString(0));
}
cursor.close();
}
Use Timestamp while storing Images
String currentDateTimeString = DateFormat.getDateTimeInstance().format(new Date());
Give this as file name. This works only if you use separate activity for clicking images.
I'm using org.apache.commons.io.FileUtils to move files from one directory to another, like so:
File source = new File("/my/image/directory/image.jpg";
File destination = new File("/new/image/directory/image.jpg");
FileUtils.moveFile(source, destination);
Note that the source directory is an external directory and destination is an internal directory.
After above code is executed, I query to get the files of my internal directory like so:
File vaultDir = ctx.getDir("dir_name", Context.MODE_PRIVATE);
String[] fileList = vaultDir.list();
//Iterate and print file names
This is working as intended. But when i query the MediaStore like so:
ArrayList<GridViewObject> objects = new ArrayList<>();
String[] mProjection = {MediaStore.Images.Media.DISPLAY_NAME,
MediaStore.Images.Media.DATA};
ContentResolver cr = ctx.getContentResolver();
Cursor mCursor = cr.query(MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
mProjection,
null,
null,
MediaStore.Images.Media.DEFAULT_SORT_ORDER);
mCursor.moveToFirst();
while (!mCursor.isAfterLast()) {
GridViewObject tmpGridViewObject = new GridViewObject();
tmpGridViewObject.setTitle(mCursor.getString(0));
tmpGridViewObject.setUrl(mCursor.getString(1));
objects.add(tmpGridViewObject);
mCursor.moveToNext();
}
The image is still returned to me by the query. Also, when I open my camera gallery app, the image is still there, as if it was never deleted.
I noticed that if I restart the phone, the image disappears from my device camera gallery app as intended (and above query return correct result). So I think it might be an indexing problem.
What do I need to do to "update" the MediaStore to show the intended result?
I solved this by instead of deleting the file using FileUtils.delete(srcFile, destFile); i copied the the file using FileUtils.copy(srcFile, destFile); and then to refresh MediaStore i used the following code to delete the source entry:
String selection = MediaStore.Images.Media.DATA + "='" + source.getAbsolutePath() + "'";
ctx.getContentResolver().delete(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, selection, null);
Credit goes to Pascal's answer to this question.
For my application, I need to refresh thumbnail image of gallery.
Because whenever I update my image content that thing don't reflected on thumbnail. The thumbnail image show first time image creation data not the present one.
But actual image contain new data so I need to reflect it into thumbnail also.
After wandering this forum I found following code snipper to delete current thumbnail but I can't able to call this function because I don't able to get photoId.
private static void removeThumbnails(ContentResolver contentResolver, long photoId) {
Cursor thumbnails = contentResolver.query(Thumbnails.EXTERNAL_CONTENT_URI, null, Thumbnails.IMAGE_ID + "=?", new String[]{String.valueOf(photoId)}, null);
for (thumbnails.moveToFirst(); !thumbnails.isAfterLast(); thumbnails.moveToNext()) {
long thumbnailId = thumbnails.getLong(thumbnails.getColumnIndex(Thumbnails._ID));
String path = thumbnails.getString(thumbnails.getColumnIndex(Thumbnails.DATA));
File file = new File(path);
if (file.delete()) {
contentResolver.delete(Thumbnails.EXTERNAL_CONTENT_URI, Thumbnails._ID + "=?", new String[]{String.valueOf(thumbnailId)});
}
}
At present I was calling this function as
removeThumbnails(pexelMimics.getContentResolver(),
ContentUris.parseId(uri));
I think this trick will work for me. But this is my guess. If you guys have better solution for this problem then please help me.
At the time of image saving, I have to provide following code to delete image content.
activity.getContentResolver().delete(
MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
MediaColumns.DATA
+ "='"
+ GameManager.getInstance().getSavedImageFilePath()
.replaceAll("'", "''") + "'", null);
After this I got new content in thumbnail icon.
You don't mention what class and inheritance you have; if you are in a class the inherits BaseAdapter, then you can do
notifyDataSetChanged();
after you change the thumbs.