ExpanderView не будет расширяться изнутри XAML
Ранее я перенес ExpanderView из набора инструментов Windows Phone в WinRT ExpanderRT, просто чтобы заметить, что если у вас есть два элемента управления ExpanderView внутри StackPanel или ListView, и вы хотите, чтобы первый expanderView расширялся с самого начала, задав для свойства IsExpanded значение True, затем сначала ExpanderView будет перекрывать второй.
Вот пример:
<Grid Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
<StackPanel>
<local:ExpanderControl
IsExpanded="True"
Expander="This is the expander">
<local:ExpanderControl.Items>
<Button Content="Yes"/>
<Button Content="No"/>
</local:ExpanderControl.Items>
</local:ExpanderControl>
<local:ExpanderControl
IsExpanded="False"
Expander="This is the expander">
<ListViewItem>
<StackPanel Orientation="Horizontal">
<Button Content="yes"/>
<Button Content="no"/>
</StackPanel>
</ListViewItem>
</local:ExpanderControl>
</StackPanel>
</Grid>
После нескольких часов попыток отладки управляющего кода ExpanderView я обнаружил, что этот код запускается 4 раза
private void OnSizeChanged(object sender, SizeChangedEventArgs e)
{
if (_presenter == null) return;
var parent = _presenter.GetParentByType<ExpanderControl>();
var gt = parent.TransformToVisual(_presenter);
var childToParentCoordinates = gt.TransformPoint(new Point(0, 0));
_presenter.Width = parent.RenderSize.Width + childToParentCoordinates.X;
}
private void OnPresenterSizeChanged(object sender, SizeChangedEventArgs e)
{
if (null != _itemsCanvas && null != _presenter && IsExpanded)
{
_itemsCanvas.Height = _presenter.DesiredSize.Height;
}
}
В течение первых 2 раз высота _itemsCanvas равна 0. В третий раз высота 64, чтобы перезаписать в 0 к четвертому разу.
Я не нашел никаких причин, почему это происходит. Кто-нибудь здесь может помочь?
1 ответ
Я столкнулся с подобными проблемами после портирования Expander из набора инструментов Windows Phone.
Чтобы исправить эту проблему, я изменил логику OnPresenterSizeChanged
private void OnPresenterSizeChanged(object sender, SizeChangedEventArgs e)
{
if (null != _itemsCanvas && null != _presenter && IsExpanded)
{
if (double.IsNaN(_itemsCanvas.Height))
{
VisualStateManager.GoToState(this, CollapsedState, false);
UpdateVisualState(true);
}
else
{
// Already expanded, so we need to update the height of the canvas directly.
_itemsCanvas.Height = _presenter.DesiredSize.Height;
}
}
}
Отличие состоит в том, что я проверяю, отображался ли элемент canvas ранее или нет, основываясь на проверке, является ли его высота Nan, если это так, я изменяю визуальное состояние, чтобы свернуть без перехода, затем я вызываю UpdateVisualState(true). иначе я просто обновляю высоту рендера canvas.
Проблема заключалась в том, что при первом вызове UpdateVisualState содержимое Presnter было пустым.