Android中通過反射使用超類的私有屬性
阿新 • • 發佈:2019-02-18
自己定義的FocusLIstiew,初始化的時候讓他選定到某一行位置(不是預設的第一行的位置0),ListView預設是從第一行開始選中的,即其超類的超類AdapterView有一個私有屬性mFirstPosition ,預設為0。所以只能通過反射去修改該私有屬性。
程式碼如下:
public void setFirstPosition(int position) {
Class superView = this.getClass(). getSuperclass(). getSuperclass(). getSuperclass();try {
Field field = superView.getDeclaredField("mFirstPosition");
field.setAccessible(true);
field.set((AdapterView)FocusedListView.this, position);
Log.d("ddd", "" + field.get(this));
} catch (SecurityException e) {
Log.d("ddd", "111111111111111111111");
e.printStackTrace();
} catch (NoSuchFieldException e) {
Log.d("ddd", "2222222222222222222222");
e.printStackTrace();
} catch (IllegalArgumentException e) {
Log.d("ddd", "3333333333333333333333333");
e.printStackTrace();
} catch (IllegalAccessException e) {
Log.d("ddd", "444444444444444444444");
e.printStackTrace();
}
}
在Class中提供了4個相關的方法獲得型別的屬性:
getField(String name):Field
getFields():Field[]
getDeclaredField(String name):Field
getDeclaredFields():Field[]
其中getField用於返回一個指定名稱的屬性,但是這個屬性必須是公有的,這個屬性可以在父類中定義。如果是私有屬性或者是保護屬性,那麼都會丟擲異常提示找不到這個屬性。getFields則是返回型別中的所有公有屬性,所有的私有屬性和保護屬性都找不到。
getDeclaredField獲得在這個型別的宣告中定義的指定名稱的屬性,這個屬性必須是在這個型別的宣告中定義,但可以使私有和保護的。getDeclaredFields獲得在這個型別的宣告中定義的所有屬性,包括私有和保護的屬性都會被返回,但是所有父類的屬性都不會被返回。