1

I have a TreeView control in my application that is populated (in the XAML) by binding its ItemsSource to an ObservableCollection of strings in my view model. There are many more nodes that can be viewed within the TreeView, so it displays a scroll bar to allow vertical scrolling. However, when I programmatically request the IsVisible property of individual TreeViewItems in my code-behind, all of them return True, regardless of whether they are actually visible or not.

XAML:

<Grid Margin="10">
    <Grid.DataContext>
        <local:NodeViewModel/>
    </Grid.DataContext>
    <TreeView Name="filterTree" ItemsSource="{Binding Path=NodeList, Mode=OneWay }" />
</Grid>

ViewModel:

class NodeViewModel
{
    public ObservableCollection<string> NodeList { get; private set; }

    public NodeViewModel()
    {
        NodeList = new ObservableCollection<string>();
        for ( int i = 0; i < 25; i++ ) {
            NodeList.Add($"{i}");
        }
    }
}

Code-behind:

    private void Window_ContentRendered(object sender, System.EventArgs e)
    {
        foreach ( string node in filterTree.Items ) {
            TreeViewItem item = filterTree.ItemContainerGenerator.ContainerFromItem(node) as TreeViewItem;
            System.Diagnostics.Debug.WriteLine($"Node {node} is {(item.IsVisible ? "visible" : "hidden")}");
        }
    }

Although the window is only large enough to display the first 10 nodes, all 25 nodes in the collection print out as "visible" in the diagnostic output.

Any ideas?

0

1 Answer 1

1

In terms of Visibility, there are 2 properties in any UIElement (ex. TreeViewItem), They are:

  1. Visibility Visibility {set; get;}, which can be set to either Visible, Collapse or Hidden.
  2. bool IsVisible {get;}, which is read only and can not be set.. this will return true if Visibility is Visible, false if Visibility is Hidden or Collapse..

In the setter of Visibility property, OnVisibilityChanged method will be triggered [see source code], and there, a private property VisibilityCache will be set.. Then, when IsVisible is called, it will return true/false based on VisibilityCache value [see source code].

Therefore, IsVisible represents the mode Visibility, that means, "Will this UIElement be visible when rendered or not?", And not, "Is this UIElement seen by the user right now or not?"

P.S. To check whether the UIElement is seen by the user or not, check this thread.

1
  • Muhammad, many thanks for that explanation. It runs completely counter to the official Microsoft documentation but your proposed solution (on the referenced thread) absolutely works. You're a star :)
    – Nick
    Commented Sep 20, 2022 at 9:25

Not the answer you're looking for? Browse other questions tagged or ask your own question.