0

I'm trying to spin my head around Asynctasks and threads and the like and I think I have a good solution made where I do all of my calculations on an Asynctask class, send them back to my activity using onCallComplete, add all the variables to a separate array, and then send that array to a List View adapter. However, for some reason that I just can't seem to grasp, Android is throwing me a java.lang.NullPointerException: Attempt to read from null array. I'm sure it's obvious, but I don't know how to fix it, so any advice would be greatly appreciated, thanks!

Activity's onCallComplete (where error occurs)

 public void onCallComplete(int listSize, String[] titles, String[] prices, Bitmap[] images, String[] productURLs ){
      ItemList[]itemArray= new ItemList[listSize];
      int i =0;
      while(i<listSize){
            itemArray[i] = new ItemList();
            itemArray[i].setTitle(titles[i]); //error occurs here
            itemArray[i].setPrice(prices[i]);
            itemArray[i].setImage(images[i]);
            itemArray[i].setProductURL(productURLs[i]);
            i++;
      }
      ListAdapter adapter = new CustomAdapter(this, itemArray);
      ListView productListView = (ListView)findViewById(R.id.productListView);
      productListView.setAdapter(adapter);
 }

ItemList class:

public class ItemList {
    private String title;
    private String price;
    private Bitmap image;
    private String productURL;


    public ItemList(){
        this.title=null;
        this.price=null;
        this.image=null;
        this.productURL=null;
    }

    void setTitle(String title){
        this.title = title;
    }

    void setImage(Bitmap image){
        this.image = image;
    }

    void setPrice(String price){
        this.price = price;
    }

    void setProductURL(String productURL){
        this.productURL = productURL;
    }

    String getTitle(){
        return title;
    }

    String getPrice(){
        return price;
    }

    Bitmap getImage(){
        return image;
    }

    String getProductURL(){
        return productURL;
    }
}

Edit: So after some experimentation and a pointer from Rajendran I did come to the conclusion that it's my AsyncTask calculations that are returning null (go figure, Asynctask always is a problem for me). Here is the code from the AsyncTask.

public class GetProductAttributes extends AsyncTask<Object, Object, Void> {
    OnCallCompleteCallBack callback;
    String url;
    int listSize;
    int index;
    String[] productURLs;
    String[] prices;
    String[] titles;
    String imageSRC;
    Bitmap[] images;
    ImageView productView;
    int listSize;
    int result;

    public GetProductAttributes(String url, int index, OnCallCompleteCallBack callback) {
        this.url = url;
        this.index = index;
        this.callback = callback;
    }
protected Void doInBackground(Object... voids) {
        //Create JSoup connection
        try { 
        Document doc = Jsoup.connect(url).get();
        String link = doc.select("h2#s-result-count").first().text();
        System.out.println(link);
        System.out.println(link.substring(1));
        if (link.substring(1, 2).equals("-")) {
            System.out.println("run1");
            listSize = Integer.parseInt(link.substring(2, 3));
            System.out.println(listSize);
            try {
                listSize = Integer.parseInt(link.substring(2, 4));
                System.out.println(listSize);
            } catch (Exception e) {
            }
        } else {
            System.out.println("run2");
            listSize = Integer.parseInt(link.substring(0, 1));
            System.out.println(listSize);
            try {
                listSize = Integer.parseInt(link.substring(0, 2));
                System.out.println(listSize);
            } catch (Exception e) {
            }
        }

            titles = new String[listSize];
            prices = new String[listSize];
            productURLs = new String[listSize];
            images = new Bitmap[listSize];
            int i = 0;
            while (i < listSize) {
                Elements basicLink = doc.select("div.showRightCol")
                        .select("div.leftCol")
                        .select("div.a-row.s-result-list-parent-container")
                        .select("ul.s-result-list.s-col-1.s-col-ws-1.s-result-list-hgrid.s-height-equalized.s-list-view.s-text-condensed")
                        .select("li[id=result_" + i + "]")
                        .select("div.s-item-container")
                        .select("div.a-fixed-left-grid")
                        .select("div.a-fixed-left-grid-inner");//start here to get to everything

                Element element = basicLink.select("a.a-link-normal.s-access-detail-page.s-color-twister-title-link.a-text-normal").first();
                String title = element.attr("title");
                //System.out.println("Title is: " + title);
                titles[i] = title;

//          Gets product URL and image source
                Elements longLink = basicLink.select("div.a-fixed-left-grid-col.a-col-left")
                        .select("div.a-row")
                        .select("div.a-column.a-span12.a-text-center")
                        .select("a.a-link-normal.a-text-normal");
                String productURL = longLink.attr("href");
                //System.out.println(productURL);
                productURLs[i] = productURL;
                imageSRC = longLink.select("img.s-access-image.cfMarker").attr("src");
                //System.out.println(imageSRC);
                images[i] = getImage(imageSRC);

                //Gets price
                String price = basicLink.select("div.a-row")
                        .select("div.a-column.a-span7")
                        .select("div.a-row.a-spacing-mini")
                        .select("div.a-row.a-spacing-none")
                        .select("a.a-size-small.a-link-normal.a-text-normal")
                        .select("span.a-size-base.a-color-base").first().text();
                System.out.println(price);
                prices[i]=price;
                i++;
            }
            //Gets title

        } catch (Exception e) {
        }
        return null;
    }
coolyfrost
  • 145
  • 10
  • 4
    May be your **titles[]** is null, add your complete code – Muthukrishnan Rajendran Aug 13 '17 at 20:49
  • 3
    Possible duplicate of [What is a NullPointerException, and how do I fix it?](https://stackoverflow.com/questions/218384/what-is-a-nullpointerexception-and-how-do-i-fix-it) – khelwood Aug 13 '17 at 20:51
  • One second, adding the rest of the code. – coolyfrost Aug 13 '17 at 20:55
  • Post has been edited to add the rest of the code – coolyfrost Aug 13 '17 at 20:59
  • What is with the empty catch block? What made you think that was a good idea? – khelwood Aug 13 '17 at 20:59
  • My code still isn't fully complete. I will add an error message soon inside the catch block so it makes more sense. Just trying to prototype a basic functionality at the moment – coolyfrost Aug 13 '17 at 21:02
  • @coolyfrost, where you are initializing the arrays..? – Muthukrishnan Rajendran Aug 13 '17 at 21:04
  • They're initialized in the field, sorry I forgot to add that. Editing code again now – coolyfrost Aug 13 '17 at 21:05
  • If you have an empty catch block, then when your code throws an exception, you don't know anything about it until some other bit of code goes wrong and you don't know why. – khelwood Aug 13 '17 at 21:05
  • Your problem is you never initialized the arrays – Muthukrishnan Rajendran Aug 13 '17 at 21:07
  • It will come inside while loop when it will try to set **titles[i] = title;** here it will give null pointer and it will get to catch and it will finish doInBackground – Muthukrishnan Rajendran Aug 13 '17 at 21:08
  • Oh my god I'm so sorry how did I forget to initialize the array. I feel like an idiot now haha. However, now instead of a null array error I'm getting an error that says: Attempt to invoke virtual method 'void .ItemList.setTitle(java.lang.String)' on a null object reference'. How would I go about fixing this? – coolyfrost Aug 13 '17 at 21:13
  • Now also you didnt set any value to listSize and you are setting this as array size, that means your array is still 0. – Muthukrishnan Rajendran Aug 13 '17 at 21:18
  • I do have a value for listSize, it's 16. I can assure you that's not the problem. – coolyfrost Aug 13 '17 at 21:21
  • ok may be you didnt updated in your question, ok nop – Muthukrishnan Rajendran Aug 13 '17 at 21:24
  • Sorry, I was trying not add too much unnecessary code to focus on the problem itself but I can see now that it just confused us. Added all the code :) – coolyfrost Aug 13 '17 at 21:26
  • In that place, it should not be null, as per the answer you posted. – Muthukrishnan Rajendran Aug 13 '17 at 22:06
  • I'm sorry, I didn't understand. What do you think is wrong with the code now that's not letting it run? – coolyfrost Aug 13 '17 at 22:08
  • So, in the onCallComplete class I wrote the line System.out.println(titles[i]) and it prints the title, so I'm pretty sure that the array is functioning. However, when the next line pops up (which is itemArray[i].setTitle(titles[i]);), then the "Attempt to invoke virtual method on a null object reference" error shows up – coolyfrost Aug 13 '17 at 22:25
  • However, after more experimentation, I'm also finding out that on the while loop in the doInBackground method of the Asynctask, it only seems to be doing the first 3 loops and then it backs out even though i=16 – coolyfrost Aug 13 '17 at 22:47

1 Answers1

-1

Here is your answer "Attempt to read from null array". That means this "titles[i]" is returning null .