How to fill the image 100% inside a button - c#

It should be simple but somehow I am getting problems to do it in a more generic way (without width and height properties).
I have a button and an image inside this button but when I insert an image I see the it is not 100% filled.
This is my code:
<Button Grid.Row="0" Grid.Column="1"
Style="{StaticResource BrowseButtonStyle}"
Click="ChangeLogo_Click">
<Image x:Name="imageControl" />
</Button>
How can I fill it?

If you go take a look at a copy of the default Button template you'll see the ContentPresenter has its Margin Template bound via a Setter with a "Padding" of 12,4 by default.
So easiest answer, just specify a zero padding.
<Button Grid.Row="0" Grid.Column="1"
Style="{StaticResource BrowseButtonStyle}"
Click="ChangeLogo_Click"
Padding="0">
<Image x:Name="imageControl" />
</Button>
Hope this helps.

Related

DockPanel is not visible even though it is set to visible

I have a DockPanel inside another DockPanel the first one is set to be docked on the whole form, but the second one is set on the top of the form and it has three buttons inside it, the background color of it is set to grey, and I can see the content blue border in the editor but it doesn't have a color or a text in it, and when I run the application there is nothing no button no colors nothing.
Here is the XAML code:
<Grid Background="White">
<DockPanel Name="MainBackground">
<DockPanel Name="Top" Height="32" Background="#FF707070" DockPanel.Dock="Top" Margin="0, 0, 0, 1000">
<Button
Width="46"
Height="32"
DockPanel.Dock="Right"
Margin="687,0,0,398"
Background="White" Click="Button_Click_1">
<StackPanel Orientation="Horizontal">
<Image Source="Res/RDI.png" Width="20" Height="20"/>
</StackPanel>
</Button>
<Button
Width="46"
Height="32"
Content="×"
FontSize="20" DockPanel.Dock="Right" Click="Button_Click" Margin="734,0,0,398" Background="White"/>
</DockPanel>
</DockPanel>
</Grid>
The issue is that you try to position all controls using Margin, which defeats the purpose of a DockPanel. You can select each of the buttons in XAML and look at the designer in Visual Studio. They are all positioned way off. Do not every use this kind of brittle positioning in WPF. There are lots of panels that already take care of that way easier and responsive to resizing.
For example, try the code below. I removed all the Margins and just set the DockPanel.Dock to Right for the buttons. Please note, that you have to set the LastChildFill to false, otherwise the last control placed in the DockPanel will take up the remaining space and is centered in there, regardless of setting a DockPanel.Dock value on it.
If you set the LastChildFill property to true, which is the default setting, the last child element of a DockPanel always fills the remaining space, regardless of any other dock value that you set on the last child element. To dock a child element in another direction, you must set the LastChildFill property to false and must also specify an explicit dock direction on the last child element.
For the outer DockPanel, I just added a new last Grid that takes up the remaining space. If it was not there, you would also have to set the LastChildFill, otherwise the bar would be centered in the window.
<Grid Background="White">
<DockPanel Name="MainBackground">
<DockPanel Name="Top" Height="32" Background="#FF707070" DockPanel.Dock="Top" LastChildFill="False">
<Button
Width="46"
Height="32"
DockPanel.Dock="Right"
Background="White" Click="Button_Click_1">
<StackPanel Orientation="Horizontal">
<Image Source="Res/RDI.png" Width="20" Height="20"/>
</StackPanel>
</Button>
<Button
Width="46"
Height="32"
Content="×"
FontSize="20" DockPanel.Dock="Right" Click="Button_Click" Background="White"/>
</DockPanel>
<StackPanel>
<TextBlock Text="This is where your content would be placed."/>
<TextBlock Text="Alternatively, set the last child fill of the dock panel to false."/>
</StackPanel>
</DockPanel>
</Grid>
Now the buttons are automatically positioned to the right, next to each other.
Of course, you could create the same layout with other panels as well, but since it is not clear what your final layout should look like, I can only provide this example using your structure.
It's here quite sure but with a margin of Margin="0, 0, 0, 1000" propably it's anywhere.
I think this is the issue.
[EDIT] And I see more of these "3 digit margins". Avoid that, it's not how WPF is meant to be used. Use margins as "a little bit of space around the element"

have stackpanel clickable and load viewport

first post here so if I do anything wrong please slap me.
I'm currently trying to learn UWP code and I want to try to create a bottom naivation bar. I'm trying to work with stackpanels to do so
The idea is that when a stackpanel is clicked / tapped it should load a new page into viewport, however I can't figure out the correct code to do so. Here's an short version of my stackpanel:
<StackPanel Orientation="Horizontal" VerticalAlignment="Bottom">
<StackPanel Name="FirstButton" Tapped="FirstButton_Tapped">
<TextBlock x:Name="Icon1" />
<TextBlock x:Name="Text1" />
</StackPanel>
<StackPanel Name="SecondButton" Tapped="SecondButton_Tapped">
<TextBlock x:Name="Icon2" />
<TextBlock x:Name="Text2" />
</StackPanel>
<StackPanel Name="ThirdButton" Tapped="ThirdButton_Tapped">
<TextBlock x:Name="Icon3" />
<TextBlock x:Name="Text3" />
</StackPanel>
I chose stackpanel because that was the best way for me to have a bottom and horizontal aligned bar with an icon on top and text displaying under it.
(if you got a better idea feel free to post it)
Now the question is how i should write my C# code so that the Tapped event will load a second page into the viewport.
(further, the style I'm aiming for is something similar to what deezer uses, example is here: http://imgur.com/WNNi96v
Thank you in advance!
As #Pedro G. Dias says far better to use Button control as it has many more benefits (Visual States) that you associate with user clicking/ Tapping a Button rather than using the Tap event of StackPanel
You can customise a Button easily by utilising the ContentTemplate
<StackPanel Orientation="Horizontal" VerticalAlignment="Bottom">
<Button x:Name="FirstButton" Click="FirstButton_Click">
<Button.ContentTemplate>
<DataTemplate>
<StackPanel>
<TextBlock x:Name="Icon1" />
<TextBlock x:Name="Text1" />
</StackPanel>
</DataTemplate>
</Button.ContentTemplate>
</Button>
<!--More buttons here-->
</StackPanel>
Simply create buttons and place them inside each stackpanel. The button.Content property of the Button control will let you put the two textblocks inside it.

Set button size to size of image

I have a couple of buttons that I am displaying on my application GUI using the following XAML in my WPF project:
<Button Style="{DynamicResource NoChromeButton}" Click="backBtn_Click" Margin="0,0,0,0" HorizontalAlignment="Left" >
<Image Source="C:\...\arrow_left.png" Height="30" Width="30" />
</Button>
<Button Style="{DynamicResource NoChromeButton}" Click="RefreshBtn_Click" Margin="0,0,0,0" HorizontalAlignment="Left" >
<Image Source="C:\...\arrow_loop3.png" Height="30" Width="30" />
</Button>
However, when I run my application, the buttons appear to be bigger than the size of the images I'm displaying on them- i.e. the images are 30x30, but the buttons are rectangular, rather than square, with their height being greater than their width.
I am drawing the buttons next to each other, in a row with a few other buttons to give a 'menu bar' look at the top of the application window. However, because the height of these buttons is displaying a greater value than what I've set, there is a bit of 'white space' being shown along the menu bar, above and below other buttons that are being displayed with the height value that I've set, for example:
<Button Style="{DynamicResource NoChromeButton}" Click="referThis" Margin="0,0,0,0" HorizontalAlignment="Left" HorizontalContentAlignment="Left" Height="30" Width="80">
<TextBlock>Send Reference</TextBlock>
</Button>
With this button, it would seem that because I am displaying text, and not an image on it, it has kept to the height & width values that I have set, but this means that it has some 'white space' above and below it, since the other buttons are causing the <StackPanel> where I've placed these buttons to take up more vertical space than I had intended.
How can I force the buttons on which I am displaying images to display at the size I have set them?
Edit
It seems that this was to do with what happens when I manually resize the window when the running the application- that the <StackPanel>/<TabPanel> are automatically resized when the window is resized... I have set the Height of the <StackPanel> to a specific value, and this now means that the buttons are all restricted to that size, so they all stay the same size, which is great.
But, when I resize the window, this causes the <TabPanel> that they are in to be resized, so I end up with white space above and below the buttons- is there a way that I can stop this?
Set the button's VerticalAlignment to the top.
Set the desired width/height on the button and not the image.
Do this via the Margin property. Also check out Alignment on MSDN.
Then set the image's stretch to Stretch.Fill.
Alternatively, something in you style might be throwing you off, because this
<Button VerticalAlignment="Top" HorizontalAlignment="Left" Margin="0">
<Image Width="30" Height="30" />
</Button>
Worked perfectly for me.
This code is exactly what you want:
<Button Width="100" Height="100" Padding="0" BorderThickness="0">
<Image Source="image.jpg" Stretch="Fill"/>
</Button>
Note Padding and BorderThickness values which fit the image to the button.
As RoyalPotato said you can change button Width and Height and the image size will be dynamically stretched.

'Live' Slider value into label

I've made an app that allowes me to control a Microsoft NXT 2.0 Mindstorms robot and I've recently added a slider that I want to use to set the current engine speed instead of having a fixed value, so I need help.
Here I have the XAML of the label and slider that I want to use:
<Slider x:Name="Speed" HorizontalAlignment="Left" Margin="40,58,0,0" VerticalAlignment="Top" Width="30" Orientation="Vertical" Height="187" Maximum="90" Minimum="-90" SmallChange="1" LargeChange="10" IsSnapToTickEnabled="True" TickFrequency="5" TickPlacement="BottomRight" AutoToolTipPlacement="BottomRight" MouseUp="Speed_MouseUp" BorderBrush="#00000000" Background="#00000000" Foreground="#FF858585">
<Label x:Name="Current_Speed" Content="Currently: " HorizontalAlignment="Right" Margin="0,0,478,257" Width="60" Height="29" VerticalAlignment="Bottom" Foreground="Black" />
I want Current_Speed to write Currently: {SliderValue} I want it to write the current value of the slider instantly as I move my slider up or down like you can do with the ToolTip option.
Any ideas?
(Bear in mind, I'm not very skilled, so detailed solutions would be much appreciated)
Thank you in advance :)
It's relatively easy. The "trick" is that you need to use two different Label objects, which you can aggregate together using a StackPanel container.
For the second Label object, just set the Label's Content attribute like this:
Content="{Binding ElementName=Speed, Path=Value}"
The whole thing will look something like this:
<Slider x:Name="Speed"
HorizontalAlignment="Left" VerticalAlignment="Top"
Margin="40,58,0,0"
Width="30" Height="187"
Orientation="Vertical"
Maximum="90" Minimum="-90"
SmallChange="1" LargeChange="10"
IsSnapToTickEnabled="True" TickFrequency="5" TickPlacement="BottomRight"
AutoToolTipPlacement="BottomRight"
MouseUp="Speed_MouseUp"
BorderBrush="#00000000" Background="#00000000" Foreground="#FF858585" />
<StackPanel Orientation="Horizontal" Margin="0,0,0,257" Height="29">
<Label x:Name="Current_Speed_Text"
Content="Currently: "
HorizontalAlignment="Right" VerticalAlignment="Bottom"
Foreground="Black" />
<Label x:Name="Current_Speed"
Content="{Binding ElementName=Speed, Path=Value}"
HorizontalAlignment="Right" VerticalAlignment="Bottom"
Foreground="Black" />
</StackPanel>
Note: I have rearranged the layout a bit to ensure the UI elements are properly visible, and have reformatted the XAML itself to aid in readability.
I will also suggest that you use some other mechanism for controlling layout than setting the Margin values. The Margin attribute is very good for ensuring adequate space between elements, but it's not very good at accommodating flexible layout of elements, as it usually requires hand-modifying the margin values as other element characteristics change (e.g. font size, number of characters in the text, etc.).
Likewise, you should use Width and Height sparingly. They have similar problems.
In other words, if you apply the above suggestion to your XAML and it doesn't seem to work, it's because the Label is currently being laid out in such a way that the extra "speed value" text can't be seen.

WPF Bitmap effect error on image source

What I am trying to do is use the Imagebox as source for my bitmap effect and i dont know how to do that.My imagebox is called image1 .
<Button Content="Blur" Height="23" HorizontalAlignment="Left" Margin="148,12,0,0" Name="button3" VerticalAlignment="Top" Width="42" Click="button3_Click" >
<Image Source ="image1">
<Image.BitmapEffect>
<BlurBitmapEffect Radius="5" />
</Image.BitmapEffect>
</Image>
</Button>
Are you using MVVM? If not, I highly recommend using this pattern because WPF is built to use it and if you don't, you will fight it all the way.
Create a ViewModel class. Create a public property of type Image in this ViewModel class.
Create an instace of the ViewModel and put it into your Window's datacontext. Then add a binding to this property.
Alternatively for a quick fix (please note that this leads to darkness, you will regret having started to program this way):
<Image Source="{Binding Source, ElementName=image1}">
Edit:
Your edit is a completely different story: You have set the Content property twice: once by directly setting it and once by having a child object. Your button has both a text and an image as content. But a button (and most other controls) can only have one content. If you want both, your content needs to be a container control like a StackPanel that can have multiple contents and you need to put both your Image and your TextBlock in there.
Example (you need to put in Orientation and Alignment as you see fit):
<Button Height="23" HorizontalAlignment="Left" Margin="148,12,0,0" Name="button3" VerticalAlignment="Top" Width="42" Click="button3_Click">
<StackPanel>
<TextBlock Text="Test"/>
<Image Source="{Binding Source, ElementName=image1}">
<Image.BitmapEffect>
<BlurBitmapEffect Radius="5" />
</Image.BitmapEffect>
</Image>
</Button>

Categories

Resources