Visão geral das propriedades anexadasAttached Properties Overview

Uma propriedade anexada é um conceito definido por XAML.An attached property is a concept defined by XAML. Uma propriedade anexada deve ser utilizada como um tipo de propriedade global configurável em qualquer objeto.An attached property is intended to be used as a type of global property that is settable on any object. No Windows Presentation Foundation (WPF)Windows Presentation Foundation (WPF), as propriedades anexadas normalmente são definidas como uma forma especializada de propriedade de dependência que não tem a propriedade “wrapper” convencional.In Windows Presentation Foundation (WPF)Windows Presentation Foundation (WPF), attached properties are typically defined as a specialized form of dependency property that does not have the conventional property "wrapper".

Pré-requisitosPrerequisites

Este tópico pressupõe que você entende as propriedades de dependência da perspectiva de um consumidor de propriedades de dependência existentes em classes Windows Presentation Foundation (WPF)Windows Presentation Foundation (WPF) e leu a Visão geral das propriedades de dependência.This topic assumes that you understand dependency properties from the perspective of a consumer of existing dependency properties on Windows Presentation Foundation (WPF)Windows Presentation Foundation (WPF) classes, and have read the Dependency Properties Overview. Para seguir os exemplos neste tópico, você também deve entender o XAML e saber como escrever aplicativos WPF.To follow the examples in this topic, you should also understand XAML and know how to write WPF applications.

Por que usar propriedades anexadasWhy Use Attached Properties

Uma das finalidades de uma propriedade anexada é permitir que diferentes elementos filho especifiquem valores exclusivos para uma propriedade que, na verdade, é definida em um elemento pai.One purpose of an attached property is to allow different child elements to specify unique values for a property that is actually defined in a parent element. Um aplicativo específico desse cenário é quando elementos filho informam ao elemento pai como devem ser apresentados no UI (interface do usuário)user interface (UI).A specific application of this scenario is having child elements inform the parent element of how they are to be presented in the UI (interface do usuário)user interface (UI). Um exemplo é a propriedade DockPanel.Dock.One example is the DockPanel.Dock property. A propriedade DockPanel.Dock é criada como uma propriedade anexada porque foi projetada para ser definida em elementos que estão contidos em um DockPanel, em vez de DockPanel em si.The DockPanel.Dock property is created as an attached property because it is designed to be set on elements that are contained within a DockPanel, rather than on DockPanel itself. A classe DockPanel define o campo de DependencyProperty estático chamado DockPropertye, em seguida, fornece os métodos GetDock e SetDock como acessadores públicos para a propriedade anexada.The DockPanel class defines the static DependencyProperty field named DockProperty, and then provides the GetDock and SetDock methods as public accessors for the attached property.

Propriedades anexadas em XAMLAttached Properties in XAML

Em XAML, as propriedades anexadas são definidas por meio do uso da sintaxe AttachedPropertyProvider.PropertyNameIn XAML, you set attached properties by using the syntax AttachedPropertyProvider.PropertyName

Veja a seguir um exemplo de como você pode definir DockPanel.Dock em XAML:The following is an example of how you can set DockPanel.Dock in XAML:

<DockPanel>
  <CheckBox DockPanel.Dock="Top">Hello</CheckBox>
</DockPanel>

Observe que o uso é um pouco semelhante a uma propriedade estática; Você sempre referencia o tipo DockPanel que possui e registra a propriedade anexada, em vez de se referir a qualquer instância especificada por nome.Note that the usage is somewhat similar to a static property; you always reference the type DockPanel that owns and registers the attached property, rather than referring to any instance specified by name.

Além disso, como uma propriedade anexada em XAML é um atributo definido na marcação, somente a operação de conjuntos tem alguma relevância.Also, because an attached property in XAML is an attribute that you set in markup, only the set operation has any relevance. Não é possível obter uma propriedade diretamente em XAML, apesar de existirem alguns mecanismos indiretos para comparar valores, como gatilhos em estilos (para mais detalhes, consulte Estilo e modelagem).You cannot directly get a property in XAML, although there are some indirect mechanisms for comparing values, such as triggers in styles (for details, see Styling and Templating).

Implementação de propriedades anexadas no WPFAttached Property Implementation in WPF

Em Windows Presentation Foundation (WPF)Windows Presentation Foundation (WPF), a maioria das propriedades anexadas que existem em tipos do WPF relacionados à apresentação da interface do usuário são implementadas como propriedades de dependência.In Windows Presentation Foundation (WPF)Windows Presentation Foundation (WPF), most of the attached properties that exist on WPF types that are related to UI presentation are implemented as dependency properties. As propriedades anexadas são um conceito XAML, enquanto as propriedades de dependência são um conceito do WPF.Attached properties are a XAML concept, whereas dependency properties are a WPF concept. Como as propriedades anexadas do WPF são propriedades de dependência, elas dão suporte a conceitos de propriedade de dependência, como metadados de propriedade, e valores padrão dos metadados de propriedade.Because WPF attached properties are dependency properties, they support dependency property concepts such as property metadata, and default values from that property metadata.

Como as propriedades anexadas são usadas pelo tipo proprietárioHow Attached Properties Are Used by the Owning Type

Embora as propriedades anexadas possam ser definidas em qualquer objeto, isso não significa, automaticamente, que a definição da propriedade produzirá um resultado tangível ou que o valor será usado por outro objeto.Although attached properties are settable on any object, that does not automatically mean that setting the property will produce a tangible result, or that the value will ever be used by another object. Em geral, as propriedades anexadas são criadas para que os objetos provenientes de uma grande variedade de hierarquias de classe possíveis ou relações lógicas possam reportar informações comuns para o tipo que define a propriedade anexada.Generally, attached properties are intended so that objects coming from a wide variety of possible class hierarchies or logical relationships can each report common information to the type that defines the attached property. O tipo que define a propriedade anexada normalmente segue um destes modelos:The type that defines the attached property typically follows one of these models:

  • O tipo que define a propriedade anexada é concebido para que possa ser o elemento pai dos elementos que definirão valores para a propriedade anexada.The type that defines the attached property is designed so that it can be the parent element of the elements that will set values for the attached property. Em seguida, o tipo itera os objetos filho por meio de lógica interna com relação a algumas estruturas de árvore de objeto, obtém os valores e age sobre eles de alguma maneira.The type then iterates its child objects through internal logic against some object tree structure, obtains the values, and acts on those values in some manner.

  • O tipo que define a propriedade anexada será usado como elemento filho para vários elementos pai e modelos de conteúdo possíveis.The type that defines the attached property will be used as the child element for a variety of possible parent elements and content models.

  • O tipo que define a propriedade anexada representa um serviço.The type that defines the attached property represents a service. Outros tipos definem valores para a propriedade anexada.Other types set values for the attached property. A seguir, quando o elemento que define a propriedade é avaliado no contexto do serviço, os valores da propriedade anexada são obtidos por meio da lógica interna da classe de serviço.Then, when the element that set the property is evaluated in the context of the service, the attached property values are obtained through internal logic of the service class.

Um exemplo de propriedade anexada definida pelo paiAn Example of a Parent-Defined Attached Property

O cenário mais comum em que o WPF define uma propriedade anexada é quando um elemento pai dá suporte a uma coleção de elementos filho e também implementa um comportamento em que as especificidades do comportamento são relatadas individualmente para cada elemento filho.The most typical scenario where WPF defines an attached property is when a parent element supports a child element collection, and also implements a behavior where the specifics of the behavior are reported individually for each child element.

DockPanel define a propriedade anexada DockPanel.Dock e DockPanel tem código de nível de classe como parte de sua lógica de renderização (especificamente, MeasureOverride e ArrangeOverride).DockPanel defines the DockPanel.Dock attached property, and DockPanel has class-level code as part of its rendering logic (specifically, MeasureOverride and ArrangeOverride). Uma instância de DockPanel sempre verificará se algum de seus elementos filho imediatos definiu um valor para DockPanel.Dock.A DockPanel instance will always check to see whether any of its immediate child elements have set a value for DockPanel.Dock. Nesse caso, tais valores se tornam uma entrada para a lógica de renderização aplicada ao elemento filho em questão.If so, those values become input for the rendering logic applied to that particular child element. As instâncias de DockPanel aninhadas tratam suas próprias coleções de elementos filho imediatos, mas esse comportamento é específico da implementação para como o DockPanel processa DockPanel.Dock valores.Nested DockPanel instances each treat their own immediate child element collections, but that behavior is implementation-specific to how DockPanel processes DockPanel.Dock values. Teoricamente, é possível ter propriedades anexadas que influenciam elementos além do pai imediato.It is theoretically possible to have attached properties that influence elements beyond the immediate parent. Se a propriedade anexada DockPanel.Dock for definida em um elemento que não tenha DockPanel elemento pai para agir sobre ela, nenhum erro ou exceção será gerado.If the DockPanel.Dock attached property is set on an element that has no DockPanel parent element to act upon it, no error or exception is raised. Isso simplesmente significa que um valor de propriedade global foi definido, mas não tem um pai de DockPanel atual que possa consumir as informações.This simply means that a global property value was set, but it has no current DockPanel parent that could consume the information.

Propriedades anexadas no códigoAttached Properties in Code

As propriedades anexadas no WPF não têm os métodos "wrapper" do CLR típicos para acesso de Get/Set fácil.Attached properties in WPF do not have the typical CLR "wrapper" methods for easy get/set access. Isso ocorre porque a propriedade anexada não é necessariamente parte do namespace CLR para instâncias em que a propriedade está definida.This is because the attached property is not necessarily part of the CLR namespace for instances where the property is set. No entanto, um processador XAML deve ser capaz de definir esses valores quando o XAML for analisado.However, a XAML processor must be able to set those values when XAML is parsed. Para dar suporte a um uso de Propriedade anexado efetivo, o tipo de proprietário da propriedade anexada deve implementar métodos de acessadores dedicados no formato Get_PropertyName_ e Set_PropertyName_ .To support an effective attached property usage, the owner type of the attached property must implement dedicated accessor methods in the form Get_PropertyName_ and Set_PropertyName_. Esses métodos de acesso dedicados também são úteis para obter ou definir a propriedade anexada em código.These dedicated accessor methods are also useful to get or set the attached property in code. De uma perspectiva de código, uma propriedade anexada é semelhante a um campo de suporte que tem métodos de acesso em vez de acessadores de propriedade; além disso, o campo de suporte pode existir em qualquer objeto, sem precisar ser definido especificamente.From a code perspective, an attached property is similar to a backing field that has method accessors instead of property accessors, and that backing field can exist on any object rather than needing to be specifically defined.

O exemplo a seguir mostra como você pode definir uma propriedade anexada em código.The following example shows how you can set an attached property in code. Neste exemplo, myCheckBox é uma instância da classe CheckBox.In this example, myCheckBox is an instance of the CheckBox class.

DockPanel myDockPanel = new DockPanel();
CheckBox myCheckBox = new CheckBox();
myCheckBox.Content = "Hello";
myDockPanel.Children.Add(myCheckBox);
DockPanel.SetDock(myCheckBox, Dock.Top);
Dim myDockPanel As New DockPanel()
Dim myCheckBox As New CheckBox()
myCheckBox.Content = "Hello"
myDockPanel.Children.Add(myCheckBox)
DockPanel.SetDock(myCheckBox, Dock.Top)

Semelhante ao caso XAML, se myCheckBox ainda não tivesse sido adicionado como um elemento filho de myDockPanel pela terceira linha de código, a quarta linha de código não geraria uma exceção, mas o valor da propriedade não interagiria com um DockPanel pai e, portanto, faria nada.Similar to the XAML case, if myCheckBox had not already been added as a child element of myDockPanel by the third line of code, the fourth line of code would not raise an exception, but the property value would not interact with a DockPanel parent and thus would do nothing. Somente um valor DockPanel.Dock definido em um elemento filho combinado com a presença de um elemento pai DockPanel causará um comportamento efetivo no aplicativo renderizado.Only a DockPanel.Dock value set on a child element combined with the presence of a DockPanel parent element will cause an effective behavior in the rendered application. (Nesse caso, você poderia definir a propriedade anexada e anexar à árvore.(In this case, you could set the attached property, then attach to the tree. Uma alternativa é anexar à árvore e, em seguida, definir a propriedade anexada.Or you could attach to the tree then set the attached property. A ordem das ações gera o mesmo resultado.)Either action order provides the same result.)

Metadados de Propriedade anexadoAttached Property Metadata

Ao registrar a propriedade, FrameworkPropertyMetadata é definido para especificar as características da propriedade, como se a propriedade afeta a renderização, a medida e assim por diante.When registering the property, FrameworkPropertyMetadata is set to specify characteristics of the property, such as whether the property affects rendering, measurement, and so on. Em geral, os metadados de uma propriedade anexada não diferem dos metadados de uma propriedade de dependência.Metadata for an attached property is generally no different than on a dependency property. Se você especificar um valor padrão em uma substituição para metadados da propriedade anexada, esse valor vai se tornar o valor padrão da propriedade anexada implícita em instâncias da classe de substituição.If you specify a default value in an override to attached property metadata, that value becomes the default value of the implicit attached property on instances of the overriding class. Especificamente, o valor padrão será relatado se algum processo consultar o valor de uma propriedade anexada por meio do acessador do método Get para essa propriedade, especificando uma instância da classe em que os metadados foram especificados, e caso o valor dessa propriedade anexada não tenha sido definido de outra maneira.Specifically, your default value is reported if some process queries for the value of an attached property through the Get method accessor for that property, specifying an instance of the class where you specified the metadata, and the value for that attached property was otherwise not set.

Se você desejar habilitar a herança de valor da propriedade em uma propriedade, deverá usar propriedades anexadas em vez de propriedades de dependência não anexadas.If you want to enable property value inheritance on a property, you should use attached properties rather than non-attached dependency properties. Para obter detalhes, consulte Herança do valor da propriedade.For details, see Property Value Inheritance.

Propriedades anexadas personalizadasCustom Attached Properties

Quando criar uma propriedade anexadaWhen to Create an Attached Property

É possível criar uma propriedade anexada quando há um motivo para ter um mecanismo de configuração de propriedade disponível para classes diferentes da classe de definição.You might create an attached property when there is a reason to have a property setting mechanism available for classes other than the defining class. O cenário mais comum para isso é o layout.The most common scenario for this is layout. Os exemplos de propriedades de layout existentes são DockPanel.Dock, Panel.ZIndexe Canvas.Top.Examples of existing layout properties are DockPanel.Dock, Panel.ZIndex, and Canvas.Top. O cenário habilitado aqui é que os elementos que existem como elementos filho para elementos de controle do layout conseguem expressar os requisitos de layout para os elementos pai de layout individualmente, sendo que cada um configura um valor da propriedade que o pai definiu como propriedade anexada.The scenario enabled here is that elements that exist as child elements to layout-controlling elements are able to express layout requirements to their layout parent elements individually, each setting a property value that the parent defined as an attached property.

Outro cenário para usar uma propriedade anexada é quando a classe representa um serviço, e você deseja que classes possam integrar o serviço de forma mais transparente.Another scenario for using an attached property is when your class represents a service, and you want classes to be able to integrate the service more transparently.

Outro cenário é receber suporte ao designer do WPF do Visual Studio, como a edição da janela Propriedades .Yet another scenario is to receive Visual Studio WPF Designer support, such as Properties window editing. Para obter mais informações, consulte Visão geral da criação de controle.For more information, see Control Authoring Overview.

Como mencionado anteriormente, será necessário registrar como propriedade anexada se você quiser usar a herança de valor da propriedade.As mentioned before, you should register as an attached property if you want to use property value inheritance.

Como criar uma propriedade anexadaHow to Create an Attached Property

Se sua classe estiver definindo a propriedade anexada estritamente para uso em outros tipos, a classe não precisará derivar de DependencyObject.If your class is defining the attached property strictly for use on other types, then the class does not have to derive from DependencyObject. Mas você precisa derivar de DependencyObject se você seguir o modelo do WPF geral de ter sua propriedade anexada também é uma propriedade de dependência.But you do need to derive from DependencyObject if you follow the overall WPF model of having your attached property also be a dependency property.

Defina a propriedade anexada como uma propriedade de dependência declarando um campo public static readonly do tipo DependencyProperty.Define your attached property as a dependency property by declaring a public static readonly field of type DependencyProperty. Você define esse campo usando o valor de retorno do método RegisterAttached.You define this field by using the return value of the RegisterAttached method. O nome do campo deve corresponder ao nome da propriedade anexada, acrescentado com a cadeia de caracteres Property, para seguir o padrão WPF estabelecido de nomear os campos de identificação versus as propriedades que eles representam.The field name must match the attached property name, appended with the string Property, to follow the established WPF pattern of naming the identifying fields versus the properties that they represent. O provedor de propriedades anexada também deve fornecer os métodos estáticos de Get_PropertyName_ e Set_PropertyName_ como acessadores para a propriedade anexada; a falha em fazer isso fará com que o sistema de propriedades não possa usar sua propriedade anexada.The attached property provider must also provide static Get_PropertyName_ and Set_PropertyName_ methods as accessors for the attached property; failing to do this will result in the property system being unable to use your attached property.

Observação

Se você omitir o acessador get da propriedade anexada, a vinculação de dados na propriedade não funcionará em ferramentas de design, como o Visual Studio e o Blend para Visual Studio.If you omit the attached property's get accessor, data binding on the property will not work in design tools, such as Visual Studio and Blend for Visual Studio.

O acessador getThe Get Accessor

A assinatura para o acessador de Get_PropertyName_ deve ser:The signature for the Get_PropertyName_ accessor must be:

public static object GetPropertyName(object target)

  • O objeto target pode ser especificado como um tipo mais específico na sua implementação.The target object can be specified as a more specific type in your implementation. Por exemplo, o método DockPanel.GetDock digita o parâmetro como UIElement, porque a propriedade anexada destina-se apenas a ser definida em instâncias de UIElement.For example, the DockPanel.GetDock method types the parameter as UIElement, because the attached property is only intended to be set on UIElement instances.

  • O valor retornado pode ser especificado como um tipo mais específico na sua implementação.The return value can be specified as a more specific type in your implementation. Por exemplo, o método GetDock o digita como Dock, porque o valor só pode ser definido para essa enumeração.For example, the GetDock method types it as Dock, because the value can only be set to that enumeration.

O acessador setThe Set Accessor

A assinatura para o acessador de Set_PropertyName_ deve ser:The signature for the Set_PropertyName_ accessor must be:

public static void SetPropertyName(object target, object value)

  • O objeto target pode ser especificado como um tipo mais específico na sua implementação.The target object can be specified as a more specific type in your implementation. Por exemplo, o método SetDock o digita como UIElement, porque a propriedade anexada destina-se apenas a ser definida em instâncias de UIElement.For example, the SetDock method types it as UIElement, because the attached property is only intended to be set on UIElement instances.

  • O objeto value pode ser especificado como um tipo mais específico na sua implementação.The value object can be specified as a more specific type in your implementation. Por exemplo, o método SetDock o digita como Dock, porque o valor só pode ser definido para essa enumeração.For example, the SetDock method types it as Dock, because the value can only be set to that enumeration. Lembre-se de que o valor para esse método é a entrada proveniente do carregador de XAML, quando ele encontra a propriedade anexada em um uso da propriedade anexada na marcação.Remember that the value for this method is the input coming from the XAML loader when it encounters your attached property in an attached property usage in markup. Essa entrada é o valor especificado como um valor de atributo XAML na marcação.That input is the value specified as a XAML attribute value in markup. Portanto, deve haver conversão de tipo, serializador de valores ou suporte à extensão de marcação para o tipo que usar, de modo que o tipo adequado possa ser criado por meio do valor do atributo (que é, basicamente, apenas uma cadeia de caracteres).Therefore there must be type conversion, value serializer, or markup extension support for the type you use, such that the appropriate type can be created from the attribute value (which is ultimately just a string).

O exemplo a seguir mostra o registro de propriedade de dependência (usando o método RegisterAttached), bem como os acessadores Get_PropertyName_ e Set_PropertyName_ .The following example shows the dependency property registration (using the RegisterAttached method), as well as the Get_PropertyName_ and Set_PropertyName_ accessors. No exemplo, o nome da propriedade anexada é IsBubbleSource.In the example, the attached property name is IsBubbleSource. Portanto, os acessadores devem ser nomeados como GetIsBubbleSource e SetIsBubbleSource.Therefore, the accessors must be named GetIsBubbleSource and SetIsBubbleSource.

public static readonly DependencyProperty IsBubbleSourceProperty = DependencyProperty.RegisterAttached(
  "IsBubbleSource",
  typeof(Boolean),
  typeof(AquariumObject),
  new FrameworkPropertyMetadata(false, FrameworkPropertyMetadataOptions.AffectsRender)
);
public static void SetIsBubbleSource(UIElement element, Boolean value)
{
  element.SetValue(IsBubbleSourceProperty, value);
}
public static Boolean GetIsBubbleSource(UIElement element)
{
  return (Boolean)element.GetValue(IsBubbleSourceProperty);
}
Public Shared ReadOnly IsBubbleSourceProperty As DependencyProperty = DependencyProperty.RegisterAttached("IsBubbleSource", GetType(Boolean), GetType(AquariumObject), New FrameworkPropertyMetadata(False, FrameworkPropertyMetadataOptions.AffectsRender))
Public Shared Sub SetIsBubbleSource(ByVal element As UIElement, ByVal value As Boolean)
    element.SetValue(IsBubbleSourceProperty, value)
End Sub
Public Shared Function GetIsBubbleSource(ByVal element As UIElement) As Boolean
    Return CType(element.GetValue(IsBubbleSourceProperty), Boolean)
End Function

Atributos de propriedade anexadaAttached Property Attributes

O WPF define vários atributos .NET que se destinam a fornecer informações sobre propriedades anexadas a processos de reflexão e a usuários típicos de informações de reflexão e propriedade, como designers.WPF defines several .NET attributes that are intended to provide information about attached properties to reflection processes, and to typical users of reflection and property information such as designers. Como as propriedades anexadas têm um tipo de escopo ilimitado, os designers precisam de uma maneira de evitar sobrecarregar os usuários com uma lista global de todas as propriedades anexadas que são definidas em uma implementação de tecnologia específica que usa XAML.Because attached properties have a type of unlimited scope, designers need a way to avoid overwhelming users with a global list of all the attached properties that are defined in a particular technology implementation that uses XAML. Os atributos do .NET que o WPF define para propriedades anexadas podem ser usados para definir o escopo das situações em que uma determinada propriedade anexada deve ser mostrada em uma janela de propriedades.The .NET attributes that WPF defines for attached properties can be used to scope the situations where a given attached property should be shown in a properties window. Você também pode considerar a possibilidade de aplicar esses atributos para suas próprias propriedades anexadas personalizadas.You might consider applying these attributes for your own custom attached properties also. A finalidade e a sintaxe dos atributos do .NET são descritas nas páginas de referência apropriadas:The purpose and syntax of the .NET attributes is described on the appropriate reference pages:

Aprendendo mais sobre propriedades anexadasLearning More About Attached Properties

  • Para obter mais informações sobre como criar uma propriedade anexada, consulte Registrar uma propriedade anexada.For more information on creating an attached property, see Register an Attached Property.

  • Para ver mais cenários de uso avançados para as propriedades de dependência e as propriedades anexadas, consulte Propriedades de dependência personalizada.For more advanced usage scenarios for dependency properties and attached properties, see Custom Dependency Properties.

  • Também é possível registrar uma propriedade como propriedade anexada e como propriedade de dependência, mas ainda expor implementações de “wrapper”.You can also register a property as an attached property, and as a dependency property, but then still expose "wrapper" implementations. Nesse caso, a propriedade pode ser definida nesse elemento ou em qualquer elemento por meio da sintaxe de propriedade anexada XAML.In this case, the property can be set either on that element, or on any element through the XAML attached property syntax. Um exemplo de uma propriedade com um cenário apropriado para usos padrão e anexados é FrameworkElement.FlowDirection.An example of a property with an appropriate scenario for both standard and attached usages is FrameworkElement.FlowDirection.

Consulte tambémSee also