#c# #wpf #user-controls
#c# #wpf #пользовательские элементы управления
Вопрос:
Я пытаюсь настроить стиль usercontrol, унаследовав его стиль и добавив к нему некоторые дополнительные стили. Я сделал небольшой проект, чтобы попробовать это. Допустим, у меня есть вызываемый пользовательский элемент управления UserControl1
(то, что он содержит, не имеет значения — в моем примере проекта он пуст).
Я использую его в своем MainWindow
следующим образом:
<Window x:Class="WpfStyleInheritance.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:WpfStyleInheritance"
Title="MainWindow" Height="350" Width="525">
<Grid>
<local:UserControl1>
<local:UserControl1.Style>
<Style TargetType="{x:Type local:UserControl1}" BasedOn="{x:Type local:UserControl1}">
<Setter Property="Margin" Value="0" />
</Style>
</local:UserControl1.Style>
</local:UserControl1>
</Grid>
</Window>
Со BasedOn
своей стороны, я получаю ошибку:
Указанное значение не может быть присвоено. Ожидался следующий тип: «Стиль».
Если я изменю его на BasedOn="{StaticResource {x:Type local:UserControl1}}"
, то получу сообщение об ошибке:
Не удалось разрешить ресурс «{x:Type local:UserControl1}».
Как я могу заставить это работать и жить долго и счастливо?
Редактировать: как я написал в комментариях к ответу здесь, если я иду по маршруту StaticResource и запускаю, я получаю исключение XamlParseException с сообщением:
Не удается найти ресурс с именем ‘WpfStyleInheritance.UserControl1’. Имена ресурсов чувствительны к регистру.
Дополнительная информация: если я заменю все экземпляры local:UserControl1
в разметке MainWindow на Button
, это работает довольно хорошо. Проблема заключается в пользовательских элементах управления.
Редактировать 2: если я добавлю стиль в UserControl, проблема останется:
<UserControl.Style>
<Style TargetType="UserControl">
<Setter Property="Height" Value="0" />
</Style>
</UserControl.Style>
Ответ №1:
BasedOn
синтаксис неверен. Это должно быть:
BasedOn="{StaticResource {x:Type local:UserControl1}}"
И даже если вы получаете ошибку конструктора, попробуйте повторно скомпилировать свой код. Убедитесь, что добавленное пространство имен правильно сопоставлено с вашим UserControl.
Кроме того, убедитесь, что MainWindow и UserControl1 находятся в одной сборке.
Если они находятся в разных сборках, необходимо указать имя сборки в объявлении пространства имен:
xmlns:local="clr-namespace:WpfStyleInheritance;assembly=AssemblyName"
Обновить
В случае, если вы не определили какой-либо стиль по умолчанию для UserControl1
, вам не нужно использовать BasedOn
, поскольку стиля по умолчанию для вашего UserControl не существует. Вот почему вы получаете исключение.
Удалите BasedOn, и он будет работать нормально.
Ресурс, который вы определили в XAML, — это не стиль по умолчанию, а локальный стиль UserControl, который будет переопределен в случае определения другого локального ресурса в MainWindow.
Если вам нужен стиль по умолчанию для вашего UserControl1, объявите его в разделе Application resources
, то есть в App.xaml
.
<Application.Resources>
<Style TargetType="{x:Type local:UserControl1}">
<Setter Property="Height" Value="0" />
</Style>
</Application.Resources>
и теперь в MainWindow.xaml это будет работать нормально:
<local:UserControl1>
<local:UserControl1.Style>
<Style TargetType="{x:Type local:UserControl1}"
BasedOn="{StaticResource {x:Type local:UserControl1}}">
<Setter Property="Margin" Value="0" />
</Style>
</local:UserControl1.Style>
</local:UserControl1>
Комментарии:
1. Я попробовал это, как я объяснил в вопросе. Если я запускаю, я получаю исключение XamlParseException
2. Можете ли вы опубликовать внутреннее исключение для XamlParseException?
3. Не удается найти ресурс с именем ‘WpfStyleInheritance. UserControl1’. Имена ресурсов чувствительны к регистру.
4. Можете ли вы опубликовать код для UserControl1? Скорее всего, сборка отличается или имя неверно.
5. Это просто пустой UserControl, который вы получаете после добавления нового элемента.