我一直在努力解决这个问题,但似乎无法找到解决方案。
问题即使从MediaStore获取专辑封面图并将其转换为drawable后,也会通过HashMap(String,Object)将其分配给自定义ListView布局中的ImageView,但最后在实际设备和模拟器上运行后,没有显示专辑封面。
也没有LogCat错误。自定义列表视图布局的ImageView不显示专辑封面。
public class AllSongs extends Fragment
{
Bitmap bitmap = null;
BitmapDrawable drawable = null;
private ArrayList<HashMap<String,Object>> list = new ArrayList<HashMap<String,Object>>();
private HashMap<String, Object> item;
private SimpleAdapter sa;
private ListView listview;
...
}
@Override
public void onViewCreated(View view, Bundle savedInstanceState)
{
...
AsyncTaskRunner runner = new AsyncTaskRunner();
runner.execute("500");
}
private class AsyncTaskRunner extends AsyncTask<String, String, String>
{
@Override
protected String doInBackground(String... params) {
getAllMusicFiles();
return "Done!";
}
@Override
protected void onPostExecute(String result) {
super.onPostExecute(result);
listview.setAdapter(sa); //Set all the file in the list.
}
}
private void getAllMusicFiles() {
// TODO Auto-generated method stub
//Some audio may be explicitly marked as not being music
String selection = MediaStore.Audio.Media.IS_MUSIC + " != 0";
String[] projection = {
MediaStore.Audio.Media.TITLE,
MediaStore.Audio.Media.ARTIST,
MediaStore.Audio.Media.ALBUM,
MediaStore.Audio.Media.ALBUM_ID
};
Cursor cursor = getActivity().getApplicationContext().getContentResolver().query(
MediaStore.Audio.Media.EXTERNAL_CONTENT_URI,
projection,
selection,
null,
null);
while(cursor.moveToNext()){
item = new HashMap<String,Object>();
String title = cursor.getString(cursor.getColumnIndexOrThrow(MediaStore.Audio.Media.TITLE));
String artist = cursor.getString(cursor.getColumnIndexOrThrow(MediaStore.Audio.Media.ARTIST));
String album = cursor.getString(cursor.getColumnIndexOrThrow(MediaStore.Audio.Media.ALBUM));
long albumId = cursor.getLong(cursor.getColumnIndexOrThrow(MediaStore.Audio.Media.ALBUM_ID));
final Uri ART_CONTENT_URI = Uri.parse("content://media/external/audio/albumart");
Uri albumArtUri = ContentUris.withAppendedId(ART_CONTENT_URI, albumId);
ContentResolver res = context.getContentResolver();
InputStream in;
try { // Yes, the album art has been found. I am sure of this.
if(bitmap != null)
{
bitmap.recycle();
bitmap = null;
if(drawable != null)
{
drawable = null;
}
}
in = res.openInputStream(albumArtUri);
bitmap = BitmapFactory.decodeStream(in);
drawable = new BitmapDrawable(getResources(), bitmap);
} catch (FileNotFoundException e) { // Album not found so set default album art
e.printStackTrace();
drawable = (BitmapDrawable) getActivity().getResources().getDrawable(R.drawable.default_albumart);
}
item.put("icon", drawable);
item.put("title", title);
item.put("artist", artist);
list.add(item);
if(cursor.isLast())
{
sa = new SimpleAdapter(getActivity(), list,
R.layout.custom_listview_layout,
new String[] {"icon", "title","artist" },
new int[] {R.id.icon,R.id.title, R.id.artist});
}
}
}
我检测到drawable可能是导致图像无法显示的那个,因为如果我更换 -
item.put("icon", drawable);
with -
item.put("icon", R.drawable.default_albumart);
显示默认的专辑封面。
知道造成这种情况的原因是什么?
答案 0 :(得分:0)
您的适配器实现导致了问题,而不是Drawable
。
看看这两行代码:
item.put("icon", drawable)
- 这会将Drawable对象放入您的hashmap
item.put("icon", R.drawable.default_albumart)
- 这会为您的地图添加int
值,但由于地图仅适用于对象,因此在放置之前为autoboxed
因此,问题是您的适配器可以使用drawables的整数标识符,但不适用于drawables本身。这些是SimpleAdapter
要解决此问题,我建议您实施自定义CursorAdapter
。它的实现非常简单,并且可以避免不必要的步骤,例如创建不必要的列表,哈希映射等,浪费应用程序内存。
随意在评论中提出任何其他问题,祝你好运!
答案 1 :(得分:0)
答案是由Drew正确给出的,但这是最终如何实施的。以下是更改 -
private void getAllMusicFiles() {
// TODO Auto-generated method stub
//Some audio may be explicitly marked as not being music
String selection = MediaStore.Audio.Media.IS_MUSIC + " != 0";
String[] projection = {
MediaStore.Audio.Media._ID, // this is required acc to documentation
MediaStore.Audio.Media.TITLE,
MediaStore.Audio.Media.ARTIST,
MediaStore.Audio.Media.ALBUM,
MediaStore.Audio.Media.ALBUM_ID
};
cursor = getActivity().getApplicationContext().getContentResolver().query(
MediaStore.Audio.Media.EXTERNAL_CONTENT_URI,
projection,
selection,
null,
null);
getActivity().startManagingCursor(cursor);
listview.setAdapter(new CustomCursorAdapter(context, cursor));
}
@Override
public void onDestroy() {
// TODO Auto-generated method stub
if(cursor != null)
{
getActivity().stopManagingCursor(cursor);
cursor.close();
}
super.onDestroy();
}
删除了AsyncTask,因为它不再需要了。
@Override
public void onViewCreated(View view, Bundle savedInstanceState)
{
...
AsyncTaskRunner runner = new AsyncTaskRunner();
runner.execute("500");
}
CustomCursorAdapter.java -
public class CustomCursorAdapter extends CursorAdapter {
@SuppressWarnings("deprecation")
public CustomCursorAdapter(Context context, Cursor c) {
super(context, c);
// TODO Auto-generated constructor stub
}
private Bitmap bitmap = null;
private BitmapDrawable drawable = null;
@Override
public void bindView(View view, Context context, Cursor cursor) {
// TODO Auto-generated method stub
TextView title1 = (TextView) view.findViewById(R.id.title);
TextView artist1 = (TextView) view.findViewById(R.id.artist);
ImageView album1 = (ImageView) view.findViewById(R.id.icon);
String title = cursor.getString(cursor.getColumnIndexOrThrow(MediaStore.Audio.Media.TITLE));
String artist = cursor.getString(cursor.getColumnIndexOrThrow(MediaStore.Audio.Media.ARTIST));
String album = cursor.getString(cursor.getColumnIndexOrThrow(MediaStore.Audio.Media.ALBUM));
long albumId = cursor.getLong(cursor.getColumnIndexOrThrow(MediaStore.Audio.Media.ALBUM_ID));
StringBuilder titleBuild = new StringBuilder();
titleBuild.append(title);
if(titleBuild.length() > 35)
{
titleBuild.setLength(32);
title = titleBuild.toString()+"...";
}
else
{
title = titleBuild.toString();
}
StringBuilder artistBuild = new StringBuilder();
artistBuild.append(artist);
if(artistBuild.length() > 35)
{
artistBuild.setLength(32);
artist = artistBuild.toString()+"...";
}
else
{
artist = artistBuild.toString();
}
final Uri ART_CONTENT_URI = Uri.parse("content://media/external/audio/albumart");
Uri albumArtUri = ContentUris.withAppendedId(ART_CONTENT_URI, albumId);
ContentResolver res = context.getContentResolver();
InputStream in;
try {
if(bitmap != null)
{
bitmap = null;
if(drawable != null)
{
drawable = null;
}
}
in = res.openInputStream(albumArtUri);
bitmap = BitmapFactory.decodeStream(in);
// bitmap = MediaStore.Images.Media.getBitmap(context.getContentResolver(), albumArtUri);
drawable = new BitmapDrawable(context.getResources(), bitmap);
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
drawable = (BitmapDrawable) context.getResources().getDrawable(R.drawable.default_albumart);
}
album1.setImageDrawable(drawable);
title1.setText(title);
artist1.setText(artist);
}
@Override
public View newView(Context context, Cursor cursor, ViewGroup parent) {
// TODO Auto-generated method stub
LayoutInflater inflater = (LayoutInflater)context.getSystemService
(Context.LAYOUT_INFLATER_SERVICE);
return inflater.inflate(R.layout.custom_listview_layout, parent, false);
}
}