代码之家  ›  专栏  ›  技术社区  ›  Peter Perháč

listbox.itemssource_binding…不起作用,但是如果我用代码设置itemssource,那就太好了!

  •  0
  • Peter Perháč  · 技术社区  · 14 年前

    我正在使用WPF进行试验,遇到了一个似乎无法解决的问题,尽管我以前在Silverlight上做过一些工作,并且成功地使用了DataContexts、数据绑定和INPC。这次我被卡住了…

    我正在使用此代码创建应用程序主窗口的实例:

    protected override void OnStartup(StartupEventArgs e)
    {
        base.OnStartup(e);
        MainWindow window = new MainWindow();
        var viewModel = new MainVM(); //implements INotifyPropertyChanged
        viewModel.Load("Brighton+UK");
        window.DataContext = viewModel;
        window.weatherList.ItemsSource = viewModel.WeatherInfo; //THIS WORKS
        window.Show();
    }
    

    当我像这样运行应用程序时,一切都很好,主窗口上的列表框会像应该的那样显示在MainVM的WeatherInfo ObservableCollection中找到的项目。

    但是,当我对该行进行注释,然后进入主窗口的xaml,并在xaml中设置weatherlist列表框的itemssource属性时,如下所示:

    <ListBox x:Name="weatherList" 
        Grid.Row="0" 
        ItemContainerStyle="{StaticResource stretched}" 
        ItemsSource="{Binding WeatherInfo}" />
    

    虽然我确实将mainWindow的dataContext设置为mainVM的一个实例(如C代码摘要所示),但列表并不会像我预期的那样被填充。

    有人能给我解释一下,为什么?

    =编辑=

    所有主窗口的XAML:

    <Window x:Class="DataTemplates.MainWindow"
            xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
            xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
            Title="Google World Weather" 
            SizeToContent="WidthAndHeight" 
            WindowStartupLocation="CenterScreen"
            xmlns:local="clr-namespace:DataTemplates" >
    
        <!--Resources section-->
        <Window.Resources>
    
            <!--Styles-->
            <Style TargetType="Label">
                <Setter Property="FontSize" Value="24" />
                <Setter Property="Margin" Value="10,0,0,0" />
            </Style>
    
            <Style x:Key="stretched" TargetType="ListBoxItem">
                <Setter Property="HorizontalContentAlignment" Value="Stretch" />
            </Style>
    
        </Window.Resources>
    
        <!--Command binding definition-->
        <Window.CommandBindings>
            <CommandBinding Command="Refresh" x:Name="cmdLoadWeatherForecast" CanExecute="cmdLoadWeatherForecast_CanExecute" Executed="cmdLoadWeatherForecast_Executed" />
        </Window.CommandBindings>
    
        <!--UI design - layout of individual controls-->
        <Grid x:Name="LayoutRoot">
            <Grid.RowDefinitions>
                <RowDefinition Height="*" />
                <RowDefinition Height="Auto" />
            </Grid.RowDefinitions>
    
            <ListBox x:Name="weatherList" Grid.Row="0" ItemContainerStyle="{StaticResource stretched}" ItemsSource="{Binding WeatherInfo}" />
    
            <StackPanel Grid.Row="1" Orientation="Horizontal" HorizontalAlignment="Center" Margin="10" >
                <TextBox Text="Brighton UK" Name="txtLocation" Width="200" FontSize="20" Margin="10" FocusManager.FocusedElement="{Binding txtLocation}" />
                <Button IsDefault="True" Name="btnLoadForecast" Content="Load Weather Forecast"  Command="Refresh" Margin="0,10,10,10" Padding="10"/>
            </StackPanel>
    
        </Grid>
    </Window>
    
    4 回复  |  直到 14 年前
        1
  •  3
  •   Falcon    14 年前

    除非列表框在另一个DataContext中,否则代码应该可以工作。

    尝试

    <ListBox x:Name="weatherList" 
        Grid.Row="0" 
        ItemContainerStyle="{StaticResource stretched}" 
        ItemsSource="{Binding DataContext.WeatherInfo, RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type yournamespace:MainWindow}}}" />
    

    找出答案。

        2
  •  2
  •   Peter Perháč    14 年前

    谢谢你们的宝贵建议。我不知道输出窗口中显示的绑定错误,从那里我只有一个谷歌可以找到解决方案。

    我遇到的问题是,我试图绑定到的weatherinfo项源是一个公共字段,而不是一个属性。因此, 我可以简单地将weatherinfo public observablecollection分配给列表框的itemssource,但是我不能依靠数据绑定机制在数据上下文中定位weatherinfo属性,因为weatherinfo在技术上不是一个属性。 . 将get;private set;添加到我的mainvm中的weatherinfo声明使数据绑定按预期工作,我不再需要在代码中将weatherinfo对象分配为列表框的itemssource。

        3
  •  1
  •   Kevin Nelson    14 年前

    [编辑:感觉愚蠢]

    好的,抱歉,我看到你在启动中…在…之前快速回答…主窗口是列表框所在的对象,对吗?

    不过,我会检查以确保与列表框(直接父项等)更近的任何内容都没有自己的数据上下文。

        4
  •  1
  •   myermian    14 年前
    1. 加载表单时,请检查 输出窗口查看是否存在 任何绑定错误消息。

    2. 一个很好的快速方法来确保你 DataContext正确的方法是引发 列表框旁边的按钮, 将事件链接到窗口的 代码隐藏并放置断点。 当你到达所说的断点时 到你的窗口偷看 通过将其强制转换到数据上下文中 到视图模型: (MainVM)DataContext

    3. 天气信息是静态的还是非静态的?

    4. 你能发布你的mainvm对象代码吗?