Использование свойства стиля BasedOn в DynamicResources - PullRequest
24 голосов
/ 25 февраля 2009

Интересно, есть ли способ использовать свойство basedOn стилей wpf с динамическими ресурсами. например,

<Style BasedOn="{DynamicResource somestyle}">
   <Setter Property="SomeProp" Value="SomeValue"/>
</Style>

это, например, выдает ошибку, указывающую, что использование динамических ресурсов в сочетании со стилями BasedOn невозможно. Интересно, как кто-то мог это сделать? спасибо

Ответы [ 2 ]

15 голосов
/ 25 февраля 2009

Я думаю, что главная причина - запечатанные объекты. Если у вас есть иерархия стилей:

       Style A
      /       \
  Style A1  Style A2

это не может быть сложным сценарием. Вы ссылаетесь на StyleA, используя динамический ресурс, поэтому всякий раз, когда этот ресурс изменяется, Style A1 и Style A2 должны менять свое свойство BasedOn. Однако, как только стиль используется в вашем приложении, он становится запечатанным объектом. Style A становится неизменным.

Один из возможных способов решения проблемы:

  1. Style A необходимо изменить.
  2. Создайте новый объект Style, который будет новым Style A ресурсом.
  3. Создайте новую версию Style A1 и Style A2. Вам нужно написать процедуру копирования, которая делает копии всех Setters, Resources и т. Д. Установите для BasedOn новую версию Style A.
  4. Обновите коллекцию ресурсов так, чтобы там были три новых стиля.

{DynamicResource StyleA1} и {DynamicResource StyleA2} теперь должны учитывать тот факт, что эти ресурсы изменяются (с шага 4), и автоматически обновлять любые ссылки.

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

Надеюсь, я понял вашу проблему и помог.

14 голосов
/ 17 февраля 2012

Я обнаружил, что, поскольку вы не можете использовать BasedOn на DynamicResource, вы можете "преобразовать" DynamicResource в StaticResource, объединив ResourceDictionary с вашими "родительскими" ресурсами в ваш текущее окно / UserControl / что угодно. Таким образом, теперь вы можете ссылаться на объект ресурса (например, Style), используя StaticResource. Таким образом, вы можете использовать Datatriggers на DynamicResource (через конвертацию).

Пример:

<Window.Resources>
    <ResourceDictionary>
        <ResourceDictionary.MergedDictionaries>
            <ResourceDictionary Source="/MyProject.Styles;component/ButtonStyles.xaml"/>
        </ResourceDictionary.MergedDictionaries>
        [*Your other resources can be put here*]
    </ResourceDictionary>
</Window.Resources>

...

<Button Command="{Binding MyCommandInViewModel, RelativeSource={RelativeSource AncestorType=Window}}">
    <Button.Style>
        <Style BasedOn="{StaticResource StyleFromButtonStyles}" TargetType="Button">
            <Style.Triggers>
                <DataTrigger Binding="{Binding SomeBool}" Value="True">
                    <Setter Property="Button.Content" Value="{StaticResource SomeImage}"/>
                </DataTrigger>
                <DataTrigger Binding="{Binding SomeBool}" Value="False">
                    <Setter Property="Button.Content" Value="{StaticResource SomeOtherImage}"/>
                </DataTrigger>
            </Style.Triggers>
        </Style>
    </Button.Style>
</Button>

Следовательно, Datatriggers применяются к кнопке, стилизованной в импортированном ResourceDictionary.

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

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