Recently, there's a mission. The main function points of the reconstructed album function module are as follows:
1 contentprovider scan phone picture get Cursor yourself write GridView because the system album can not be a picture multi-select and each mobile phone system album style is not unified
2 minutes before the album module is because there is no multiple folders to the system album all the photos out of the show
3 recently photographed or screen photos folder top and photo show in the GridView first
4 support format JPG PNG bmp JPEG
5 Multi-Image preview (not yet implemented)
First of all, look at a photo album interface without refactoring because the simulator often has fewer photos or does not use the real machine to demonstrate it is not very convenient to display with GIF animation
The default entry is this interface, all the photos on the phone are useless. The sort of user's recent photo-loading is faster but the user experience is not very good.
Here's a look at the effects of the new refactoring here special thanks Hyman Adu because basically is to make reference to them just read the code logic then make a slight change
First the default comes in is to pop-up Select Picture folder interface then focus is the default show is your recent photo album and the last photo shows the first bit in the GridView
Don't say much nonsense on the code
/ **
* Use ContentProvider to scan the pictures in the mobile phone. This method runs in a sub-thread to complete the scan of the pictures, and finally gets the folder with the most jpg
* /
private void getImages () {
if (! Environment.getExternalStorageState (). equals (
Environment.MEDIA_MOUNTED)) {
Toast.makeText (this, "No external storage", Toast.LENGTH_SHORT) .show ();
return;
}
mProgressDialog = ProgressDialog.show (this, null, "Loading ...");
mThread = new MineThread ();
mThread.start ();
}
MineThread mThread;
class MineThread extends Thread {
@Override
public void run () {
String firstImage = null;
Uri mImageUri = MediaStore.Images.Media.EXTERNAL_CONTENT_URI;
ContentResolver mContentResolver = ChoosePictureActivity.this
.getContentResolver ();
// Query only jpeg and png images
Cursor mCursor = mContentResolver.query (mImageUri, null, MediaStore.Images.Media.MIME_TYPE + "=? Or" + MediaStore.Images.Media.MIME_TYPE + "=? Or"
+ MediaStore.Images.Media.MIME_TYPE + "=?",
new String [] {"image / jpeg", "image / png", "image / bmp"},
MediaStore.Images.Media.DATE_ADDED + "DESC");
Log.e ("-----------------", mCursor.getCount () + "");
while (mCursor.moveToNext ()) {
// Get the path of the picture
String path = mCursor.getString (mCursor
.getColumnIndex (MediaStore.Images.Media.DATA));
Log.e ("-----------------", path);
// Validate the validity of the image in advance
final File file = new File (path);
if (! file.exists ()) {
throw new IllegalArgumentException ("Uri file does not exist");
// If an exception is thrown here, it is foreseen that an invalid picture is detected. At this point, the developer releases the following continue and then comments the code that throws the exception.
// continue;
}
// The path to the first image
if (firstImage == null)
firstImage = path;
// Get the parent path name of the image
File parentFile = new File (path) .getParentFile ();
if (parentFile == null)
continue;
String dirPath = parentFile.getAbsolutePath ();
ImageFloder imageFloder = null;
// Use a HashSet to prevent scanning the same file multiple times
if (mDirPaths.contains (dirPath)) {
continue;
} else {
mDirPaths.add (dirPath);
// initialize imageFloder
imageFloder = new ImageFloder ();
imageFloder.setDir (dirPath);
imageFloder.setFirstImagePath (path);
}
if (parentFile.list () == null) continue;
int picSize = parentFile.list (new FilenameFilter () {
@Override
public boolean accept (File dir, String filename) {
if (filename.endsWith (". jpg")
|| filename.endsWith (". png")
|| filename.endsWith (". jpeg")
|| filename.endsWith (". bmp"))
return true;
return false;
}
}). length;
totalCount + = picSize;
imageFloder.setCount (picSize);
mImageFloders.add (imageFloder);
if (picSize> mPicsSize) {
mPicsSize = picSize;
mImgDir = parentFile;
}
}
mCursor.close ();
mCursor = null;
// After the scan is completed, the auxiliary HashSet can also release the memory.
mDirPaths = null;
// Notify the Handler that the scanning of the image is complete
mHandler.sendEmptyMessage (0x110);
}
}
This is the core code snippet:
1 Determine the external storage first
2 Query content provider Android Multimedia database conditions determine the type of PNG jpg bmp to get the cursor and then traverse
3 Judging the picture validity gets the parent folder of the picture and the first picture in the folder
Here to get the parent folder is to do folder
The following is the Bean class for folder
public class ImageFloder
{
/ **
* Picture folder path
* /
private String dir;
/ **
* Path to the first picture
* /
private String firstImagePath;
/ **
* Name of the folder
* /
private String name;
/ **
* Number of pictures
* /
private int count;
public String getDir ()
{
return dir;
}
public void setDir (String dir)
{
this.dir = dir;
int lastIndexOf = this.dir.lastIndexOf ("/");
this.name = this.dir.substring (lastIndexOf);
}
public String getFirstImagePath ()
{
return firstImagePath;
}
public void setFirstImagePath (String firstImagePath)
{
this.firstImagePath = firstImagePath;
}
public String getName ()
{
return name;
}
public int getCount ()
{
return count;
}
public void setCount (int count)
{
this.count = count;
}
Ranch
}
Loading of the final image shows a Imageloader class used here but for most apps there's a picture frame for you personally recommended Universal-image-loader
This way, detailed code for the ListView and Girdview no longer shows the end of the article will post the relevant source code connection and display demo Just here there is an unresolved bug here
Brainstorm a moment to see:
You can clearly see that there are 0 bytes of invalid images but just because the format URI is exactly correct is the JPG suffix ending successfully loaded on the GridView display transparent
I tried to make a length judgement, but found that there was still no effect on the scan.
Validate the validity of a picture beforehand
Final file File = new file (path);
if (!file.exists ()) {
throw new IllegalArgumentException ("Uri file does not exist");
If an exception is thrown here, the preview checks to an invalid image at this point, the developer put the following continue release and then throw the exception code comments can be
Continue
}
This code is also made to judge but has not yet tried to be effective on this bug if you know this bug has a better solution to the Danale Welcome to the message is appreciated
The source and Demo address are attached at the end of the article:
Https://github.com/rongcloud/demo-app-android-v2 Welcome to Fork Star
Note: Photo album logic is all under the photo package directly try the APK effect in rongcloud.cn/downloads instantly scan code experience
Thanks
Copyright NOTICE: This article for Bo Master original article, without Bo Master permission not reproduced.
Android Multi-Folder album + Get recent Photo analysis