WPF: назначить дочерний элемент свойству в XAML - PullRequest
1 голос
/ 18 сентября 2009

Привет, я хочу сделать следующее в xaml:

В моем классе управления есть свойство FocusTarget, которому я хочу назначить UIElement из текущего класса. Возможно ли это в XAML?

<my:BaseControl x:Class="SectionControl"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"        
    FocusTarget="myCtrl">   // this fails           
       ..       
       <my:CodeBlockControl x:Name="myCtrl" />           
       ..       
</my:BaseControl>

UPDATE: Теперь я реализовал это свойство как свойство зависимости, но, похоже, назначения не происходит, хотя я назначаю его в XAML. Но нет ни ошибки компиляции, ни времени выполнения:

в xaml:

    FocusTarget="{Binding ElementName=myCtrl}"

в CS:

   public static readonly DependencyProperty FocusTargetProperty;      

    static BaseControl()
    {
        FrameworkPropertyMetadata metadata = new FrameworkPropertyMetadata(null);
        FocusTargetProperty = DependencyProperty.Register("FocusTarget", typeof(FrameworkElement), typeof(BaseControl), metadata, Validate);
   }

    public FrameworkElement FocusTarget
    {
        get { return GetValue(FocusTargetProperty)as FrameworkElement; }
        set { SetValue(FocusTargetProperty, value); }
    }

Ответы [ 3 ]

2 голосов
/ 18 сентября 2009

Может быть множество причин, по которым {Binding ElementName=...} не работает для вас. Он выполняет поиск через унаследованный контекст, который распространяется через дерево визуальных элементов. Если нет способа пройтись по визуальному дереву от привязки к элементу, на который он ссылается, связывание завершится неудачей. Например, если my:CodeBlockControl объявлено внутри Resources, или в ControlTemplate какого-либо элемента управления, или если между ним и root есть Popup (включая неявный, например, введенный ContextMenu) вот что будет.

К сожалению, нет универсального способа ссылаться на любой другой элемент из того же XAML напрямую. Будет в .NET 4.0 XamlReader, хотя он все равно будет отключен для BAML (и, следовательно, для WPF). Одна альтернатива - использовать ресурсы и {StaticResource} вместо:

<my:BaseControl x:Class="SectionControl"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    FocusTarget="{StaticResource myCtrl}">

  <my:BaseControl.Resources>
    <my:CodeBlockControl x:Key="myCtrl" />
  </my:BaseControl.Resources>

  ...
  <!-- where it originally was -->
  <StaticResource ResourceKey="myCtrl"/>
  ...

</my:BaseControl>
1 голос
/ 18 сентября 2009

Убедитесь, что FocusTarget является свойством зависимости, и привяжите целевой элемент управления с помощью привязки элемента:

<my:BaseControl x:Class="SectionControl"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    FocusTarget="{Binding ElementName=myCtrl}">
    ..
    <my:CodeBlockControl x:Name="myCtrl" />
    ..

0 голосов
/ 18 сентября 2009

Синтаксис привязки имеет вид: Target = "{Источник привязки}"

Платформа требует, чтобы Target всегда был свойством зависимости, тогда как source может быть просто старым свойством CLR.

Ответ Мэтта Гамильтона должен сработать.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...