I would be fine with an answer in VB or C#, I know both, ultimate solution will be written in VB.Net though. Essentially I want to use a template for reuse of the Dependent Properties of the base in n numbers of permutations but I was going a xaml with code behind route and abandoned a Style template. Basically I want to do something like this in a user control I would want to use for a base:
XAML:
<UserControl x:Class="Test"
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:WPFControls"
mc:Ignorable="d"
d:DesignHeight="300" d:DesignWidth="300">
<Grid Name="PART_TestLayout">
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<TextBlock Text="{Binding TestTitle}" Height="30" Background="White" Foreground="Black" />
<TextBlock Name="PART_Text2" Grid.Row="1" Background="White" />
</Grid>
</UserControl>
Code Behind of XAML:
Imports System.ComponentModel
Public Class Test
Public Sub New()
InitializeComponent()
PART_TestLayout.DataContext = Me
End Sub
Public Shared ReadOnly TestTitleProperty As DependencyProperty = DependencyProperty.Register("TestTitle", GetType(String), GetType(Test), New UIPropertyMetadata(String.Empty, AddressOf TestChanged))
Public Property TestTitle As String
Get
Return CType(GetValue(TestTitleProperty), String)
End Get
Set
SetValue(TestTitleProperty, Value)
End Set
End Property
Private Shared Sub TestChanged(d As DependencyObject, e As DependencyPropertyChangedEventArgs)
Dim m = DirectCast(d, Test)
m.PART_Text2.Text = $"Changed {DateTime.Now.ToLongTimeString}"
End Sub
Public MustOverride Sub DoThing()
End Class
What I would like to do is something like this:
Use1:
<local:Test x:Class="TestInheritance"
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:WPFControls"
mc:Ignorable="d"
d:DesignHeight="300" d:DesignWidth="300">
<Grid>
<Label Content="I am the first implentation"/>
<local:Test TestTitle="{Binding TestText}" />
</Grid>
</local:Test>
Use2
<local:Test x:Class="TestInheritance2"
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:WPFControls"
mc:Ignorable="d"
d:DesignHeight="300" d:DesignWidth="300">
<Grid>
<Label Content="I am the second implentation"/>
<local:Test TestTitle="{Binding TestText}" />
</Grid>
</local:Test>
Now I know I could do something like this (and may be the way I should go)
<UserControl x:Class="TestInheritance"
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:WPFControls"
mc:Ignorable="d"
d:DesignHeight="300" d:DesignWidth="300">
<Grid>
<local:Part1 TestTitle="{Binding TestText}" />
<!-- myproprietaryContent -->
<local:Part2 TestLegend="{Binding TestText2}" />
</Grid>
</local:Test>
But I would rather just inherit from a base template and just apply everything I need from that. Do I need to use a Style Template to have to do that or can I reuse a XAML UserControl ALMOST EXACTLY as is? Everytime I try to do 'inherits (baseclassname)' in the code behind I get this error:
'Base class 'Test' specified for class 'TestInheritance' cannot be different from the base class 'UserControl' of one of its other partial types.'
So I am kind of stuck scratching my head not knowing enough on the language and capabilities of WPF is this can be done, or should be done for that matter.
You cannot reuse the content of the base UserControl
as the content will be overridden by the derived controls. The base class should only define the dependency properties and don't have any XAML markup.
Please refer to the following sample code:
Test.vb (the base class):
Public MustInherit Class Test
Inherits UserControl
Public Shared ReadOnly TestTitleProperty As DependencyProperty = DependencyProperty.Register("TestTitle", GetType(String), GetType(Test), New UIPropertyMetadata(String.Empty, AddressOf TestChanged))
Public Property TestTitle As String
Get
Return CType(GetValue(TestTitleProperty), String)
End Get
Set
SetValue(TestTitleProperty, Value)
End Set
End Property
Private Shared Sub TestChanged(d As DependencyObject, e As DependencyPropertyChangedEventArgs)
'...
End Sub
Public MustOverride Sub DoThing()
End Class
UserControl1.xaml:
<local:Test x:Class="UserControl1"
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:WpfApplicationVb1"
mc:Ignorable="d"
d:DesignHeight="300" d:DesignWidth="300">
<Grid>
</Grid>
</local:Test>
UserControl1.xaml.vb:
Public Class UserControl1
Inherits Test
Public Overrides Sub DoThing()
'...
End Sub
End Class
UserControls
are for composition. If you want sensible inheritance you should use custom controls.
http://wpftutorial.net/HowToCreateACustomControl.html
In your case I would inherit from TextBlock and add a BottomText dependency property to it. Then style it in Generic.xaml largely as you have done.
See also here for the difference between UserControls and Custom Controls (the latter pattern was built for your use case): http://wpftutorial.net/CustomVsUserControl.html
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.