在Android应用程序中使用TypedArray

时间:2011-02-21 15:16:31

标签: android

我遇到了

的代码

HelloGallery示例

ImageAdapter.java - http://developer.android.com/resources/tutorials/views/hello-gallery.html

TypedArray a = obtainStyledAttributes(R.styleable.HelloGallery);
mGalleryItemBackground = a.getResourceId(
        R.styleable.HelloGallery_android_galleryItemBackground, 0);
a.recycle();

attrs.xml - http://developer.android.com/resources/tutorials/views/hello-gallery.html

<?xml version="1.0" encoding="utf-8"?>
<resources>
    <declare-styleable name="HelloGallery">
        <attr name="android:galleryItemBackground" />
    </declare-styleable>
</resources>

并代码:

蛇游戏示例

TileView.java - http://developer.android.com/resources/samples/Snake/src/com/example/android/snake/TileView.html

TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.TileView);
mTileSize = a.getInt(R.styleable.TileView_tileSize, 12);
a.recycle();

attrs.html - http://developer.android.com/resources/samples/Snake/res/values/attrs.html

<resources>
  <declare-styleable name="TileView">
    <attr name="tileSize" format="integer" />
  </declare-styleable>
</resources>

  1. 我可以知道为什么他们需要从XML获取整数值吗?为什么他们不只是编码mGalleryItemBackground = 0;mTileSize = 12;?我的猜测是,他们希望能够在不触及Java代码的情况下改变一些东西。但是,我没有看到XML文件本身明确指定任何值。 用于演示TypedArray和context.obtainStyledAttributes目的的代码示例非常有用。
  2. 两人都试图读取整数。为什么其中一个示例使用getResourceId技术,另一个使用getInt技术?
  3. 我指的是TypedArray JavaDoc,但我很难理解recycle的作用是什么?
  4.   

    回馈以前检索过的   StyledAttributes,供以后重复使用。

2 个答案:

答案 0 :(得分:21)

  
      
  1. 我可以知道为什么他们需要从XML获取整数值吗?为什么不呢   只是代码mGalleryItemBackground = 0;   和mTileSize = 12;?
  2.   

我认为这主要是为了演示从View构造函数中读取XML属性的技术,而不是满足绝对要求。如果你想在其他地方重新使用你的自定义视图(不太可能像Snake那样特别容易的话),那么这是一个非常有用的东西能够做到...改变背景颜色等而不必触摸Java代码。

特别是对于图块大小,如果不同的设备类型有不同的布局,那么从XML读取可能会有用...您可能需要不同尺寸的图块用于不同的密度和尺寸组合。

  
      
  1. 两人都试图读取整数。为什么其中一个例子正在使用   getResourceId技术,另一个是   使用getInt技术?
  2.   

因为图库背景不是整数...所以它应该是资源标识符(例如@ drawable / foo)。是的 仍然是一个整数,但是一个整数,其值在运行时才知道。相反,tile大小是一个常量值,不需要任何类型的运行时解析。

  
      
  1. 我指的是TypedArray JavaDoc,但我很难理解什么是回收   呢?
  2.   

如果有疑问,look at the source。它基本上是一个优化,以避免LayoutInflater必须为它膨胀的每个视图分配其中一个。

答案 1 :(得分:10)

关于可设置属性

除了能够在不触及Java代码的情况下更改该值之外,它还允许他们根据设备配置将不同的样式应用于他们的应用程序。而不是用XML声明:

<com.example.android.snake.SnakeView
    android:id="@+id/snake"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tileSize="24" />

他们可以在res/values/styles.xml

中声明这些值
<style name="Control.SnakeViewStyle">
    <item name="android:layout_width">match_parent</item>
    <item name="android:layout_height">match_parent</item>
    <item name="tileSize">24</item>
</style>

然后参考那种风格:

<com.example.android.snake.SnakeView
    android:id="@+id/snake"
    style="@styles/SnakeViewStyle" />

在分离这样的样式后,它们可以为每个设备配置提供不同的styles.xml文件。例如,纵向模式可能有一个res/values/styles.xml,横向模式可能有一个res/values-land/styles.xml

关于资源和整数

如果将一个styleable属性声明为“reference”而不是“integer”,那么(1)在为该属性编写XML时会获得IDE内容辅助,并且(2)编译器会检查您是否未提供对该属性的引用不存在的资源。因此,要获得它,您需要使用getResourceId,因为它可能会进行一些额外的解析以获得实际的资源ID。

关于回收

我不太确定,但从TypedArray的代码判断,似乎内部有一些缓存机制,recycle()使其有效。