Skip to content

Commit ec8bb8b

Browse files
committed
Added some basic logic to a custom layouting class
1 parent 6ff5159 commit ec8bb8b

File tree

3 files changed

+58
-10
lines changed

3 files changed

+58
-10
lines changed

src/Files.App.Controls/BreadcrumbBar/BreadcrumbBar.Events.cs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -80,5 +80,13 @@ private void RootItemChevronDropDownMenuFlyout_Closed(object? sender, object e)
8080
VisualStateManager.GoToState(this, "ChevronNormalOff", true);
8181
VisualStateManager.GoToState(this, "PointerNormal", true);
8282
}
83+
84+
private void ItemsRepeater_ElementPrepared(ItemsRepeater sender, ItemsRepeaterElementPreparedEventArgs args)
85+
{
86+
if (args.Element is not BreadcrumbBarItem item)
87+
return;
88+
89+
item.SetOwner(this);
90+
}
8391
}
8492
}

src/Files.App.Controls/BreadcrumbBar/BreadcrumbBar.cs

Lines changed: 0 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -105,15 +105,5 @@ internal void RaiseItemDropDownFlyoutClosed(BreadcrumbBarItem item, MenuFlyout f
105105
var index = _itemsRepeater?.GetElementIndex(item) ?? throw new ArgumentNullException($"{_itemsRepeater} is null.");
106106
ItemDropDownFlyoutClosed?.Invoke(this, new(flyout, item, index));
107107
}
108-
109-
// Event methods
110-
111-
private void ItemsRepeater_ElementPrepared(ItemsRepeater sender, ItemsRepeaterElementPreparedEventArgs args)
112-
{
113-
if (args.Element is not BreadcrumbBarItem item)
114-
return;
115-
116-
item.SetOwner(this);
117-
}
118108
}
119109
}

src/Files.App.Controls/BreadcrumbBar/BreadcrumbBarLayout.cs

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,16 +8,66 @@
88
using Microsoft.UI.Xaml.Markup;
99
using Microsoft.UI.Xaml.Media;
1010
using Microsoft.UI.Xaml.Shapes;
11+
using Windows.Foundation;
1112

1213
namespace Files.App.Controls
1314
{
1415
public partial class BreadcrumbBarLayout : NonVirtualizingLayout
1516
{
17+
private Size _availableSize;
18+
private BreadcrumbBarItem? _ellipsisButton = null;
1619
private WeakReference<BreadcrumbBar>? _ownerRef;
1720

21+
private bool _ellipsisIsRendered;
22+
private uint _firstRenderedItemIndexAfterEllipsis;
23+
private uint _visibleItemsCount;
24+
1825
public BreadcrumbBarLayout(BreadcrumbBar breadcrumb)
1926
{
2027
_ownerRef = new(breadcrumb);
2128
}
29+
30+
protected override Size MeasureOverride(NonVirtualizingLayoutContext context, Size availableSize)
31+
{
32+
var accumulatedSize = new Size(0, 0);
33+
34+
// Go through all items and measure them
35+
foreach (var item in context.Children)
36+
{
37+
if (item is BreadcrumbBarItem breadcrumbItem)
38+
{
39+
breadcrumbItem.Measure(availableSize);
40+
accumulatedSize.Width += breadcrumbItem.DesiredSize.Width;
41+
accumulatedSize.Height = Math.Max(accumulatedSize.Height, breadcrumbItem.DesiredSize.Height);
42+
}
43+
}
44+
45+
// Get a reference to the ellipsis item
46+
if (context.Children.Count is not 0)
47+
_ellipsisButton ??= context.Children[0] as BreadcrumbBarItem;
48+
49+
// Sets the ellipsis item's visibility based on whether the items are overflowing
50+
_ellipsisIsRendered = accumulatedSize.Width > availableSize.Width;
51+
52+
return accumulatedSize;
53+
}
54+
55+
protected override Size ArrangeOverride(NonVirtualizingLayoutContext context, Size finalSize)
56+
{
57+
float accumulatedWidths = 0f;
58+
59+
// Go through all items and arrange them
60+
foreach (var item in context.Children)
61+
{
62+
if (item is BreadcrumbBarItem breadcrumbItem)
63+
{
64+
breadcrumbItem.Arrange(new Rect(accumulatedWidths, 0, breadcrumbItem.DesiredSize.Width, finalSize.Height));
65+
66+
accumulatedWidths += (float)breadcrumbItem.Width;
67+
}
68+
}
69+
70+
return finalSize;
71+
}
2272
}
2373
}

0 commit comments

Comments
 (0)