我正在使用Picasso在Gridview和DBFlow中加载我的所有图像以保存在本地数据库中。但是当我第一次下载图像时,如果我在gridview中滚动,我会遇到问题。下一个图像具有先前的图像,并且1秒后加载好的图像。我必须滚动5次或更多次,当所有图像都加载时我没有这个问题但是第一次是。
您有想法优化我的代码吗?
的GridView
<?xml version="1.0" encoding="utf-8"?>
<GridView xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/gridview"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:columnWidth="130dp"
android:numColumns="auto_fit"
android:verticalSpacing="10dp"
android:horizontalSpacing="10dp"
android:stretchMode="columnWidth"
android:gravity="center"
android:background="@color/colorAppBackground"/>
项目网格
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="130dp">
<ImageView
android:id="@+id/iv_thumbnail"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:adjustViewBounds="true"
android:scaleType="centerCrop"/>
<TextView
android:id="@+id/text_thumb"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:gravity="center"
android:textColor="@android:color/white"
android:background="#99000000"/>
</RelativeLayout>
活动
public class GalleryActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_gallery);
Bundle bundle = getIntent().getExtras();
int idAccount = bundle.getInt("idAccount");
callAdminPictures(idAccount);
}
public void callAdminPictures(final int idAccount){
// Build REST Adapter
Retrofit restAdapter = new Retrofit.Builder()
.baseUrl(Globals.SERVER_NAME)
.addConverterFactory(SimpleXmlConverterFactory.create())
.build();
// Create the App Service
ApplicationService appService = restAdapter.create(ApplicationService.class);
// Call Get admin pictures WS
Call<AdminPictures> getAdminPicturesWS = appService.getAdminPictures(idAccount);
getAdminPicturesWS.enqueue(new Callback<AdminPictures>() {
@Override
public void onResponse(Call<AdminPictures> call, Response<AdminPictures> response) {
AdminPictures apResponse = response.body();
List<PictureInfos> pictureInfos = apResponse.getPicturesList();
for (PictureInfos infos : pictureInfos) {
if (infos.exists()) {
infos.update();
} else {
infos.save();
}
}
List<PictureInfos> tablePictureInfos = new Select()
.from(PictureInfos.class)
.where(PictureInfos_Table.idAccount.is("" + idAccount))
.orderBy(PictureInfos_Table.idPicture, false)
.queryList();
GridView gridView = (GridView) findViewById(R.id.gridview);
gridView.setAdapter(new ImageAdapter(GalleryActivity.this, tablePictureInfos));
gridView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
Toast.makeText(GalleryActivity.this, "" + position, Toast.LENGTH_SHORT).show();
}
});
}
@Override
public void onFailure(Call<AdminPictures> call, Throwable t) {
if (t.getMessage() != null) {
Log.e("AdminPictures WS Fail", t.getMessage());
}
}
});
}
适配器
public class ImageAdapter extends BaseAdapter {
private Context mContext;
private LayoutInflater mLayoutInflater;
private List<PictureInfos> mPInfoList;
private boolean mToSave;
public ImageAdapter(Context context, List<PictureInfos> pInfoList) {
mContext = context;
mPInfoList = pInfoList;
mLayoutInflater = LayoutInflater.from(context);
}
@Override
public int getCount() {
return mPInfoList.size();
}
@Override
public Object getItem(int position) {
return null;
}
@Override
public long getItemId(int position) {
return 0;
}
@Override
public View getView(final int position, View convertView, ViewGroup parent) {
View view;
final ImageView imageView;
final TextView legend;
if(convertView == null){
view = mLayoutInflater.inflate(R.layout.thumbnail_gallery, parent, false);
}else{
view = convertView;
}
imageView = (ImageView) view.findViewById(R.id.iv_thumbnail);
legend = (TextView) view.findViewById(R.id.text_thumb);
final File file = new File(mContext.getExternalFilesDir(Environment.DIRECTORY_PICTURES), mPInfoList.get(position).getFilename());
mToSave = !file.exists();
Target target = new Target() {
@Override
public void onBitmapLoaded(final Bitmap bitmap, Picasso.LoadedFrom from) {
if(mToSave) {
new Thread(new Runnable() {
@Override
public void run() {
try {
FileOutputStream fileOutput = new FileOutputStream(file);
Log.i("catch", mPInfoList.get(position).getFilename());
bitmap.compress(Bitmap.CompressFormat.JPEG, 100, fileOutput);
fileOutput.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}).start();
}
imageView.setImageBitmap(bitmap);
if (mPInfoList.get(position).getFilename() != null) {
legend.setText(mPInfoList.get(position).getLegend());
}
}
@Override
public void onBitmapFailed(Drawable errorDrawable) {
}
@Override
public void onPrepareLoad(Drawable placeHolderDrawable) {
}
};
String pic = Globals.SERVER_NAME+Globals
.ACCOUNT_SERVER_PATH+mPInfoList
.get(position).getFolderPath()+"/"+
VgzTools.addSuffix(mPInfoList.get(position).getFilename(), "-thumb");
imageView.setTag(target);
if(!file.exists()){
Picasso.with(mContext)
.load(pic)
.into(target);
mToSave = true;
}else{
Picasso.with(mContext)
.load(file)
.into(target);
mToSave = false;
}
return view;
}
答案 0 :(得分:2)
在getView()里面放了这行
imageView.setImageDrawable(null);
由于视图回收,之前的图片即将到来。对于每个项目,您并不总是获得新视图,而是回收视图以节省内存。因此,一旦您滚动了最初可见的项目,您将获得已经在其中设置了图像的上一个项目的视图。所以你必须明确地删除它。
答案 1 :(得分:1)
我的猜测是,因为您未明确清除getView()
中的imageView,所以当它被回收时,它会保留当前图像(IE - 当它被&#39;以convertView
)传入。毕加索最终会打电话给onBitmapLoaded()
,但在此之前,你已经离开了“老人”。图像。
尝试明确清除图像。