14

ファイルにfloatを追加しようとしていdimens.xmlます。

私は次のSOの答えを読んでいました。解決策を試したところ、コメントに記載されている例外が発生しました。その例外がスローされる理由を理解しようとしています。

完全を期すために、ここにXMLがあります。

<item name="zoom_level" format="float" type="dimen">15.0</item>

爆発するコードは次のとおりです。

final float zoom = this.getResources().getDimension(R.dimen.zoom_level);

Androidソースにジャンプしました。これが、getDimensionのメソッド定義です。

public float getDimension(int id) throws NotFoundException {
    synchronized (mTmpValue) {
        TypedValue value = mTmpValue;
        getValue(id, value, true);
        if (value.type == TypedValue.TYPE_DIMENSION) {
            return TypedValue.complexToDimension(value.data, mMetrics);
        }
        throw new NotFoundException(
                "Resource ID #0x" + Integer.toHexString(id) + " type #0x"
                + Integer.toHexString(value.type) + " is not valid");
    }
}

だからどんな理由でもvalue.type != TypedValue.TYPE_DIMENSION。Androidソースが完全にセットアップされていないためLog.w("YARIAN", "value type is " + value.type)'、そこにステートメントを簡単に追加できません。

それから私は飛び込んだgetValue、そして呼び出しの連鎖は次のように思われる:

Resources.getValue -> AssetManager.getResourceValue -> AssetManager.loadResourceValue

loadResourceValueはネイティブメソッドであり、ここで私の掘り下げが崩壊します。

何が起こっているのかを理解するための最良の方法を知っている人はいますか?


また、とResourcesがあることに気づきました。しかし、XMLでは書くことができません。TypedValue.TYPE_FLOATTypedValue.TYPE_DIMENSIONtype="float"

コメントで説明されている回避策は、を使用してからtype=string、を使用Float.parseしてフロートを取得することです。これは必要ですか?なぜまたはなぜそうではないのですか?

4

4 に答える 4

22

遅い答えだと思いますが、提案したように文字列をfloatに解析する代わりに、TypedValue#getFloat()を使用する必要があります。

XML:

    <item name="float_resource" format="float" type="raw">5.0</item>

Java:

TypedValue out = new TypedValue();
context.getResources().getValue(R.raw.float_resource, out, true);
float floatResource = out.getFloat();

を置くことができます。またはfraction、必要に応じて、これはのリソースクラスにのみ対応します。rawstringtypeR

于 2013-06-10T15:31:41.477 に答える
3

私もこの問題に遭遇しました。エラーメッセージはあまり役に立ちませんが、リソースファイルにfloat値だけを入れていて、測定値を指定していなかったことが問題であることに気付きました。たとえば、15.0から15.0dpに切り替えると、問題が回避され、通常のディメンションリソースを引き続き使用できるようになります。

于 2018-04-12T21:31:59.830 に答える
2

Resources.getFloat(API 29から)とResourcesCompat.getFloatがあります:

val zoomLevel: Float = ResourcesCompat.getFloat(resources, R.dimen.zoom_level)

zoom_levelXMLはそのままにしておくことができます。

于 2020-08-25T16:14:12.403 に答える
1

リッチアンサーから作成されたKotlin拡張関数:

fun Resources.getFloatValue(@DimenRes floatRes:Int):Float{
    val out = TypedValue()
    getValue(floatRes, out, true)
    return out.float
}

使用法:

resources.getFloatValue(R.dimen.my_float)
于 2020-05-05T11:28:18.337 に答える