How to make Responsive Grid using Avalonia framework - c#

I want to make responsive desktop application which can run on different screen size as well as different platform.
I have used Grid.Extra.Avalonia library but it is only working for border.
I want to make grid Which have 2X2 column and row within that column and row we can place other control which would be responsive based on scree size.
Below is my code.
<Window
xmlns="https://github.com/avaloniaui"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:ge="clr-namespace:GridExtra.Avalonia;assembly=GridExtra.Avalonia"
x:Class="ResponsiveGridSample.MainWindow"
Title="ResponsiveGrid Example" Height="350" Width="525">
<Grid>
<Grid.Styles>
<Style Selector="Grid">
<Setter Property="ge:ResponsiveGrid.XS" Value="12" />
<Setter Property="ge:ResponsiveGrid.SM" Value="6" />
<Setter Property="ge:ResponsiveGrid.MD" Value="2" />
</Style>
</Grid.Styles>
<ge:ResponsiveGrid>
<Grid ShowGridLines="True">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="250"/>
<ColumnDefinition Width="250"/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="40"/>
<RowDefinition Height="40"/>
</Grid.RowDefinitions>
<!--<Label Grid.Column="0" Grid.Row="0">Vehilce Class</Label>-->
<ComboBox Grid.Column="1" Grid.Row="0" Width="250">
<ComboBoxItem>Car</ComboBoxItem>
<ComboBoxItem>Jeep</ComboBoxItem>
<ComboBoxItem>Van</ComboBoxItem>
</ComboBox>
</Grid>
</ge:ResponsiveGrid>
</Grid>
</Window>```
Where can we add class selector for grid to make responsive.

Related

WPF - Why are buttons resizing after busy indicator goes away?

When the busy indicator is visible the buttons resize to a wider width and when the indicator goes away it resizes back down to expected width. I thought using span attribute would fix this but it didn't.
<Window x:Class="TelerikWpfApp3.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:telerik="http://schemas.telerik.com/2008/xaml/presentation"
Title="MainWindow" Height="350" Width="525" >
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="auto" />
<ColumnDefinition Width="auto" />
<ColumnDefinition Width="auto" />
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="auto" />
<RowDefinition Height="auto" />
<RowDefinition Height="auto" />
</Grid.RowDefinitions>
<telerik:RadBusyIndicator x:Name="LogonBusyIndicator" IsBusy="True" Grid.ColumnSpan="3" Grid.RowSpan="3">
<StackPanel>
<Button x:Name="button1" Content="Button 1" Grid.Column="0" Grid.Row="0" Margin="20" Padding="10" />
<Button x:Name="button2" Content="Button 2" Grid.Column="1" Grid.Row="0" Margin="20" Padding="10" Click="button2_Click"/>
</StackPanel>
</telerik:RadBusyIndicator>
</Grid>
</Window>
Set the Content of the RadBusyIndicator to the Grid with the buttons:
<telerik:RadBusyIndicator x:Name="LogonBusyIndicator" IsBusy="True" HorizontalAlignment="Left" VerticalAlignment="Top">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="auto" />
<ColumnDefinition Width="auto" />
<ColumnDefinition Width="auto" />
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="auto" />
<RowDefinition Height="auto" />
<RowDefinition Height="auto" />
</Grid.RowDefinitions>
<Button x:Name="button1" Content="Button 1" Grid.Row="0" Margin="20" Padding="10" />
<Button x:Name="button2" Content="Button 2" Grid.Row="1" Margin="20" Padding="10" Click="button2_Click"/>
</Grid>
</telerik:RadBusyIndicator>
What action causes the busy indicator to disappear? Are you programmatically setting IsBusy to False in code-behind once login is ready? If you don't want Button1 and Button2 to be clicked before the busy indicator closes, you can always do a trigger like this.
<StackPanel>
<Button x:Name="button1" Content="Button 1" Grid.Column="0" Grid.Row="0" Margin="20" Padding="10" />
<Button x:Name="button2" Content="Button 2" Grid.Column="1" Grid.Row="0" Margin="20" Padding="10" Click="button2_Click"/>
<StackPanel.Style>
<Style TargetType="StackPanel">
<Setter Property="IsHitTestVisible" Value="False"/>
<Style.Triggers>
<DataTrigger Binding="{Binding IsBusy, ElementName=LogonBusyIndicator}" Value="False">
<Setter Property="IsHitTestVisible" Value="True" />
</DataTrigger>
</Style.Triggers>
</Style>
</StackPanel.Style>
</StackPanel>
<telerik:RadBusyIndicator x:Name="LogonBusyIndicator" IsBusy="True"/>
Here's what's happening with the code above.
First and foremost, by removing the buttons entirely from the telerik RadBusyIndicator xaml definition, the buttons size will remain their original size and not get resized whenever the busy indicator turns off or on. I think by placing these buttons inside of the RadBusyIndicator, you have put a reliance on how that telerik control sizes itself. Now there should be no dependency.
The busy indicator will ALWAYS be placed above the buttons in the visual tree z-order, because I defined it last.
To prevent the user from clicking the buttons until the busy indicator is ready, I have set the IsHitTestVisible to false by default. This means that anything in the StackPanel cannot be clicked.
But then I set up a trigger to say, when the busy indicator's "IsBusy" property gets set to False (programmatically?), then set the StackPanel's IsHitTestVisible property to True so that the user can now click these buttons.

Styling for Grid inside Another Grid

I have a GridView(B) inside a GridView(A).
The style for GridView-A is different from style for GridView-B, but the issue arises when my GridView-B inherits all the style from GridView-A.
I don't want that to happen.
Is their any way, I can achieve this in xaml only ?
Just Follow the follwoing steps and let me know if you have any problem with this. Out of these you meight be aware already. May be you miss something.
1) Add ResourceDictionary as style sheet.
<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:XYZApplication">
<!-- Style 1-->
<Style x:Key="GridStyle1" TargetType="{x:Type Grid}">
<Setter Property="Background" Value="BlanchedAlmond"></Setter>
<Setter Property="Margin" Value="1,1,1,1"></Setter>
</Style>
<!-- Style 2-->
<Style x:Key="GridStyle2" TargetType="{x:Type Grid}">
<Setter Property="Background" Value="Aqua"></Setter>
<Setter Property="Margin" Value="5,5,5,5"></Setter>
</Style>
</ResourceDictionary>
2) Add resource file into your user control/window as follows...
<UserControl x:Class="XYZApplication.Views.Payment"
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:XYZApplication.Views"
mc:Ignorable="d">
<UserControl.Resources>
<ResourceDictionary>
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary Source="../Style/Styles.xaml"/>
</ResourceDictionary.MergedDictionaries>
</ResourceDictionary>
</UserControl.Resources>
</UserControl>
3) Use those specific styles to designated grid inside the usercontrol/window
<Grid Style="{StaticResource GridStyle1}">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto"></ColumnDefinition>
<ColumnDefinition Width="Auto"></ColumnDefinition>
<ColumnDefinition Width="Auto"></ColumnDefinition>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"></RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
</Grid.RowDefinitions>
<Grid Grid.Column="1" Grid.Row="1" Style="{StaticResource GridStyle2}" >
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto"></ColumnDefinition>
<ColumnDefinition Width="Auto"></ColumnDefinition>
<ColumnDefinition Width="Auto"></ColumnDefinition>
<ColumnDefinition Width="Auto"></ColumnDefinition>
<ColumnDefinition Width="Auto"></ColumnDefinition>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"></RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
</Grid.RowDefinitions>
<Label Grid.Column="0" Grid.Row="0">Bank Name</Label>
<Label Grid.Column="1" Grid.Row="0">Branch</Label>
<Label Grid.Column="2" Grid.Row="0">Account holder</Label>
<Label Grid.Column="3" Grid.Row="0">Account Number</Label>
<Label Grid.Column="4" Grid.Row="0">Balance</Label>
<Label Grid.Column="0" Grid.Row="1">Bank of ...</Label>
<Label Grid.Column="1" Grid.Row="1">...Branch</Label>
<Label Grid.Column="2" Grid.Row="1">My Name</Label>
<Label Grid.Column="3" Grid.Row="1">Account Number 123</Label>
<Label Grid.Column="4" Grid.Row="1">1 billion</Label>
</Grid>
</Grid>
You can add these both styles in code behind also.
Hope it helps!!!
You should explicitly define your style for both the gridviews. In WPF the child control inherits the properties of parent control, may be you have this issue. You might have defined style for gridviewA and not for gridviewB or you are using the same style for all gridviews. If you can share the code, i can tell you exactly what is the problem.

Buttons get clipped when I resize the window in WPF

I have a UserControl with MinWidth and MinHeight set.
There a grid and many controls inside.
I have another Grid inside the main grid. The inner grid's code is as below.
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="*"/>
<RowDefinition Height="30"/>
</Grid.RowDefinitions>
<DataGrid Grid.Row="0" helpers:RowHeaderNumber.DisplayRowNumber="True" AutoGenerateColumns="False"
RowHeaderWidth="40" CanUserSortColumns="False" CanUserResizeColumns="False"
Margin="10,65,20,0" ItemsSource="{Binding ExpressionCollection, Mode=TwoWay}"
SelectionUnit="CellOrRowHeader" SelectionChanged="ExpressionGrid_SelectionChanged" PreviewMouseRightButtonUp="ExpressionGrid_PreviewMouseRightButtonUp" BorderBrush="{x:Null}" VerticalAlignment="Top" >
<DataGrid.RowHeaderStyle>
<Style TargetType="DataGridRowHeader">
<Setter Property="ContextMenu" Value="{StaticResource ExpressionContextMenu}"/>
<Setter Property="Padding" Value="4,0,0,20"/>
<Setter Property="Background" Value="#FFF1F0F0"/>
<Setter Property="BorderBrush" Value="Black"/>
<Setter Property="BorderThickness" Value="1,0,1,1"/>
</Style>
</DataGrid.RowHeaderStyle>
</DataGrid>
<Button Grid.Row="1" Content="OK" HorizontalAlignment="Right" VerticalAlignment="Bottom" Width="75" Click="Ok_Button_Click" Margin="0,0,112,10"/>
<Button Grid.Row="1" Content="Cancel" HorizontalAlignment="Right" VerticalAlignment="Bottom" Width="75" Click="Cancel_Button_Click" Margin="0,0,20,10"/>
</Grid>
The buttons in the bottom get clipped when I resize the window. What changes should I make to make the DataGrid resize when the window is resized?
<Grid>
<Grid.RowDefinitions>
<RowDefinition/>
<RowDefinition Height="30"/>
</Grid.RowDefinitions>
<DataGrid Grid.Row="0"/>
<Button Grid.Row="1" HorizontalAlignment="Left" Content="Button 1"/>
<Button Grid.Row="1" Content="Button 2" HorizontalAlignment="Left" Margin="55,0,0,0"/>
</Grid>
The above code doesnt clip the Buttons.
Remember not to set Width and Height
PS: It will Clip when the Window Width is less than 50 and in such similar cases :) thats obvious :)
Remove the Margin & width from the button. the problem should be. if the width goes less then 75+120 + 75 + 20 it will start clipping the button. I would suggest not to use the width & margin instead use extra row & column in your grid & set it accordingly. also do give min & max height or min & max width to your user control to control it overall.
See the following example
<Window x:Class="Test1.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="MainWindow" Height="100" Width="200" MinHeight="100" MinWidth="100">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition/>
<ColumnDefinition/>
</Grid.ColumnDefinitions>
<Button Width="50" Margin="20"></Button>
<Button Width="50" Margin="20" Grid.Column="1"></Button>
</Grid>
</Window>
in This example buttons will always clip when you resize & decrease the size of your window.
But if you use it like this it will never clip
<Window x:Class="Test1.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="MainWindow" Height="100" Width="200" MinHeight="100" MinWidth="100">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition/>
<ColumnDefinition/>
</Grid.ColumnDefinitions>
<Button></Button>
<Button Grid.Column="1"></Button>
</Grid>

How can I easily set the default alignment for the contents of a Grid layout?

Currently, some sample code might right like this:
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="*" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<Button Content="Click me" Name="MainButton" Click="MainButton_Click" Grid.Column="0" Grid.Row="0" HorizontalAlignment="Center" VerticalAlignment="Center" />
<TextBlock Name="CounterBlock" Text="Count: 0" Grid.Row="1" Grid.Column="0" HorizontalAlignment="Center" VerticalAlignment="Center" />
</Grid>
I'm looking for a way to set default cell alignments for contents, so I don't have to specify a HorizontalAlignment and VerticalAlignment for each cell:
<Grid DefaultHorizontalAlignment="Center" DefaultVerticalAlignment="Center">
...
</Grid>
or even:
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="*" DefaultHorizontalAlignment="Center" />
<RowDefinition Height="*" DefaultHorizontalAlignment="Center" />
</Grid.RowDefinitions>
</Grid>
Am I missing something, or is this not such a straightforward process? Thanks!
There is nothing like ContentAlignment property at Grid level. You can set styles for child elements.
you can add this to the Grid.
<Grid.Resources>
<Style x:Key="alignmentStyle" TargetType="{x:Type FrameworkElement}">
<Setter Property="HorizontalAlignment" Value="Center"/>
<Setter Property="VerticalAlignment" Value="Center"/>
</Style>
<Style TargetType="Button" BasedOn="{StaticResource alignmentStyle}"/>
<Style TargetType="TextBlock" BasedOn="{StaticResource alignmentStyle}"/>
</Grid.Resources>
As you see above, we have to explicitly set Style for each type, as setting for a base type like FrameworkElement alone doesn't work.
This may not be very helpful if you have only few elements. or you have many elements and almost each is of different type.

Strange behavior of control position in wpf

It's a strange behaviour about the WPF Control positioning. I had a below controls and aligned well during design time. However runtime gave the misaligned positioning in the corner of button
<Window x:Class="StackOverflow.LookAndWork"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="Tables" Height="388" Width="314" ResizeMode="NoResize" >
<Grid>
<TextBox Margin="12,12,12,41"></TextBox>
<Button Content="OK" Height="23" Margin="205,314,12,12" Name="button3" Width="75" IsCancel="True" IsEnabled="False" />
</Grid>
</Window>
DesignTime Snap
Runtime Snap
Suppose If i removed the ResizeMode="NoResize" from the Window. I can able to see the correct positioning at runtime. What is the problem with ResizeMode="NoResize" ?
Anyhelp would be greatly appreciated !!!
Instead of adding the margin in control level, why don't you add the minimum margin in grid level?
Example:
<Grid Margin="12,12,12,12">
This way you will get a 12 pixel margin border.
On the button, don't do hardcoded left margin. Instead, you can use HorizontalAlignment="Right" to do the job.
On a side note, I less prefer to add controls in grid without specifying the Grid.RowDefinitions, Grid.ColumnDefinitions, Grid.Row and Grid.Column. It is a poweful tool for Grid.
For better looking, don't use Margin or Size. Use Grid definition to split your application.
With the following xaml, your application will always have a good looking :
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="*" />
<RowDefinition Height="23" />
</Grid.RowDefinitions>
<TextBox />
<Grid Grid.Row="1">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="75" />
</Grid.ColumnDefinitions>
<Button Grid.Column="1" Content="OK" Name="button3" IsCancel="True" IsEnabled="False" />
</Grid>
</Grid>
Width and Height can be define in a Dictionary. In this case, in RowDefinition and ColumnDefinition properties, use Auto instead of values.
Edit :
Use a Dictionnary like
<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
<Style TargetType="{x:Type Button}">
<Setter Property="Width" Value="75"/>
<Setter Property="Height" Value="23"/>
</Style>
</ResourceDictionary>
then
<Window.Resources>
<ResourceDictionary>
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary Source="Dictionary1.xaml" />
</ResourceDictionary.MergedDictionaries>
</ResourceDictionary>
</Window.Resources>
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="*" />
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<TextBox />
<Grid Grid.Row="1">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<Button Grid.Column="1" Content="OK" Name="button3" IsCancel="True" IsEnabled="False" />
</Grid>
</Grid>
I can't see the same issue in VisualStudio 2012 designer: http://screencast.com/t/TGVgUyfR
Both design-time and runtime are look the same. So there should be a bug in a prior version of the designer.
Nevertheless I'd suggest you to move your button into separate grid row or use another layout controls to organise your views.
To extend Xaruth's answer, I'd not fix the height for the button row, but instead have it use the default height. The same goes for the width, which I'd have the button define.
Also note that I give the button a margin. The added bonus of not fixing the grid column/row sizes it that now the row height also takes the margin into account:
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="*" />
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<TextBox />
<Grid Grid.Row="1">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<Button Grid.Column="1" Content="OK" Name="button3" IsCancel="True" IsEnabled="False" Width="75" Margin="0,8,0,0" />
</Grid>
</Grid>

Categories

Resources