[Android][Kotlin]Androidの設定値について

<p>指定したターゲット（パッケージ名や利用するサービスの設定）でAndroidアプリケーションをビルドする方法は複数ある。初期のものであったり、それを改善したものであったり。最新の方法だと利点が多いので選択できればいいのだが、歴史が長いソースコードだと、様々な理由から方法を変更できなかったり。</p>

<p>何がベストなのかは状況によって異なるが、まずは知らないことには話にならないということで調べてた方法を列挙してみる。</p>

androidコマンド
<p>最新のAndroid SDKのツールではなくなったコマンド。オプションで指定したAndroidアプリケーションの雛形となるソース一式を生成されるので、例えば、異なるパッケージ名のソースを生成する場合に使っていた。</p>

<pre><code>$ android create project \
    --name プロジェクト名 \
    --target ターゲットID \
    --path プロジェクトを生成するファイル・パス \
    --package パッケージ名 \
    --activity デフォルト・アクティビティ名
</code></pre>

代替リソース
<p>条件毎に用意したディレクトリにリソースを置いて切り替える方法。</p>
<p>以下は高密度画面(hdpi)とそれ以外の画面の端末でアイコン画像を切り替える例だ。</p>

<pre><code>res/drawable/icon.png
res/drawable-hdpi/icon.png
</code></pre>

<p>hdpiは設定修飾子と呼ばれる識別子だが、どんな設定修飾子があるのか表にしてみる。</p>

<table border="1">
<tr><th>設定</th><th>修飾子の値</th><th>説明</th></tr>
<tr><td>MCC と MNC</td><td>mcc310 mcc310-mnc004</td><td>モバイル カントリー コード（MCC）とモバイル ネットワーク コード（MNC）</td></tr>
<tr><td>言語と地域</td><td>en en-rUS b+en+US</td><td>ISO 639-1言語コード BCP 47言語タグ</td></tr>
<tr><td>レイアウトの方向</td><td>ldrtl ldltr</td><td>ldrtlは右から左。ldltrは左から右。</td></tr>
<tr><td>smallestWidth</td><td>sw<N>dp</td><td>使用可能な画面領域の最小寸法で指定。</td></tr>
<tr><td>使用可能な幅</td><td>w<N>dp</td><td>使用可能な最小の画面幅をdp単位で指定。</td></tr>
<tr><td>使用可能な高さ</td><td>h<N>dp</td><td>使用可能な最小の画面の高さをdp単位で指定。</td></tr>
<tr><td>画面サイズ</td><td>small normal large xlarge</td><td></td></tr>
<tr><td>画面アスペクト</td><td>long notlong</td><td></td></tr>
<tr><td>円形の画面</td><td>round notround</td><td></td></tr>
<tr><td>広色域</td><td>widecg nowidecg</td><td></td></tr>
<tr><td>HDR</td><td>highdr lowdr</td><td>ハイ ダイナミック レンジ</td></tr>
<tr><td>画面の向き</td><td>port land</td><td></td></tr>
<tr><td>UI モード</td><td>car desk ...</td><td>端末をホルダーに装着したり、取り外す場合</td></tr>
<tr><td>ナイトモード</td><td>night notnight</td><td></td></tr>
<tr><td>画面ピクセル密度</td><td>ldpi xxxhdpi ...</td><td>画面ピクセル密度（dpi）</td></tr>
<tr><td>タッチスクリーン タイプ</td><td>notouch finger</td><td></td></tr>
<tr><td>テキスト入力方法</td><td>nokeys qwerty 12key</td><td></td></tr>
<tr><td>ナビゲーション キー</td><td>navexposed navhidden</td><td></td></tr>
<tr><td>ナビゲーション方法</td><td>nonav dpad trackball wheel</td><td></td></tr>
<tr><td>プラットフォーム Ver.</td><td>v3 v4 v7 ...</td><td>API レベル</td></tr>
</table>

ローカライズ
<p>設定修飾子を使った代替リソースを利用する方法。例を挙げる。</p>

<pre><code>res/values/strings.xml
res/drawable/
</code></pre>

<pre><code>res/values-en/strings.xml
</code></pre>

<pre><code>res/values-ja/strings.xml
res/drawable-ja/
</code></pre>

<p>文字列リソースを英語と日本語で切り替えるのと、画像を日本語とそれ以外で切り替える例となっている。</p>

ビルド バリアント
<p>ビルド・バリアントは、ビルドタイプとプロダクト フレーバーを組み合わせたも。build.gradleの例だ。</p>

<pre><code>android {
    defaultConfig {
    }
 
    signingConfigs {
        release {}
    }
 
    buildTypes {
        release {
            signingConfig signingConfigs.release
        }
        debug {}
        staging {}
    }
 
    flavorDimensions "api", "mode"
    productFlavors {
        demo {
            dimension "mode"
        }
        full {
            dimension "mode"
        }
 
        minApi24 {
            dimension "api"
        }
        minApi23 {
            dimension "api"
        }
        minApi21s {
            dimension "api"
        }
    }
 
    variantFilter { variant ->
        def names = variant.flavors*.name
        if (names.contains("minApi21") && names.contains("demo")) {
            setIgnore(true)
        }
    }
}
</code></pre>

<p>ビルド バリアントの形式は、&lt;product-flavor&gt;&lt;Build-Type&gt;となる。</p>
<p>例えば、minApi24DemoDebugは、minApi24とdemoとdebugの組み合わせという意味。この場合、apkはapp-minApi24-demo-debug.apkとなる。</p>
<p>ビルド・バリアントに対応したJavaソースのパスは、例えば src/demoMinApi24/java/ となる。</p>

<p>ソースセットの優先順位の例だ。</p>

<ul>
<li>src/demoDebug/</li>
<li>src/debug/</li>
<li>src/demo/</li>
<li>src/main/</li>
</ul>

gradle.properties
<p>build.gradleに渡すパラメータを設定できる。</p>

<p>gradle.propertiesの例。</p>

<pre><code>DEMO_STRING="demo string"
DEMO_NUM_DEMO=1234
DEMO_NUM_FULL=5678
DEMO_BOOLEAN=true
</code></pre>

<p>build.gradleの例。</p>

<pre><code>android {
    defaultConfig {
        // resの値を追加（AndroidManifest.xml で参照）
        resValue 'string', 'DEMO_STRING', "${DEMO_STRING}"
 
        // BuildConfigクラスのメンバーを追加（Kotlinコードで参照）
        buildConfigField 'boolean', 'DEMO_BOOLEAN', "${DEMO_BOOLEAN}"
    }
    productFlavors {
        demo {
            // BuildConfigクラスのメンバーを追加（Kotlinコードで参照）
            buildConfigField 'long', 'DEMO_NUM', "${DEMO_NUM_DEMO}"
        }
        full {
            // BuildConfigクラスのメンバーを追加（Kotlinコードで参照）
            buildConfigField 'long', 'DEMO_NUM', "${DEMO_NUM_FULL}"
        }
}
</code></pre>

<p>リソースの値を設定することでAndroidManifest.xmlで使い値を切り替えたり、BuildConfigクラスのメンバーを設定することで、ソースコードで参照する値を切り替えられる。</p>

【関連情報】
<a href="https://love-kotlin.connpass.com/event/166497/">集まれKotlin好き！Kotlin愛好会 vol.20</a><br />
<a href="https://cocoa-kanto.connpass.com/">Cocoa.swift</a><br />
<a href="https://www.facebook.com/groups/cocoa.kanto/">Cocoa勉強会 関東</a><br />
<a href="http://www.bitz.co.jp/weblog/">Cocoa練習帳</a><br />