2012年2月1日水曜日

Android, Viewにstyleを動的に設定する方法

AndroidアプリのButtonやViewに動的にstyleを設定したい。
例えばActivityからnew Button()したようなオブジェクトに共通で使っているstyleを設定したい。

かなり探したけど全然見つからなかった。
唯一ここに発見。
ソースコード内で生成したViewインスタンスにStyleを適用

はじめは書いてある内容が理解できなかったので、備忘録として以下メモ。
#リンク先と同じこと書いてるだけ。

・アウトライン

Viewのコンストラクタを見てると
View(Context context)
View(Context context, AttributeSet attrs)
View(Context context, AttributeSet attrs, int defStyle)
こんな風に定義されている。

Contextはクラスのオブジェクトを指定。この辺りを参照。
AttributeSetはXMLで指定した場合のプロパティが渡ってくる。
style指定は3つ目のdefStyle。

なので、Activityから生成したViewオブジェクトにstyleを指定した場合は、3つ目のパラメタにR.foo.barのリソースIDを渡せばよい。
っていうのは比較的すぐ分かるんですが、具体的にどうやるのかは一苦労。

以下。

・styleの指定

R.styleというのがあるので、こいつを指定すればいいんだろうと格闘してましたが、どうやら違ってR.attrでないとダメな模様。
このstyleリソースIDを直接指定できれば楽なんだけどなー、というのが最初のリンク先で触れられていた内容。

・R.attrについて

R.attrのドキュメント

ドキュメントを見る限り、R.attrはwidthやcheckedのようなAndroidのXMLエレメントのアトリビュートを定義してるものらしい。
R.attrの中にはdialogLayoutやbuttonStyleのようなレイアウト周りのリソースIDを指定していると思われるものも存在しますが、本来styleとは直接は関係ない(はず)。
なのでR.attrの指定からしかstyleを適用できない、というのは勘違いかAndroidのバグだと思う。

でも他にやり方が分からないので以下進めます。
#詳しい方、教えて。。

・R.attrを指定する

XMLはres/values/style.xmlで指定する。
#ここじゃないとダメなのかはよく分からない。

1. 適用させるstyleを作成
<!-- <item name="android:layout_*">の要素はR.attrでスタイル適用出来ないっぽい -->
<style name="MyButtonStyle" parent="android:style/Widget.Button">
    <item name="android:layout_width">match_parent</item>
    <item name="android:layout_height">wrap_content</item>
    <item name="android:layout_marginBottom">2dp</item>
    <item name="android:textColor">@color/foo</item>
    <item name="android:textSize">16dp</item>
    <item name="android:background">@drawable/bar</item>
    <item name="android:textStyle">bold</item>
</style>

作ったstyleをR.attrで参照可能なように設定。

2. テーマの適用

theme属性としてstyleを設定するので、先にテーマをアプリケーションに適用させておく。
AndroidManifest.xml
  <application
      android:icon="@drawable/ic_launcher"
      android:label="@string/app_name"
+     android:theme="@style/MyApplicationStyle" >


3. テーマの設定

<style name="MyApplicationStyle" parent="android:Theme">
</style>


4. styleのテーマへの組み込み

+ <attr name="myButtonStyle" format="integer|reference" />
  <style name="MyApplicationStyle" parent="android:Theme">
+      <item name="myButtonStyle">@style/MyButtonStyle</item>
  </style>

これでR.attr.myButtonStyleが参照可能になった。

5. Activityでの適用

Button btn = new Button(this, null, R.attr.myButtonStyle);

でstyle定義済みのViewオブジェクトが生成可能。
後は如何様にも。

btn.setText("foo");
LinearLayout layout = new LinearLayout(this);
layout.addView(
    btn,
    new LinearLayout.LayoutParams(
        LinearLayout.LayoutParams.WRAP_CONTENT,
        LinearLayout.LayoutParams.WRAP_CONTENT));
setContentView(layout);

とか。

0 件のコメント:

コメントを投稿