天天看點

android自定義屬性dimen,Android自定義屬性以及組合View

概念

自定義組合View是指android給我們提供的View本身功能不夠用,但是可以把幾個View粘合起來形成一個獨立的類,對外部提供統一的職能,内部View之間的邏輯實作可以隐藏,使之整體看起來就像是一個新的View。另外,還可以通過自定義屬性功能,使得我們的組合View直接在XML布局檔案中友善的使用

實作

定義一個基類,之後的組合View都繼承自它

public abstract class BaseCustomView extends RelativeLayout {

private static final String NAMESPACE = "http://schemas.android.com/apk/res-auto";

//重載構造函數 通過new建構對象時會調用此處

//View.java中原文:Simple constructor to use when creating a view from code

public BaseCustomView(Context context) {

super(context);

initView();

}

//在XML中建構時會調用此處,也是我們自定義屬性的構造函數,style預設用app的主題

//View.java中原文:Constructor that is called when inflating a view from XML

//...This version uses a default style of 0, so the only attribute values

//applie are those in the Context's Theme and the given AttributeSet

public BaseCustomView(Context context, AttributeSet attrs) {

super(context, attrs);

TypedArray a = context.obtainStyledAttributes(attrs, getStyleable());

initAttributes(a);

initView();

a.recycle();

}

public BaseCustomView(Context context, AttributeSet attrs, int defStyleAttr) {

super(context, attrs, defStyleAttr);

initView();

}

private void initView() {

View view = View.inflate(getContext(), getLayout(), this);

ButterKnife.bind(this, view);

initData(view);

}

//傳回 R.styleable.xxx styleable是自定義的一組declare-styleable

protected abstract int[] getStyleable();

//根據擷取到的屬性數組在代碼中初始化屬性值

protected abstract void initAttributes(TypedArray a);

//擷取自定義組合View的布局 R.layout.xxx

protected abstract int getLayout();

//初始化一些預設資料

protected abstract

一個簡單的例子

一般我們在應用中會有很多類似的View,比如設定界面的View都可以抽取出來獨立成章,簡化代碼友善維護下邊是一個簡單的例子,實作了一個比較通用的設定條目,XML中沒有設定相關資源的時候就隐藏相應内部View,否之顯示出來。一個空的效果顯示如下:

android自定義屬性dimen,Android自定義屬性以及組合View

示例

public class SettingItemView extends BaseCustomView {

private String mLeftString;

private String mEndString;

private Drawable mLeftImage;

private Drawable mEndImage;

private int mLeftColor;

public SettingItemView(Context context) {

super(context);

}

public SettingItemView(Context context, AttributeSet attrs) {

super(context, attrs);

}

public SettingItemView(Context context, AttributeSet attrs, int defStyle) {

super(context, attrs, defStyle);

}

@Override

protected int[] getStyleable() {

return R.styleable.SettingItemView;

}

@Override

protected void initAttributes(TypedArray a) {

mLeftString = a.getString(R.styleable.SettingItemView_textLeft);

mEndString = a.getString(R.styleable.SettingItemView_textEnd);

mLeftImage = a.getDrawable(R.styleable.SettingItemView_imageLeft);

mEndImage = a.getDrawable(R.styleable.SettingItemView_imageEnd);

mLeftColor = a.getColor(R.styleable.SettingItemView_colorLeft, getResources().getColor(R

.color.text_color));

}

@Override

protected int getLayout() {

return R.layout.ui_setting_item;

}

@Override

protected void initData(View view) {

setLeftText(mLeftString);

setEndText(mEndString);

setLeftImage(mLeftImage);

setEndImage(mEndImage);

tv_left.setTextColor(mLeftColor);

}

public void setLeftImage(Drawable image) {

iv_left.setImageDrawable(image);

}

public void setEndImage(Drawable image) {

if (image != null) {

iv_end.setVisibility(VISIBLE);

iv_end.setImageDrawable(image);

}

}

public void setLeftText(String text) {

tv_left.setText(text);

}

public void setEndText(String text) {

if (!TextUtils.isEmpty(text)) {

tv_end.setVisibility(VISIBLE);

tv_end.setText(text);

}

}

}

建立一個屬性檔案attrs.xml

添加以下自定義屬性(一些通用的可以抽取出來供其它使用):

關于styleable屬性類型可以搜尋一下有很多資料,就不展開說了

布局檔案如下:

android:id="@+id/rl_root"

xmlns:android="http://schemas.android.com/apk/res/android"

android:layout_width="match_parent"

android:layout_height="@dimen/item_height">

android:id="@+id/line"

android:layout_width="match_parent"

android:layout_height="0.1dp"

android:background="#ffd2d2d2"

android:layout_alignParentBottom="true"/>

android:layout_width="match_parent"

android:layout_height="@dimen/item_height"

android:orientation="horizontal"

android:layout_above="@id/line">

android:id="@+id/iv_left"

android:layout_width="wrap_content"

android:layout_height="match_parent"

android:scaleType="centerInside"

android:visibility="gone"/>

android:layout_width="wrap_content"

android:layout_height="match_parent"

android:layout_weight="1"

android:gravity="center_vertical"

android:layout_weight="1"

android:visibility="gone"/>

android:id="@+id/iv_end"

android:layout_width="wrap_content"

android:layout_height="match_parent"

android:scaleType="centerInside"

android:visibility="gone"/>

android:id="@+id/tv_end"

android:layout_width="wrap_content"

android:layout_height="match_parent"

android:gravity="center_vertical"

android:visibility="gone"/>

應用

在布局中應用剛才寫的組合View就像普通View一樣就好了,别忘了在跟布局中添加一行

xmlns:item="http://schemas.android.com/apk/res-auto"

這樣新屬性就可以以item的命名空間調用了

android:id="@+id/siv_test"

android:layout_width="match_parent"

android:layout_height="wrap_content"

item:imageLeft="@drawable/xxx"

item:textLeft="test"/>