尝试在asynctask上填充列表视图适配器时出错

时间:2014-07-30 14:14:50

标签: android listview android-asynctask simpleadapter

这是我的代码的一部分,我使用异步任务从数据库中搜索并使用简单的适配器填充listview。

protected String doInBackground(String... arg0)
    {
        Cursor TROWS;
        ArrayList<HashMap<String, String>> LstViw_VItem=new ArrayList<HashMap<String,String>>();
        HashMap<String, String>VMap;
        try
        {
            DBH.openDataBase();

            SQLiteDatabase SQLITE=SQLiteDatabase.openDatabase(myPath, null, Context.MODE_PRIVATE);
            if (TxtVerminSearch.getText().length()==0)
            {
                TROWS=SQLITE.rawQuery("select id,vermin_name from pistachio_vermins", null);
            }
            else
            {
                TROWS=SQLITE.rawQuery("select id,vermin_name from pistachio_vermins where vermin_name like '%"+TxtVerminSearch.getText()+"%'", null);
            }
            if (TROWS.moveToFirst())
            {
                do
                {
                    String VID      =TROWS.getString(0);
                    String VName    =TROWS.getString(1);

                    VMap=new HashMap<String, String>();
                    VMap.put("VerminID", VID);
                    VMap.put("VerminName", VName);
                    LstViw_VItem.add(VMap);
                }
                while (TROWS.moveToNext());
                SimpleAdapter SA=new SimpleAdapter(getApplicationContext(), LstViw_VItem, R.layout.xvermin_items, new String[]{"VerminID","VerminName"}, new int[]{R.id.mainmenu_items__lbl_vermin_id,R.id.mainmenu_items__lbl_vermins});
                LstViwVerminItems.setAdapter(SA);

                LstViwVerminItems.setEnabled(true);
            }
            else 
            {
                VMap=new HashMap<String, String>();
                VMap.put("VerminID", "-1");
                VMap.put("VerminName", "nothing found");

                VMap.put("ImgViw",String.valueOf(R.drawable.warning_48));

                LstViw_VItem.add(VMap);

                SimpleAdapter SA=new SimpleAdapter(getApplicationContext(), LstViw_VItem, R.layout.xvermin_items, new String[]{"VerminID","VerminName","ImgViw"}, new int[]{R.id.mainmenu_items__lbl_vermin_id,R.id.mainmenu_items__lbl_vermins,R.id.mainmenu_items__ImgViw});
                LstViwVerminItems.setAdapter(SA);

                LstViwVerminItems.setEnabled(false);    
            }
        }
        catch (Exception e)
        {
            final String errString;
            errString=e.getMessage();
            Log.d("ERR: ", errString);
            runOnUiThread(new Runnable()
            {
                public void run()
                {
                    Toast.makeText(JAct_Vermins.this, errString, Toast.LENGTH_LONG).show();
                }
            }); 
        }

        return null;
    }

每件事都很好但是当搜索结果为空时我会给出这样的错误:

  

只有创建视图层次结构的原始线程才能触及其视图。

问题发生在这一行

    VMap.put("ImgViw",String.valueOf(R.drawable.warning_48));

为此,我使用runOnUiThread函数来访问ui。但我现在不能这样做因为我不能宣布VMap为最终

4 个答案:

答案 0 :(得分:0)

您应该使用onPostExecute方法在UI上显示结果。了解有关AsyncTask的更多信息。你不应该在doInBackground方法处理UI。

答案 1 :(得分:0)

尝试在HashMap<String, String> VMap;之外声明doInBackgound()并使用runOnUiThread()。如果它仍然不起作用,请尝试创建一个Handler并将hashmap key-val作为Message传递。

注意:在VMap

之外声明您的doInBackground()变量

示例:

    HashMap<String, String> VMap;

    @Override
    protected String doInBackground(String... params) {
        Cursor TROWS;
        ArrayList<HashMap<String, String>> LstViw_VItem = new ArrayList<HashMap<String, String>>();

        try {
            DBH.openDataBase();

            SQLiteDatabase SQLITE = SQLiteDatabase.openDatabase(myPath, null,
                    Context.MODE_PRIVATE);
            if (TxtVerminSearch.getText().length() == 0) {
                TROWS = SQLITE.rawQuery("select id,vermin_name from pistachio_vermins", null);
            } else {
                TROWS = SQLITE.rawQuery(
                        "select id,vermin_name from pistachio_vermins where vermin_name like '%"
                                + TxtVerminSearch.getText() + "%'", null);
            }
            if (TROWS.moveToFirst()) {
                do {
                    String VID = TROWS.getString(0);
                    String VName = TROWS.getString(1);

                    VMap = new HashMap<String, String>();
                    VMap.put("VerminID", VID);
                    VMap.put("VerminName", VName);
                    LstViw_VItem.add(VMap);
                } while (TROWS.moveToNext());
                SimpleAdapter SA = new SimpleAdapter(getApplicationContext(), LstViw_VItem,
                        R.layout.xvermin_items, new String[] { "VerminID", "VerminName" },
                        new int[] { R.id.mainmenu_items__lbl_vermin_id,
                                R.id.mainmenu_items__lbl_vermins });
                LstViwVerminItems.setAdapter(SA);

                LstViwVerminItems.setEnabled(true);
            } else {
                VMap = new HashMap<String, String>();
                VMap.put("VerminID", "-1");
                VMap.put("VerminName", "nothing found");

                mHandler.sendEmptyMessage(0);

                LstViw_VItem.add(VMap);

                SimpleAdapter SA = new SimpleAdapter(getApplicationContext(), LstViw_VItem,
                        R.layout.xvermin_items, new String[] { "VerminID", "VerminName",
                                "ImgViw" }, new int[] { R.id.mainmenu_items__lbl_vermin_id,
                                R.id.mainmenu_items__lbl_vermins, R.id.mainmenu_items__ImgViw });
                LstViwVerminItems.setAdapter(SA);

                LstViwVerminItems.setEnabled(false);
            }
        } catch (Exception e) {
            final String errString;
            errString = e.getMessage();
            Log.d("ERR: ", errString);
            runOnUiThread(new Runnable() {
                public void run() {
                    Toast.makeText(JAct_Vermins.this, errString, Toast.LENGTH_LONG).show();
                }
            });
        }

        return null;
    }

    private Handler mHandler = new Handler(){
        @Override
        public void handleMessage(Message msg) {

            VMap.put("ImgViw", String.valueOf(R.drawable.warning_48));

            super.handleMessage(msg);
        }
    };

希望它有所帮助!

答案 2 :(得分:0)

您正在尝试从背景更新listview,这是错误的。 为了更新ui android提供post执行方法,你应该在postexecute方法中编写更新listview的代码。供您参考,您可以看到此链接http://www.compiletimeerror.com/2013/01/why-and-how-to-use-asynctask.html

答案 3 :(得分:0)

函数doInBackgound() - 无法从ui tread调用函数

使用runOnUiThread()或onPostExecute()