使用 ArrayList 使用 ParseFile 下载多个图像

Posted

技术标签:

【中文标题】使用 ArrayList 使用 ParseFile 下载多个图像【英文标题】:downloading multiple images with ParseFile using ArrayList 【发布时间】:2018-06-09 11:57:12 【问题描述】:

我无法将图像位图存储在全局数组列表中。我已经声明了一个全局数组列表 final ArrayList prod_image = new ArrayList(); 我正在尝试从 Parse Server 调用图像并将其保存在数组列表中。 在 ParseFile 回调中,我试图保存位图, prod_image.add(bp); 但是,该数组在回调之外返回一个空值。

如何在回调中将图像存储在数组中?

ParseFile file = (ParseFile) object.get("image_book");

                            file.getDataInBackground(new GetDataCallback() 
                                @Override
                                public void done(byte[] data, ParseException e) 
                                    if(e== null && data != null)

                                       Bitmap bitmap = BitmapFactory.decodeByteArray(data, 0, data.length);

                                       if(bitmap != null)
                                           Log.i("image download","Success");

                                           bp = bitmap;
                                           Log.i("image Content",bp.toString());

                                           prod_image.add(bp);
                                           //adapter.notifyDataSetChanged();
                                           if(prod_image.size()>0)
                                               Log.i("inside count","Ok");
                                           else 
                                               Log.i("inside Count","Not Ok");
                                           


                                           //adapter.notifyDataSetChanged();

                                       else 
                                           Log.i("image download","Failure");
                                       
                                    else 
                                        e.printStackTrace();
                                    
                                
                            );


`
public class UserFeed extends AppCompatActivity 

    ImageView account;
    ImageView notif;
    RecyclerView recyclerView;
    RecyclerView.Adapter adapter;
    //UserFeedAdapter adapter;
    ArrayList<String> prod_name ;
    ArrayList<String> prod_cat;
    ArrayList<String> prod_pub;
    ArrayList<String> prod_price;

    Bitmap bp=null;
    RecyclerView.LayoutManager layoutManager;
    final ArrayList<Bitmap> prod_image =  new ArrayList<Bitmap>();
    //final Bitmap bitmap;


    @Override
    protected void onCreate(Bundle savedInstanceState) 
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_user_feed);
        //setTitle("My Feed");

        account = (ImageView)findViewById(R.id.account);
        notif = (ImageView)findViewById(R.id.notif);

        account.setOnClickListener(new View.OnClickListener() 
            @Override
            public void onClick(View v) 
                Intent intent = new Intent(getApplicationContext(), AccountActivity.class);
                startActivity(intent);
            
        );

        notif.setOnClickListener(new View.OnClickListener() 
            @Override
            public void onClick(View v) 
                Intent intent = new Intent(getApplicationContext(), NotificationActivity.class);
                startActivity(intent);
            
        );

        //myListView = (ListView)findViewById(R.id.listView);
        recyclerView = (RecyclerView) findViewById(R.id.recyclerView);
        recyclerView.setHasFixedSize(true);

        layoutManager = new LinearLayoutManager(this);
        recyclerView.setLayoutManager(layoutManager);


        prod_name = new ArrayList<>();
        prod_cat = new ArrayList<>();
        prod_pub = new ArrayList<>();
        prod_price = new ArrayList<>();


        //MyData myImage = new MyData();

        ParseQuery<ParseObject> dashboardQuery = new ParseQuery<ParseObject>("Sell");
        dashboardQuery.findInBackground(new FindCallback<ParseObject>() 
            @Override
            public void done(List<ParseObject> objects, ParseException e) 
                if(e == null)
                    if(objects.size() > 0)
                        for (final ParseObject object : objects)
                            String name = (String) object.get("name");
                            String cat = (String) object.get("category");
                            String pub = (String)object.get("publisher");
                            String price = (String) object.get("price");
                            //Bitmap image = (Bitmap)object.get("image_book");

                            prod_name.add(name);
                            prod_cat.add(cat);
                            prod_pub.add(pub);
                            prod_price.add(price);


                            //prod_image.add(image);

                            ParseFile file = (ParseFile) object.get("image_book");

                            file.getDataInBackground(new GetDataCallback() 
                                @Override
                                public void done(byte[] data, ParseException e) 
                                    if(e== null && data != null)

                                       Bitmap bitmap = BitmapFactory.decodeByteArray(data, 0, data.length);

                                       if(bitmap != null)
                                           Log.i("image download","Success");

                                           bp = bitmap;
                                           Log.i("image Content",bp.toString());

                                           prod_image.add(bp);
                                           //adapter.notifyDataSetChanged();
                                           if(prod_image.size()>0)
                                               Log.i("inside count","Ok");
                                           else 
                                               Log.i("inside Count","Not Ok");
                                           


                                           //adapter.notifyDataSetChanged();

                                       else 
                                           Log.i("image download","Failure");
                                       
                                    else 
                                        e.printStackTrace();
                                    
                                
                            );

                            //prod_image.add(bp);
                            //<-- not ok
                          //adapter.notifyDataSetChanged();

                        

                    
                
                if(prod_image.size()>0)
                    Log.i("outside count","Ok");
                else 
                    Log.i("outside Count","Not Ok");
                
                //<-- It's first crashing then second time its loading successfully!!
                adapter = new UserFeedAdapter(prod_name,prod_cat,prod_pub,prod_price,prod_image);
                //recyclerView.setAdapter(adapter);
                adapter.notifyDataSetChanged();
                recyclerView.setAdapter(adapter);
            
        );


        //<---Not working at all
        //adapter = new UserFeedAdapter(prod_name,prod_cat,prod_pub,prod_price,prod_image);
       //recyclerView.setAdapter(adapter);
        if(prod_image.size()>0)
            Log.i("very outside count","Ok");
        else 
            Log.i("very outside Count","Not Ok");
        


    




    `

【问题讨论】:

如果这是您的实际代码,而不仅仅是(非常长的)简化:您的数组正在异步填充,因此在调用 findInBackground 后直接检查其内容是行不通的。相反,您应该在获取所有文件后在下载处理程序中调用回调,并在那里执行您的下一步操作。 【参考方案1】:

如果您将数组声明为全局数组,那么在您的位图数组中添加位图后,您必须更新适配器并且它应该可以工作。但是,要小心,因为这样做需要时间,并且应该在 ASYNC 中完成,尤其是在图像又大又重的情况下。

public void done(byte[] data, ParseException e) 
if(e== null && data != null)
Bitmap bitmap = BitmapFactory.decodeByteArray(data, 0, data.length);
if(bitmap != null)
Log.i("image download","Success");
bp = bitmap;
Log.i("image Content",bp.toString());
prod_image.add(bp);  
//----------------- UPDATE YOUR ARRAY-ADAPTER HERE-----------------
yourView.setAdapter(prod_image);
enter code here

【讨论】:

“全球”是什么意思?你能添加一个代码示例吗? 变量/数组可以是全局的(如果它们是在主活动方法的顶部声明的)或本地的(如果它们是在“非主”方法中声明的)。上面代码的问题是使用局部变量来填充全局数组。 位图被复制到 bp 中,由您的定义声明为“全局”(我将其称为类的成员或属性)

以上是关于使用 ArrayList 使用 ParseFile 下载多个图像的主要内容,如果未能解决你的问题,请参考以下文章

从 ParseObject 中检索 ParseFile - Android C# Xamarin Parse

Xamarin C# android 和 PARSE - 在 parseObject 中下载 parseFile

使用回调异步加载列表视图中的图像

将 Parse Cloud 代码与 .NET SDK 结合使用

phppdfparser的使用

phppdfparser的使用