Android 试图使微调器可见时,ViewRoot$CalledFromErrorThreadException

Android 试图使微调器可见时,ViewRoot$CalledFromErrorThreadException,android,multithreading,parsing,spinner,Android,Multithreading,Parsing,Spinner,我正在解析来自服务器的plist,根据条件,我有一个微调器来显示并从中选择值 这是我实现该功能的代码 public class RaconTours extends Activity implements OnClickListener { @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentV

我正在解析来自服务器的plist,根据条件,我有一个微调器来显示并从中选择值

这是我实现该功能的代码

public class RaconTours extends Activity implements OnClickListener {

@Override
    public void onCreate(Bundle savedInstanceState) {

        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        btn = (ImageButton) findViewById(R.id.arrowBtn);
        btn.setOnClickListener(this);
        tourArray = new ArrayList<Tour>();
        btnProfile = (ImageButton) findViewById(R.id.profileBtn);
        spinner = (Spinner) findViewById(R.id.spinner);

        checkSDcardSupport();
        dialog = ProgressDialog.show(RaconTours.this, "", "Loading...",
                true, true);
        splashThread = new Thread() {
            @Override
            public void run() {
                try {
                    /**** Specify the path of the plist file ****/
                    File f = new File(RaconTours.PATH
                            + Constants.TOUR_MASTER_PLIST);
                    if (!f.exists()) {
                        f.createNewFile();
                    }
                    if (f.length() <= 0) {
                        URL plistUrl = new URL(Constants.TOUR_PLIST_URL);
                        TourDescription.httpDownload(f, plistUrl);
                    }
                } catch (MalformedURLException mue) {
                    mue.printStackTrace();
                } catch (IOException ioe) {
                    ioe.printStackTrace();
                }
                /**** Call the method to parse the downloaded plist file ****/
                parsePlist();
                if(dialog!=null){
                    dialog.dismiss();
                }
            }
        };
        splashThread.start();



    }
排队

spinner.setVisibility(View.VISIBLE)


对此有何回答?

您的
splashtread
运行在它自己的线程(而不是UI线程)上,这意味着对
parseList
的调用也将运行在非UI线程上,这将导致对UI的更改成为“非法”操作

您应该研究一下-它可能有更好的用途,因为它有一个在UI线程上运行的方法来进行UI更改

异步任务示例

将您的方法
parsePList()
替换为以下内容:

private class PListParser extends AsyncTask<Void, Void, Boolean> {
  public Boolean doInBackground( Void... params ) {
    //do the things your method parsePList does here.

    if( dict.size() > 2 )
      return true;
    else
      return false;
  }

  public void onPostExecute( Boolean result ) {
    //result is the return-value of the doInBackground-method
    if( result )
      spinner.setVisibility( View.VISIBLE );
    else
      spinner.setVisibility( View.GONE );
  }
}
私有类PListParser扩展异步任务{
公共布尔doInBackground(Void…params){
//执行您的方法parsePList在此处执行的操作。
如果(dict.size()>2)
返回true;
其他的
返回false;
}
public void onPostExecute(布尔结果){
//结果是doInBackground方法的返回值
如果(结果)
spinner.setVisibility(View.VISIBLE);
其他的
spinner.setVisibility(View.GONE);
}
}

然后不调用
parsePList()
而是执行以下操作:
new PListParser().execute()

您需要扩展AsyncTask或使用处理程序回发到UI线程。一旦你在不同的线程中,你就不能直接调用改变用户界面

10-17 08:24:33.240: WARN/System.err(4538): android.view.ViewRoot$CalledFromWrongThreadException: Only the original thread that created a view hierarchy can touch its views.
10-17 08:24:33.250: WARN/System.err(4538):     at android.view.ViewRoot.checkThread(ViewRoot.java:2932)
10-17 08:24:33.250: WARN/System.err(4538):     at android.view.ViewRoot.focusableViewAvailable(ViewRoot.java:1712)
10-17 08:24:33.260: WARN/System.err(4538):     at android.view.ViewGroup.focusableViewAvailable(ViewGroup.java:452)
10-17 08:24:33.270: WARN/System.err(4538):     at android.view.ViewGroup.focusableViewAvailable(ViewGroup.java:452)
10-17 08:24:33.270: WARN/System.err(4538):     at android.view.ViewGroup.focusableViewAvailable(ViewGroup.java:452)
10-17 08:24:33.290: WARN/System.err(4538):     at android.view.View.setFlags(View.java:4633)
10-17 08:24:33.290: WARN/System.err(4538):     at android.view.View.setVisibility(View.java:3116)
10-17 08:24:33.290: WARN/System.err(4538):     at com.racontrs.Racontours.RaconTours.parsePlist(RaconTours.java:157)
10-17 08:24:33.300: WARN/System.err(4538):     at com.racontrs.Racontours.RaconTours$1.run(RaconTours.java:85)
private class PListParser extends AsyncTask<Void, Void, Boolean> {
  public Boolean doInBackground( Void... params ) {
    //do the things your method parsePList does here.

    if( dict.size() > 2 )
      return true;
    else
      return false;
  }

  public void onPostExecute( Boolean result ) {
    //result is the return-value of the doInBackground-method
    if( result )
      spinner.setVisibility( View.VISIBLE );
    else
      spinner.setVisibility( View.GONE );
  }
}