2009-11-07 2 views
1

У меня есть существующий элемент, который является дочерним элементом холста. Стиль элемента содержится в словаре ресурсов, который содержит различные кисти, которые можно использовать для окраски элемента.Управление обновлением WPF на месте Использование XAMLReader

Когда экземпляр элемента создан, он получает расцветку по умолчанию. Я в настоящее время не в состоянии взаимодействовать непосредственно со свойством Заливка как в:

item.Fill = BrushBlue; 

По этой причине я начал смотреть на XAML для каждого экземпляра элемента.

Части XAML Я заинтересован в артикулы после создания экземпляра является:

<d:Item IsSelected="True" Width="78" Height="65" Panel.ZIndex="0" Canvas.Left="233"  Canvas.Top="352.54"> 
    <Path ToolTip="Process"> 
     <Path.Style> 
      <Style TargetType="Path"> 
       <Style.BasedOn> 
        <Style TargetType="Path"> 
         <Style.Resources> 
          <ResourceDictionary /> 
         </Style.Resources> 
         <Setter Property="Shape.Fill"> 
          <Setter.Value> 
           <DynamicResource ResourceKey="ItemBrush" /> 
          </Setter.Value> 
         </Setter> 
        </Style> 
       </Style.BasedOn> 
      </Style> 
     </Path.Style> 
    </Path> 
. 
. 
. 
</d:Item> 

Я бы в идеале хотелось бы иметь возможность связать значение Shape.Fill свойства экземпляра элемента , или, по крайней мере, иметь возможность изменить это значение на основе выбора пользователя в приложении.

Я редактирую XAML элемента, чтобы изменить его цвет заливки. Для этого я использую следующий код, на основе выборки кнопки клона из MSDN:

string savedItem = XamlWriter.Save(this) as String; 

string newItem = savedItem.Replace(GetFillBrush(this), "BrushBlue"); 
SetFillBrush(this, "BrushBlue"); 

StringReader stringReader = new StringReader(newItem); 
XmlReader xmlReader = XmlReader.Create(stringReader); 

thisCanvas.Children.Add((Item)XamlReader.Load(xmlReader)); 

Я получаю XAML, обновление имени кисти ресурса, а затем генерировать новый элемент.

Этот подход является доказательством концепции. Я хочу иметь возможность обновлять XAML существующего элемента без необходимости создания нового элемента на холсте.

Каков наилучший способ выполнить это обновление «на месте» свойства заполнения объекта?

ответ

2

Я полагаю, что кисть используется более чем в одном месте, поэтому вы не можете просто установить свойство Fill:

item.Fill = Brushes.Blue; 

В таком случае, что вы должны сделать, это инкапсулировать деталь в UserControl или настраиваемый элемент управления, с свойством зависимости типа Brush. (В зависимости от использования кисти вы также можете вызвать этот Fill, или это может быть более конкретным, например, AccentFill, OuterBorderFill и т. Д.). Затем в вашем XAML свяжите все эти множественные вхождения кисти с этим свойством. Теперь вы сделать есть единственное место, где вы можете установить свойство, и через привязки она будет распространяться на все места, это необходимо:

item.AccentFill = Brushes.Blue; 

В любом случае, самое главное, что не думать о том, «обновление XAML существующего элемента». XAML - это формат сериализации. Ваш существующий элемент уже является объектом .NET в памяти, и вы можете напрямую установить его свойства, а не перезагружать его из сериализованной формы.

+0

Кисть в настоящее время используется только в одном месте, однако в настоящее время я не могу получить доступ к объекту недвижимости напрямую. Я добавил дополнительную информацию о текущей настройке стиля элемента. – amarcy

+0

Метод привязки должен работать с вашим кодом из того, что я вижу. Объявите свойство зависимостей Fill в классе Item и измените ваш сеттер на . (Обратите внимание на RelativeSource, чтобы стиль Path выглядел для свойства Fill на прилагаемом элементе.) Затем вы можете установить item.Fill в свой код, и привязка обнаружит изменение. – itowlson

+0

Когда я меняю установщик на указанное выше значение, он выдает следующую ошибку: «Строка AncestorType {x: Тип d: Item} 'не может быть преобразована в объект типа« System.Windows.Data.RelativeSourceMode ». AncestorType { x: Тип d: Item} не является допустимым значением для RelativeSourceMode. " Любые советы? – amarcy

0

Если я не понимаю ваш вопрос, вы делаете это действительно. Почему бы не работать?

this.Fill = Brushes.Blue; 

или, если это важно, чтобы использовать имя ресурса:

this.Fill = (Brush)FindResource("BlueBrush") 

Может быть, вам нужно уточнить ваш вопрос, чтобы объяснить, почему вы не можете просто установить значение и сделать с ней.

+0

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

+0

Вы можете назвать его и использовать FindName(), но для вашей ситуации я рекомендую привязку. См. Ответ itowlson для деталей. –