在WP8中为网格控件创建“行”和“列”属性

时间:2014-09-08 12:31:33

标签: c# xaml windows-phone-8

如您所知,WP8中的网格(以及其他平台也使用XAML)使用这些代码来定义列和行

<Grid>
    <Grid.ColumnDefinitions>
        <ColumnDefinition Width="*"/>
        <ColumnDefinition Width="*"/>
    </Grid.ColumnDefinitions>
    <Grid.RowDefinitions>
        <RowDefinition Height="*"/>
        <RowDefinition Height="*"/>
    </Grid.RowDefinitions>
</Grid>

现在我想添加一个新属性来更短地定义行和列,就像这样

<local:GridEx
      ColumnMulti={"*","*"}
      RowMulti={"*","*"}  >
</local:GridEx>

我只是想知道如何添加它,我尝试了一个,但它没有工作:|

public class GridEX : Grid
{
    public GridEX()
    {
        ManipulateColumnMulti(ColumnMulti);
    }

    public void ManipulateColumnMulti(string[] array)
    {
        foreach (var item in array)
        {
            if (item.Contains("Auto"))
            {
                ColumnDefinition cd = new ColumnDefinition()
                {
                    Width = new GridLength(1, GridUnitType.Auto)
                };
                this.ColumnDefinitions.Add(cd);
            }
            else if (item.Contains("*"))
            {
                int length = int.Parse(item.Replace("*",""));
                ColumnDefinition cd = new ColumnDefinition()
                {
                    Width = new GridLength(length, GridUnitType.Star)
                };                    
                this.ColumnDefinitions.Add(cd);                
            }
            else
            {
                ColumnDefinition cd = new ColumnDefinition()
                {
                    Width = new GridLength(int.Parse(item))
                };
                this.ColumnDefinitions.Add(cd);
            }                
        }  
    }

    ////////////////////////////////////
    public string[] ColumnMulti
    {
        get { return (string[])GetValue(ColumnMultiProperty); }
        set { SetValue(ColumnMultiProperty, value); }
    }
    public static readonly DependencyProperty ColumnMultiProperty = DependencyProperty.RegisterAttached(
        "ColumnMulti",
        typeof(string[]),
        typeof(GridEX),
        new PropertyMetadata(null)
    );

    public static string[] GetColumnMulti(UIElement element)
    {
        if (element == null)
        {
            new ArgumentNullException("element");
        }
        return (string[])element.GetValue(ColumnMultiProperty);
    }

    public static void SetColumnMulti(UIElement element, string[] value)
    {
        if (element == null)
        {
            new ArgumentNullException("element");
        }

        element.SetValue(ColumnMultiProperty, value);
    }
}

2 个答案:

答案 0 :(得分:0)

我写了一个辅助类,它在前一段时间完成,请在my blog上查看。

与您尝试子类Grid不同,我的版本为此目的使用附加属性。

答案 1 :(得分:0)

感谢Toni Petrina,我修复了代码并在这里上传了那些需要它的人:D(只是行定义,与列相同)

public class CustomGrid : Grid
{        
    /// <summary>
    /// Rows Auto
    /// </summary>
    public string RowsAuto
    {
        get { return (string)GetValue(RowsAutoProperty); }
        set { SetValue(RowsAutoProperty, value); }
    }
    public static readonly DependencyProperty RowsAutoProperty = DependencyProperty.Register(
        "RowsAuto", typeof(string), typeof(CustomGrid), new PropertyMetadata(RowsAuto_PropertyChangedCallback));

    private static void RowsAuto_PropertyChangedCallback(DependencyObject d, DependencyPropertyChangedEventArgs e)
    {
        var grid = d as CustomGrid;
        if (d != null)
            grid.RowDefinitions.ManiRows(e.NewValue as string);            
    }
    public static String GetRowsAuto(UIElement element)
    {
        if (element == null)
        {
            new ArgumentNullException("element");
        }
        return (string)element.GetValue(RowsAutoProperty);
    }

    public static void SetRowsAuto(UIElement element, String value)
    {
        if (element == null)
        {
            new ArgumentNullException("element");
        }

        element.SetValue(RowsAutoProperty, value);
    }
}

public static class DefinitionExtensions
{
    public static void ManiRows(this RowDefinitionCollection rowDef, string format)
    {

        if (rowDef == null)
            throw new NullReferenceException("rowDef nust not be null");
        rowDef.Clear();

        if (string.IsNullOrWhiteSpace(format))
            return;

        string[] value = format.Split(new[] {','}, StringSplitOptions.RemoveEmptyEntries);

        foreach (var item in value)
        {
            if (item.Contains("auto"))
            {
                RowDefinition cd = new RowDefinition()
                {
                    Height = new GridLength(1, GridUnitType.Auto)
                };
                rowDef.Add(cd);
            }
            else if (item.Equals("*"))
            {
                RowDefinition cd = new RowDefinition()
                {
                    Height = new GridLength(1, GridUnitType.Star)
                };
                rowDef.Add(cd);
            }
            else if (item.EndsWith("*"))
            {
                double length;
                if (double.TryParse(item.Substring(0,item.Length-1),out length))
                {
                    RowDefinition cd = new RowDefinition()
                    {
                        Height = new GridLength(length, GridUnitType.Star)
                    };
                    rowDef.Add(cd);
                }
            }
            else
            {
                RowDefinition cd = new RowDefinition()
                {
                    Height = new GridLength(double.Parse(item))
                };
                rowDef.Add(cd);
            }
        }
    }
}

使用xaml代码:

<local:CustomGrid RowsAuto="*,auto,40">
            <TextBlock Grid.Row="0" Text="abc"/>
            <TextBlock Grid.Row="1" Text="def"/>
            <TextBlock Grid.Row="2" Text="ghi"/>
        </local:CustomGrid>