在我的android應用程序,我從API的加載圖像。但在網格視圖中加載圖像後,滾動不平滑。我使用異步線程來獲取圖像,以便它不會阻止用戶界面。滾動是不光滑的android網格視圖
現在有任何建議來提高滾動的性能。
在我的android應用程序,我從API的加載圖像。但在網格視圖中加載圖像後,滾動不平滑。我使用異步線程來獲取圖像,以便它不會阻止用戶界面。滾動是不光滑的android網格視圖
現在有任何建議來提高滾動的性能。
將圖像加載到單獨的線程中肯定有幫助,但是在這裏需要處理另一個重要的性能問題,那就是「查看可重用性」,一旦您在適配器中設置了圖像,請確保您實際上正在重用在適配器的getView方法中提供的視圖,並且每次調用該方法時都不會創建/膨脹新的Layout(GridElement),這通常是導致滾動在所有圖像加載後變慢的原因,有幾種可用模式解決這個問題,你應該閱讀有關ViewHolder,是最常見的,易於使用模式這個問題...
希望這有助於...
問候
現在,滾動很好,但圖像正在改變位置向下滾動。我傳遞imageView對象來設置下載後的圖像。我使用ViewHolder保存ImageView,但問題仍然存在 –
代碼getView()方法 {{{
@Override
public View getView(final int position, View convertView, ViewGroup parent) {
final HashMap<String, String> song = songsList.get(position);
imageURL = song.get(VariablesList.TAG_ALBUM_IMAGE);
View v = null;
if (convertView != null)
v = convertView;
else
v = inflater.inflate(R.layout.gridlayout_item, parent, false);
final ImageView imageView = (ImageView) v.findViewById(R.id.icon_image);
final Thread startAlbum = new Thread() {
public void run() {
imageView.setImageBitmap(AlbumList
.LoadImagetoGridView(imageURL));
synchronized (this) {
this.notifyAll();
}
}
};
synchronized (startAlbum) {
startAlbum.start();
try {
startAlbum.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
imageView.setOnClickListener(new View.OnClickListener() {
// @Override
public void onClick(View v) {
albumUrl = new StringBuffer(resources.getString(R.string.songsListURL));
String albumIndex = song.get("id");
albumName = (song.get("name"));
imageURL = song.get(VariablesList.TAG_ALBUM_IMAGE);
SongsList albumList = new SongsList(imageURL, albumUrl,
albumName,albumIndex,resources);
Thread threadAlbumList = new Thread(albumList);
threadAlbumList.start();
synchronized (albumList) {
try {
albumList.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
if (!NewMediaPlayer.mediaPlayer.isPlaying()) {
HashMap<String, String> playingSong = NewMediaPlayer.selectedSongs
.get(0);
if (playingSong != null) {
String url = playingSong.get("songUrl");
String songName = playingSong.get("songName");
if (songName != null)
{
NewMediaPlayer.songTitleLabel.setText(albumName
+ " - " + songName);
NewMediaPlayer.songTitle.setText(albumName+"-"+songName);
}
NewMediaPlayer.playSong(url);
}
}
}
});
TextView itemAlbumName = (TextView) v.findViewById(R.id.icon_text);
itemAlbumName.setText(song.get("name"));
itemAlbumName.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
HashMap<String, String> song = songsList.get(position);
String songIndex = song.get("id");
String albumName = (song.get("name"));
Intent in = new Intent(context, SongListActivity.class);
in.putExtra("albumIndex", songIndex);
in.putExtra("albumName", albumName);
in.putExtra("AlbumImage", song.get(VariablesList.TAG_ALBUM_IMAGE));
context.startActivity(in);
}
});
return v;
}
}}}
在強制主UI線程等待時,在單獨的線程中執行setImageBitmap有什麼意義? –
如何在UI上加載位圖圖像呢? –
僅僅在一個單獨的線程上執行它,幾乎就是你在做什麼,但是不需要等待,因爲它實際上將它加載到主線程上,因爲無論如何您都在等待它加載,所以最好的方法是讓線程運行自己做,一旦完成,然後你設置圖像,但是你必須使用處理程序,因爲爲了修改視圖,你需要在主線程中執行的代碼。現在,如果你正在從URL下載imgs看看這個抽象項目,它有一個完美的緩存圖像機制,所以如果一個圖像已經被下載,它只是從緩存中獲得它... –
而不是採取努力使用通用圖像裝載機library.And它的表現還是不錯的。 在onCreate方法 gridView.setAdapter(new ImageAdapter(this,ImagesArrayPath));
private static class ImageAdapter extends BaseAdapter {
private final String[] IMAGE_URLS ;
private LayoutInflater inflater;
private DisplayImageOptions options;
ImageAdapter(Context context,String source[]) {
inflater = LayoutInflater.from(context);
IMAGE_URLS=source;
options = new DisplayImageOptions.Builder()
.showImageOnLoading(R.mipmap.ico_place_holder)
.showImageForEmptyUri(R.drawable.ic_empty)
.showImageOnFail(R.drawable.ic_error)
.cacheInMemory(true)
.cacheOnDisk(true)
.considerExifParams(true)
.bitmapConfig(Bitmap.Config.RGB_565)
.build();
}
@Override
public int getCount() {
return IMAGE_URLS.length;
}
@Override
public Object getItem(int position) {
return null;
}
@Override
public long getItemId(int position) {
return position;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
final ViewHolder holder;
View view = convertView;
if (view == null) {
view = inflater.inflate(R.layout.item_grid_image, parent, false);
holder = new ViewHolder();
assert view != null;
holder.imageView = (ImageView) view.findViewById(R.id.image);
holder.progressBar = (ProgressBar) view.findViewById(R.id.progress);
view.setTag(holder);
} else {
holder = (ViewHolder) view.getTag();
}
ImageLoader.getInstance()
.displayImage(IMAGE_URLS[position], holder.imageView, options, new SimpleImageLoadingListener() {
@Override
public void onLoadingStarted(String imageUri, View view) {
holder.progressBar.setProgress(0);
holder.progressBar.setVisibility(View.VISIBLE);
}
@Override
public void onLoadingFailed(String imageUri, View view, FailReason failReason) {
holder.progressBar.setVisibility(View.GONE);
}
@Override
public void onLoadingComplete(String imageUri, View view, Bitmap loadedImage) {
holder.progressBar.setVisibility(View.GONE);
}
}, new ImageLoadingProgressListener() {
@Override
public void onProgressUpdate(String imageUri, View view, int current, int total) {
holder.progressBar.setProgress(Math.round(100.0f * current/total));
}
});
return view;
}
}
static class ViewHolder {
ImageView imageView;
ProgressBar progressBar;
}
願這能幫助你。享受編碼。
你重複使用ViewHolder模式嗎? –
您可以添加代碼(適用於您的適配器)(具體爲getView()方法) – Selecsosi
我也有過這個問題,我減少了我的圖像的大小,並完美的工作 –