2017-08-15 71 views
1

我想寫一個自定義視圖組,我目前在我的佈局文件中重複了很多。這是一個非常簡單的,兩個文本框放置在一個linearlayout垂直方向和一些填充。值得一提的是,我使用Xamarin來開發這個應用程序,但我認爲這個問題並不是Xamarin特有的。我的實現如下: Android自定義視圖組無法呈現兒童

[Register("qube.AppListItem")] 
class AppListItem : LinearLayout 
{ 
    private string m_Label; 
    private string m_Value; 
    private int m_LabelSize; 
    private int m_ValueSize; 
    private int m_HorizontalPadding; 
    private int m_VerticalPadding; 
    private ValueType m_ValueType; 

    private TextView m_LabelView; 
    private TextView m_ValueView; 

    public AppListItem(Context context) : this(context, null) 
    { 
    } 

    public AppListItem(Context context, IAttributeSet attrs) : this(context, attrs, 0) 
    { 
    } 

    public AppListItem(Context context, IAttributeSet attrs, int defStyleAttr) : base(context, attrs, defStyleAttr) 
    { 
     Initialize(context, attrs); 
    } 

    private void Initialize(Context context, IAttributeSet attrs) 
    { 
     var a = context.ObtainStyledAttributes(attrs, Resource.Styleable.AppListItem, 0, 0); 

     m_Label = a.GetString(Resource.Styleable.AppListItem_label); 
     m_Value = a.GetString(Resource.Styleable.AppListItem_value); 
     m_LabelSize = a.GetDimensionPixelOffset(Resource.Styleable.AppListItem_labelSize, Resource.Dimension.font_small); 
     m_ValueSize = a.GetDimensionPixelOffset(Resource.Styleable.AppListItem_valueSize, Resource.Dimension.font_medium); 
     m_HorizontalPadding = a.GetDimensionPixelOffset(Resource.Styleable.AppListItem_horizontalPadding, Resource.Dimension.row_padding); 
     m_VerticalPadding = a.GetDimensionPixelOffset(Resource.Styleable.AppListItem_verticalPadding, Resource.Dimension.info_list_padding); 
     m_ValueType = (ValueType)a.GetInt(Resource.Styleable.AppListItem_valueType, (int)ValueType.STRING); 

     a.Recycle(); 

     Orientation = Orientation.Vertical; 
     Clickable = true; 
     SetPadding(m_HorizontalPadding, m_VerticalPadding, m_HorizontalPadding, m_VerticalPadding); 

     if (Build.VERSION.SdkInt >= BuildVersionCodes.Honeycomb) 
     { 
      // If we're running on Honeycomb or newer, then we can use the Theme's 
      // selectableItemBackground to ensure that the View has a pressed state 
      TypedValue outValue = new TypedValue(); 
      Context.Theme.ResolveAttribute(Android.Resource.Attribute.SelectableItemBackground, outValue, true); 
      SetBackgroundResource(outValue.ResourceId); 
     } 

     BuildView(); 
    } 

    private void BuildView() 
    { 
     m_LabelView = new TextView(Context); 
     m_LabelView.LayoutParameters = new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MatchParent, ViewGroup.LayoutParams.WrapContent); 
     m_LabelView.TextSize = m_LabelSize; 
     m_LabelView.Text = m_Label; 
     AddView(m_LabelView); 

     if (m_ValueType == ValueType.EDITTEXT) 
      m_ValueView = new EditText(Context); 
     else 
      m_ValueView = new TextView(Context); 

     m_ValueView.LayoutParameters = new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MatchParent, ViewGroup.LayoutParams.WrapContent); 
     m_ValueView.TextSize = m_ValueSize; 
     m_ValueView.Text = m_Value; 
     AddView(m_ValueView); 
    } 

    protected override void OnMeasure(int widthMeasureSpec, int heightMeasureSpec) 
    { 
     base.OnMeasure(widthMeasureSpec, heightMeasureSpec); 
    } 

    protected override void OnLayout(bool changed, int l, int t, int r, int b) 
    { 
     base.OnLayout(changed, l, t, r, b); 
    } 

    public string Label 
    { 
     get { return m_Label; } 
     set 
     { 
      m_Label = value; 
      m_LabelView.Text = value; 
      Invalidate(); 
      RequestLayout(); 
     } 
    } 

    public string Value 
    { 
     get { return m_ValueView.Text; } 
     set 
     { 
      m_ValueView.Text = value; 
      m_Value = value; 
      Invalidate(); 
      RequestLayout(); 
     } 
    } 

    public enum ValueType 
    { 
     STRING, EDITTEXT 
    } 
} 

預期的行爲是,作爲所述,堆疊在彼此的頂部上兩個文本框,然而,實際的行爲與高度0的圖(如果android:layout_height="wrap_content")。手動將layout_height設置爲像20dp這樣的內容僅顯示該高度的空白視圖。

回答

0

好的,我犯的錯誤是一個愚蠢的,這是可以預料的。當我從類型數組中獲得維度時,我傳入的默認值是資源ID,而不是與這些ID關聯的實際值。例如:

m_LabelSize = a.GetDimensionPixelOffset(Resource.Styleable.AppListItem_labelSize, Resource.Dimension.font_small); 

應該

m_LabelSize = a.GetDimensionPixelOffset(Resource.Styleable.AppListItem_labelSize, Resources.GetDimensionPixelOffset(Resource.Dimension.font_small));