フラグメントのテーマを設定しようとしています。
マニフェストでテーマを設定しても機能しません。
android:theme="@android:style/Theme.Holo.Light"
以前のブログを見ると、ContextThemeWrapperを使用する必要があるように見えます。コード化された例を誰かに紹介してもらえますか?何も見つかりません。
フラグメントのテーマを設定しようとしています。
マニフェストでテーマを設定しても機能しません。
android:theme="@android:style/Theme.Holo.Light"
以前のブログを見ると、ContextThemeWrapperを使用する必要があるように見えます。コード化された例を誰かに紹介してもらえますか?何も見つかりません。
回答:
マニフェストにテーマを設定することは、通常、アクティビティに使用されます。
フラグメントのテーマを設定する場合は、フラグメントのonCreateView()に次のコードを追加します。
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
// create ContextThemeWrapper from the original Activity Context with the custom theme
final Context contextThemeWrapper = new ContextThemeWrapper(getActivity(), R.style.yourCustomTheme);
// clone the inflater using the ContextThemeWrapper
LayoutInflater localInflater = inflater.cloneInContext(contextThemeWrapper);
// inflate the layout using the cloned inflater, not default inflater
return localInflater.inflate(R.layout.yourLayout, container, false);
}
フラグメントは、そのアクティビティからテーマを取得します。各フラグメントには、そのフラグメントが存在するアクティビティのテーマが割り当てられます。
テーマはFragment.onCreateViewメソッドで適用されます。コードはビューを作成します。ビューは実際にはテーマが使用されるオブジェクトです。
Fragment.onCreateViewでは、ビューを膨らませるLayoutInflaterパラメーターを取得し、テーマに使用されるコンテキストを保持します。これは実際にはアクティビティです。したがって、インフレートされたビューはアクティビティのテーマを使用します。
テーマをオーバーライドするには、LayoutInflater.cloneInContextを呼び出します。これは、テーマの変更に使用できることをドキュメントで説明しています。ここではContextThemeWrapperを使用できます。次に、複製されたインフレーターを使用してフラグメントのビューを作成します。
私が使用した単一のスタイルを適用するために
getContext().getTheme().applyStyle(styleId, true);
中onCreateView()
の断片の前にフラグメントのルートビューを膨張させると、それは私のために動作します。
getContext()
また、フラグメントダイアログをそのアクティビティとは異なるテーマで表示するように試み、この解決策に従いました。コメントで言及された一部の人々のように、私はそれを機能させておらず、ダイアログはマニフェストで指定されたテーマで表示され続けました。問題AlertDialog.Builder
は、onCreateDialog
メソッドでダイアログを作成していたため、onCreateView
リンク先の回答に示されているメソッドを使用していないことでした。そして、インスタンス化しているときに、代わりにインスタンス化されたものを使用するべきだったときにAlertDialog.Builder
使用してコンテキストで渡していました。getActivity()
ConstextThemeWrapper
これが私のonCreateDialogのコードです。
@Override
public Dialog onCreateDialog(Bundle savedInstanceState) {
// Create ContextThemeWrapper from the original Activity Context
ContextThemeWrapper contextThemeWrapper = new ContextThemeWrapper(getActivity(), android.R.style.Theme_DeviceDefault_Light_Dialog);
LayoutInflater inflater = getActivity().getLayoutInflater().cloneInContext(contextThemeWrapper);
// Now take note of the parameter passed into AlertDialog.Builder constructor
AlertDialog.Builder builder = new AlertDialog.Builder(contextThemeWrapper);
View view = inflater.inflate(R.layout.set_server_dialog, null);
mEditText = (EditText) view.findViewById(R.id.txt_server);
mEditText.requestFocus(); // Show soft keyboard automatically
mEditText.setOnEditorActionListener(this);
builder.setView(view);
builder.setTitle(R.string.server_dialog);
builder.setPositiveButton(android.R.string.ok, this);
Dialog dialog = builder.create();
dialog.setCanceledOnTouchOutside(false);
return dialog;
}
私はもともとAlertDialog.Builder
次のようにインスタンス化されていました:
AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
私が変更したもの:
AlertDialog.Builder builder = new AlertDialog.Builder(contextThemeWrapper);
この変更後、フラグメントダイアログは正しいテーマで表示されました。他の誰かが同様の問題を抱えており、AlertDialog.Builder
then を利用している場合は、ビルダーに渡されるコンテキストを確認してください。お役に立てれば!:)
android:minSdkVersion="11"
マニフェストに設定したことを確認してください。これが、Davidが例がうまく機能しなかっます。
また、セットandroid:theme="@android:style/Theme.Holo.Light"
の属性<application>
タグとはありません<activity>
タグ。
別の考えられる問題は、を使用するときにコンテキストを取得する方法ですContextThemeWrapper()
。getActivity().getApplicationContext()
単にそれを置き換えるようなものを使用する場合getActivity()
代わりに。
通常、Theme.HoloはMainActivityにリンクされたフラグメントに適用されます。
フラグメントに別のテーマを適用する場合は、ContextThemeWrapperを使用することに注意してください。フラグメントを追加するMainActivityからコードを提供すると役立つ場合があります。
いくつかの便利なリンク:
私はデイビッドがそれが機能することを提案したソリューションを試しましたが、すべてのシナリオではありません:
1.スタックに追加された最初のフラグメントはアクティビティのテーマを持ち、onCrateViewで定義されたものではなく、2番目のフラグメントでスタックに追加して、フラグメントに適用されていることを修正します。
2.それらが正しく表示された2番目のフラグメントで、メモリをクリーンアップしてアプリを強制的に閉じ、アプリを再度開き、フラグメントでアクティビティが再作成されたときに、フラグメントがそれらを間違って変更しましたアクティビティ。フラグメントのonCrateViewで設定されたものとは異なります。
この問題を修正するために、小さな変更を加え、inflater.inflateのコンテナー引数をnullに置き換えました。
インフレーターがいくつかのシナリオでコンテナービューからのコンテキストを使用する方法がわかりません。
注-そのandroid.support.v4.app.Fragment&android.support.v7.app.AppCompatActivityを使用しています。
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
// create ContextThemeWrapper from the original Activity Context with the custom theme
final Context contextThemeWrapper = new ContextThemeWrapper(getActivity(), R.style.yourCustomTheme);
// clone the inflater using the ContextThemeWrapper
LayoutInflater localInflater = inflater.cloneInContext(contextThemeWrapper);
// inflate the layout using the cloned inflater, not default inflater
return localInflater.inflate(R.layout.yourLayout, null, false);
}
特定のフラグメントにスタイルを適用するだけの場合は、onCreateView()
またはonAttach()
フラグメントを呼び出す前にこの行を追加します。
getActivity().getWindow().getDecorView().setSystemUiVisibility(View.SYSTEM_UI_FLAG_LAYOUT_STABLE | View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN);
getActivity().getWindow().setStatusBarColor(Color.TRANSPARENT);
透明なステータスバーを設定する場合は、ルートレイアウトのプロパティにfalseを設定しfitsSystemWindows
ます。
android:fitsSystemWindows="false"
インフレータを呼び出す前に、フラグメントコンテキストにテーマを設定することで機能します。
注:これは、MvvmCrossと組み合わせたXamarin.Androidの例です。これがJavaプログラマーでも機能するかどうかは、100%わかりません。しかし、あなたは試すことができます:)
public override View OnCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState)
{
Context.SetTheme(Theme);
base.OnCreateView(inflater, container, savedInstanceState);
var view = this.BindingInflate(FragmentLayoutId, container, false);
// Doing some other stuff
return view;
}
SetTheme拡張メソッドコード
public static void SetTheme(this Context context, AppThemeStyle themeStyle)
{
var themeStyleResId = themeStyle == AppThemeStyle.Dark ? Resource.Style.AppTheme : Resource.Style.AppTheme_Light;
context.SetTheme(themeStyleResId);
}
これが一部の人々の助けになることを願っています。
android:theme = "@style/myTheme"
フラグメントのレイアウトファイルで使用して問題を解決しました。たとえば、これはのスタイルとLinearLayout
コンテンツを変更しますが、以外のことは変更しませんLinearLayout
。したがって、フラグメント全体を任意のスタイルで装飾するには、テーマを最も外側の親レイアウトに適用します。
注:まだ解決策が見つからない場合に備えて、試してみることができます。
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical"
android:theme = "@style/myTheme" >
<TextView
android:id="@+id/tc_buttom_text1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Time elapsed"/>
<TextView
android:id="@+id/tc_buttom_text2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="10dp"
android:text="00:00:00 00"/>
</LinearLayout>
あなたはonAttachでロリポップのためにこれを試すことができます
最終的なウィンドウウィンドウ= activity.getWindow(); window.setStatusBarColor(myStatusBarColor)
オンデッタッチでデフォルトに戻します