3

我的想法是在AsyncTask中创建新片段,然后在onPostExecute上将它与显示的进度条片段交换。我的问题是片段从不交换,因此它保留在进度条片段中。这不可能做到吗?这是一个坏方法吗?我应该在DetailFragment里面有进度条吗? (会有很多与进度条片段在其中)是否有可能在后台线程中交换片段

@Override 
protected void onStart() {  
    super.onStart(); 
    getSupportFragmentManager().beginTransaction() 
      .replace(R.id.content_frame, new ProgressBarFragment()).commit(); 
    TestSwapFragment d = new TestSwapFragment(); 
    d.execute(data); 
} 

class TestSwapFragment extends AsyncTask<FragmentData, Void, MyFragment> { 

FragmentData data = null; 

    @Override 
    protected MyFragment doInBackground(FragmentData... params) { 

     try { 
      Thread.sleep(15000); // Simulate the long running method below 
     } catch (InterruptedException e) {     
      e.printStackTrace(); 
     } 

     this.data = params[0]; 
     DetailFragment df= new DetailFragment(); 
     df.ExecuteFragment(this.data); // Long running 

     return df; 
    } 

    @Override 
    protected void onPostExecute(MyFragment result) {    
     super.onPostExecute(result); 

     if (this.data.Position == FragmentPosition.PaneOne) 
       getSupportFragmentManager().beginTransaction() 
       .replace(R.id.content_frame, result).commit(); 
     else 
       getSupportFragmentManager().beginTransaction() 
       .replace(R.id.content_frame2, result).commit(); 
    } 

} 

回答

2

我看不出有任何理论上的原因,这不应该工作。但是说,这对我来说是一个非常奇怪的方法。

AsyncTask.doInBackground()通常用于创建/下载/处理数据,而AyncTask.onPostExecute()用于更新UI。但是你要在两种方法上分发UI部件。

此外,Fragment是一个UI类,您正在使用它来完成数据处理,再次混合每个类的目的。作为一般规则,在我的项目中,我倾向于遵循类似的东西(例如显示一些通用名称,但在真实的东西上,使用有意义的名称,也可能忽略一些构造函数,只是为了保持简短)

MyActivity.java 
public class MyActivity extends Activity{ 


     private class MyWorker extends AsyncTask<SomeDataObject, Integer, SomeDataListObject>{ 
      @Override 
      protected MyFragment doInBackground(SomeDataObject... params) { 
       // in here we use SomeDataObject to generate the SomeDataListObject 
       return MyDataCruncher.processData(someDataObject); 
       // see it's a static method, process A and generates B, that's all. 
       // but very important that it's its own class, separate from Activity and Fragment 
      } 

      @Override 
      protected void onPostExecute(SomeDataListObject result){ 
       if(results != null){ 
        // Here we create the fragment, pass the data to it and do the transaction 
        getSupportFragmentManager().beginTransaction().replace(R.id.content_frame, MyFrag.newInstance(result)).commit(); 

       }else{ /* do some error handling or whatever */ } 
      } 
} 

,然后在你的片段你这样做:

public class MyFrag extends Fragment{ 
    private static String KEY_DATA = "_key_data_" 
    public static MyFrag newInstance(SomeDataListObject data){ 
     MyFrag frag = new MyFrag(); 
     Bundle b = new Bundle(); 
     frag.setArguments(b); 
     // it's important to make your data parcelable and pass it with a Bundle as part of the fragment life-cycle 
     b.putParcelableArrayList(KEY_DATA, data); 
     return frag; 
    } 

    // then inside onCreateView 
    SomeDataListObject data = getArguments.getParcelableArray(KEY_DATA); 
    // --- 

} 

希望它有助于

+0

为什么很重要,以使数据parcelable? (重写后,我意识到我需要传入一个特定的类)为什么不只是创建一个方法,setData()这是一个变量? MyData _data; .. public void setData(MyData data){_data = data; } – Patrick

+1

我对答案说。这是因为片段的生命周期。如果片段对象被销毁,但系统稍后需要相同的片段(后退按钮,旋转,添加到管理器中的布局片段等),系统将传递相同的Bundle到片段,以便可以重新构建。如果你只是创建一个这样的函数,这将不会发生,你的片段将在这些条件下有一个空数据。 – Budius

相关问题