Michał Turecki
Michał Turecki

Reputation: 3167

When binding Width to ViewportWidth in the ListBox with images the horizontal scrollbar is visible

What I'm trying to achieve is to create a vertical list of photos with frames on the rightmost side of a WPF window. The images are data bound to ObservableCollection and the images list should be able to be resized by a user using GridSplitter.

Current code is as follows:

    <ListBox Grid.Row="0" Grid.Column="2" Grid.RowSpan="3" ItemsSource="{Binding Sheet.Images}">
        <ListBox.ItemTemplate>
            <DataTemplate>
                <Border Background="#CCC" BorderThickness="8" Width="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type ScrollViewer}}, Path=ViewportWidth}">
                    <Image Source="{Binding Contents}"/>
                </Border>
            </DataTemplate>
        </ListBox.ItemTemplate>
    </ListBox>

    <GridSplitter Grid.Row="0" Grid.Column="1" Grid.RowSpan="3" Width="2" Background="Transparent"/>

There is one problem with it - regardless of the number of images, horizontal scrollbar is always visible and the part of right border is hidden unless uncovered by scrolling. When I bind to ActualWidth, the problem is visible even more as the scrollbar width is not substracted from a parent container width.

How to create such a vertical list of images with vertical scrollbar visible when needed and horizontal scrollbar never visible, while seeing the whole border?

And a small other issue: how to add a distance between borders of 2 consecutive images ?

Upvotes: 2

Views: 1271

Answers (1)

Michał Turecki
Michał Turecki

Reputation: 3167

I have found a solution to this problem although not very elegant. It seems ViewportWidth for some reason is exactly 2 pixels narrower than reported (or Border with Image are 2 pixels wider). Anyway, I used MathConverter which can be found here.

The end result is:

    <ListBox Grid.Row="0" Grid.Column="2" Grid.RowSpan="3" ItemsSource="{Binding Sheet.Images}">
            <ListBox.ItemTemplate>
                <DataTemplate>
                    <Border Background="#CCC" BorderThickness="8" Width="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type ScrollViewer}},
                        Path=ViewportWidth,
                        Converter={converters:MathConverter},
                        ConverterParameter=@VALUE-2}">
                        <Image Source="{Binding Contents}"/>
                    </Border>
                </DataTemplate>
            </ListBox.ItemTemplate>
    </ListBox>

    <GridSplitter Grid.Row="0" Grid.Column="1" Grid.RowSpan="3" Width="2" Background="Transparent"/>

If somebody has a better solution or at least reason why these 2 pixels are causing a problem in the first place, feel free to share.

Upvotes: 1

Related Questions