Есть ли какой-нибудь уникальный идентификатор для wpf UIElement? - PullRequest
8 голосов
/ 03 апреля 2012

Для регистрации действий пользователя в моих формах WPF я добавил несколько глобальных обработчиков событий

Я хочу точно указать, какой элемент управления запускает событие, есть ли какой-то уникальный идентификатор для wpf UIElement, подобного ClientId в ASP.Net?

Ответы [ 5 ]

11 голосов
/ 03 апреля 2012

Почему бы вам не использовать хэш-код.

Вы можете сравнить значения, чтобы убедиться, что они являются одним и тем же объектом, и их легко получить с помощью .GetHashCode()


Редактировать

Очевидно, что это меняется каждый раз, когда вы запускаете программу, так что на самом деле это плохая идея, если только вы не хотите обновлять журнал каждый раз, когда регистрируется процесс. Все еще возможно, хотя

Я имею в виду, что вы могли бы сохранить хеш-значение для каждого объекта во время создания журнала, но я не знаю, нравится ли мне это

2 голосов
/ 30 мая 2012

Кажется, я нашел ответ на свой вопрос, ответ - нет, теперь способ сделать это, как отмечено в MSDN здесь (http://msdn.microsoft.com/en-us/magazine/dd483216.aspx)

Обратите внимание, что определение элемента управления Window верхнего уровня не содержит Имя атрибута. Это важно, потому что, как мы скоро увидим, когда вы пишете автоматизацию тестирования, простой способ получить ссылку на управлять с помощью библиотеки MUIA для доступа к свойству AutomationId, который генерируется компилятором из атрибута Name элемента управления. Элементы управления без атрибута имени XAML не получат Свойство AutomationId. Эта идея является конкретным примером низкого уровня важность рассмотрения вопросов дизайна приложений для вещей такие как безопасность, расширяемость и автоматизация тестирования.

1 голос
/ 20 апреля 2012

Один из способов сделать это - с помощью пользовательского атрибута. Вот так ...

UIElement, в который вы хотите войти (например, UserControl):

[UserInterfaceID(ID = "{F436E9B3-C2F6-4CF8-8C75-0A2A756F1C74}")]
public partial class MyUserControl : UserControl
{
    InitializeComponent();
    // or whatever...
}

Тогда вам нужен класс пользовательских атрибутов

[System.AttributeUsage(AttributeTargets.Class)]
public class UserInterfaceIDAttribute : Attribute
{
    public Guid ID { get; set; }
}

Теперь в своем коде вы можете сделать что-то вроде этого:

MyUserControl control = new MyUserControl();
foreach(object att in control.GetCustomAttributes(typeof(UserInterfaceAttribute),false))
{
    UserInterfaceAttribute uiAtt = (UserInterfaceAttribute)att;
    Guid theID = uiAtt.ID;
}

Поскольку вы помечаете элемент управления с помощью атрибута в коде, уникальный идентификатор никогда не изменяется независимо от того, сколько раз вы удаляете / запускаете приложение.

Конечно, это базовый пример, который показывает, как получить доступ к идентификатору, но вы, вероятно, захотите использовать какой-либо аспектно-ориентированное программирование. Я делаю именно такие вещи, используя Castle Windsor Interceptors, но это выходит за рамки этого поста.

В идеале вы будете получать доступ к этому идентификатору, когда происходит какое-то событие, которое запускается. Использование перехватчиков позволяет вам перехватывать вызовы методов до их вызова, где вы можете найти идентификатор, как показано выше, и записать действие. Кроме того, вы можете просто использовать

this.GetCustomAttributes(...)

в каком-то методе, когда событие срабатывает в элементе управления и вставляет туда свой код регистрации. Эта модель не самая лучшая, потому что вы разбрасываете сквозные проблемы повсюду, делая какой-то подход к аспектно-ориентированному программированию лучше ... но я опять отвлекся, и это выходит за рамки этого поста ... но вы получите идея.

Надеюсь, это поможет.

0 голосов
/ 03 апреля 2012

Я считаю, что для регистрации действий пользователя вы можете использовать UIAutomation tree и свойство AutomationElement.AutomationId , поскольку этот подход по умолчанию поддерживается во всех стандартных элементах управления пользовательского интерфейса.Многие сторонние элементы управления также поддерживают AutomationId для своих элементов (например, ячеек сетки).AutomationId полезен для создания сценариев автоматизации тестирования.

0 голосов
/ 03 апреля 2012

Вы просто добавляете Name или x:Name, чтобы Window / UserControl / Page предоставлял элемент управления остальному классу с указанным именем.

<Window ...>
   <Grid>
       ...

       <!-- These controls are named, so you can access them directly by name -->
       <Button x:Name="btnMyNamedButton" ... />
       <Button Name="btnMyOtherNamedButton" ... />

       <!-- This control is not named, so you can not directly access it by name -->
       <Button ... />
   <Grid>
</Window>

public partial class MyWindow : Window
{
    public MyWindow()
    {
        InitializeComponent();

        //btnMyNamedButton can be accessed
        //btnMyOtherNamedbutton can also be accessed

        //The third button can be accessed, but not directly by name.
    }
}

Кроме того, вы всегда можете использовать объект FrameworkElement.Tag . Он предназначен для хранения произвольной информации, поэтому вы можете использовать ее как уникальный идентификатор, если хотите.

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