WPF alignment of textbox and button within a Grid? - c#

this is a rather simple question and its technically not that big of a deal but my OCD is tingling when i see this.
I have designed a basic WPF application and i cannot figure out why exactly the button and the textboxs are not alligning correctly as can be seen in this image(bottom right side):
This is the code responsible for it:
<Grid Margin="283,365.288,18,10" Grid.ColumnSpan="2">
<Label Content="GUID" HorizontalAlignment="Left" Margin="0,0.998,0,0" VerticalAlignment="Top" Height="22.96"/>
<Label Content="UniqueID" HorizontalAlignment="Left" Margin="0,22.68,0,0" VerticalAlignment="Top" Height="25.516" Width="63.297"/>
<Label Content="Akt/GZ" HorizontalAlignment="Left" Margin="0,48.196,0,0" VerticalAlignment="Top" Height="25.516" Width="63.297"/>
<TextBox HorizontalAlignment="Left" Height="23.958" Margin="63.297,0,0,49.754" TextWrapping="Wrap" Text="TextBox" VerticalAlignment="Bottom" Width="125"/>
<TextBox HorizontalAlignment="Left" Height="23.958" Margin="63.297,0,0,25.796" TextWrapping="Wrap" Text="TextBox" VerticalAlignment="Bottom" Width="125"/>
<TextBox HorizontalAlignment="Left" Height="23.958" Margin="63.297,0,0,1.558" TextWrapping="Wrap" Text="TextBox" VerticalAlignment="Bottom" Width="125"/>
<Button Content="Search" HorizontalAlignment="Left" Margin="193.297,0.998,0,0" VerticalAlignment="Top" Width="60.703" Height="22.96"/>
<Button Content="Search" HorizontalAlignment="Left" Margin="193.297,25.236,0,0" VerticalAlignment="Top" Width="60.703" Height="22.96"/>
<Button Content="Search" HorizontalAlignment="Left" Margin="193.297,49.194,0,0" VerticalAlignment="Top" Width="60.703" Height="22.96"/>
<CheckBox Content="07" HorizontalAlignment="Left" Margin="259,5.498,0,0" VerticalAlignment="Top"/>
<CheckBox Content="10" HorizontalAlignment="Left" Margin="296.915,5.498,0,0" VerticalAlignment="Top"/>
<CheckBox Content="07" HorizontalAlignment="Left" Margin="259,29.736,0,0" VerticalAlignment="Top"/>
<CheckBox Content="10" HorizontalAlignment="Left" Margin="296.915,29.736,0,0" VerticalAlignment="Top"/>
<CheckBox Content="07" HorizontalAlignment="Left" Margin="259,53.694,0,0" VerticalAlignment="Top"/>
<CheckBox Content="10" HorizontalAlignment="Left" Margin="296.915,53.694,0,0" VerticalAlignment="Top"/>
</Grid>
Either way I am not quite sure what causes it to... drift away for a bit. Also (in case someone asks) I am not sure why i used a Grid to group these objects, I googled on object groupings in WPF and i found some answers but the Grid and the Stackpanel seemed like the easiest to use, but the Stackpanel gave me even bigger headaches when aligning the content properly.
If you have some criticism regarding the imlpementation please feel free to do so, I have already ordered some books regardnig WPF design but I am more than happy and willing to listen to experienced devs and learn.
I apologize for the "noobish" question but I have spent the last 2 days fiddling around with the settings to no avail and wouldn't have come here and asked otherwise.
Thank you

You are using the Grid layout in the wrong way.
Using Margin in Grid is not recommended, for many reasons (Performance, Stretching problems and so on)
The Grid layout allows you to set Rows and Columns and order your controls in a table.
You can read more about it here
http://www.wpftutorial.net/GridLayout.html
You first have to declare your rows and cols using ColumnDefinitions and RowDefinitions and then apply each control to it's row and column using the attribute Grid.Row and Grid.Column
reading the link I've attached will explain things better

Related

How to Fill SolidColorBrush/Ellipse [duplicate]

I am trying to create this in WPF (I realize I could just use an image, but I am trying to learn WPF):
(source)
This is what I have so far but it isn't producing the desired result, in that, the textbox seems completely hide the ellipse whereas it should simply have a transparent background:
<StackPanel>
<TextBlock HorizontalAlignment="Left" Margin="144,207,0,0" TextWrapping="Wrap" Text="TextBlock" VerticalAlignment="Top"/>
<Ellipse HorizontalAlignment="Left" Height="52" Margin="142,189,0,0" Stroke="Black" VerticalAlignment="Top" Width="52"/>
</StackPanel>
You can put things like this in a viewbox to make scaling easier, something like this. You'll need to remove the stack panel, it's going to stack items one on top of the other which isn't what you're after here. I used a grid in this case.
<Viewbox Width="100" Height="100">
<Grid Width="20" Height="20">
<Ellipse Stroke="Black"/>
<TextBlock HorizontalAlignment="Center" Text="i" TextAlignment="Center" VerticalAlignment="Center"/>
</Grid>
</Viewbox>
Or you can use the unicode character: ⓘ
code 0x24D8
<TextBlock Text="ⓘ" FontSize="52" />
So a stackpanel will place the first item at the top, the second just below it, third below the second, and so forth. What you could do is use a Canvas or a Grid. Like the stackpanel, they are "Content Controls" and support placing multiple objects inside of them like you have done with the stackpanel.
So a really quick way to do what you're trying to accomplish would be:
<Grid >
<Ellipse HorizontalAlignment="Left" Height="52" Stroke="Black" VerticalAlignment="Top" Width="52"/>
<TextBlock Text="i" FontSize="52" Margin="18,-13,-6,13" />
</Grid>
You can do it using a border and a TextBlock. A square border will become a circle if you make its CornerRadius equals half its Width (or Height):
<Border Width="100" Height="100" CornerRadius="50" BorderBrush="Black" BorderThickness="2">
<TextBlock HorizontalAlignment="Center" VerticalAlignment="Center"
FontSize="50" Foreground="Blue" >i</TextBlock>
</Border>
Don't use a StackPanel for this, the purpose of it is to stack things, not show them overlapped, you're using the wrong tool for that. Use a Grid, it's far more suited for what you're trying to do.
To have a transparent background, you have to either set the TextBlock's Background property to Transparent, or set a null background.
Background={x:Null}

How to Animate Visibility.Collapsed + Update StackPanel

I think my title is a bit confusing so let me explain my question in detail.
I have a StackPanel with multiple Grids inside it. It basicly looks like a table with a "Header Grid" and a "Content Grid" below. The StackPanel itself is inside a ScrollViewer.
Whenever the user clicks on the "Header Grid" the corresponding "Content Grid" should be collapsed and visible vice versa.
Here is a short version of my table:
<ScrollViewer Margin="0,0,0,10">
<StackPanel>
<Grid x:Name="Header_Grid1" Height="24" Background="#BF101820" VerticalAlignment="Top" Margin="34,0,0,0" Cursor="Hand" >
<Label Content="Click me to show/hide Content_Grid1" Padding="5,0" VerticalContentAlignment="Center" Margin="5,0,0,0" Grid.ColumnSpan="2" Width="982"/>
</Grid>
<Grid x:Name="Content_Grid1" Height="100" Width="967" HorizontalAlignment="Right" Margin="0,5,0,0" RenderTransformOrigin="0.5,0.5">
<Label Content="some content" Foreground="#FF918F82" Padding="5,0" VerticalContentAlignment="Center" Margin="0,0,719,75"/>
<Label Content="some content" Foreground="#FF918F82" Padding="5,0" VerticalContentAlignment="Center" Margin="0,25,719,50"/>
</Grid>
<Grid x:Name="Header_Grid2" Height="24" Background="#BF101820" Width="1001" HorizontalAlignment="Right" VerticalAlignment="Top" Margin="0,10,0,0">
<Label Content="Click me to show/hide Content_Grid2" Padding="5,0" VerticalContentAlignment="Center" Margin="5,0,0,0" Grid.ColumnSpan="2" Width="982"/>
</Grid>
<Grid x:Name="Content_Grid2" Height="100" Width="967" HorizontalAlignment="Right" Margin="0,5,0,0" RenderTransformOrigin="0.5,0.5">
<Label Content="some content" Foreground="#FF918F82" Padding="5,0" VerticalContentAlignment="Center" Margin="0,0,719,75"/>
<Label Content="some content" Foreground="#FF918F82" Padding="5,0" VerticalContentAlignment="Center" Margin="0,25,719,50"/>
</Grid>
</StackPanel>
</ScrollViewer >
Lets say the user clicks on "Header_Grid1" the "Content_Grid1" hides with an kinda "flow to the top" animation by reducing its size. Thats no problem at all - the thing is I´d like the "Header_Grid2" aswell as the "Content_Grid2" to flow to the top while the animation of hiding "Content_Grid1" is playing. "Header_Grid2" and "Content_Grid2" should not just pop to the place where "Content_Grid1" has been. It should rather happen in a smooth animation.
Hopefully someone understands what I mean. It´s pretty hard to explain...
Thanks
As far as I am aware you can't animate the collapsed method, but there are various tricks to get around that such as animating the opacity, size, location etc...

How to create own GUI component in WPF?

i am trying to do some people administration application and i would like to use own component. I have a listBox with actions and i would like to show people who are in list in selected action. There is no problem for me to show just their names in another list, but i would like to have a pane where would be a card (my component) for every person asociated with that action. That card should look like
<WrapPanel HorizontalAlignment="Left" Height="296" Margin="668,59,0,0" VerticalAlignment="Top" Width="230">
<Image x:Name="image" Height="124" Width="226"/>
<TextBlock x:Name="textBlock_Copy5" TextWrapping="Wrap" Text="Name: " FontSize="18"/>
<TextBox x:Name="textBox_Copy2" Height="25" TextWrapping="Wrap" Width="151"/>
<TextBlock x:Name="textBlock_Copy6" TextWrapping="Wrap" Text="Surname: " FontSize="18"/>
<TextBox x:Name="textBox_Copy3" Height="25" TextWrapping="Wrap" Width="145"/>
<TextBlock x:Name="textBlock_Copy7" TextWrapping="Wrap" Text="Birthday: " FontSize="18"/>
<DatePicker Width="136" DisplayDate="2016-06-27" DisplayDateStart="1950-01-01" FirstDayOfWeek="Monday" SelectedDate="{Binding Selected.DatumOdjezdu}"/>
</WrapPanel>
So there are two problems for me.
How to create own component.
How to create a pane(it can be scrollable), where would be as many those cards as needed.
Thanks for any hint.
WPF offers more than one way to achieve your goal.
It depends on your Application, what fits your needs the most.
You can reach this by
DataTemplates
UserControl
CustomControl
Here some more Info about the Differences of UserControl and CustomControl
Depending on your posted Code, i'd suggest a DataTemplate in your case.

Placing more than one element into a GroupBox in WPF

I'm trying to make a GroupBox with a few (radio)buttons in it. But in the samples i'm using checkbox.
<GroupBox Header="Aðgerðir" HorizontalAlignment="Left" VerticalAlignment="Bottom" Margin="270,0,0,178" Height="106" Width="176">
<CheckBox Content="CheckBox" HorizontalAlignment="Left" VerticalAlignment="Top"/>
<CheckBox Content="CheckBox" HorizontalAlignment="Left" VerticalAlignment="Bottom"/>
</GroupBox>
The above does not work and visual studio says "Invalid Markup".
This here works fine though
<GroupBox Header="Aðgerðir" HorizontalAlignment="Left" VerticalAlignment="Bottom" Margin="270,0,0,178" Height="106" Width="176">
<CheckBox Content="CheckBox" HorizontalAlignment="Left" VerticalAlignment="Top"/>
</GroupBox>
I don't get it. It says "Content can only be set once" if i run the debugger, but erasing the Content part of the checkbox seems to have no effect.
The content of the GroupBox can only be set once, meaning that it can only have a single control inside it. If you want to two radio button, place them in a stack panel or a grid.
GroupBox Overview
<GroupBox Header="Aðgerðir" HorizontalAlignment="Left" VerticalAlignment="Bottom" Margin="270,0,0,178" Height="106" Width="176">
<StackPanel>
<CheckBox Content="CheckBox" HorizontalAlignment="Left" VerticalAlignment="Top"/>
<CheckBox Content="CheckBox" HorizontalAlignment="Left" VerticalAlignment="Bottom"/>
</StackPanel>
</GroupBox>

How to get the value of the checked radiobutton in wpf

I have four RadioButtons in a grid panel, but when I do this:
<GroupBox x:Name="radioButtons">
<RadioButton Content="1" Height="16" HorizontalAlignment="Left" Margin="10,45,0,0" Name="status1" VerticalAlignment="Top" />
<RadioButton Content="2" Height="16" HorizontalAlignment="Left" Margin="10,67,0,0" Name="status2" VerticalAlignment="Top" />
<RadioButton Content="3" Height="16" HorizontalAlignment="Left" Margin="10,89,0,0" Name="status3" VerticalAlignment="Top" />
<RadioButton Content="4" Height="16" HorizontalAlignment="Left" Margin="10,111,0,0" Name="status4" VerticalAlignment="Top" />
</GroupBox>
It says that:
Error 1 The object 'GroupBox' already has a child and cannot add 'RadioButton'. 'GroupBox' can accept only one child.
And the last three RadioButtons say:
The property 'Content' is set more than once.
What's wrong with my GroupBox? Furthermore, in my code I want to access the RadioButton that is checked (preferably as an int). How do I do this? I tried to look in Google and I found a lot of results, but I couldn't understand any of them.
GroupBox can only hold 1 item, hence the error about trying to set the Content property of the GroupBox multiple times.
So, make that a Layout item and then put the RadioButtons inside it. Now, you set the Content once, which is the StackPanel, and that Layout item can hold many children -> RadioButtons.
<GroupBox x:Name="radioButtons">
<StackPanel>
<RadioButton Name="status1"
Height="16"
Margin="10,45,0,0"
HorizontalAlignment="Left"
VerticalAlignment="Top"
Content="1" />
<RadioButton Name="status2"
Height="16"
Margin="10,67,0,0"
HorizontalAlignment="Left"
VerticalAlignment="Top"
Content="2" />
<RadioButton Name="status3"
Height="16"
Margin="10,89,0,0"
HorizontalAlignment="Left"
VerticalAlignment="Top"
Content="3" />
<RadioButton Name="status4"
Height="16"
Margin="10,111,0,0"
HorizontalAlignment="Left"
VerticalAlignment="Top"
Content="4" />
</StackPanel>
</GroupBox>
As for your second question, Christian Mosers WPF Tutorial.net has a decent sample. If you don't understand it, you maybe should look at the topics Binding and Converter, first.
A very crude way to be notified of RadioButton checked in a non MVVM way:
private void RadioButtonChecked(object sender, RoutedEventArgs e) {
var radioButton = sender as RadioButton;
if (radioButton == null)
return;
int intIndex = Convert.ToInt32(radioButton.Content.ToString());
MessageBox.Show(intIndex.ToString(CultureInfo.InvariantCulture));
}
Then, in each of your RadioButtons in xaml, add Checked="RadioButtonChecked".
If you want many elements or controls then you have to put them in layout containers.
Grid
StackPanel
DockPanel
WrapPanel
Etc.....

Categories