web-dev-qa-db-fra.com

java.lang.NullPointerException: tentative d'appel de la méthode d'interface sur une erreur de référence d'objet nul sur OnPostExecute () - AsyncTask

J'essaie d'obtenir un résultat d'un AsyncTask à afficher dans mon activité de recherche.

J'ai eu un exemple d'une application précédente, qui a été réalisé avec l'aide d'un collègue (j'étais stagiaire là-bas).

J'ai ajusté l'exemple aux besoins de cette application, mais maintenant je reçois le NullPointerException:

03-04 03:50:23.865: E/AndroidRuntime(8224): FATAL EXCEPTION: main 
03-04 03:50:23.865: E/AndroidRuntime(8224): Process: com.cyberdog.what2watch, PID: 8224
03-04 03:50:23.865: E/AndroidRuntime(8224): Java.lang.NullPointerException: Attempt to invoke interface method 'void com.cyberdog.what2watch.JsonHandling$IOnFinish.onGetData(org.json.JSONObject)' on a null object reference
03-04 03:50:23.865: E/AndroidRuntime(8224):     at com.cyberdog.what2watch.JsonHandlingTMDBAsync.onPostExecute(JsonHandling.Java:321)
03-04 03:50:23.865: E/AndroidRuntime(8224):     at com.cyberdog.what2watch.JsonHandlingTMDBAsync.onPostExecute(JsonHandling.Java:1)
03-04 03:50:23.865: E/AndroidRuntime(8224):     at Android.os.AsyncTask.finish(AsyncTask.Java:632)
03-04 03:50:23.865: E/AndroidRuntime(8224):     at Android.os.AsyncTask.access$600(AsyncTask.Java:177)
03-04 03:50:23.865: E/AndroidRuntime(8224):     at Android.os.AsyncTask$InternalHandler.handleMessage(AsyncTask.Java:645)
03-04 03:50:23.865: E/AndroidRuntime(8224):     at Android.os.Handler.dispatchMessage(Handler.Java:102)
03-04 03:50:23.865: E/AndroidRuntime(8224):     at Android.os.Looper.loop(Looper.Java:135)
03-04 03:50:23.865: E/AndroidRuntime(8224):     at Android.app.ActivityThread.main(ActivityThread.Java:5274)
03-04 03:50:23.865: E/AndroidRuntime(8224):     at Java.lang.reflect.Method.invoke(Native Method)
03-04 03:50:23.865: E/AndroidRuntime(8224):     at Java.lang.reflect.Method.invoke(Method.Java:372)
03-04 03:50:23.865: E/AndroidRuntime(8224):     at com.Android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.Java:909)
03-04 03:50:23.865: E/AndroidRuntime(8224):     at com.Android.internal.os.ZygoteInit.main(ZygoteInit.Java:704)

J'ai également vérifié d'autres échantillons sur onPostExecute(), et il semble que j'ai fait la bonne chose .. mais j'obtiens toujours l'erreur.

J'ai utilisé un point d'arrêt à la onPostExecute() et le résultat n'est pas nul, mais il exécute le code deux fois.

code de l'asyncclass:

class JsonHandlingTMDBAsync extends AsyncTask<String, Void, JSONObject> {// params,
                                                                        // progress,
                                                                        // result

private String api_key_tmdb = "2fb98d2bca5895c89a6efaf70903f706";
private String tmdb_multi_url = "http://api.themoviedb.org/3/search/multi?query=";
int Total_pages;
int number_entries_per_page;
private JSONObject resultObject;
private IOnFinish listener;
String Titel="";
String Year ="";
public JsonHandlingTMDBAsync(String titel, String year, IOnFinish listener) {
    this.listener = listener;
    this.Titel=titel;
    this.Year=year;
}

@Override
protected JSONObject doInBackground(String... params) {
    return loadJSON(params);
}

private JSONObject loadJSON(String... params) {
    resultObject = new JSONObject();
    StringBuilder builder = new StringBuilder();
    HttpClient client = new DefaultHttpClient();
    HttpGet httpGet;

    if (Titel.trim().length() == 0 && Year.trim().length() != 0) {
        httpGet = new HttpGet(tmdb_multi_url + Year + "&api_key="
                + api_key_tmdb);
    } else if (Titel.trim().length() != 0 && Year.trim().length() == 0) {
        httpGet = new HttpGet(tmdb_multi_url + Titel + "&api_key="
                + api_key_tmdb);

    } else if (Titel.trim().length() == 0 && Year.trim().length() == 0) {
        System.out.print("error null titel/year");
        httpGet = new HttpGet(tmdb_multi_url + "star+wars&api_key="
                + api_key_tmdb);
    } else {
        httpGet = new HttpGet(
                "http://www.omdbapi.com/?s=star&y=2008&r=JSON"
                        + "&plot=short");
    }

    try {
        HttpResponse response = client.execute(httpGet);
        StatusLine statusLine = response.getStatusLine();
        int statusCode = statusLine.getStatusCode();
        if (statusCode == 200) {
            HttpEntity entity = response.getEntity();
            InputStream content = entity.getContent();
            BufferedReader reader = new BufferedReader(
                    new InputStreamReader(content));
            String line;
            while ((line = reader.readLine()) != null) {
                builder.append(line);
            }
        } else {
            Log.e(JsonHandling.class.toString(), "Failed to download file");
        }

        resultObject = new JSONObject(builder.toString());
    } catch (ClientProtocolException e) {
        e.printStackTrace();
    } catch (IOException e) {
        e.printStackTrace();
    } catch (JSONException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
    return resultObject;
}

@Override
protected void onPostExecute(JSONObject result){
    super.onPostExecute(result);
    listener.onGetData(result);
}}

code d'activité:

    package com.cyberdog.what2watch;

import Java.util.List;

import org.json.JSONObject;

import com.cyberdog.what2watch.JsonHandling.IOnFinish;

import Android.app.Activity;
import Android.content.Context;
import Android.os.Bundle;
import Android.util.Log;
import Android.view.View;
import Android.view.View.OnClickListener;
import Android.view.inputmethod.InputMethodManager;
import Android.widget.AbsListView;
import Android.widget.AbsListView.OnScrollListener;
import Android.widget.Button;
import Android.widget.EditText;
import Android.widget.ListView;
import Android.widget.Toast;

public class SearchActivity extends Activity implements OnScrollListener, IOnFinish{



    /** Called when the activity is first created. */

    private static SearchCustomAdapter adapter;
    EditText tvTitel = null;
    EditText tvYear = null;
    ListView lvSearch = null;
    JsonHandling jh = new JsonHandling(this);
    int pageNumber =0;
    int previeusTotal=0;
    private static List<Serie> searchResult;
    private IOnFinish iof;
    private static List<Serie>series;


    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.search);

        tvTitel = (EditText) findViewById(R.id.etf_search_titel);
        tvYear = (EditText) findViewById(R.id.etf_search_year);
        lvSearch = (ListView)findViewById(R.id.lvSearch);



        Button btnSearch = (Button) findViewById(R.id.btnSearch_search);
        btnSearch.setOnClickListener(new OnClickListener() {

            public void onClick(View v) {
                InputMethodManager inputManager = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);

                inputManager.hideSoftInputFromWindow(getCurrentFocus()
                        .getWindowToken(), InputMethodManager.HIDE_NOT_ALWAYS);

                JsonHandling.getInstance().getJSONFromUrl(tvTitel.getText().toString(), tvYear.getText().toString(),iof);
            }
        });
    }

    public void search(int pageNumber){
        // adapter for the custom list
        //lvSearch = (ListView) findViewById(R.id.lvSearch);

//      SearchCustomAdapter lvAdapt = new SearchCustomAdapter(
//              SearchActivity.this, jh.search_db(tvTitel.getText()
//                      .toString(), tvYear.getText().toString(),
//                      searchSite, pageNumber));
//                      lvSearch.setAdapter(lvAdapt);

                        //lvAdapt.notifyDataSetChanged();
    }

    @Override
    public void onGetData(JSONObject obj) {
        if (obj == null) {
            Toast.makeText(this,
                    "obj is null",
                    Toast.LENGTH_LONG).show();
            Serie serie = new Serie("not found","");
            Serie[] seriesList = new Serie[series.size()];
            seriesList[0] = serie;
            adapter = new SearchCustomAdapter(this, seriesList);
            lvSearch = (ListView) findViewById(R.id.lvSearch);
            lvSearch.setAdapter(adapter);
        }
        if(obj !=null){
            if (JsonHandling.pageNumber == 0){
            series =Serie.serieListFromJSON(this, JsonHandling.getInstance().getJSONArraySerieFromUrlTMDB(obj));
            Serie[] seriesList =series.toArray(new Serie[series.size()]);
            adapter = new SearchCustomAdapter(this, seriesList);
            lvSearch = (ListView)findViewById(R.id.lvSearch);
            lvSearch.setAdapter(adapter);
            //lvSearch.setOnItemClickListener(this);
            lvSearch.setOnScrollListener(this);


            }}

        }

    @Override
    public void onScroll(AbsListView view, int firstVisibleItem,
            int visibleItemCount, int totalItemCount) {
        int lastInScreen = firstVisibleItem+visibleItemCount;
        totalItemCount = 20+20 * pageNumber;
        //int totalSearchResults = 0;

        Log.i("total, last in screen, pagenumber outside", totalItemCount+":" + lastInScreen+ ":"+pageNumber);
        if((lastInScreen +20*pageNumber == totalItemCount)){
            Log.i("total, last in screen, pagenumber inside", totalItemCount+":" + lastInScreen+ ":"+pageNumber);



            pageNumber++;

            search(pageNumber);

        }
        else{

        }

    }

    @Override
    public void onScrollStateChanged(AbsListView arg0, int arg1) {
        // TODO Auto-generated method stub

    }

}

et le code pièce json/interface:

public interface IOnFinish{
    void onGetData(JSONObject obj);
}

public void getJSONFromUrl(String titel, String year, IOnFinish listener) {
    JsonHandlingTMDBAsync task = new JsonHandlingTMDBAsync(titel, year, listener);
    task.execute();
}

Dans ma classe d'activité, j'ai un point d'arrêt sur la onGetData() mais il n'est jamais atteint, bien que la onPostExecute() ait l'objet et soit appelée deux fois (je ne sais pas pourquoi).

6
cc2k

Tentative d'appel de la méthode d'interface 'void com.cyberdog.what2watch.JsonHandling $ IOnFinish.onGetData

Parce que iof l'objet de IOnFinish interface est null.

Initialisez iof après setContentView:

setContentView(R.layout.search);
iof=this;
12
ρяσѕρєя K

lorsque vous appelez listener.onGetData(result);, il est préférable de vérifier d'abord l'auditeur, comme

if (listener != null) {
     listener.onGetData(result);
}

car il n'y a aucune garantie que l'écouteur n'est pas nul dans votre code.

5
Simon Jinyu Liu