当前位置: 动力学知识库 > 问答 > 编程问答 >

Running XML Parser in Android Fragment (Slide Menu) [edited]

问题描述:

I have some problem when developing Android Apps with SlideMenu. I'm going to made a fragment called "BeritaTerbaru", but I got new exception in logcat.

Here's the code :

public class BeritaTerbaru extends Fragment {

// All variables

XMLParser parser;

Document doc;

String xml;

ListView lv;

ListViewAdapter adapter;

ArrayList<HashMap<String, String>> menuItems;

ProgressDialog pDialog;

private String URL = "http://api.androidhive.info/list_paging/?page=1";

// XML node keys

static final String KEY_ITEM = "item"; // parent node

static final String KEY_ID = "id";

static final String KEY_NAME = "name";

// Flag for current page

int current_page = 1;

public void onStart(){

super.onStart();

lv = (ListView) getView().findViewById(R.id.list);

menuItems = new ArrayList<HashMap<String, String>>();

new loadMoreListView().execute();

// LoadMore button

Button btnLoadMore = new Button(getActivity());

btnLoadMore.setText("Load More");

// Adding Load More button to lisview at bottom

lv.addFooterView(btnLoadMore);

// Getting adapter

adapter = new ListViewAdapter(getActivity(), menuItems);

lv.setAdapter(adapter);

/**

* Listening to Load More button click event

* */

btnLoadMore.setOnClickListener(new View.OnClickListener() {

@Override

public void onClick(View arg0) {

// Starting a new async task

new loadMoreListView().execute();

}

});

/**

* Listening to listview single row selected

* **/

lv.setOnItemClickListener(new OnItemClickListener() {

@Override

public void onItemClick(AdapterView<?> parent, View view,

int position, long id) {

// getting values from selected ListItem

String name = ((TextView) view.findViewById(R.id.name))

.getText().toString();

// Starting new intent

Intent in = new Intent(getActivity(),

SingleMenuItemActivity.class);

in.putExtra(KEY_NAME, name);

startActivity(in);

}

});

}

@Override

public View onCreateView(LayoutInflater inflater, ViewGroup container,

Bundle savedInstanceState) {

View view = inflater.inflate(R.layout.fragment_beritaterbaru,container,false);

return view;

}

/**

* Async Task that send a request to url

* Gets new list view data

* Appends to list view

* */

private class loadMoreListView extends AsyncTask<Void, Void, Void> {

@Override

protected void onPreExecute() {

// Showing progress dialog before sending http request

pDialog = new ProgressDialog(getActivity());

pDialog.setMessage("Please wait..");

pDialog.setIndeterminate(true);

pDialog.setCancelable(false);

pDialog.show();

}

protected Void doInBackground(Void... unused) {

// increment current page

current_page += 1;

// Next page request

URL = "http://api.androidhive.info/list_paging/?page=" + current_page;

xml = parser.getXmlFromUrl(URL); // getting XML

doc = parser.getDomElement(xml); // getting DOM element

NodeList nl = doc.getElementsByTagName(KEY_ITEM);

// looping through all item nodes <item>

for (int i = 0; i < nl.getLength(); i++) {

// creating new HashMap

HashMap<String, String> map = new HashMap<String, String>();

Element e = (Element) nl.item(i);

// adding each child node to HashMap key => value

map.put(KEY_ID, parser.getValue(e, KEY_ID));

map.put(KEY_NAME, parser.getValue(e, KEY_NAME));

// adding HashList to ArrayList

menuItems.add(map);

}

return null;

}

protected void onPostExecute(Void unused) {

// closing progress dialog

pDialog.dismiss();

// get listview current position - used to maintain scroll position

int currentPosition = lv.getFirstVisiblePosition();

// Appending new data to menuItems ArrayList

adapter = new ListViewAdapter(getActivity(),

menuItems);

lv.setAdapter(adapter);

// Setting new scroll position

lv.setSelectionFromTop(currentPosition + 1, 0);

}

}

}

here is the log cat :

06-25 00:33:00.700: E/AndroidRuntime(895): FATAL EXCEPTION: AsyncTask #1

06-25 00:33:00.700: E/AndroidRuntime(895): Process: info.androidhive.slidingmenu, PID: 895

06-25 00:33:00.700: E/AndroidRuntime(895): java.lang.RuntimeException: An error occured while executing doInBackground()

06-25 00:33:00.700: E/AndroidRuntime(895): at android.os.AsyncTask$3.done(AsyncTask.java:300)

06-25 00:33:00.700: E/AndroidRuntime(895): at java.util.concurrent.FutureTask.finishCompletion(FutureTask.java:355)

06-25 00:33:00.700: E/AndroidRuntime(895): at java.util.concurrent.FutureTask.setException(FutureTask.java:222)

06-25 00:33:00.700: E/AndroidRuntime(895): at java.util.concurrent.FutureTask.run(FutureTask.java:242)

06-25 00:33:00.700: E/AndroidRuntime(895): at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:231)

06-25 00:33:00.700: E/AndroidRuntime(895): at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1112)

06-25 00:33:00.700: E/AndroidRuntime(895): at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:587)

06-25 00:33:00.700: E/AndroidRuntime(895): at java.lang.Thread.run(Thread.java:841)

06-25 00:33:00.700: E/AndroidRuntime(895): Caused by: java.lang.NullPointerException

06-25 00:33:00.700: E/AndroidRuntime(895): at info.androidhive.slidingmenu.BeritaTerbaru$loadMoreListView.doInBackground(BeritaTerbaru.java:127)

06-25 00:33:00.700: E/AndroidRuntime(895): at info.androidhive.slidingmenu.BeritaTerbaru$loadMoreListView.doInBackground(BeritaTerbaru.java:1)

06-25 00:33:00.700: E/AndroidRuntime(895): at android.os.AsyncTask$2.call(AsyncTask.java:288)

06-25 00:33:00.700: E/AndroidRuntime(895): at java.util.concurrent.FutureTask.run(FutureTask.java:237)

06-25 00:33:00.700: E/AndroidRuntime(895): ... 4 more

06-25 00:33:00.830: W/EGL_emulation(895): eglSurfaceAttrib not implemented

06-25 00:33:01.180: W/EGL_emulation(895): eglSurfaceAttrib not implemented

06-25 00:33:01.380: I/Choreographer(895): Skipped 37 frames! The application may be doing too much work on its main thread.

06-25 00:33:02.270: I/Choreographer(895): Skipped 52 frames! The application may be doing too much work on its main thread.

06-25 00:33:02.940: E/WindowManager(895): android.view.WindowLeaked: Activity info.androidhive.slidingmenu.MainActivity has leaked window com.android.internal.policy.impl.PhoneWindow$DecorView{b4fa1328 V.E..... R......D 0,0-383,96} that was originally added here

06-25 00:33:02.940: E/WindowManager(895): at android.view.ViewRootImpl.<init>(ViewRootImpl.java:346)

06-25 00:33:02.940: E/WindowManager(895): at android.view.WindowManagerGlobal.addView(WindowManagerGlobal.java:248)

06-25 00:33:02.940: E/WindowManager(895): at android.view.WindowManagerImpl.addView(WindowManagerImpl.java:69)

06-25 00:33:02.940: E/WindowManager(895): at android.app.Dialog.show(Dialog.java:286)

06-25 00:33:02.940: E/WindowManager(895): at info.androidhive.slidingmenu.BeritaTerbaru$loadMoreListView.onPreExecute(BeritaTerbaru.java:117)

06-25 00:33:02.940: E/WindowManager(895): at android.os.AsyncTask.executeOnExecutor(AsyncTask.java:587)

06-25 00:33:02.940: E/WindowManager(895): at android.os.AsyncTask.execute(AsyncTask.java:535)

06-25 00:33:02.940: E/WindowManager(895): at info.androidhive.slidingmenu.BeritaTerbaru.onStart(BeritaTerbaru.java:49)

06-25 00:33:02.940: E/WindowManager(895): at android.app.Fragment.performStart(Fragment.java:1724)

06-25 00:33:02.940: E/WindowManager(895): at android.app.FragmentManagerImpl.moveToState(FragmentManager.java:918)

06-25 00:33:02.940: E/WindowManager(895): at android.app.FragmentManagerImpl.moveToState(FragmentManager.java:1062)

06-25 00:33:02.940: E/WindowManager(895): at android.app.FragmentManagerImpl.moveToState(FragmentManager.java:1044)

06-25 00:33:02.940: E/WindowManager(895): at android.app.FragmentManagerImpl.dispatchStart(FragmentManager.java:1858)

06-25 00:33:02.940: E/WindowManager(895): at android.app.Activity.performStart(Activity.java:5259)

06-25 00:33:02.940: E/WindowManager(895): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2149)

06-25 00:33:02.940: E/WindowManager(895): at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2226)

06-25 00:33:02.940: E/WindowManager(895): at android.app.ActivityThread.access$700(ActivityThread.java:135)

06-25 00:33:02.940: E/WindowManager(895): at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1397)

06-25 00:33:02.940: E/WindowManager(895): at android.os.Handler.dispatchMessage(Handler.java:102)

06-25 00:33:02.940: E/WindowManager(895): at android.os.Looper.loop(Looper.java:137)

06-25 00:33:02.940: E/WindowManager(895): at android.app.ActivityThread.main(ActivityThread.java:4998)

06-25 00:33:02.940: E/WindowManager(895): at java.lang.reflect.Method.invokeNative(Native Method)

06-25 00:33:02.940: E/WindowManager(895): at java.lang.reflect.Method.invoke(Method.java:515)

06-25 00:33:02.940: E/WindowManager(895): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:777)

06-25 00:33:02.940: E/WindowManager(895): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:593)

06-25 00:33:02.940: E/WindowManager(895): at dalvik.system.NativeStart.main(Native Method)

I got another support class like XMLParser, ListViewAdapter, SingleListMenu, and another fragment class. But I think my mistake is in this class. Anybody help me, please?

网友答案:

Try this..

Inside onStart() remove below lines

    parser = new XMLParser();
    xml = parser.getXmlFromUrl(URL); // getting XML
    doc = parser.getDomElement(xml); // getting DOM element

    NodeList nl = doc.getElementsByTagName(KEY_ITEM);
    // looping through all item nodes <item>
    for (int i = 0; i < nl.getLength(); i++) {
        // creating new HashMap
        HashMap<String, String> map = new HashMap<String, String>();
        Element e = (Element) nl.item(i);
        // adding each child node to HashMap key => value
        map.put(KEY_ID, parser.getValue(e, KEY_ID)); // id not using any where
        map.put(KEY_NAME, parser.getValue(e, KEY_NAME));

        // adding HashList to ArrayList
        menuItems.add(map);
    }

and add

new loadMoreListView().execute();

At the same time you cannot do UI update inside doInBackground change your AsyncTask like below

private class loadMoreListView extends AsyncTask<Void, Void, Void> {

    @Override
    protected void onPreExecute() {
        // Showing progress dialog before sending http request
        pDialog = new ProgressDialog(getActivity());
        pDialog.setMessage("Please wait..");
        pDialog.setIndeterminate(true);
        pDialog.setCancelable(false);
        pDialog.show();
    }

    protected Void doInBackground(Void... unused) {
                // increment current page
                current_page += 1;

                // Next page request
                URL = "http://api.androidhive.info/list_paging/?page=" + current_page;

                parser = new XMLParser();
                xml = parser.getXmlFromUrl(URL); // getting XML
                doc = parser.getDomElement(xml); // getting DOM element

                NodeList nl = doc.getElementsByTagName(KEY_ITEM);
                // looping through all item nodes <item>
                for (int i = 0; i < nl.getLength(); i++) {
                    // creating new HashMap
                    HashMap<String, String> map = new HashMap<String, String>();
                    Element e = (Element) nl.item(i);

                    // adding each child node to HashMap key => value
                    map.put(KEY_ID, parser.getValue(e, KEY_ID));
                    map.put(KEY_NAME, parser.getValue(e, KEY_NAME));

                    // adding HashList to ArrayList
                    menuItems.add(map);
                }
    }


    protected void onPostExecute(Void unused) {
        // closing progress dialog
        pDialog.dismiss();

        // get listview current position - used to maintain scroll position
        int currentPosition = lv.getFirstVisiblePosition();

        // Appending new data to menuItems ArrayList
         adapter = new ListViewAdapter(getActivity(),
                        menuItems);
        lv.setAdapter(adapter);

        // Setting new scroll position
        lv.setSelectionFromTop(currentPosition + 1, 0);
    }
}
分享给朋友:
您可能感兴趣的文章:
随机阅读: