Создание элемента управления текстовым полем WPF, такого как текстовое поле получателя электронной почты Outlook - PullRequest
7 голосов
/ 11 мая 2010

Я хочу создать элемент управления текстовым полем WPF, который действует аналогично текстовым полям получателя электронной почты в Outlook (вводы To, Cc и Bcc). Меня не очень заботит автозаполнение (я нашел миллионы примеров для этого), но я действительно борюсь с тем, как сделать так, чтобы текстовые записи с разделителями в текстовом поле вели себя так же, как в Outlook (после того, как введенный вами получатель разрешается, этот текст становится «сущностью», которую вы можете щелкнуть, чтобы выбрать, щелкнуть правой кнопкой мыши, чтобы получить контекстное меню, и т. Д. Это больше не «обычный текст», в котором вы можете поместить курсор) ...

У кого-нибудь есть идеи высокого уровня, как этого добиться? Знаете какие-нибудь существующие примеры (я гуглил часами)?

Заранее большое спасибо,

Майкл.

1 Ответ

5 голосов
/ 11 мая 2010

Мой грубый мыслительный процесс был бы таким ... (примечание: я на самом деле не кодирую его, поэтому мои данные могут быть немного не в порядке ...).

Поведение высокого уровня:

  • тип данных в вашем элементе управления - это список элементов, которые нельзя выбрать. Следовательно, ваш элемент управления примерно равен ItemsControl (с точки зрения визуального / XAML, это ItemsControl с макетом стиля WrapPanel и очень простым TextBlock для шаблона элемента).
  • когда ваш элемент управления получает фокус, вам нужно переключить шаблон на TextBox
  • когда ваш элемент управления теряет фокус, вам нужно разделить введенный текст и преобразовать его в список для отображения.

Следовательно, думая код:

  • вам нужен UserControl, возможно производный от ItemsControl. Это дает вам базовое поведение для представления списка элементов.
  • вам нужен пользовательский DependencyProperty для вашего элемента управления, который представляет строку с разделителями.
  • при изменении свойства строки необходимо проанализировать его и заменить список элементов в элементе управления.
  • при изменении свойства списка необходимо заменить строковое свойство соответствующим списком с разделителями.

С точки зрения кода, эта часть должна быть довольно простой. Затем для шаблона XAML ...

  • вам нужен базовый шаблон, который отображает ваше свойство Items в виде списка, используя макет WrapPanel, упомянутый выше.
  • вам нужен триггер, который заменяет этот шаблон, когда элемент управления имеет фокус.
  • шаблон замены должен быть TextBox, привязанным к строковому свойству элемента управления.
  • поведение привязки по умолчанию для TextBox будет выдвигать новое значение только тогда, когда TextBox теряет фокус, поэтому вам нужно подумать, хотите ли вы, например, сделать фокус ввода нажатием клавиши «Ввод» (таким образом, возвращая шаблон для версии списка - при изменении значения свойства строки ваш кодовый код обновит список).

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

...