2014-02-18 17 views
5

Dies kann eine ziemlich lange und umstrittene Frage sein. Lassen Sie mich zunächst sagen, dass ich in C# und XAML entwickle. Ich möchte ein Steuerelement erstellen, die die folgende Vorlage stapelt:Erstellen Sie zweispaltige, vertikal gestapelte Spalten-Steuerelement für Windows Phone 8

_____________ 
|   | 
| Text  | 
| Image  | 
| More Text | 
|___________| 

für eine Folge von Elementen, die in zwei Spalten, etwa so:

______ ______ 
| | | | 
| 1 | | 2 | 
|____| | | 
| | |____| 
| 3 | | | 
| | | 4 | 
| | |____| 
|____| | | 
| | | 5 | 
| 6 | | | 
| | 

Beachten Sie, dass sie zum ersten Mal von der Höhe bestellt werden und dann nach links nach rechts.

Dies ist relativ einfach zu tun als ein zweispaltiges Gitter mit einem vertikalen Stapelfeld in jedem.

Für mich ist dies eine Repräsentation einer Sequenz von Elementen, daher ist es sinnvoll, dies als Steuerelement darzustellen, das von ItemsControl erbt.

Wie würde ich das machen? Das Einstellen eines ItemTemplate scheint offensichtlich, alles andere entgeht mir.

+0

Also, wenn ich das richtig verstehe, Sie etwas sehr ähnlich zu einem Wrap-Panel wollen? –

+0

Die Dokumentation für ein Wrap-Panel besagt: "Standardmäßig werden die Elemente in einem Wrap-Panel horizontal von links nach rechts und von oben nach unten platziert, Sie können sie aber auch vertikal von oben nach unten und links platzieren -nach rechts." Meine Situation ist, dass Elemente horizontal angeordnet werden müssen, von oben nach unten, von links nach rechts, wenn das sinnvoll ist. Ich glaube, dass ein Wrap Panel das fünfte Element nicht dort platzieren würde, wo es ist, sondern es würde zur nächsten Zeile gehen. Wirklich, ich interessiere mich nicht allzu sehr für den Algorithmus, ich kann das herausfinden, ich möchte nur in der Lage sein, Elemente in einem ItemsControl manuell auszulegen. – overgroove

+0

Ja, genau, es würde es nicht dort hinstellen, ich wollte nur klarstellen :) –

Antwort

2

Ich denke, wir sollten die ListBox verwenden und die ItemsPanel von ListBox ändern. Wir passen ein Panel als ItemsPanel an, definieren das column property und überschreiben das Verfahren von MeasureOverride und ArrangeOverride.

-Code befindet sich unter:

using System; 
using System.Linq; 
using System.Windows; 
using System.Windows.Controls; 

namespace TravelHelper_WP8 
{ 
    public class CustomPanel : Panel 
    { 
     public CustomPanel() 
     { 
      /**default 2 columns**/ 
      ColumnCount = 2; 
      columnHeight = new double[ColumnCount]; 
      this.UseLayoutRounding = true; 
     } 

     static double[] columnHeight; 

     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<---- Measure Value 

      for (int i = 0; i < indexY; i++)//Column 
      { 
       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<------Layout 
      for (int i = 0; i < indexY; i++)//Column 
      { 
       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; 
     } 
    } 
} 
+0

Während ich die Anordnungs- und Messalgorithmen ändern musste, war dies genau das, was ich brauchte, um mir ins Ziel zu kommen. Vielen Dank. – overgroove

+0

Gern geschehen. Ich bin froh, dass ich dir helfen kann. –