I have a XAML view that I created in a .NET Framework WPF app, and I'm trying to upgrade the app to .NET 5:
<Window
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:AutoPBW="clr-namespace:AutoPBW;assembly=AutoPBW"
xmlns:scm="clr-namespace:System.ComponentModel;assembly=WindowsBase"
xmlns:shell="clr-namespace:System.Windows.Shell;assembly=PresentationFramework"
mc:Ignorable="d"
x:Name="window"
x:Class="AutoPBW.WPF.MainWindow"
Title="AutoPBW" Height="397" Width="653" Loaded="window_Loaded" Closing="window_Closing" Icon="AutoPBW.ico">
<Window.Resources>
<!-- this CollectionViewSource gives a null reference exception on the d:DesignSource attribute -->
<CollectionViewSource x:Key="playerGameViewSource" d:DesignSource="{d:DesignInstance {x:Type AutoPBW:PlayerGame}, CreateList=True}"/>
<Style x:Key="ListItemStyle" TargetType="{x:Type ListBoxItem}">
<Style.Resources>
</Style.Resources>
<Setter Property="Template">
<Setter.Value>
<!-- this ControlTempate gives an error saying that the Item.MouseOver.Background resource could not be found -->
<ControlTemplate TargetType="{x:Type ListBoxItem}">
<Border x:Name="Bd" BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" Background="{TemplateBinding Background}" Padding="{TemplateBinding Padding}" SnapsToDevicePixels="true">
<ContentPresenter HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}" VerticalAlignment="{TemplateBinding VerticalContentAlignment}"/>
</Border>
<ControlTemplate.Triggers>
<MultiTrigger>
<MultiTrigger.Conditions>
<Condition Property="IsMouseOver" Value="True"/>
</MultiTrigger.Conditions>
<!-- here is where the Item.MouseOver.Background resource is actually referenced -->
<Setter Property="Background" TargetName="Bd" Value="{StaticResource Item.MouseOver.Background}"/>
<Setter Property="BorderBrush" TargetName="Bd" Value="{StaticResource Item.MouseOver.Border}"/>
</MultiTrigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</Window.Resources>
<Grid>
<!-- this is where the actual UI is defined, no errors here -->
</Grid>
</Window>
I have removed a few irrelevant sections, but the comments denote where I encountered compile errors.
The errors I see are:
XDG0062 Object not set to an instance of an object.
and
XDG0062 Cannot find resource named 'Item.MouseOver.Background'. Resource names are case sensitive.
How can I solve these errors?
Thanks! 🙂
Oh, I figured it out. I had my TargetFramework set incorrectly in my project file. It should have been net5-windows, but I had it set to net5.0-windows.
Related
I want to make impossible checking checkbox in WPF (from C# code). Only unchecking would be allowed.
How can I do it?
PS.Writing event handler on Click event which would immediately uncheck checkbox after checking it is not acceptable.
[edit]Checkbox should always be enabled, so that user can think that checkbox can be checked. It's strange but it's specific programme.
<CheckBox Content="Checkbox"
IsEnabled="{Binding RelativeSource={RelativeSource Self}, Path=IsChecked}" />
Edit after being informed that the checkbox always has to look to be in an checkable state, even when it's not. Here is a working example:
<Window
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:Microsoft_Windows_Themes="clr-namespace:Microsoft.Windows.Themes;assembly=PresentationFramework.Aero" x:Class="WpfTest.MainWindow"
Title="MainWindow" Height="350" Width="525">
<Window.Resources>
<ControlTemplate x:Key="DeceptiveCheckbox" TargetType="{x:Type CheckBox}">
<BulletDecorator Background="Transparent" SnapsToDevicePixels="True">
<BulletDecorator.Bullet>
<Microsoft_Windows_Themes:BulletChrome BorderBrush="{TemplateBinding BorderBrush}" Background="{TemplateBinding Background}" IsChecked="{TemplateBinding IsChecked}" RenderMouseOver="{TemplateBinding IsMouseOver}" RenderPressed="{TemplateBinding IsPressed}"/>
</BulletDecorator.Bullet>
<ContentPresenter ContentTemplate="{TemplateBinding ContentTemplate}" Content="{TemplateBinding Content}" ContentStringFormat="{TemplateBinding ContentStringFormat}" HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" Margin="{TemplateBinding Padding}" RecognizesAccessKey="True" SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}" VerticalAlignment="{TemplateBinding VerticalContentAlignment}"/>
</BulletDecorator>
<ControlTemplate.Triggers>
<Trigger Property="HasContent" Value="True">
<Setter Property="FocusVisualStyle">
<Setter.Value>
<Style>
<Setter Property="Control.Template">
<Setter.Value>
<ControlTemplate>
<Rectangle Margin="14,0,0,0" SnapsToDevicePixels="True" Stroke="{DynamicResource {x:Static SystemColors.ControlTextBrushKey}}" StrokeThickness="1" StrokeDashArray="1 2"/>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</Setter.Value>
</Setter>
<Setter Property="Padding" Value="4,0,0,0"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Window.Resources>
<Grid>
<CheckBox Content="CheckBox" IsEnabled="{Binding IsChecked, RelativeSource={RelativeSource Self}}" Template="{StaticResource DeceptiveCheckbox}" />
</Grid>
</Window>
The fix was simple. I simply created a copy of the current checkbox template and removed:
<Trigger Property="IsEnabled" Value="False">
<Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}"/>
</Trigger>
How about this:
<Grid>
<Grid.Resources>
<Style TargetType="CheckBox">
<Style.Triggers>
<Trigger Property="IsChecked" Value="False">
<Setter Property="IsEnabled" Value="False" />
</Trigger>
</Style.Triggers>
</Style>
</Grid.Resources>
<CheckBox IsChecked="True" />
</Grid>
This approach has the benefit of being applied to all (as-is) or many (if you apply a x:Key attribute and then assign the resource to the desired checkboxes) without needing to do anything special or change the bindings of the individual checkboxes.
An easy solution could be to bind the IsEnabled property to be equal to the IsChecked property.
How I can bottom align text in RichTextBox? It seems that control doesn't support it directly. So I am looking for ways to emulate it. Ideally I would have the boundary of the control fixed and end of text aligned with the bottom.
The text comes from a ScrollViewer named PART_ContentHost inside the default control template for the TextBoxBase which is wrapped by the RichTextBox. You should override the control template and either have the ScrollViewer declare its VerticalAlignment to be Bottom, or have it template bind to the VerticalContentAlignment.
Below, I've done the latter. This is a modified version of the default control template as pulled from Blend. The only change I've made is to add VerticalAlignment="{TemplateBinding VerticalAlignment}" to the ScrollViewer.
(Also note that it references Microsoft_Windows_Themes which is defined as xmlns:Microsoft_Windows_Themes="clr-namespace:Microsoft.Windows.Themes;assembly=PresentationFramework.Aero"
I am unsure how this will work if Aero is not on the user's machine)
<Style x:Key="BottomAlignedTextBoxBaseStyle"
TargetType="TextBoxBase"
BasedOn="{StaticResource {x:Type TextBoxBase}}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type TextBoxBase}">
<Microsoft_Windows_Themes:ListBoxChrome x:Name="Bd"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
Background="{TemplateBinding Background}"
RenderMouseOver="{TemplateBinding IsMouseOver}"
RenderFocused="{TemplateBinding IsKeyboardFocusWithin}" SnapsToDevicePixels="true">
<ScrollViewer x:Name="PART_ContentHost"
SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}"
VerticalAlignment="{TemplateBinding VerticalContentAlignment}" />
</Microsoft_Windows_Themes:ListBoxChrome>
<ControlTemplate.Triggers>
<Trigger Property="IsEnabled"
Value="false">
<Setter Property="Background"
TargetName="Bd"
Value="{DynamicResource {x:Static SystemColors.ControlBrushKey}}"/>
<Setter Property="Foreground"
Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
Then, to use it, simply say:
<RichTextBox Style="{StaticResource BottomAlignedTextBoxBaseStyle}"
VerticalContentAlignment="Bottom" />
I am setting peroperty Margin and Padding of a window and it doesn't take effect:
Here is an example:
<Window
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
SizeToContent="WidthAndHeight"
ResizeMode="NoResize"
Padding="22"
Margin="22">
<Grid>
<Label
FontWeight="Bold"
FontSize="36"
BorderThickness="1"
BorderBrush="Red"
Content="Hello world!"/>
</Grid>
</Window>
Result:
The desired result is that the red frame of the lable should be away 44px from the window's frame (margin+padding).
Yes, I know I can set the margin of the label, but that's not what I want.
I have a whole project that all its windows are set to a style, I want to set this properties (or other) in the general window style.
I guess if I won't find any solution I will create a named style for greed where I will set the margin/padding, then I will go Window by window and set the Grid's style, but that's the last option I wanna do.
Thanks in advance.
It's not surprising that Margin doesn't work, because Margin is the amount of space to be placed around the control. For a Window, this would mean making the frame smaller (and offset), not the client area, and that would be a bit strange (and might not play nicely with the Win32 hosting environment, not sure). It is a bit surprising that Padding doesn't work, and I'm not sure why that would be.
However, there is a workaround which you can encapsulate in a style: replace the default Window ControlTemplate with your own template that does respect the Padding:
<ControlTemplate TargetType="Window">
<Border Background="White" Padding="{TemplateBinding Padding}">
<ContentPresenter />
</Border>
</ControlTemplate>
(You would probably want the Border Background to be the dynamic window background brush for production code, but you get the idea.)
Obviously you can put this template in a style Template setter so as to avoid having to repeat it on each Window.
Here is the full template (generated with Microsoft Expression):
<Style x:Key="WindowStyle" TargetType="{x:Type Window}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type Window}">
<Border Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
Margin="{TemplateBinding Margin}"
Padding="{TemplateBinding Padding}">
<AdornerDecorator>
<ContentPresenter/>
</AdornerDecorator>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
<Style.Triggers>
<Trigger Property="ResizeMode" Value="CanResizeWithGrip">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type Window}">
<Border Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}">
<Grid>
<AdornerDecorator>
<ContentPresenter/>
</AdornerDecorator>
<ResizeGrip
x:Name="WindowResizeGrip"
HorizontalAlignment="Right"
VerticalAlignment="Bottom"
IsTabStop="false"
Visibility="Collapsed"
/>
</Grid>
</Border>
<ControlTemplate.Triggers>
<MultiTrigger>
<MultiTrigger.Conditions>
<Condition
Property="ResizeMode"
Value="CanResizeWithGrip"
/>
<Condition
Property="WindowState"
Value="Normal"
/>
</MultiTrigger.Conditions>
<Setter
Property="Visibility"
TargetName="WindowResizeGrip"
Value="Visible"/>
</MultiTrigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Trigger>
</Style.Triggers>
</Style>
Here's a simple alternative: just set a background colour on your Window and the Margin on the Grid within your Window:
I have some changes I need to make to the Silverlight toolkit Charting source
I downloaded the Silverlight toolkit ... unzipped the source to a new directory
Added the
Controls.DataVisualization.Toolkit.csproj Project to my Solution
Removed The reference in my silverlight application to
System.Windows.Controls.DataVisualization.Toolkit
and Added
A project Reference to The Controls.DataVisualization.Toolkit.csproj Project
I then changed the Legend.xaml
to
<Style TargetType="datavis:Legend">
<Setter Property="BorderBrush" Value="Lime"/>
<Setter Property="BorderThickness" Value="1"/>
<Setter Property="IsTabStop" Value="False"/>
<Setter Property="TitleStyle">
<Setter.Value>
<Style TargetType="datavis:Title">
<Setter Property="Margin" Value="0,5,0,10"/>
<Setter Property="FontWeight" Value="Bold"/>
<Setter Property="HorizontalAlignment" Value="Center"/>
</Style>
</Setter.Value>
</Setter>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="datavis:Legend">
<Border
Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
Padding="2">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition/>
</Grid.RowDefinitions>
<datavis:Title
Grid.Row="0"
Content="{TemplateBinding Title}"
Style="{TemplateBinding TitleStyle}"/>
<TextBlock>Yeah</TextBlock>
</Grid>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
Added a simple columnchart to my MainPage.xaml
and Then ran it
neither of the changes are visible in my Silverlight Page.
Thanks
Mark
The Silverlight Toolkit uses some build tasks to move the control templates out of the seperate xaml files into the generic.xaml file. Since you probably don't have this build task (I think the team has made it available) you will need to make your changes in generic.xaml instead of Legend.xaml (or get the build task).
I am replacing the style of a radio button with that of a check box. I know you are going to say that is a bad idea, but it really needs to work this way. Anyway, using Expression Blend I was able to extract the style of the CheckBox and apply it to a RadioButton. My only problem is now that when it draws there is no border. Can anyone tell me why? Here is the code (THIS HAS BEEN UPDATED SINCE THE ORIGINAL POST):
<Window x:Class="WpfApplication1.Window1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:Microsoft_Windows_Themes="clr-namespace:Microsoft.Windows.Themes;assembly=PresentationFramework.Royale"
Title="Customized RadioButton" Width="496" ShowInTaskbar="True" ResizeMode="NoResize" Height="105">
<Window.Resources>
<SolidColorBrush x:Key="CheckBoxStroke" Color="#8E8F8F"/>
<Style x:Key="RadioButtonCheckBoxStyle" TargetType="{x:Type RadioButton}">
<Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.ControlTextBrushKey}}"/>
<Setter Property="Background" Value="#F4F4F4"/>
<Setter Property="BorderBrush" Value="{StaticResource CheckBoxStroke}"/>
<Setter Property="BorderThickness" Value="1"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type RadioButton}">
<Border BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}">
<BulletDecorator Background="Transparent">
<BulletDecorator.Bullet>
<Microsoft_Windows_Themes:BulletChrome Background="{TemplateBinding Background}" BorderBrush="{TemplateBinding BorderBrush}" IsChecked="{TemplateBinding IsChecked}" IsRound="false" RenderMouseOver="{TemplateBinding IsMouseOver}" RenderPressed="{TemplateBinding IsPressed}"/>
</BulletDecorator.Bullet>
<ContentPresenter HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" Margin="{TemplateBinding Padding}" VerticalAlignment="{TemplateBinding VerticalContentAlignment}" RecognizesAccessKey="True"/>
</BulletDecorator>
</Border>
<ControlTemplate.Triggers>
<Trigger Property="HasContent" Value="true">
<Setter Property="Padding" Value="4,0,0,0"/>
</Trigger>
<Trigger Property="IsEnabled" Value="false">
<Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</Window.Resources>
<StackPanel>
<CheckBox Height="16" Name="checkBox1" Width="120">CheckBox</CheckBox>
<RadioButton Height="16" Name="radioButton1" Width="120">RadioButton</RadioButton>
<RadioButton Content="RadioButton with CheckBox Style" Margin="4" Style="{DynamicResource RadioButtonCheckBoxStyle}" FocusVisualStyle="{x:Null}" GroupName="Header" IsChecked="False" IsEnabled="True" HorizontalAlignment="Center" />
</StackPanel>
alt text http://img260.imageshack.us/img260/65/33733770.jpg
To see how this displays, please paste it into Visual Studio. You will see that the Customized RadioButton doesn't look correct. It is missing the regular 3D effects that a CheckBox normally has. I don't care about any content (I won't be having any) I just want it to look like a normal CheckBox.
Since you're overriding the template, you need to attach to the class's properties yourself.
Declare a border in the template in the following fashion:
<Border BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}"/>
Also, you've got a small bug. You've defined the setter for "BorderBrush" multiple times in your style.
Edit: After seeing your image, here's your real issue:
<Microsoft_Windows_Themes:BulletChrome Background="{TemplateBinding Background}" BorderThickness="{TemplateBinding BorderThickness}" BorderBrush="{TemplateBinding BorderBrush}" IsChecked="{TemplateBinding IsChecked}" IsRound="false" RenderMouseOver="{TemplateBinding IsMouseOver}" RenderPressed="{TemplateBinding IsPressed}"/>
You were missing the BorderThickness in your bullet. It was effectively setting your thickness to 0, which is why you didn't see anything.
An image might help here, but where do you expect the border to be? Are you expecting a border around the entire content?? The only border there should be according to the template you're using is around where the check mark will be. If you want a border around all the content then you need to add a Border into the ControlTemplate like so:
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type RadioButton}">
<Border BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}">
<BulletDecorator Background="Transparent">
<BulletDecorator.Bullet>
<Microsoft_Windows_Themes:BulletChrome Background="{TemplateBinding Background}" BorderBrush="{TemplateBinding BorderBrush}" IsChecked="{TemplateBinding IsChecked}" IsRound="false" RenderMouseOver="{TemplateBinding IsMouseOver}" RenderPressed="{TemplateBinding IsPressed}"/>
</BulletDecorator.Bullet>
<ContentPresenter HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" Margin="{TemplateBinding Padding}" VerticalAlignment="{TemplateBinding VerticalContentAlignme nt}" RecognizesAccessKey="True"/>
</BulletDecorator>
<ControlTemplate.Triggers>
<Trigger Property="HasContent" Value="true">
<Setter Property="FocusVisualStyle" Value="{StaticResource CheckRadioFocusVisual}"/>
<Setter Property="Padding" Value="4,0,0,0"/>
</Trigger>
<Trigger Property="IsEnabled" Value="false">
<Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
Side note: You have set FocusVisualStyle="{x:Null}" on the Checkbox itself, but your template changes this property in its HasContent property trigger. If you really don't want a FocusVisualStyle you should remove that setter.