首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >带有自定义面板的Silverlight 2 ListBox不尊重来自ArrangeOverride的大小

带有自定义面板的Silverlight 2 ListBox不尊重来自ArrangeOverride的大小
EN

Stack Overflow用户
提问于 2009-02-07 16:46:55
回答 2查看 1.9K关注 0票数 1

如果我使用一个自定义面板来布局我的ListBoxItems,那么ListBox就不会尊重它们的合并高度(虽然它确实尊重它们的合并宽度)--即使我的ArrangeOverride返回一个包围所有项目的大小。

设置ListBox的高度显式地使一切正常工作,但我希望它自己解决这个问题!

有人见过这个吗?

谢谢

更新:在下面的示例中,ListBox使用一个定制面板,该面板根据Row属性垂直堆叠文章,并返回足够大的大小来包围所有文章。但是,除非我为ListBox设置了高度,否则它就会崩溃!

代码语言:javascript
复制
<UserControl x:Class="SilverlightApplication1.Page"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
xmlns:local="clr-namespace:SilverlightApplication1">
<UserControl.Resources>
    <DataTemplate x:Key="ArticleTemplate">
        <TextBlock Text="{Binding Title}" />
    </DataTemplate>
</UserControl.Resources>
<ListBox Height="200"
        Background="AntiqueWhite"
        ItemTemplate="{StaticResource ArticleTemplate}"
        ItemsSource="{Binding}" VerticalAlignment="Top"
        Margin="0,0,0,0">
    <ListBox.ItemsPanel>
        <ItemsPanelTemplate>
            <local:MyPanel />
        </ItemsPanelTemplate>
    </ListBox.ItemsPanel>
</ListBox>
</UserControl>

小组成员如下:

代码语言:javascript
复制
public class MyPanel : Panel
{
    protected override Size ArrangeOverride(Size arrangeSize)
    {
        double width = 0, height = 0;
        foreach (UIElement child in this.Children)
        {
            var article = (Article)((ContentControl)child).DataContext;
            var y = child.DesiredSize.Height * article.Row;
            var location = new Point(0, y);
            var rect = new Rect(location, child.DesiredSize);
            child.Arrange(rect);
            width = Math.Max(width, child.DesiredSize.Width);
            height = Math.Max(height, y + child.DesiredSize.Height);
        }

        return new Size(width, height);
    }

    protected override Size MeasureOverride(Size availableSize)
    {
        foreach (UIElement child in this.Children)
        {
            if (child != null)
            {
                child.Measure(new Size(double.PositiveInfinity, double.PositiveInfinity));
            }
        }

        return new Size();
    }
}

域类:

代码语言:javascript
复制
public class Article
{
    private readonly int row;
    private readonly string title;

    public Article(string title, int row)
    {
        this.title = title;
        this.row = row;
    }

    public int Row { get { return this.row; } }

    public string Title { get { return this.title; } }
}
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2009-02-08 00:57:51

我无法重现你描述的问题。你能提供一些示例代码/xaml让我看看吗?

更新:

我相信这里的问题是,您将返回(0,0)作为面板的DesiredSize从MeasureOverride。你可能想做这样的事情:

代码语言:javascript
复制
    protected override Size MeasureOverride(Size availableSize)
    {
        double width = 0;
        double height = 0;
        foreach (UIElement child in this.Children)
        {
            if (child != null)
            {
                child.Measure(new Size(double.PositiveInfinity, double.PositiveInfinity));
                width = Math.Max(width, child.DesiredSize.Width);
                height = Math.Max(height, child.DesiredSize.Height);
            }
        }

        return new Size(width, height);
    }

根据您的需求,实际的大小调整逻辑可能会有所不同。

在您的代码中所发生的事情是,通过从MeasureOverride返回(0,0),您的面板实质上是在“请求”它的父节点为它保留这么多空间。因此,当涉及布局周期的排列阶段时,传递给ArrangeOverride的ArrangeOverride非常小(至少在一维中为0)。您可以通过在ArrangeOverride中设置断点,然后检查finalSize参数来验证这一点。要使您的代码正确地使用布局系统,您需要从MeasureOverride返回包含其子级所需的最小空间。

票数 1
EN

Stack Overflow用户

发布于 2009-02-09 02:03:16

别忘了ListBoxes包含ScrollViewers。ScrollViewer可能看到了孩子们的身高,并认为“我能处理好”,然后设定自己的尺寸。

试着设置

代码语言:javascript
复制
ScrollViewer.VerticalScrollBarVisibility = "Hidden"

代码语言:javascript
复制
ScrollViewer.VerticalScrollBarVisibility = "Disabled"

在您的ListBox中,看看会发生什么。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/524099

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档