2012-02-10 11 views
3

したがって、検索基準を入力できる検索条件フラグメントがあります。検索が実行されると、検索結果が検索結果フラグメントに表示されます。タブレット上の風景では、2つの断片が自然に並べて表示できます。これは今までのところ実装が簡単です。フラグメントを、回転中のダイアログから埋め込みに切り替えることはできますか?

携帯電話では、検索結果の横に表示されるのではなく、検索条件フラグメントがポップアップダイアログのように表示されます。 DialogFragmentのSelecting Between Dialog or Embeddingセクションには、フラグメントを埋め込むか、ダイアログとして表示することができます。オリエンテーションの変更によって複雑にならないなら、これは私のために働くかもしれません。

アクティビティのレイアウトにXMLタグ<<>を使用している場合、向きを変更するとさまざまな問題が発生します。

EDIT:今日、私はダイアログの表示とデバイスの向きに応じた埋め込みを切り替えるDialogFragmentを使用して簡単なワークフローを得ることができるかどうか試してみることにしました。これは非常に困難であることが判明し、私はまだ動作するものを見つけていません。ここに私がこれまで持っているものがあります。

package org.nsdev.experiments; 

import android.os.Bundle; 
import android.support.v4.app.DialogFragment; 
import android.support.v4.app.FragmentActivity; 
import android.view.Menu; 
import android.view.MenuItem; 
import android.view.View; 

public class FragmentSearchTestActivity extends FragmentActivity 
{ 
    private static SearchCriteriaFragment searchCriteriaFragment; 

    @Override 
    public void onCreate(Bundle savedInstanceState) 
    { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.main); 

     View container = findViewById(R.id.search_criteria_container); 

     android.support.v4.app.FragmentTransaction ft = getSupportFragmentManager().beginTransaction(); 

     if (searchCriteriaFragment == null) 
     { 
      searchCriteriaFragment = SearchCriteriaFragment.newInstance(); 
      searchCriteriaFragment.setStyle(DialogFragment.STYLE_NO_TITLE, 0); 
     } 

     android.support.v4.app.Fragment f = getSupportFragmentManager().findFragmentByTag("search_criteria"); 
     if (f != null) 
     { 
      ft.remove(f); 
     } 

     if (container == null) 
     { 
      searchCriteriaFragment.setCancelable(true); 
      searchCriteriaFragment.setHasOptionsMenu(false); 
      searchCriteriaFragment.show(getSupportFragmentManager(), "search_criteria"); 
     } 
     else 
     { 
      ft.remove(searchCriteriaFragment); 
      ft.add(R.id.search_criteria_container, searchCriteriaFragment, "search_criteria"); 
      ft.commit(); 
     } 
    } 

    @Override 
    public boolean onCreateOptionsMenu(Menu menu) 
    { 
     getMenuInflater().inflate(R.menu.main_menu, menu); 
     return super.onCreateOptionsMenu(menu); 
    } 

    @Override 
    public boolean onOptionsItemSelected(MenuItem item) 
    { 
     if (item.getItemId() == R.id.menu_item_search) 
     { 
      searchCriteriaFragment.show(getSupportFragmentManager(), "search_criteria"); 
     } 
     return super.onOptionsItemSelected(item); 
    } 
} 

私はSearchCriteriaFragmentの静的なコピーを保持してのonCreateが活動中で呼ばれた時はいつでも、それを再利用しない限り、具体的に私が働いて何かを得ることができませんでした。これは私にとって非常に間違っているようです。

SearchResultsFragment.java:

package org.nsdev.experiments; 

import android.os.Bundle; 
import android.view.LayoutInflater; 
import android.view.View; 
import android.view.ViewGroup; 

public class SearchResultsFragment extends android.support.v4.app.Fragment 
{ 

    @Override 
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) 
    { 
     return inflater.inflate(R.layout.results, container); 
    } 

} 

SearchCriteriaFragment.java:

package org.nsdev.experiments; 

import android.os.Bundle; 
import android.util.Log; 
import android.view.LayoutInflater; 
import android.view.View; 
import android.view.ViewGroup; 

public class SearchCriteriaFragment extends android.support.v4.app.DialogFragment 
{ 

    private static final String TAG = "SearchCriteriaFragment"; 
    View v; 

    static SearchCriteriaFragment newInstance() 
    { 
     Log.e(TAG, "newInstance"); 
     SearchCriteriaFragment d = new SearchCriteriaFragment(); 
     return d; 
    } 

    @Override 
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) 
    { 
     if (v == null) 
     { 
      v = inflater.inflate(R.layout.criteria, container, false); 
     } 
     else 
     { 
      if (v.getParent() instanceof ViewGroup) 
      { 
       Log.e(TAG, "Removing from viewgroup"); 
       ((ViewGroup)v.getParent()).removeAllViews(); 
      } 
     } 

     return v; 
    } 

} 

あなたは、私が再利用されているビューで問題を回避しなければならなかったことを、ここでは、見ることができます。ビューに既に親があり、他の親に追加する前に削除する必要があるというエラーが表示されました。再び、私はそれを間違ったやり方にしなければならないようです。

のres /レイアウト/ main.xml:

<?xml version="1.0" encoding="utf-8"?> 
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" 
    android:layout_width="fill_parent" 
    android:layout_height="fill_parent" > 

    <fragment 
     android:id="@+id/search_results" 
     android:name="org.nsdev.experiments.SearchResultsFragment" 
     android:layout_width="fill_parent" 
     android:layout_height="fill_parent" /> 

</RelativeLayout> 

のres /レイアウト・ランド/ main.xml:

<?xml version="1.0" encoding="utf-8"?> 
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" 
    android:layout_width="fill_parent" 
    android:layout_height="fill_parent" > 

    <FrameLayout 
     android:id="@+id/search_criteria_container" 
     android:layout_width="wrap_content" 
     android:layout_height="fill_parent" /> 

    <fragment 
     android:id="@+id/search_results" 
     android:layout_toRightOf="@+id/search_criteria_container" 
     android:name="org.nsdev.experiments.SearchResultsFragment" 
     android:layout_width="fill_parent" 
     android:layout_height="fill_parent" /> 

</RelativeLayout> 

あなたは私は何をしようとしています、これらの2つのレイアウトから見ることができます。通常の方向では、FrameLayoutは存在しないので、これを検出してDialogFragmentを表示することができます。それ以外の場合は、DialogFragmentをFrameLayoutに埋め込むことができます。

私はちょうど結果と基準レイアウトのためのプレースホルダを入れてきた最後の2つのレイアウト:

のres /レイアウト/ criteria.xml:

<?xml version="1.0" encoding="utf-8"?> 
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" 
    android:layout_width="match_parent" 
    android:layout_height="match_parent" android:background="#300F"> 

    <CheckBox 
     android:id="@+id/checkBox" 
     android:layout_width="wrap_content" 
     android:layout_height="wrap_content" 
     android:layout_alignParentLeft="true" 
     android:layout_alignParentTop="true" 
     android:layout_marginLeft="21dp" 
     android:paddingRight="30dp" 
     android:text="Test Criteria" /> 

</RelativeLayout> 

のres /レイアウト/ results.xml:

<?xml version="1.0" encoding="utf-8"?> 
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" 
    android:layout_width="match_parent" 
    android:layout_height="match_parent" android:background="#f00"> 

    <TextView 
     android:id="@+id/textView1" 
     android:layout_width="wrap_content" 
     android:layout_height="wrap_content" 
     android:layout_alignParentLeft="true" 
     android:layout_alignParentTop="true" 
     android:layout_marginLeft="16dp" 
     android:layout_marginTop="16dp" 
     android:text="Results" 
     android:textAppearance="?android:attr/textAppearanceLarge" /> 

</RelativeLayout> 

私は、デバイスを回転させてICSデバイスのチェックボックスをチェックするまで、わかっていると思いました。 criteria.xmlのRelativeLayoutバックグラウンドの色を半透明に設定していることに注目してください。私が気づいたのは、横向きの場合、埋め込みビューは実際には古いバージョンのビューを保持していたことです。これらのビューは、ポートレートに戻って再び戻るたびに新しいビューのコピーでオーバーレイされます。これは、SeachCriteriaFragmentのonCreateViewから返されたビューのコピーを1つだけ保持しようとした理由の1つです。これはこの問題を解決しません。

私は1つの結論にのみ来ることができます:私はこれを間違っている必要があります。私は、フラグメントフレームワークがこの種のフラグメント再利用を行うように設計されていないと考えています。ポートレートでDialogFragmentをダイアログとして表示し、ランドスケープに埋め込まれているところで、いい回転をするにはどうすればいいですか?このようなことをより自動的に行うフレームワークを手に入れることはできますか?

searchCriteriaFragment.setRetainInstance(true)を設定しようとしましたが、すべての地獄が壊れてしまったので、すぐにその行を削除しました。

ここで正しいトラックを私に手伝ってくれてありがとう。

+0

私はあなたのconfigChanges属性またはあなたの断片が回転して消えてしまうかもしれないアクティビティコードについて何かがあると思います。できるだけ多くのコードを共有することはうまくいくと思います。 – nmr

答えて

0

私はこれを言うでしょう。

電話でSearchFormFragmentをアクティビティにして、テーマダイアログを付けます。 次に、SearchResultsFragmentはそれ自身の別のアクティビティです。

SearchForm XMLは次のようになります。Dialog themeを取得するには

<LinearLayout > 
    <fragment class="com.your.package.ui.fragment.SearchFormFragment" /> 
</LinearLayout> 

<manifest . . . > 
     <application . . . > 
     <activity 
      android:name=".ui.phone.SearchFormFragmentActivity" 
      android:theme="@android:style/Theme.Dialog" . . . > 
     <activity 
      android:name=".ui.phone.SearchResultsFragmentActivity" . . . > 

これはonSaveInstanceStateonRestoreInstanceStateを使用して姿勢変更、シンプルでアクティビティのライフサイクルになります。あなたはあなたの二つの断片と別のアクティビティを持っているタブレットのその後

  <activity 
      android:name=".ui.tablet.SearchFragmentActivity" . . . > 

SearchFragmentActivity.xml:。

<LinearLayout > 
    <fragment class="com.your.pacakage.ui.fragment.SearchFormFragment"/> 
    <fragment class="com.your.package.ui.fragment.SearchResultsFragment" /> 
    </LinearLayout> 

簡体。

+0

理想的には、Android Compatibility Libraryと実際のUI要素のFragmentsを使用したいと考えています。 – Thorinside

+0

それはまさに私が言っていることですか?フラグメントxmlを編集して(それはちょうどpseadoです) – Blundell

+0

しかし、3つのアクティビティではなく、2つのフラグメントを適切に管理する1つのアクティビティを作成する方法を知りたいと思います。 – Thorinside

関連する問題