How to add a floating action button to WPF Desktop tool? - c#

I'm coding a database tool to use as Windows Desktop Applikation. Im using C#, WPF and SQLite. How can I add a floating action button in front of the ListView?

As for positioning a button over another element there are various options, it depends on your use case what fits best. In this example, I nest a DockPanel inside a Grid that has two rows. The ListView in there spans both rows, while the DockPanel is in the second row.
<Grid>
<Grid.RowDefinitions>
<RowDefinition/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<ListView Grid.Row="0" Grid.RowSpan="2" ItemsSource="{Binding StringItems}"/>
<DockPanel Grid.Row="1" LastChildFill="False">
<Button DockPanel.Dock="Right" Width="50" Height="50" Content="-" Margin="5"/>
<Button DockPanel.Dock="Right" Width="50" Height="50" Content="+" Margin="5"/>
</DockPanel>
</Grid>
If you look for a more Android looking button, you can use the Material Design WPF library that offers different button styles for that purpose. See the documentation on floating action button styles, e.g.:
<Button DockPanel.Dock="Right" Content="-" Margin="5" Style="{StaticResource MaterialDesignFloatingActionButton}"/>
This is how the result for both variants looks like.

Related

UWP: Control won't fit to the available view area of my Grid cell

I am working on a Phone Dialer UWP application for Windows Mobile devices. In searching for dialer examples, I came across the PhoneCall sample that is bundled with Windows Universal Samples at https://github.com/Microsoft/Windows-universal-samples. The PhoneCall sample contains an example implementation of Dialer and a DialerPanel, complete with a text box to display or edit the number being typed, as well as the Call button. So far so good.
However, the sample dialer panel is hosted as a PivotItem in a tabbed interface implemented by MainPage.xaml, and it occupies the entire space available to it.
What I am looking for is something like a DialerPanel in the sample, but one that could shrink to fit in my Grid cell. I will have the available space split into two Grid cells, with the upper half occupying a custom control or an image, while the lower half will host the Dial Pad.
In my attempt to accomplish what I need, I modified the sample DialerPanel.xaml as follows:
I created a new outer Grid with two rows, each taking up 50% of the available space.
In the upper row, I added a rectangle with a fill of "Light Yellow"
In the lower row, I added the original Dialer Panel layout contained in a Grid (basically, I moved the ORIGINAL Grid into a Grid cell at Row 1, Column 0.
Below is the image of my XAML outline (with certain blocks collapsed for clarity):
Here's the XAML:
<UserControl
x:Class="PhoneCall.Controls.DialerPanel"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:PhoneCall.Controls"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="1*"/>
<RowDefinition Height="1*"/>
</Grid.RowDefinitions>
<Rectangle Fill="LightYellow" Grid.Row="0"/>
<Grid Grid.Row="1">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<StackPanel Grid.Row="0">
<local:LinePicker Margin="0,20,0,0"/>
<Grid Style="{StaticResource DigitViewGridStyle}">
<Grid.ColumnDefinitions>
<ColumnDefinition />
<ColumnDefinition Width="Auto"/>
</Grid.ColumnDefinitions>
<ScrollViewer x:Name="dialerNumberControlScrollviewer"
Grid.Column="0"
Style="{StaticResource DigitViewScrollerStyle}">
<TextBlock Style="{StaticResource DigitViewTextStyle}"
SizeChanged="OnDialerNumberControlSizeChanged"
Text="{Binding DialerPhoneNumber.NumberToDial, Mode=OneWay}">
</TextBlock>
</ScrollViewer>
<Button Grid.Column="1"
Command="{Binding ProcessBackspace}"
IsEnabled="{Binding DialerPhoneNumber.DialPadEnabled, Mode=OneWay}"
Holding="OnBackspaceHolding">
<FontIcon FontFamily="Segoe MDL2 Assets" Glyph="" FontSize="30"/>
</Button>
</Grid>
</StackPanel>
<StackPanel Grid.RowSpan="2" VerticalAlignment="Bottom">
<StackPanel Style="{StaticResource DialpadPanelStyle}">
<local:Dialpad x:Name="Dialpad"/>
<Button IsEnabled="{Binding DialerPhoneNumber.DialPadEnabled, Mode=OneWay}"
Style="{StaticResource AccentLongButtonStyle}"
Command="{Binding ProcessDialDialerNumberHeap}" >
<Button.ContentTemplate>
<DataTemplate>
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<FontIcon FontFamily="Segoe MDL2 Assets" Glyph="" RenderTransformOrigin="0.5,0.5">
<FontIcon.RenderTransform>
<CompositeTransform ScaleX=".75" ScaleY=".75"/>
</FontIcon.RenderTransform>
</FontIcon>
<TextBlock Text="Call"
Grid.Row="1"
Style="{StaticResource CaptionTextBlockStyle}"
Margin="0,4,0,0"
LineHeight="14"
HorizontalAlignment="Center" />
</Grid>
</DataTemplate>
</Button.ContentTemplate>
</Button>
</StackPanel>
</StackPanel>
</Grid>
</Grid>
</UserControl>
When I build the app with the changes above and run the sample, this is how it appears on the phone with my rectangle covering the Dial Pad:
I tried a couple of things including reduced fixed width and height for the Dialer Panel, but I could not make it work.
A couple of questions:
1. What am I doing wrong here and how can I fix it?
2. Is there a third party DialPad control (free or paid) that I can reference in my project and just use it?
Thanks for all your help!
I think the problem is in this line:
<StackPanel Grid.RowSpan="2" VerticalAlignment="Bottom">
This stack panel starts in row 0 where you the put
<StackPanel Grid.Row="0">
Can you try this?
<StackPanel Grid.Row="2" VerticalAlignment="Bottom">

WPF - How to draw lines between custom controls programmatically

so I'm trying to make a program that allows users to design simple programs using modules with different functions in WPF.
I've created custom controls for my modules that look like this:
<Border Height="75" Width="150" BorderThickness="1" BorderBrush="Black">
<Grid Background="Gray" Height="75" Width ="150">
<Grid.RowDefinitions>
<RowDefinition Height="1*"/>
<RowDefinition Height="2*"/>
</Grid.RowDefinitions>
<Label Content="Double" FontSize="12" Grid.Row="0" HorizontalContentAlignment="Center" Background="Aquamarine"/>
<Grid Grid.Row="1">
<Grid.ColumnDefinitions>
<ColumnDefinition/>
<ColumnDefinition Width="3*"/>
<ColumnDefinition/>
</Grid.ColumnDefinitions>
<Button Name="IncomingConnection" Height="15" Width="15" Background="Black" Margin="5" VerticalAlignment="Top" HorizontalAlignment="Left"/>
<Button Name="OutgoingConnection" Grid.Column="2" Height="15" Width="15" VerticalAlignment="Top" Background="Black" Margin="5" HorizontalAlignment="Right"/>
<Button Name="OutgoingData" Grid.Column="2" Height="15" Width="15" VerticalAlignment="Bottom" Background="Aquamarine" Margin="5" HorizontalAlignment="Right"/>
</Grid>
</Grid>
</Border>
Anyways, I want to be able to click on one of these buttons (incomingConnection or outgoingConnection), and have a line connect the two buttons.
Other information: The custom controls are all being placed inside thumbs so they can be dragged around. Everything is on a canvas. I don't want to create a line between the controls, but instead between the buttons on the controls.
Thanks a ton!
I would have a class for the lines that contains the x and y coordinates for both endpoints. I would put an instance for each line in to a list on the view model. Then use an ItemsControl bound to that property with a Canvas as the template. You can then use a WPF Line control as the ItemTemplate for the ItemsControl. You can bind the Line control's X1, Y1, X2, and Y2 to the endpoint properties of the line class that was created at the beginning.
With that setup, all you have to do is add instances of your line class to the list and they will automatically show up on the Canvas.

UWP app is not scaling

I'm trying to make text editor for Windows (PC) in UWP but the scaling is not working, I've done the same in WPF and it worked.
The page size is set to 800x600, these are columns:
<Grid Background="White" >
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<TextBlock x:Name="filename" Margin="10" Grid.ColumnSpan="2">Untitled</TextBlock>
<Border Margin="5" Grid.Row="1">
<TextBox x:Name="text" AcceptsReturn="True"
ScrollViewer.VerticalScrollBarVisibility="Visible"
ScrollViewer.HorizontalScrollBarVisibility="Visible" TextChanged="text_TextChanged"/>
</Border>
<StackPanel Grid.Row="2" Margin="3,3" Orientation="Horizontal" MinHeight="31" >
<Button x:Name="saveButton" FontSize="15" Content="Save" Margin="0,0,0,-0.125" VerticalAlignment="Top" Click="saveButton_Click" />
<Button x:Name="button" Content="Save as..." Margin="5,0" HorizontalAlignment="Stretch" VerticalAlignment="Stretch" Click="button_Click" />
<Button x:Name="loadButton" FontSize="15" Content="Read" Margin="5,0" VerticalAlignment="Bottom" Click="loadButton_Click"/>
</StackPanel>
</Grid>
Title is in 1st row, content is in 2nd, buttons (save, load) are in 3rd, it looks like grid it wouldn't exist:
That's with normal size
After size change
How do I fix it?
The page size is set to 800x600
If you've set the page size to 800x600 like this: <Page Width="800" Height="600"... it will always be 800x600 and it will not scale. If you want it to scale properly, just don't set these properties.
I assume you wanted to set the size of the app when it starts for the first time. You can approach it by setting the ApplicationView.PreferredLaunchViewSize.
Also I recommend to use the RichEditBox to display and edit text files.

Custom message popup WPF

This doesn't actually describe what I mean, but I'll try to explain. I've been using C# for an year now and never touched WPF. Only recently I've realized how awesome it is and started using it. I'm now facing a problem.
I want to let the user know the password/username are incorrect, so instead of the old WinForms MessageBox I want to make it more pleasent. I thought about creating a grid that tints the application darker, and then I'll be able to show some text on it. However - how's that possible?... Do you have any nicer ideas to show a message for the application (not a popup)? Thanks.
You can create an UserControl with translucent background (like #33000000), and 3-row grid to show title, message and OK button, like bellow:
<UserControl x:Class="ApplicationNameSpace.MessageControl" ... >
<Grid Background="#33000000" HorizontalAlignment="Stretch" VerticalAlignment="Stretch">
<Grid HorizontalAlignment="Center" VerticalAlignment="Center" Background="#FFFFFF" MinHeight="100" MinWidth="200">
<Grid.RowDefinitions>
<RowDefinition Height="30"></RowDefinition>
<RowDefinition Height="*"></RowDefinition>
<RowDefinition Height="35"></RowDefinition>
</Grid.RowDefinitions>
<Grid Grid.Row="0" Background="#EEEEEE">
<Label Content="Unable to Login" HorizontalAlignment="Center" VerticalAlignment="Center" />
</Grid>
<Grid Grid.Row="1" Margin="10,20">
<TextBlock Text="Wrong username or password. Try again." HorizontalAlignment="Stretch" VerticalAlignment="Stretch" />
</Grid>
<Grid Grid.Row="2" Background="#EEEEEE">
<Button Content="OK" Width="80" Height="25" />
</Grid>
</Grid>
</Grid>
</UserControl>
To use, you can add the control at the end of your window, and change the visibility to Visible when needs to show it.
<Window x:Class="ApplicationNameSpace.MainWindow"
xmlns:local="clr-namespace:ApplicationNameSpace" ... >
<Grid>
...
<local:MessageControl Name="messageControl" Visibility="Collapsed" />
</Grid>
</Window>
You can also create a generic control that you pass to a show method the title and message content, like MessageBox show method. You can also add the user control element programmatically in the window in this method.
You can use the validation and the INotifyDataError which is on WPF 4.5 and you can show a nice message next to the textbox check this link for example

C# .Net WPF Custom User Control zIndex issue with similar user control

User control details:
Have created drop down list control (Like as combo box), clicking on down arrow button, it displays a list below the text box
I have set zIndex property of my User control
Issue:
Case 1: When there is another user control (other than my custom user control), and if drop down list is displayed, other user control hides behind my user control. This is perfectly Ok
Case 2: There are 2 Custom User controls, if list is displayed from first user control, second user control appears on the list. This is where i am facing issue
XAML of my control is as below
<UserControlx:Class="UserControls.AutoCompleteComboBox"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Panel.ZIndex="1110" LostFocus="UserControl_LostFocus" Height="Auto">
<Canvas Name="MainCanvas">
<Grid>
<Grid.RowDefinitions>
<RowDefinition></RowDefinition>
<RowDefinition></RowDefinition>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto" MinWidth="150"></ColumnDefinition>
<ColumnDefinition Width="20"></ColumnDefinition>
</Grid.ColumnDefinitions>
<TextBox Name="autoTextBox" Height="20" MinWidth="150" Width="Auto" MinHeight="20" Style="{DynamicResource AutoCompleteBox}" BorderThickness="2"
Margin="0,0,0,0" TextWrapping="NoWrap" Grid.Row="0" Grid.Column="0" HorizontalAlignment="Stretch" VerticalAlignment="Top"/>
<Button Content="6" FontFamily="Marlett" Grid.Row="0" Grid.Column="1" FontSize="15" Margin="0,0,0,0" Height="20" Width="20" HorizontalAlignment="Right" VerticalAlignment="Top" Background="{StaticResource BackgroudBlueBrush}" Click="Button_Click" Padding="0" Cursor="Hand"></Button>
<StackPanel Grid.Row="1" Grid.ColumnSpan="2" >
<ListBox Name="suggestionListBox" SelectionChanged="suggestionListBox_SelectionChanged" MouseDown="suggestionListBox_MouseDown"
Background="LightYellow" SnapsToDevicePixels="True"
Visibility="Collapsed"
MinWidth="150" IsHitTestVisible="True" MinHeight="70" Height="70"
VerticalAlignment="Top" LostFocus="suggestionListBox_LostFocus"/>
</StackPanel>
</Grid>
</Canvas>
</UserControl>
Your approach is not the right one to correctly manage the overlap of controls. Perhaps you may create some trick using the ZIndex property, but that won't be the solution.
If you need a drop-down control, the best way is to use a Popup control and play around it. Basically, it creates another borderless window, being child of the yours.
Another approach, maybe simpler but not good as the Popup, is using an Adorner. Maybe this one is the most similar techinique to the yours.
Cheers
Have you tried setting the ZIndex of the StackPanel to 1+ the control's zindex? That should raise the drop down portion above any other instance of your user control.
Canvas.ZIndex can be used on StackPanels.

Categories