Как назначить ресурсы WPF другим тегам ресурсов - PullRequest
9 голосов
/ 14 июня 2010

Это довольно неясно, я могу просто упустить что-то очень простое.

Сценарий 1

Допустим, я создаю градиентную кисть, как показано в разделе <Window.Resources>:

<LinearGradientBrush x:Key="GridRowSelectedBackBrushGradient" StartPoint="0,0" EndPoint="0,1">
    <GradientStop Color="#404040" Offset="0.0" />
    <GradientStop Color="#404040" Offset="0.5" />
    <GradientStop Color="#000000" Offset="0.6" />
    <GradientStop Color="#000000" Offset="1.0" />
</LinearGradientBrush>

Затем, намного позже, я хочу переопределить HighlightBrushKey для DataGrid. Я в основном сделал это так (ужасно);

<LinearGradientBrush x:Key="{x:Static SystemColors.HighlightBrushKey}"
                     GradientStops="{Binding Source={StaticResource GridRowSelectedBackBrushGradient}, Path=GradientStops}"
                     StartPoint="{Binding Source={StaticResource GridRowSelectedBackBrushGradient}, Path=StartPoint}"
                     EndPoint="{Binding Source={StaticResource GridRowSelectedBackBrushGradient}, Path=EndPoint}" />

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

Сценарий 2

Скажем, я создал два цвета в моей <Window.Resources> разметке, вот так:

<SolidColorBrush x:Key="DataGridRowBackgroundBrush" Color="#EAF2FB" />
<SolidColorBrush x:Key="DataGridRowBackgroundAltBrush" Color="#FFFFFF" />

Затем я хочу добавить их в массив, который передает ConverterParameter в привязку, чтобы я мог предоставить пользовательскому конвертеру мои экземпляры статического ресурса:

<Setter Property="Background">
    <Setter.Value>
        <Binding RelativeSource="{RelativeSource Mode=Self}" 
                 Converter="{StaticResource BackgroundBrushConverter}">
            <Binding.ConverterParameter>
                <x:Array Type="{x:Type Brush}">
                    <SolidColorBrush Color="{Binding Source={StaticResource DataGridRowBackgroundBrush}, Path=Color}" />
                    <SolidColorBrush Color="{Binding Source={StaticResource DataGridRowBackgroundAltBrush}, Path=Color}" />
                </x:Array>
            </Binding.ConverterParameter>
        </Binding>
    </Setter.Value>
</Setter>

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

Поскольку теперь я решил эту проблему хотя бы дважды, есть ли лучший способ?

Спасибо, Том

Ответы [ 2 ]

10 голосов
/ 16 июня 2010

Мне было интересно, когда кто-то собирается спросить об этом.

Что вы хотите сделать в сценарии 1, так это эффективно дать одному ресурсу «псевдоним».Это легко сделать с помощью разметки, которая кажется очевидной только после того, как вы ее увидите.Предположим, у нас есть это в нашем App.xaml или где-то:

<ResourceDictionary>
  <LinearGradientBrush x:Key="GridRowSelectedBackBrushGradient" ... />
</ResourceDictionary>

Чтобы включить псевдоним в другой ResourceDictionary, просто:

<ResourceDictionary>
  <StaticResourceExtension x:Key="{x:Static SystemColors.HighlightBrushKey}"
                           ResourceKey="GridRowSelectedBackBrushGradient" />
</ResourceDictionary>

Это ищет объект кисти в первом ResourceDictionaryи добавляет тот же объект ко второму ResourceDictionary под новым ключом.Это также работает в пределах одного ResourceDictionary.

Для вашего сценария 2 решение так же просто:

<Binding.ConverterParameter>
  <x:Array Type="{x:Type Brush}">
    <StaticResourceExtension ResourceKey="DataGridRowBackgroundBrush" />
    <StaticResourceExtension ResourceKey="DataGridRowBackgroundAltBrush" />
  </x:Array>
</Binding.ConverterParameter>

Опять добавляются фактические Brush объекты, найденные с помощью ResourceKeyнепосредственно в массив Brush[].Никакого нового Brush не создается.

Я думаю, что мы все настолько привыкли к использованию StaticResourceExtension с синтаксисом расширения разметки (например, {StaticResource Xyz}), что легко забыть, что его также можно использовать с обычнымисинтаксис элемента.

0 голосов
/ 14 июня 2010

Разметка, с которой вы работаете, недостаточно высока.Вы не создаете LinearGradientBrush, ваш первый пример: вы просто ссылаетесь на ресурс.Например:

<DataGrid HighlightBrushKey="{StaticResource GridRowSelectedBackBrushGradient}"  ....

Во втором примере я бы сказал, что вы хотите объявить массив как ресурс:

<x:Array Type="{x:Type Brush}" x:Key="MyArray">
  <SolidColorBrush Color="#EAF2FB" />
  <SolidColorBrush Color="#FFFFFF" />
</x:Array>

И затем выможно использовать

<Binding RelativeSource="{RelativeSource Mode=Self}" 
         Converter="{StaticResource BackgroundBrushConverter}"
         ConverterParameter="{Staticresource MyArray}" />
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...