【问题标题】:error when try to fill list view adapter on asynctask尝试在 asynctask 上填充列表视图适配器时出错
【发布时间】:2014-07-30 14:14:49
【问题描述】:

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

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 声明为 final

【问题讨论】:

    标签: android listview android-asynctask simpleadapter


    【解决方案1】:

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

    注意:在 doInBackground() 之外声明您的 VMap 变量

    示例:

        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】:

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

      【讨论】:

        【解决方案3】:

        您正在尝试从后台更新列表视图,这是错误的。 要更新 ui android 提供 post execute 方法,您应该在 postexecute 方法中编写更新 listview 的代码。供您参考,您可以查看此链接http://www.compiletimeerror.com/2013/01/why-and-how-to-use-asynctask.html

        【讨论】:

          【解决方案4】:

          function doInBackgound() - 无法从 ui 踏板调用函数

          使用 runOnUiThread() 或 onPostExecute()

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 2016-11-29
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2012-12-19
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多