If a custom control with OnApply template really stucks inside the mainwindow constructor function.

Stefan Schmidt 1 Reputation point
2022-04-28T13:36:00.613+00:00

Hello,

its always the same ,, i not wanna use custom control so likely,, cause they have one major draw back. that if i wanna expose a part from the template to the application so it can access its properties all seems fine , until one point ,, i can not access that part from the custom control in my application, hosting the dll,, for out the Main constructor method..,, means the dll seems to simply load after this method was called as to get there still an error the object is not set to an instance of an object. What i do wrong there?? Is that really the behavior of a custom control??

here the custom control:
Generic.xaml (only most important things

ResourceDictionary
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:NumberEnumerateTextBox">
<Style TargetType="{x:Type local:NumberEnumerateTextBox}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type local:NumberEnumerateTextBox}">
<Border >
<StackPanel HorizontalAlignment="Stretch" VerticalAlignment="Stretch">
<ScrollViewer :Name="PART_ContentHost" />
<RepeatButton x:Name="UpCountRepeatButton" Margin="0,2,0,0" Width="9" Height="11"/>
<RepeatButton x:Name="DownCountRepeatButton" Margin="0,0,0,2" Width="Auto" Height="Auto" G />
<Rectangle Opacity="0.5" x:Name="OverlayRectangle" Fill="#FF0F477B"/>
<TextBlock Opacity="0.9" Foreground="White" x:Name="OverlayTextBlock" FontSize="26" Margin="2,-3,0,0" G"/>
</StackPanel >
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</ResourceDictionary>

and here is code file from the custom control what i mean to use the OnApply method to assign public members:

public class NumberEnumerateTextBox : Control
{
static NumberEnumerateTextBox()
{
DefaultStyleKeyProperty.OverrideMetadata(typeof(NumberEnumerateTextBox), new FrameworkPropertyMetadata(typeof(NumberEnumerateTextBox)));
}

    public RepeatButton UpCountRepeatButton = null;
    public RepeatButton DownCountRepeatButton = null;
    public Rectangle OverlayRectangle = null;
    public TextBlock OverlayTextBlock = null;
    public override void OnApplyTemplate()
    {

        base.OnApplyTemplate();
        UpCountRepeatButton = GetTemplateChild("UpCountRepeatButton") as RepeatButton;
        DownCountRepeatButton = GetTemplateChild("DownCountRepeatButton") as RepeatButton;
        OverlayRectangle = GetTemplateChild("OverlayRectangle") as Rectangle;
        OverlayTextBlock = GetTemplateChild("OverlayTextBlock") as TextBlock;
    }

}

so all seems fine until that point,, but yet i create may solution to test the dll,, also use project reference and add the library to that Solution,,
then i try following in the Main function of the solution,,

also first i assign that control in the xaml code:

xmlns:num="clr-namespace:NumberEnumerateTextBox;assembly=NumberEnumerateTextBox"

<num:NumberEnumerateTextBox x:Name="box" Width="50" Height="50"/>

and then i try in the constructor to call after that object:

public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
box.Background = Brushes.Yellow;
}
}

I get there always an error message as the object is still not set to an instance what simply works fine , if ya ahs have loaded already the application and then in a different method ya try again the same access. But me there asking if that behavior is really intention and where could be the mistake to still retrieve such error message?

Windows Presentation Foundation
Windows Presentation Foundation
A part of the .NET Framework that provides a unified programming model for building line-of-business desktop applications on Windows.
2,670 questions
{count} votes

1 answer

Sort by: Most helpful
  1. Hui Liu-MSFT 38,191 Reputation points Microsoft Vendor
    2022-04-29T02:22:52.427+00:00

    You could try to check if your namespace and class names are the same.If it is the same, an error will be reported. You can refer to the code below.
    Project structure:

    197538-image.png
    Generic.xaml:

    <ResourceDictionary  
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"  
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"  
        xmlns:local="clr-namespace:NumberEnumerateTextBox">  
        <Style TargetType="{x:Type local:NumberEnumerateTextBox1}">  
            <Setter Property="Template">  
                <Setter.Value>  
                    <ControlTemplate TargetType="{x:Type local:NumberEnumerateTextBox1}">  
                        <Border Background="{TemplateBinding Background}"  
                                BorderBrush="{TemplateBinding BorderBrush}"  
                                BorderThickness="{TemplateBinding BorderThickness}">  
                            <StackPanel HorizontalAlignment="Stretch" VerticalAlignment="Stretch">  
                                <ScrollViewer x:Name="PART_ContentHost" />  
                                <RepeatButton x:Name="UpCountRepeatButton" Margin="0,2,0,0" Width="9" Height="11"/>  
                                <RepeatButton x:Name="DownCountRepeatButton" Margin="0,0,0,2" Width="Auto" Height="Auto" />  
                                <Rectangle Opacity="0.5" x:Name="OverlayRectangle" Fill="#FF0F477B"/>  
                                <TextBlock Opacity="0.9" Foreground="White" x:Name="OverlayTextBlock" FontSize="26" Margin="2,-3,0,0" />  
                            </StackPanel >  
                        </Border>  
                    </ControlTemplate>  
                </Setter.Value>  
            </Setter>  
        </Style>  
    </ResourceDictionary>  
    

    NumberEnumerateTextBox1:

    using System.Windows;  
    using System.Windows.Controls;  
    using System.Windows.Controls.Primitives;  
    using System.Windows.Shapes;  
    
    namespace NumberEnumerateTextBox  
    {  
        public class NumberEnumerateTextBox1 : Control  
        {  
            static NumberEnumerateTextBox1()  
            {  
                DefaultStyleKeyProperty.OverrideMetadata(typeof(NumberEnumerateTextBox1), new FrameworkPropertyMetadata(typeof(NumberEnumerateTextBox1)));  
            }  
        public RepeatButton UpCountRepeatButton = null;  
        public RepeatButton DownCountRepeatButton = null;  
        public Rectangle OverlayRectangle = null;  
        public TextBlock OverlayTextBlock = null;  
        public override void OnApplyTemplate()  
        {  
          base.OnApplyTemplate();  
          UpCountRepeatButton = GetTemplateChild("UpCountRepeatButton") as RepeatButton;  
          DownCountRepeatButton = GetTemplateChild("DownCountRepeatButton") as RepeatButton;  
          OverlayRectangle = GetTemplateChild("OverlayRectangle") as Rectangle;  
          OverlayTextBlock = GetTemplateChild("OverlayTextBlock") as TextBlock;  
        }  
      }  
    }  
    

    Add NumberEnumerateTextBox dll to OnApplyTemplateCustomControlDemo project.
    MainWindow.xaml:

    xmlns:num="clr-namespace:NumberEnumerateTextBox;assembly=NumberEnumerateTextBox"  
       <Grid>  
            <num:NumberEnumerateTextBox1 x:Name="box" Width="150" Height="150"/>  
        </Grid>  
    

    MainWindow.xaml.cs:

    public partial class MainWindow : Window  
      {  
        public MainWindow()  
        {  
          InitializeComponent();  
          box.Background = Brushes.Yellow;  
    
        }  
      }  
    

    The result:
    197591-image.png


    If the response is helpful, please click "Accept Answer" and upvote it.
     Note: Please follow the steps in our [documentation][5] to enable e-mail notifications if you want to receive the related email notification for this thread. 

    [5]: https://learn.microsoft.com/en-us/answers/articles/67444/email-notifications.html

    0 comments No comments