There is DockPanel with three child controls placed side by side in a horizontal manner:
1) TreeView
2) RichTextBox
3) Grid
RichTextBox lies in middle of TreeView and Grid. I made RichTextBox the last child of DockPanel and set LastChildFill attribute to True. Now since Grid can be closed at run time, I want the RichTextBox to occupy all the space that became empty after the Grid is closed. But if the Grid is again shown the RichTextBox should contract from Right hand side to allow the Grid to fit in. How to achieve this? I'm new to WPF. Also, how to hide the Grid? Here is the XAML.
<DockPanel Grid.Row="2" HorizontalAlignment="Stretch" VerticalAlignment="Stretch" LastChildFill="True">
<Border BorderThickness="1" DockPanel.Dock="Left" Height="Auto" HorizontalAlignment="Stretch" Margin="1" VerticalAlignment="Stretch" Width="Auto" CornerRadius="0" BorderBrush="#FF646464">
<TreeView Name="TV" Height="Auto" Width="Auto" HorizontalAlignment="Stretch" VerticalAlignment="Stretch"/>
</Border>
<Border Name="Notification_Pane" BorderThickness="1" DockPanel.Dock="Right" Height="Auto" HorizontalAlignment="Stretch" Margin="1" VerticalAlignment="Stretch" Width="Auto" CornerRadius="0" BorderBrush="#FF646464">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<Label Content="Notification" Margin="0" HorizontalAlignment="Stretch" VerticalAlignment="Top" Background="LemonChiffon" Grid.Row="0" Grid.Column="0"/>
<Button Name="btn_Close" Content="X" Margin="0" HorizontalAlignment="Stretch" VerticalAlignment="Stretch" Background="LemonChiffon" Height="Auto" Width="Auto" Grid.Row="0" Grid.Column="1" Padding="10,0,10,0" BorderThickness="0" Cursor="Hand" Focusable="True" IsHitTestVisible="True" ClickMode="Release" Click="Button_Click" />
<ScrollViewer Height="Auto" Name="ScrollViewer" Width="Auto" Margin="0" Grid.Row="1" Grid.Column="0" Grid.ColumnSpan="2">
<StackPanel CanVerticallyScroll="True" Height="Auto" Name="Notification_Panel" Width="Auto" HorizontalAlignment="Stretch" VerticalAlignment="Stretch">
</StackPanel>
</ScrollViewer>
</Grid>
</Border>
<Border BorderThickness="1" Height="Auto" HorizontalAlignment="Stretch" Margin="1" VerticalAlignment="Stretch" Width="Auto" CornerRadius="0" BorderBrush="#FF646464">
<RichTextBox Name="rtb" Height="Auto" Width="Auto" Grid.Row="2" HorizontalAlignment="Stretch" Grid.Column="1" Margin="0" />
</Border>
</DockPanel>
You can use Grid.Visibility property to show and hide the grid.
The following code should do the job:
private void Button_Click(object sender, RoutedEventArgs e) //X Button click event.
{
//grid is the name of our Grid Control we want to hide.
grid.Visibility = System.Windows.Visibility.Collapsed;
}
to show the grid again you should use the following code:
grid.Visibility = System.Windows.Visibility.Visible;
The RichTextBox control will always fit in the DockPanel Control.
Related
I have a UserControl, empty StackPanel like following.
<Grid>
<StackPanel x:Name="datawrapper" Orientation="Horizontal" Background="Yellow"/>
</Grid>
Main window's XAML is like following.
<ScrollViewer Grid.Row="2" Grid.Column="0" Background="Gray">
<StackPanel x:Name="holderpanel" Orientation="Vertical"/>
</ScrollViewer>
I want to put datawrapper into holderpanel from the Main Window's code behind programmatically.
If there's control in the datawrapper, dadawrapper is inserted into holder panel.
However, in case of empty StackPanel, never inserted.
How to do this?
To help you clarify your question, I'll provide an example of exactly what you asked for:
<Grid>
<ScrollViewer Grid.Row="2" Grid.Column="0" Background="Gray">
<StackPanel x:Name="holderpanel" Orientation="Vertical"/>
</ScrollViewer>
<Grid>
<StackPanel x:Name="datawrapper" Orientation="Horizontal" Background="Yellow">
<TextBlock Text="Test"/>
</StackPanel>
</Grid>
</Grid>
codebehind (for this example, I added to Loaded event handler, but it could be used elsewhere):
private void MainWindow_Loaded(object sender, RoutedEventArgs e)
{
if (datawrapper.Children.Count > 0)
{
var grid = datawrapper.Parent as Grid;
grid.Children.Remove(datawrapper);
holderpanel.Children.Add(datawrapper);
}
}
The datawrapper should be separated user control and empty like following.
<Grid>
<StackPanel x:Name="datawrapper" Orientation="Horizontal" Background="Yellow"/>
</Grid>
I will add another user controls into the datawrapper horizontally 5 later. That user control is like following.
<UserControl x:Class="WpfTest.ResultItem"
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:local="clr-namespace:WpfTest"
mc:Ignorable="d"
d:DesignHeight="450" d:DesignWidth="800">
<Grid x:Name="resultitem">
<Border CornerRadius="5" BorderBrush="#e0e0e0" Background="White" BorderThickness="2" DockPanel.Dock="Top" Margin="10 10 10 15">
<Grid Margin="0 30 0 30" Background="White">
<Grid.RowDefinitions>
<RowDefinition Height="*"/>
<RowDefinition Height="*"/>
<RowDefinition Height="*"/>
<RowDefinition Height="*"/>
<RowDefinition Height="*"/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto"/>
<ColumnDefinition Width="Auto"/>
</Grid.ColumnDefinitions>
<TextBlock Grid.Row="0" Grid.Column="0" Text="Chart#" Width="Auto" Height="30" Margin="5 5 0 5" FontSize="20" VerticalAlignment="Center"></TextBlock>
<TextBlock Grid.Row="1" Grid.Column="0" Text="Patient Name" Width="Auto" Height="Auto" Margin="5 5 0 5" FontSize="20" VerticalAlignment="Center"></TextBlock>
<TextBlock Grid.Row="2" Grid.Column="0" Text="Home Phone#" Width="Auto" Height="Auto" Margin="5 5 0 5" FontSize="20" VerticalAlignment="Center"></TextBlock>
<TextBlock Grid.Row="3" Grid.Column="0" Text="Cell Phone#" Width="Auto" Height="Auto" Margin="5 5 0 5" FontSize="20" VerticalAlignment="Center"></TextBlock>
<TextBlock Grid.Row="4" Grid.Column="0" Text="Patient Type" Width="Auto" Height="Auto" Margin="5 5 0 5" FontSize="20" VerticalAlignment="Center"></TextBlock>
</Grid>
</Border>
</Grid>
If the datawrapper is filled with 5 ResultItems, datawrapper will added into the holderpanel vertically.
I would like to fill my Dock panel with 9 textblocks. I would like the text blocks to fill the entire dock panel. I have set the height to auto and the vertical/horizontal alignment to stretch.
The textblocks, however, don't fill the entire dock panel. Any ideas on what can be going wrong. Thanks
My dockpanel lives in a grid.
<Border DockPanel.Dock="Top" Background="White" BorderBrush="DodgerBlue" BorderThickness="5,5,5,5" CornerRadius="10" Margin="2" Height="700">
<DockPanel >
<TextBlock DockPanel.Dock="Top" Name="txtID" VerticalAlignment="Stretch" HorizontalAlignment="Stretch" Height="Auto">1</TextBlock>
<TextBlock DockPanel.Dock="Top" Name="txtOAG" VerticalAlignment="Stretch" HorizontalAlignment="Stretch" Height="Auto">2</TextBlock>
<TextBlock DockPanel.Dock="Top" Name="txtFAILURE_ID" VerticalAlignment="Stretch" HorizontalAlignment="Stretch" Height="Auto">3</TextBlock>
<TextBlock DockPanel.Dock="Top" Name="txtWIDTH" VerticalAlignment="Stretch" HorizontalAlignment="Stretch" Height="Auto">4</TextBlock>
<TextBlock DockPanel.Dock="Top" Name="txtHeight" VerticalAlignment="Stretch" HorizontalAlignment="Stretch" Height="Auto">5</TextBlock>
<TextBlock DockPanel.Dock="Top" Name="txtBARCODE_READ" VerticalAlignment="Stretch" HorizontalAlignment="Stretch" Height="Auto">6</TextBlock>
<TextBlock DockPanel.Dock="Top" Name="txtBARCODE_NUM" VerticalAlignment="Stretch" HorizontalAlignment="Stretch" Height="Auto">7</TextBlock>
<TextBlock DockPanel.Dock="Top" Name="txtANOMOLY" VerticalAlignment="Stretch" HorizontalAlignment="Stretch" Height="Auto">8</TextBlock>
<TextBlock DockPanel.Dock="Top" Name="txtTRACECODE" VerticalAlignment="Stretch" HorizontalAlignment="Stretch" Height="Auto">9</TextBlock>
</DockPanel>
</Border>
DockPanel "docks" to sides, StackPanel "stacks" together. You should use a Grid.
Like this (example for 3 rows):
<Grid>
<Grid.RowDefinitions>
<RowDefinition />
<RowDefinition />
<RowDefinition />
</Grid.RowDefinitions>
<TextBlock Text="1" />
<TextBlock Grid.Row="1" Text="2" />
<TextBlock Grid.Row="2" Text="3" />
</Grid>
This is my XAML design
<Grid x:Name="ContentPanel2" Grid.Row="1" Background="Black" Height="440" Width="440">
<Grid.RowDefinitions>
<RowDefinition Height="*" />
<RowDefinition Height="*" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="*" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<Border BorderThickness="0" Grid.Row="0" Grid.Column="0" Background="White" />
<Border BorderThickness="0" Grid.Row="0" Grid.Column="1" Background="White" />
<Border BorderThickness="0" Grid.Row="0" Grid.Column="2" Background="White" />
<Border BorderThickness="0" Grid.Row="1" Grid.Column="0" Background="White" />
<Border BorderThickness="0" Grid.Row="1" Grid.Column="1" Background="White" />
<Border BorderThickness="0" Grid.Row="1" Grid.Column="2" Background="White" />
<Border BorderThickness="0" Grid.Row="2" Grid.Column="0" Background="White" />
<Border BorderThickness="0" Grid.Row="2" Grid.Column="1" Background="White" />
<Border BorderThickness="0" Grid.Row="2" Grid.Column="2" Background="White" />
</Grid>
Here are the images
wvga image
wxga image
720pimage
This appears differently in each resolutions (wvga,wxga & 720p).
Anybody knows why this behaviour happens?
How to resolve this issue?
This is a known issue (thought it had another StackOverflow question but I couldn't find it) with how the fractional pixels work out - you can see the background of the Grid showing through "gaps" between your items.
You can fix it by making the Background of the Grid White.
I have a expander which contains a grid in which I have a grid splitter.
The Document Outline and UI is like this
and here is the code.
<Grid x:Name="TopGrid" ShowGridLines="True" >
<Grid.RowDefinitions>
<RowDefinition Height="Auto" MaxHeight="150"/>
<RowDefinition Height="200" />
</Grid.RowDefinitions>
<Expander x:Name="CompanyDescriptionExpander" Grid.ColumnSpan="2"
VerticalAlignment="Top" IsExpanded="True" Background="Black" >
<Expander.Header>
<Grid Width="{Binding ElementName=CompanyDescriptionExpander,
Path=ActualWidth}" Background="Aquamarine">
<TextBlock Grid.Column="0" Text="Expander Header" Foreground="Black" />
</Grid>
</Expander.Header>
<Expander.Content>
<Grid x:Name="DescriptionGrid" MaxHeight="130" ShowGridLines="True">
<Grid.RowDefinitions>
<RowDefinition Height="*" MinHeight="25" MaxHeight="25"/>
<RowDefinition Height="Auto" MinHeight="25" MaxHeight="120"/>
<RowDefinition Height="4" MinHeight="10" MaxHeight="10"/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<TextBox Grid.Column="0" Background="Orange" Grid.Row="0" Grid.RowSpan="2"
MinHeight="40" MaxHeight="120" x:Name="DescriptionText"
Text="TextBlock Content" HorizontalAlignment="Stretch"
VerticalAlignment="Stretch" HorizontalContentAlignment="Stretch"
VerticalContentAlignment="Top"
HorizontalScrollBarVisibility="Hidden"
VerticalScrollBarVisibility="Auto" />
<Button x:Name="SaveIconButton" Grid.Column="1" Grid.Row="0" Width="20"
Height="20" VerticalAlignment="Top" />
<Button x:Name="CancelIconButton" Grid.Column="1" Grid.Row="1" Width="20"
Height="20" VerticalAlignment="Top" />
<GridSplitter ResizeBehavior="PreviousAndCurrent" ResizeDirection="Rows"
Grid.Row="2" Grid.ColumnSpan="2"
Height="10" MaxHeight="10" HorizontalAlignment="Stretch"
VerticalAlignment="Top" Background="Red" />
</Grid>
</Expander.Content>
</Expander>
<Button Grid.Row="1" Grid.Column="0" Margin="0,5,0,0" Height="20"
VerticalAlignment="Top" Background="Green" />
</Grid>
When we use grid splitter it expands
But it goes on even after textbox reaches its maximum height and gridsplitter goes behind button(green).
My problem scenario can be replicated copying my code in a project
I want that it should stop when textbox reaches its maximum height.
How to do that?
In your DescriptionGrid change the second rows MaxHeight from 120 to 95.
The combined max height of the three rows in that grid exceeds the max height of the grid itself.
I am trying to access a Grid inside the DataTemplate while the ItemsControl is binded by ItemsSource.
this is the full XMAL code, How do i find a certain element from outside?
for (int i = 0; i < allViewControl.Items.Count; i++)
{
var container = allViewControl.ItemContainerGenerator.ContainerFromItem(allViewControl.Items[i]) as FrameworkElement;
var grid = allViewControl.ItemTemplate.FindName("grid", container) as DataGrid;
}
i found this always returning null ?
<ScrollViewer Grid.Row="0" HorizontalScrollBarVisibility="Disabled" VerticalScrollBarVisibility="Auto">
<ItemsControl x:Name="allViewControl" Focusable="False" HorizontalContentAlignment="Center"
Grid.IsSharedSizeScope="true" ItemsSource="{Binding AllClassCharacters}"
ItemTemplate="{StaticResource CharacterViewModelTemplate}" >
<ItemsControl.ItemsPanel>
<ItemsPanelTemplate>
<Extensions:AnimatedWrapPanel IsItemsHost="true" />
</ItemsPanelTemplate>
</ItemsControl.ItemsPanel>
</ItemsControl>
</ScrollViewer>
<DataTemplate x:Key="CharacterViewModelTemplate" DataType="{x:Type ViewModel:CharacterViewModel}">
<Grid x:Name="grid" Width="200" Height="Auto" MinHeight="115" Margin="1" MinWidth="130" HorizontalAlignment="Stretch" VerticalAlignment="Stretch" RenderTransformOrigin="0.5,0.5" Background="#66000000" >
<Grid.RowDefinitions>
<RowDefinition Height="70"/>
<RowDefinition Height="*"/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<ProgressBar x:Name="playerProgressBar" VerticalAlignment="Top" Background="Transparent" Height="5" Width="Auto" Value="0" Visibility="Collapsed" Grid.Column="0" Grid.Row="0" Grid.ColumnSpan ="2" Grid.RowSpan="2" Foreground="White" BorderThickness="0" Style="{DynamicResource ProgressBarStyle1}" />
</Grid>
Short answer is that you shouldn't need to do this - using MVVM should give you simpler solutions to whatever you're trying to achieve.
If you need it for some niche cases like setting the focus, search for 'find control wpf' on so - there are some existing questions (example) to hack and get controls out of the WPF UI Tree