WP7 ListBox自定义Panel仿瀑布流

实现瀑布流,一开始是想是不是可以通过更改它的ItemTemplate,试了一下不行发现问题不在这,还是得改ItemsPanel,不罗嗦了,上图

添加一个类继承Panel,然后重写MeasureOverride及ArrangeOverride 及定义一个列数属性,具体代码如下:

public class CustomPanel : Panel
    {
        public CustomPanel()
        {
            /**默认三列**/
            ColumnCount = 3;
            ColumnHeight = new double[ColumnCount];
            this.UseLayoutRounding = true;
        }


        static double[] ColumnHeight;

        /// <summary>
        /// 列数
        /// </summary>
        public int ColumnCount
        {
            get { return (int)this.GetValue(ColumnCountProperty); }
            set { this.SetValue(ColumnCountProperty, value); }
        }

        public static DependencyProperty ColumnCountProperty = DependencyProperty.Register("ColumnCount", typeof(int), typeof(CustomPanel), new PropertyMetadata(new PropertyChangedCallback((o, e) =>
        {
            ColumnHeight = new double[(int)e.NewValue];
            if (o == null || e.NewValue == e.OldValue)
                return;
            o.SetValue(ColumnCountProperty, e.NewValue);
        })));

        protected override Size MeasureOverride(Size availableSize)
        {
            int indexY = this.Children.Count / ColumnCount;
            if (this.Children.Count % ColumnCount > 0) indexY++;
            int flagY = 0;
            Size resultSize = new Size(0, 0);
            #region<---- 测量值

            for (int i = 0; i < indexY; i++)//列
            {
                if (i == indexY - 1)
                {
                    int residual = Children.Count - i * ColumnCount;
                    if (Children.Count <= ColumnCount)
                    {
                        residual = Children.Count;
                    }
                    for (int h = 0; h < residual; h++)
                    {
                        Children[ColumnCount * flagY + h].Measure(availableSize);
                        resultSize.Width = (Children[ColumnCount * flagY + h].DesiredSize.Width) * ColumnCount;
                        ColumnHeight[h] += Children[ColumnCount * flagY + h].DesiredSize.Height;
                    }
                }
                else
                {

                    for (int y = 0; y < ColumnCount; y++)
                    {
                        Children[ColumnCount * flagY + y].Measure(availableSize);
                        resultSize.Width = (Children[ColumnCount * flagY + y].DesiredSize.Width) * ColumnCount;
                        ColumnHeight[y] += Children[ColumnCount * flagY + y].DesiredSize.Height;
                    }
                    flagY++;
                }
            }
            #endregion
            resultSize.Height = ColumnHeight.Max();
            return resultSize;
        }

        protected override Size ArrangeOverride(Size finalSize)
        {
            for (int i = 0; i < ColumnHeight.Count(); i++)
            {
                ColumnHeight[i] = 0;
            }
            int indexY = this.Children.Count / ColumnCount;
            if (this.Children.Count % ColumnCount > 0) indexY++;
            int flagY = 0;
            double flagX = 0;
            #region<------布局

            for (int i = 0; i < indexY; i++)//列
            {
                finalSize.Width = (Children[i].DesiredSize.Width) * ColumnCount;
                if (i == indexY - 1)
                {
                    flagX = 0;
                    int residual = Children.Count - i * ColumnCount;
                    if (Children.Count <= ColumnCount)
                    {
                        residual = Children.Count;
                    }

                    for (int h = 0; h < residual; h++)
                    {

                        Children[ColumnCount * i + h].Arrange(new Rect(new Point(flagX, ColumnHeight[h]), Children[ColumnCount * i + h].DesiredSize));
                        ColumnHeight[h] += Children[ColumnCount * flagY + h].DesiredSize.Height;

                        flagX += Children[ColumnCount * i + h].DesiredSize.Width;
                    }
                }
                else
                {
                    for (int y = 0; y < ColumnCount; y++)
                    {
                        Children[ColumnCount * flagY + y].Arrange(new Rect(new Point(flagX, ColumnHeight[y]), Children[ColumnCount * i + y].DesiredSize));
                        ColumnHeight[y] += Children[ColumnCount * flagY + y].DesiredSize.Height;
                        flagX += Children[ColumnCount * flagY + y].DesiredSize.Width;
                    }
                    flagX = 0; flagY++;
                }
            }

            #endregion
            return finalSize;
        }
    }

 布局实现,欢迎拍砖...

源码:瀑布流源码

posted on 2012-10-19 11:52  the rock.  阅读(1646)  评论(7编辑  收藏  举报

导航