2015-01-25 5 views
1

У меня есть неинтерактивный интерфейс, который отображает информацию. Информация хранится в элементе управления Listbox с помощью специального элемента управления listboxitem.Предотвратить отображение списка с дисплея частично Listboxitem

Размер каждого списка может варьироваться, окно может быть изменено в соответствии с требованиями пользователя.

Я хочу, чтобы не отображались элементы списка, которые частично отображаются в приложении, это всегда будет последняя строка. Однако, если я изменил размер пользовательского интерфейса, изменится «последняя строка».

Я экспериментировал с this SO answer без везения.

protected override Size ArrangeOverride(Size finalSize) 
     { 
     // Arrange in a stack 
      double curX = 0; 
      double curY = 0; 
      foreach (UIElement child in InternalChildren) 
      { 
       double nextY = curY + child.DesiredSize.Height; 
       if (nextY > finalSize.Height)   // Don't display partial items 
        child.Arrange(new Rect()); 
       else 
        child.Arrange(new Rect(curX, curY, child.DesiredSize.Width, child.DesiredSize.Height)); 
       curY = nextY; 
      } 

      return finalSize; 

     } 

«InternalChildren» Я предполагаю, что это мой список, но Listbox не перечислим. Я не уверен, как использовать этот пример.

Как достичь желаемого результата?

Главное управление

<UserControl x:Class="Cis.CustomControls.CisDeparturesPanel" 
      xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
      xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
      xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
      xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
      xmlns:customControls="clr-namespace:Cis.CustomControls" 
      mc:Ignorable="d" d:DesignHeight="600" d:DesignWidth="800"> 
    <UserControl.Resources> 
     <DataTemplate x:Key="DataTemplate"> 

      <ListBoxItem Padding="0" > 
       <customControls:CisDeparturesRow /> 
      </ListBoxItem> 

     </DataTemplate> 
    </UserControl.Resources> 

    <Grid> 
     <Grid.RowDefinitions> 
      <RowDefinition Height="48"/> 
      <RowDefinition Height="44"/> 
      <RowDefinition Height="229*"/> 
      <RowDefinition Height="279*" /> 
     </Grid.RowDefinitions> 


     <ListBox Grid.Row="2" HorizontalContentAlignment="Stretch" Name="ListBoxDepart" Background="Black" Margin="1,0,-1,0" BorderThickness="0" ItemsSource="{Binding Path=StationMovementList}" ItemTemplate="{StaticResource DataTemplate}" ScrollViewer.VerticalScrollBarVisibility="Hidden" ScrollViewer.HorizontalScrollBarVisibility="Hidden" Grid.RowSpan="2"> 
      <ListBox.ItemContainerStyle> 
       <Style TargetType="{x:Type ListBoxItem}"> 
        <Setter Property="Focusable" Value="False"/> 
       </Style> 
      </ListBox.ItemContainerStyle> 

     </ListBox> 


    </Grid> 
</UserControl> 

ListBoxItem таможенного контроля

<UserControl x:Class="Cis.CustomControls.CisDeparturesRow" 
      xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
      xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
      xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
      xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
      mc:Ignorable="d" d:DesignHeight="80" d:DesignWidth="800" Background="{Binding RelativeSource={RelativeSource FindAncestor,AncestorType={x:Type UserControl}}, Path=Background}" HorizontalContentAlignment="Stretch" Margin="0,0,0,0" Width="{Binding RelativeSource={RelativeSource FindAncestor,AncestorType={x:Type UserControl}}, Path=ActualWidth}"> 
    <UserControl.Resources> 
<!-- snip ---> 
</UserControl.Resources> 
    <Grid x:Name="ArrivalRowGrid"> 
     <Grid.RowDefinitions> 
      <RowDefinition Height="47*"/> 
      <RowDefinition Height="33*"/> 
     </Grid.RowDefinitions> 
     <Grid.ColumnDefinitions> 
      <ColumnDefinition/> 
      <ColumnDefinition Width="141"/> 
      <ColumnDefinition Width="117"/> 
      <ColumnDefinition Width="241"/> 
     </Grid.ColumnDefinitions> 

     <TextBlock Name="TxtDestinationName" MouseDown="TxtDestinationName_OnMouseDown" Style="{StaticResource MainRowStyle}" TextWrapping="Wrap" Text="{Binding Path=DestinationName,NotifyOnTargetUpdated=True, Mode=OneWay}" Margin="10,0"/> 
     <TextBlock Name="TxtPlatNum" TextWrapping="Wrap" Style="{StaticResource MainRowStyle}" Text="{Binding Path=Platform,NotifyOnTargetUpdated=True, Mode=OneWay}" Margin="11,0,8,0" 
        Grid.Row="0" Grid.Column="1"/> 

     <TextBlock Name="TxtArrTime" TextWrapping="Wrap" Style="{StaticResource MainRowStyle}" TextAlignment="Right" Text="{Binding Path=ExpectedDepartureTime,NotifyOnTargetUpdated=True, Mode=OneWay}" Margin="10,0,21,8" 
        Grid.Row="0" Grid.Column="3" /> 

     <TextBlock Grid.Row="1" Grid.Column="0" Grid.ColumnSpan="4" x:Name="TxtCallingAt" TextWrapping="Wrap" Style="{StaticResource SubRowStyle}" TextAlignment="Left" Text="{Binding Path=CallingAt,NotifyOnTargetUpdated=True, Mode=OneWay}" Margin="10,0,21,0" /> 

    </Grid> 
</UserControl> 

ответ

0

Так вопрос, который вы ссылаетесь на содержит ArrangeOverride метод, который предназначен для использования на пользовательских Panel, а не ListBox сам. Шаблон

WPF ListBox элемента управления после того, как он был расширен, выглядит вроде как это (упрощенный конечно):

<Border> 
    <ScrollViewer> 
     <SomePanel> 
      <ListBoxItem>your item</ListBoxItem> 
      <ListBoxItem>your item</ListBoxItem> 
      <ListBoxItem>your item</ListBoxItem> 
      <ListBoxItem>etc</ListBoxItem> 
     </SomePanel> 
    </ScrollViewer> 
</Border> 

где SomePanel является экземпляром класса, производного от Panel. Значение по умолчанию для списка является VirtualizingStackPanel, но который может быть заменен следующим образом:

<ListBox> 
    <ListBox.ItemsPanel> 
     <ItemsPanelTemplate> 
      your panel type here 
     </ItemsPanelTemplate> 
    </ListBox.ItemsPanel> 
</ListBox> 

Вы сказали, что в вашем вопросе это было для «не-интерактивного пользовательского интерфейса». Это имеет несколько разных интерпретаций, но предполагает, что вы можете заменить ListBox на ItemsControl, потому что вам не нужны возможности выбора в списке. Затем создайте настраиваемую панель (класс, который происходит от Panel), добавьте метод ArrangeOverride из связанного вопроса SO и замените панель ItemControl на свой собственный.

+0

Спасибо, я создал свою панель с MessureOverride и ArrangeOverride и добавил ее в свой шаблон данных, однако я все еще вижу последний частичный элемент. (добавлено окружение ) Можете ли вы посоветовать, почему показывается частичный элемент? – Damo

+0

Не уверен. Может быть потому, что шаблон управления «ListBox» по умолчанию включает в себя «ScrollViewer», который будет в основном давать бесконечную высоту дочерней панели, поэтому, поскольку метод 'ArrangeOverride' имеет всегда достаточную высоту для отображения всех элементов , Вам нужно прокрутить список? Если нет, есть другой подход, который вы могли бы предпринять. –

+0

Я переосмыслил подход, и я улавливаю событие Onloaded элемента ItemsControl и повторяя каждую строку и вычисляя размер каждой строки и скрывая строки, которые больше, чем родительский контейнер. Кажется, работает. Ваше объяснение помогло мне найти правильный путь. Спасибо. – Damo

Смежные вопросы