none
ユーザーコントロールを使う側で「インスタンスを作成できませんでした」のエラーが出る RRS feed

  • 質問

  • お世話になっております。

    ユーザーコントロールを作成中です。

    ユーザーコントロールにはテキストボックスがあります。
    それにTextプロパティを追加しました。

    問題なかったので、同じ要領でFontSizeプロパティを追加しました。

    そうしますとユーザーコントロール自体はコンパイル出来ましたが、
    ユーザーコントロールを使う側で以下のエラーが出てコンパイルも出来ません。

    「型 'UserControl2' のインスタンスを作成できませんでした。」

    FontSizeプロパティを追加したのが原因だとは分かるのですが、
    具体的な場所が特定出来ません。

    何が原因でしょうか?

    UserControl xaml

    <UserControl x:Class="ctrl.UserControl2"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Height="300" Width="300">
    
        <Canvas>
            <TextBox x:Name="myTextBox" Width="100" Height="20"/>
        </Canvas>
    
    </UserControl>
    
    

    UserControl  c#

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.Windows;
    using System.Windows.Controls;
    using System.Windows.Data;
    using System.Windows.Documents;
    using System.Windows.Input;
    using System.Windows.Media;
    using System.Windows.Media.Imaging;
    using System.Windows.Navigation;
    using System.Windows.Shapes;
    
    namespace ctrl
    {
        /// <summary>
        /// UserControl2.xaml の相互作用ロジック
        /// </summary>
        public partial class UserControl2 : UserControl
        {
    
            public UserControl2()
            {
                InitializeComponent();
    
            }
    
            #region Textプロパティ
    
                public static readonly DependencyProperty TextProperty
                = DependencyProperty.Register("Text",
                                            typeof(string),
                                            typeof(UserControl2),
                                            new FrameworkPropertyMetadata(string.Empty, FrameworkPropertyMetadataOptions.BindsTwoWayByDefault, OnTextChanged));
    
    
                public static void OnTextChanged(DependencyObject sender, DependencyPropertyChangedEventArgs e)
                {
                    UserControl2 userCtrl = (UserControl2)sender;
    
                    TextBox t = userCtrl.FindName("myTextBox") as TextBox;
    
                    if (t != null)
                    {
                        t.Text = (string)e.NewValue;
                    }
                }
    
                public string Text
                {
                    get { return (string)GetValue(TextProperty); }
                    set { SetValue(TextProperty, value); }
                }
    
            #endregion 
    
            
    
            #region FontSizeプロパティ
    
                public static new readonly DependencyProperty FontSizeProperty
                = DependencyProperty.Register("FontSize",
                    typeof(double),
                    typeof(UserControl2),
                    new FrameworkPropertyMetadata(0, FrameworkPropertyMetadataOptions.BindsTwoWayByDefault, OnFontSizeChanged));
    
    
    
                public static void OnFontSizeChanged(DependencyObject sender, DependencyPropertyChangedEventArgs e)
                {
                    UserControl2 ctrl = (UserControl2)sender;
                    TextBox t = ctrl.FindName("myTextBox") as TextBox;
                    if (t != null)
                    {
                        t.FontSize = (double)e.NewValue;
    
                    }
                   
                }
    
                public new double FontSize
                {
                    get { return (double)GetValue(FontSizeProperty); }
                    set { SetValue(FontSizeProperty, value); }
                }
    
            #endregion
    
            
     
    
        }
    }
    

    UserControlを使う側 xaml

    <Window x:Class="WpfApplication1.Window1"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
            xmlns:Controls="clr-namespace:ctrl;assembly=ctrl"
        Title="Window1" Height="300" Width="300"
          >
        <StackPanel>
            <Button Width="100" Height="50" Click="Button_Click"  />
            <Controls:UserControl2  Text="今日は雨です" Name="hoge" />
        </StackPanel>
    </Window>
    

    UserControlを使う側 c#

    using System;
    using System.Collections.Generic;
    using System.Windows;
    using System.Windows.Controls;
    namespace WpfApplication1 { /// <summary> /// Window1.xaml の相互作用ロジック /// </summary> public partial class Window1 : Window { public Window1() { InitializeComponent(); } private void Button_Click(object sender, RoutedEventArgs e) { } } }

    2012年10月17日 5:22

回答

  • FontSizePropertyのDependencyProperty.Registerするところで、初期値に [0] を指定しますが、C#においてはとくに型を指定しない2147483647以下の整数リテラルはInt32として扱われます。FontSizePropertyはdoubleなので、型の不整合が発生します。

    ところで、FontSizeはUserControlの祖先であるControlがすでに登録済みですが、なぜ改めて登録しているのでしょうか? プロパティ変更イベントを追加したいのであれば、UserControl2に静的コンストラクタを用意し、そこでControl.FontSizePropertyに対してOverrideMetadataを実施することで実現できます。

    // そもそもFontSizeはInheritableだから、UserControl2のFontSizeを設定すれば自動的に子孫のTextBoxにも適用されるはずですが。

    • 回答としてマーク sumi_sumi 2012年10月17日 6:01
    2012年10月17日 5:55

すべての返信

  • FontSizePropertyのDependencyProperty.Registerするところで、初期値に [0] を指定しますが、C#においてはとくに型を指定しない2147483647以下の整数リテラルはInt32として扱われます。FontSizePropertyはdoubleなので、型の不整合が発生します。

    ところで、FontSizeはUserControlの祖先であるControlがすでに登録済みですが、なぜ改めて登録しているのでしょうか? プロパティ変更イベントを追加したいのであれば、UserControl2に静的コンストラクタを用意し、そこでControl.FontSizePropertyに対してOverrideMetadataを実施することで実現できます。

    // そもそもFontSizeはInheritableだから、UserControl2のFontSizeを設定すれば自動的に子孫のTextBoxにも適用されるはずですが。

    • 回答としてマーク sumi_sumi 2012年10月17日 6:01
    2012年10月17日 5:55
  • Hongliang さま

    有難う御座います。

    型指定しない場合のルール、知りませんでした。
    すみません。

    初期値の箇所で(double)0
    としましたらコンパイル通り実行出来ました。

    FontSizeプロパティ→何も考えずに追加してました。要らないようです(^^:)

    大変助かりました。

    有難う御座いました。

    ※今回、ユーザーコントロールとか何も関係ありませんでした。初歩的な質問ですみませんでした。。。


    2012年10月17日 6:08