2011-05-03 27 views
13

DÜZENLEMEGarip parçası yaşam döngüsü hatası

Yani benim Fragment onu yeniden başlatmak çalışır FragmentManager tutulur gibi görünüyor. Hala neden Activity ile yok edilmediğinden emin değilsiniz. Yükleme mesajına gelince, ListView bir adaptör seti içermediğinde bu görüntülenir. Ancak, adaptör öğelerini onCreate ve onResume olarak ayarladım, bu yüzden bu yükleme ekranının neden gösterildiğini bilmiyorum. Ben parçaları ile oynamak ve ben ekranın yönünü değiştirdiğinizde fazla haşhaş garip bir hata fark ediyorum

Orjinal bu davranışın herhangi açıklamalar hala açık. Bu hata, ekran yönelimi değiştirildiğinde, tüm veriler onCreate'da yeniden oluşturulduğundan dolayı olmamalıdır. Ayrıca, rotasyondan sonra iki kere onResume() parçası çağrılmaktadır. İşte, hata oluşturmak için adım adım ve hata ayıklayıcının işlevlere nasıl isabet ettiğini.

  • Aktivite: onCreate()
  • Aktivite: onResume()
  • Parça: onResume()
  • EkranıDöndür'e
  • Aktivite: onCreate()
  • Aktivite: onResume()
  • Parça: onResume() (Activity.onResume() onları ayarlamasına rağmen öğeler sıfırdır)
  • Parça: onResume() (items boş değil, neden bu, bu son fragman onResume sonra

isabet)? iki kez denilen tablet "Yükleniyor ..." mesajı ve simgesini görüntüler ediliyor. Veriler listede artık gösterilmiyor? Şüphelerim, onCreate'ın ikinci bir fragman yaratmasıdır. İlk fragman, görünümleri yok eden oryantasyon nedeniyle verilerini kaybeder, ikinci fragman verileri alır ve yükleme ekranı, veri öğeleri olmayan ilk fragmandır ve ikinci fragman gizlenir. Yanılıyor olabilirim. Ekran Activity gibi döndürüldüğünde fragmanların hepsi yok edilmiyor? Bu sorunu çözmek için lütfen kodu eleştirmeyin. Aslında bir uygulama yapmıyorum, parça işlevselliğini deniyorum. Teşekkürler!

Ana Etkinlik

private ArrayList<Object> items = new ArrayList<Object>(); 
private MyListFragment mylistFragment; 

public MainActivity() { 
    items.add("Hello"); 
    items.add("World"); 
    items.add("Goodbye"); 
} 

/** Called when the activity is first created. */ 
@Override 
public void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.main); 

    FragmentManager fm = getFragmentManager(); 
    FragmentTransaction ft = fm.beginTransaction(); 

    mylistFragment = new MyListFragment(); 
    mylistFragment.setItems(items); 

    ft.add(R.id.container, mylistFragment); 
    ft.commit(); 
} 

@Override 
public void onResume() { 
    super.onResume(); 

    mylistFragment.setItems(items); 
    mylistFragment.getListView().setOnItemClickListener(new OnItemClickListener() { 
     public void onItemClick(AdapterView<?> parent, View view, int position, long id) { 
      Toast.makeText(MainActivity.this, ((TextView)view).getText(), Toast.LENGTH_LONG).show(); 
     } 

    }); 
} 

Liste Parçası

private List<Object> items = null; 
private Boolean isSet = false; 

@Override 
public void onResume() { 
    super.onResume(); 
    if(!isSet && items != null) { 
     setListAdapter(new ArrayAdapter<Object>(getActivity(), R.layout.item, items)); 
     isSet = true; 
    } 
} 

public void setItems(List<Object> items) { 
    this.items = items; 
    if(this.isResumed()) { 
     setListAdapter(new ArrayAdapter<Object>(getActivity(), R.layout.item, items)); 
     isSet = true; 
    } else { 
     isSet = false; 
    } 
} 

cevap

5

FragmentManager benim için otomatik olarak Fragment yeniden oluşturur. Ancak, içlerindeki verilerin yeniden başlatılması gerekiyor. Bu yüzden kodum ikinci bir parça oluşturuyordu. Yükleme ekranı, ilk parçanın artık bir adaptörüne sahip olmaması ve ikinci parçanın gizlenmesiydi. Ne bir baş ağrısı, neredeyse FragmentManagerFragments imha etmeliyim, böylece onları tuttukları veriler ile yeniden oluşturabilirsiniz.

+1

Üzgünüm ancak çok net bir şekilde cevap görmüyorum ... Bu sorunun çözümü eline nasıl geçtiğini? Sizinle aynı sonuca vardım, ancak bu sorunu kolayca çözmenin bir yolunu bulamıyorum. Eski parçaları nasıl öldürdüğünüzü ve yeniden yaratılan yenilerini nasıl kullanırsınız? – Maurycy

+0

Eski Fragmenti kaldırmak ve yeni kullanmak istiyorsanız, FragmentTransaction.replace() işlevini kullanın. Sonra eski olan yenisi ile değiştirilecek. Sadece verilerin yeniden yüklenmesi gerektiğini biliyoruz. – Spidy

0

Bu yüzden Diane ve diğer google örnekleri aracılığıyla çeşitli demolarda bu yüzden ...Genellikle statik bir yöntemle sıfır başlatma işlemine yardımcı olmanın bazı yollarına sahiptirler ... veArGames'i ayarlayın.

IIRC, parça oluşturma nesnesi oluşturmak için varsayılan yapıcıyı çağırır, ancak yalnızca setArguments aracılığıyla uygun verilerle doldurmayı bilir. Android geliştirme blogunda yer alan örnekte, kimlik listactivity'den ayrıntılar bölümüne aktarılıyordu. SetParams çağrıldıktan sonra fragmentManager onu yeniden canlandırabilmelidir.

Dokümantasyon konu hakkında seyrek görünüyor ve ben doğru şeyler yapmak isterim, bu yüzden eğer geribildiriminiz varsa, bunu takdir ediyorum.

0

Destek kitaplığından FragmentActivity kullanılması, örneği otomatik olarak kaydedip geri yükler. Bu nedenle, yalnızca parça işlemleriniz savedInstanceStatenull ise. senin FragmentActivity 'ın onCreate() yılında

Örneğin

, aşağıdakileri yapın:

if(savedInstanceState == null){ 
     FragmentManager fragmentManager = getSupportFragmentManager(); 
     fragmentManager.beginTransaction() 
     .replace(R.id.fragment_container, mFragment).commit(); //mFragment is your own defined fragment 
} 
İlgili konular