ListView 内部片段错误

ListView inside fragment error

我的片段:

public class NewsFragment extends ListFragment {

    private ProgressDialog pDialog;

    // URL to get contacts JSON
    private static String url = "url";

    // JSON Node names
    private static final String TAG_NEWS = "news";
    private static final String TAG_ID = "id";
    private static final String TAG_JUDUL = "judul";
    private static final String TAG_TGL = "tanggal";
    private static final String TAG_ISI = "isi";
    private static final String TAG_SUMBER = "sumber";
    private static final String TAG_GAMBAR = "gambar";

    // contacts JSONArray
    JSONArray news = null;

    // Hashmap for ListView
    ArrayList<HashMap<String, String>> newsList;

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
        View newsView = inflater.inflate(R.layout.fragment_news, container, false) ;
        newsList = new ArrayList<HashMap<String, String>>();

        ListView lv = getListView();
        lv.setOnItemClickListener(new AdapterView.OnItemClickListener() {

            @Override
            public void onItemClick(AdapterView<?> parent, View view,
                                    int position, long id) {
                // getting values from selected ListItem
                String judul = ((TextView) view.findViewById(R.id.judul))
                        .getText().toString();
                String tanggal = ((TextView) view.findViewById(R.id.tglPublish))
                        .getText().toString();
                String sumber = ((TextView) view.findViewById(R.id.sumber))
                        .getText().toString();

                // Starting single contact activity
                Intent in = new Intent(getActivity().getApplicationContext(),
                        NewsDetailActivity.class);
                in.putExtra(TAG_JUDUL, judul);
                in.putExtra(TAG_TGL, tanggal);
                in.putExtra(TAG_SUMBER, sumber);
                startActivity(in);

            }
        });

        // Calling async task to get json
        new GetNews().execute();

        return newsView ;
    }

    /**
     * Async task class to get json by making HTTP call
     * */
    private class GetNews extends AsyncTask<Void, Void, Void> {

        @Override
        protected void onPreExecute() {
            super.onPreExecute();
            // Showing progress dialog
            pDialog = new ProgressDialog(getActivity());
            pDialog.setMessage("Mohon tunggu...");
            pDialog.setCancelable(false);
            pDialog.show();

        }

        @Override
        protected Void doInBackground(Void... arg0) {
            // Creating service handler class instance
            ServiceHandler sh = new ServiceHandler();

            // Making a request to url and getting response
            String jsonStr = sh.makeServiceCall(url, ServiceHandler.POST);

            Log.d("Response: ", "> " + jsonStr);

            if (jsonStr != null) {
                try {
                    JSONObject jsonObj = new JSONObject(jsonStr);

                    // Getting JSON Array node
                    news = jsonObj.getJSONArray("");

                    // looping through All Contacts
                    for (int i = 0; i < news.length(); i++) {
                        JSONObject c = news.getJSONObject(i);

                        String id = c.getString(TAG_ID);
                        String judul = c.getString(TAG_JUDUL);
                        String tgl = c.getString(TAG_TGL);
                        String sumber = c.getString(TAG_SUMBER);
//                        String gambar = c.getString(TAG_GENDER);


                        // tmp hashmap for single contact
                        HashMap<String, String> news = new HashMap<String, String>();

                        // adding each child node to HashMap key => value
                        news.put(TAG_ID, id);
                        news.put(TAG_JUDUL, judul);
                        news.put(TAG_TGL, tgl);
                        news.put(TAG_SUMBER, sumber);

                        // adding contact to contact list
                        newsList.add(news);
                    }
                } catch (JSONException e) {
                    e.printStackTrace();
                }
            } else {
                Log.e("ServiceHandler", "Couldn't get any data from the url");
            }

            return null;
        }

        @Override
        protected void onPostExecute(Void result) {
            super.onPostExecute(result);
            // Dismiss the progress dialog
            if (pDialog.isShowing())
                pDialog.dismiss();
            /**
             * Updating parsed JSON data into ListView
             * */
            ListAdapter adapter = new SimpleAdapter(
                    getActivity().getApplicationContext(), newsList,
                    R.layout.list_item, new String[] { TAG_JUDUL, TAG_TGL,
                    TAG_SUMBER }, new int[] { R.id.judul,
                    R.id.tglPublish, R.id.sumber });

            setListAdapter(adapter);
        }

    }

}

我的 xml :

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    android:layout_marginLeft="12dp"
    android:layout_marginRight="12dp">

    <!-- Main ListView
         Always give id value as list(@android:id/list)
    -->
    <ListView
        android:id="@android:id/list"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"/>

</LinearLayout>

list_item.xml :

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="wrap_content"
    android:orientation="vertical"
    android:padding="10dp"
    android:paddingLeft="10dp"
    android:paddingRight="10dp" >

    <!-- Judul -->

    <TextView
        android:id="@+id/judul"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:paddingBottom="2dip"
        android:paddingTop="6dip"
        android:textColor="#43bd00"
        android:textSize="16sp"
        android:textStyle="bold" />

    <!-- Tgl Publish -->
    <TextView
        android:id="@+id/tglPublish"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:paddingBottom="2dip"
        android:textColor="#acacac" />

    <!-- Sumber -->
    <TextView
        android:id="@+id/sumber"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:gravity="left"
        android:textColor="#5d5d5d"
        android:textStyle="bold" />
    <ImageView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content" />

</LinearLayout>

和错误日志:

05-20 00:24:41.091  20376-20376/com.emaszda.nutrisibunda E/AndroidRuntime﹕ FATAL EXCEPTION: main
    java.lang.IllegalStateException: Content view not yet created
            at android.support.v4.app.ListFragment.ensureList(ListFragment.java:328)
            at android.support.v4.app.ListFragment.getListView(ListFragment.java:222)
            at com.emaszda.nutrisibunda.NewsFragment.onCreateView(NewsFragment.java:58)
            at android.support.v4.app.Fragment.performCreateView(Fragment.java:1786)
            at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:953)
            at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1136)
            at android.support.v4.app.BackStackRecord.run(BackStackRecord.java:739)
            at android.support.v4.app.FragmentManagerImpl.execPendingActions(FragmentManager.java:1499)
            at android.support.v4.app.FragmentManagerImpl.executePendingTransactions(FragmentManager.java:488)
            at android.support.v4.app.FragmentPagerAdapter.finishUpdate(FragmentPagerAdapter.java:141)
            at android.support.v4.view.ViewPager.populate(ViewPager.java:1073)
            at android.support.v4.view.ViewPager.populate(ViewPager.java:919)
            at android.support.v4.view.ViewPager.onMeasure(ViewPager.java:1441)
            at android.view.View.measure(View.java:15891)
            at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:5035)
            at android.widget.FrameLayout.onMeasure(FrameLayout.java:310)
            at android.view.View.measure(View.java:15891)
            at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:5035)
            at android.support.v7.internal.widget.ActionBarOverlayLayout.onMeasure(ActionBarOverlayLayout.java:453)
            at android.view.View.measure(View.java:15891)
            at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:5035)
            at android.widget.FrameLayout.onMeasure(FrameLayout.java:310)
            at android.view.View.measure(View.java:15891)
            at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:5035)
            at android.widget.LinearLayout.measureChildBeforeLayout(LinearLayout.java:1404)
            at android.widget.LinearLayout.measureVertical(LinearLayout.java:695)
            at android.widget.LinearLayout.onMeasure(LinearLayout.java:588)
            at android.view.View.measure(View.java:15891)
            at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:5035)
            at android.widget.FrameLayout.onMeasure(FrameLayout.java:310)
            at com.android.internal.policy.impl.PhoneWindow$DecorView.onMeasure(PhoneWindow.java:2208)
            at android.view.View.measure(View.java:15891)
            at android.view.ViewRootImpl.performMeasure(ViewRootImpl.java:1957)
            at android.view.ViewRootImpl.measureHierarchy(ViewRootImpl.java:1156)
            at android.view.ViewRootImpl.performTraversals(ViewRootImpl.java:1336)
            at android.view.ViewRootImpl.doTraversal(ViewRootImpl.java:1056)
            at android.view.ViewRootImpl$TraversalRunnable.run(ViewRootImpl.java:5542)
            at android.view.Choreographer$CallbackRecord.run(Choreographer.java:749)
            at android.view.Choreographer.doCallbacks(Choreographer.java:562)
            at android.view.Choreographer.doFrame(Choreographer.java:532)
            at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:735)
            at android.os.Handler.handleCallback(Handler.java:730)
            at android.os.Handler.dispatchMessage(Handler.java:92)
            at android.os.Looper.loop(Looper.java:137)
            at android.app.ActivityThread.main(ActivityThread.java:5162)
            at java.lang.reflect.Method.invokeNative(Native Method)
            at java.lang.reflect.Method.invoke(Method.java:525)
            at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:756)
            at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:572)
            at miui.dexspy.DexspyInstaller.main(DexspyInstaller.java:171)
            at dalvik.system.NativeStart.main(Native Method)

作为 onCreateView:

Creates and returns the view hierarchy associated with the fragment. Since the method does not return the view, you will not able to access the ListView through getListView().

getListView() 放入 onViewCreated() 方法中,如下所示:

@Override
public void onViewCreated(View view, Bundle savedInstanceState) {
    super.onViewCreated(view, savedInstanceState);
    ListView lv = getListView();
    lv.setOnItemClickListener(new AdapterView.OnItemClickListener() {

        @Override
        public void onItemClick(AdapterView<?> parent, View view,
                                int position, long id) {
            // getting values from selected ListItem
            String judul = ((TextView) view.findViewById(R.id.judul))
                    .getText().toString();
            String tanggal = ((TextView) view.findViewById(R.id.tglPublish))
                    .getText().toString();
            String sumber = ((TextView) view.findViewById(R.id.sumber))
                    .getText().toString();

            // Starting single contact activity
            Intent in = new Intent(getActivity().getApplicationContext(),
                    NewsDetailActivity.class);
            in.putExtra(TAG_JUDUL, judul);
            in.putExtra(TAG_TGL, tanggal);
            in.putExtra(TAG_SUMBER, sumber);
            startActivity(in);

        }
    });
}

onViewCreated是在api level 13中添加的,所以如果你的minSdkVersion低于13那么使用onActivityCreated获取Listview对象。

只需覆盖 onActivityCreated 并输入您的代码:

// Calling async task to get json
        new GetNews().execute();

这里的问题是你试图在 UI 尚未创建时对其进行操作,因为 onCreateView 尚未执行 return 语句

onActivityCreated() 而不是 onCreateView() 中调用您的 GetNews().execute(); 方法,因为当您启动 AsyncTask 时您的视图甚至还没有创建。

@Override
public void onActivityCreated(Bundle savedInstanceState) {
    super.onActivityCreated(savedInstanceState);
    new GetNews().execute();
}

将此 ListView lv = getListView(); 代码放入片段

onActivityCreated()onCreate()