Zum Inhalt
Kuonen.UI

ItemsRepeater

Zeigt die Einträge einer Quelle mit einem austauschbaren Layout, ohne Auswahl und Rahmen, wie in WinUI: gestapelt, als gleichmässiges Raster, umbrechend oder in versetzten Spalten. Er erzeugt nur die Elemente, die gerade zu sehen sind; hier sind es 10 000 Kacheln.

Vorführung: ItemsRepeaterVorführung: ItemsRepeater

KXAML

ItemsRepeaterSeite.kxaml
<StackPanel xmlns="https://ui.kuonen.org/kxaml"
            xmlns:x="https://ui.kuonen.org/kxaml/x"
            x:Class="Kuonen.UI.Galerie.Seiten.ItemsRepeaterVorfuehrung"
            Spacing="12">
  <!-- Das Layout wählen; der Wiederholer ordnet neu, die Elemente bleiben. -->
  <StackPanel Orientation="Horizontal" Spacing="12">
    <RadioButton Content="Stapel" GroupName="RepeaterLayout" IsChecked="False" Checked="Layout_Checked" />
    <RadioButton Content="Raster" GroupName="RepeaterLayout" IsChecked="True" Checked="Layout_Checked" />
    <RadioButton Content="Umbruch" GroupName="RepeaterLayout" IsChecked="False" Checked="Layout_Checked" />
    <RadioButton Content="Versetzt" GroupName="RepeaterLayout" IsChecked="False" Checked="Layout_Checked" />
  </StackPanel>
  <!-- 10 000 Kacheln; Quelle und Vorlage kommen aus dem Code-Behind. -->
  <ScrollViewer Width="440" Height="260">
    <ItemsRepeater x:Name="Wiederholer">
      <ItemsRepeater.Layout>
        <UniformGridLayout MinItemWidth="64" MinRowSpacing="4" MinColumnSpacing="4" />
      </ItemsRepeater.Layout>
    </ItemsRepeater>
  </ScrollViewer>
</StackPanel>
ItemsRepeaterSeite.kxaml.cs
using System.Globalization;
using Kuonen.UI;
using Kuonen.UI.Controls;
using Kuonen.UI.Ereignisse;
using Kuonen.UI.Layout;
using Kuonen.UI.Media;

namespace Kuonen.UI.Galerie.Seiten;

public sealed partial class ItemsRepeaterSeite
{
    protected override Func<UIElement>? KxamlFabrik => () => new ItemsRepeaterVorfuehrung();
}

/// <summary>KXAML-Fassung der ItemsRepeater-Seite: der Baum steht in ItemsRepeaterSeite.kxaml, hier Quelle, Vorlage und Layoutwechsel.</summary>
public sealed partial class ItemsRepeaterVorfuehrung
{
    public ItemsRepeaterVorfuehrung()
    {
        InitializeComponent();
        Wiederholer.ItemsSource = Enumerable.Range(0, 10_000).ToArray();
        Wiederholer.ItemTemplate = new DataTemplate(daten => Kachel((int)daten!));
    }

    private void Layout_Checked(object sender, RoutedEventArgs e) => Wiederholer.Layout = (string?)((RadioButton)sender).Content switch
    {
        "Stapel" => new StackLayout { Spacing = 4 },
        "Umbruch" => new WrapLayout { HorizontalSpacing = 4, VerticalSpacing = 4 },
        "Versetzt" => new StaggeredLayout { DesiredColumnWidth = 96, ColumnSpacing = 4, RowSpacing = 4 },
        _ => new UniformGridLayout { MinItemWidth = 64, MinRowSpacing = 4, MinColumnSpacing = 4 },
    };

    // Eine Kachel: Farbe, Breite und Höhe wechseln mit der Zahl (so zeigen Umbruch und versetzte Spalten ihre Wirkung).
    private static Border Kachel(int n) => new()
    {
        Background = new SolidColorBrush(Color.FromRgb((byte)(80 + (n * 47 % 150)), (byte)(120 + (n * 23 % 110)), (byte)(160 + (n * 11 % 90)))),
        Width = 48 + (n % 3 * 24),
        Height = 32 + (n % 4 * 12),
        Child = new TextBlock { Text = n.ToString(CultureInfo.InvariantCulture), HorizontalAlignment = HorizontalAlignment.Center, VerticalAlignment = VerticalAlignment.Center },
    };
}

C#

ItemsRepeaterSeite.cs
using System.Globalization;
using Kuonen.UI;
using Kuonen.UI.Controls;
using Kuonen.UI.Layout;
using Kuonen.UI.Media;

namespace Kuonen.UI.Galerie.Seiten;

/// <summary>Galerie-Seite: <see cref="ItemsRepeater"/> mit vier Layouts.</summary>
public sealed partial class ItemsRepeaterSeite : GalerieSeite
{
    public override string Titel => "ItemsRepeater";

    public override string Beschreibung =>
        "Zeigt die Einträge einer Quelle mit einem austauschbaren Layout, ohne Auswahl und Rahmen, wie in WinUI: gestapelt, als gleichmässiges "
        + "Raster, umbrechend oder in versetzten Spalten. Er erzeugt nur die Elemente, die gerade zu sehen sind; hier sind es 10 000 Kacheln.";

    public override string Stichworte => "Wiederholer Layout StackLayout UniformGridLayout WrapLayout StaggeredLayout Masonry Virtualisierung Kacheln WinUI";

    public override string Datei => nameof(ItemsRepeaterSeite);

    public override UIElement Baue()
    {
        var zahlen = Enumerable.Range(0, 10_000).ToArray();
        var wiederholer = new ItemsRepeater
        {
            ItemsSource = zahlen,
            Layout = new UniformGridLayout { MinItemWidth = 64, MinRowSpacing = 4, MinColumnSpacing = 4 },
            ItemTemplate = new DataTemplate(daten => Kachel((int)daten!)),
        };
        var rollen = new ScrollViewer { Width = 440, Height = 260, Content = wiederholer };

        var layouts = new StackPanel { Orientation = Orientation.Horizontal, Spacing = 12 };
        foreach (var name in new[] { "Stapel", "Raster", "Umbruch", "Versetzt" })
        {
            var feld = new RadioButton { Content = name, GroupName = "RepeaterLayout", IsChecked = name == "Raster" };
            feld.Checked += (_, _) => wiederholer.Layout = name switch
            {
                "Stapel" => new StackLayout { Spacing = 4 },
                "Umbruch" => new WrapLayout { HorizontalSpacing = 4, VerticalSpacing = 4 },
                "Versetzt" => new StaggeredLayout { DesiredColumnWidth = 96, ColumnSpacing = 4, RowSpacing = 4 },
                _ => new UniformGridLayout { MinItemWidth = 64, MinRowSpacing = 4, MinColumnSpacing = 4 },
            };
            layouts.Children.Add(feld);
        }

        var seite = new StackPanel { Spacing = 12 };
        seite.Children.Add(layouts);
        seite.Children.Add(rollen);
        return seite;
    }

    // Eine Kachel: Farbe, Breite und Höhe wechseln mit der Zahl (so zeigen Umbruch und versetzte Spalten ihre Wirkung).
    private static Border Kachel(int n) => new()
    {
        Background = new SolidColorBrush(Color.FromRgb((byte)(80 + (n * 47 % 150)), (byte)(120 + (n * 23 % 110)), (byte)(160 + (n * 11 % 90)))),
        Width = 48 + (n % 3 * 24),
        Height = 32 + (n % 4 * 12),
        Child = new TextBlock { Text = n.ToString(CultureInfo.InvariantCulture), HorizontalAlignment = HorizontalAlignment.Center, VerticalAlignment = VerticalAlignment.Center },
    };
}