为什么 ArrayAdapter 在 activity 重启后无法更新列表视图?

Why does ArrayAdapter fail to update listview after activity restart?

我有一个 activity,它在 onCreate() 中执行以下操作:

  1. 创建一个空的 ArrayList
  2. 创建一个与上述 ArrayList 关联的新 ArrayAdapter
  3. 设置 ListView 使用上面的 ArrayAdapter
  4. 使用 Volley 向我的 API 发送 GET 请求以获取一些 JSON 数据以加载到 ListView

获取数据后,我将其添加到我的 ArrayList 并按预期填充 ListView

我的问题是当 activity 重新启动时(即通过模拟器旋转屏幕或通过 Android Studio 重新启动 activity)ListView 不再填充。

我没有保存任何状态。我希望 activity 到 return 到其初始默认状态,所以我认为 onSaveInstanceState() 不是答案。

我已验证数据已从 API 成功 returned 并且适配器的哈希码在 volley 请求之前和之后相同,并且它等于 ListView 的设置适配器。我还验证了当 activity 重新启动时会调用 onDestroy() 和 onCreate() ,所以我知道它正在经历一个完整的生命周期。

如果我使用 setRequestedOrientation() 以编程方式旋转屏幕,我不会遇到此问题。如果我在 GET 请求回调之外向我的 ArrayList 添加项目,我不会遇到此问题。

这是我的 activity onCreate()

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_test);
    //The data to be displayed
    descriptions = new ArrayList<>();
    listView = (ListView)this.findViewById(R.id.myListView);
    //Link 'descriptions' to the adapter
    adapter = new ArrayAdapter<>(this, R.layout.list_json_text_view, descriptions);
    listView.setAdapter(adapter);

    this.addTextFilter();
    this.addListViewClickListener();

    //See my ApiGetRequest class below
    request = new ApiGetRequest();
    request.send(this.getContext(), getDataUrl(), this, "", REQUEST_TYPES.TEXT);
}

还有我的activity GET 请求回调

public void onSuccess(DescriptiveJSONArray items, REQUEST_TYPES type) {

    descriptions.clear();
    try {
        for (int i = 0; i < items.length(); ++i) {
            JSONObject obj = items.getJSONObject(i);
            String desc = obj.optString("name", "") + " " + obj.optString("description", "");
            //TODO: Remove debug code
            System.out.println("Adding: "+desc);
            descriptions.add(desc);
        }
    }
    catch(JSONException e) {
        e.printStackTrace();
        //getJSONObject failed
    }
}

还有我的 ApiGetRequest 方法

    //My activity implements ApiGetCallback
    public void send(Context context, String url, ApiGetCallback callback, String tag, REQUEST_TYPES type) {
      StringRequest stringRequest = getStringRequest(url, callback, tag, type);
      //Singleton wrapper for RequestQueue
      AppRequestQueue queue = AppRequestQueue.getInstance(context);
      queue.add(stringRequest);
    }

    //Inner class inside ApiGetCallback
    class SuccessListener implements Response.Listener<String> {
      ApiGetCallback callback;
      REQUEST_TYPES type;

      public SuccessListener(ApiGetCallback callback, REQUEST_TYPES type) {
          this.callback = callback;
          this.type = type;
      }

      @Override
      public void onResponse(String response) {
          try {
              DescriptiveJSONArray jsonResp = new DescriptiveJSONArray(response);
              callback.onSuccess(jsonResp, type);
          }
          catch(JSONException e) {
              callback.onJsonException(e);
          }
      }
  } 

知道发生了什么吗?我正在测试 Marshmallow 和 Nougat

在 onSuccess 函数完成后,您缺少对 notifyDataSetChanged 的调用。

adapter = new ArrayAdapter<>(this, R.layout.list_json_text_view, descriptions);
    listView.setAdapter(adapter);

    //See my ApiGetRequest class below
    request = new ApiGetRequest();
    request.send(this.getContext(), getDataUrl(), this, "", REQUEST_TYPES.TEXT);

在onResume方法中使用这部分代码。

您可能需要覆盖 onStart 并更新其中的任何内容