Using DrawingVisual Objects
Este tópico fornece uma visão geral de como usar objetos DrawingVisual na camada visual WPF.
Este tópico contém as seguintes seções.
Objeto Visual de Desenho
Contêiner para Hospedagem de DrawingVisual
Criação de Objetos DrawingVisual
Criação de Substituições para Elementos FrameworkElement
Oferecimento de Suporte a Teste de Clique
Tópicos relacionados
Objeto DrawingVisual
A DrawingVisual é uma classe leve utilizada para renderizar formas, imagens ou texto. Esta classe é considerada leve porque não fornece layout ou manipulação de eventos, o que melhora o seu desempenho. Por este motivo, os desenhos são ideais para planos de fundo e clip art.
Contêiner para Hospedagem de DrawingVisual
Para poder usar objetos DrawingVisual, é necessário criar um contêiner para hospedá-los, denominado "contêiner host". O objeto contêiner host deve ser derivado da classe FrameworkElement, que fornece o suporte a layout e manipulação de eventos não fornecido pela classe DrawingVisual. O objeto contêiner host não exibe nenhuma propriedade visível, pois sua principal função é conter objetos filhos. No entanto, a propriedade Visibility do contêiner host deve ser definida como Visible; caso contrário, nenhum de seus elementos filho será visível.
Quando você cria um objeto contêiner para hospedagem de objetos visuais, é necessário armazenar as referências dos objetos visuais em um VisualCollection. Use o método Add para adicionar um objeto visual no contêiner host. No exemplo a seguir, cria-se um objeto contêiner host, e adiciona-se três objetos visuais a seu VisualCollection.
// Create a host visual derived from the FrameworkElement class.
// This class provides layout, event handling, and container support for
// the child visual objects.
public class MyVisualHost : FrameworkElement
{
// Create a collection of child visual objects.
private VisualCollection _children;
public MyVisualHost()
{
_children = new VisualCollection(this);
_children.Add(CreateDrawingVisualRectangle());
_children.Add(CreateDrawingVisualText());
_children.Add(CreateDrawingVisualEllipses());
// Add the event handler for MouseLeftButtonUp.
this.MouseLeftButtonUp += new System.Windows.Input.MouseButtonEventHandler(MyVisualHost_MouseLeftButtonUp);
}
Observação: |
---|
Para obter a amostra de código completo do qual o exemplo de código anterior foi extraído, consulte Teste usando o exemplo de DrawingVisuals de visitas. |
Criação de Objetos DrawingVisual
Quando você cria um objeto DrawingVisual, ele não possui nenhum conteúdo desenhado. Você pode adicionar conteúdo com texto, gráficos, ou imagens ao recuperar o DrawingContext do objeto para desenhar nele. Um DrawingContext é retornado ao chamar o método RenderOpen de um objeto DrawingVisual.
Para desenhar um retângulo no DrawingContext, use o método DrawRectangle do objeto DrawingContext. Existem métodos semelhantes para desenhar outros tipos de conteúdo. Quando você terminar de desenhar conteúdo no DrawingContext, chame o método Close para fechar o DrawingContext e fazer persistir o conteúdo.
No exemplo a seguir, cria-se um objeto DrawingVisual, e desenha-se um retângulo em seu DrawingContext.
// Create a DrawingVisual that contains a rectangle.
private DrawingVisual CreateDrawingVisualRectangle()
{
DrawingVisual drawingVisual = new DrawingVisual();
// Retrieve the DrawingContext in order to create new drawing content.
DrawingContext drawingContext = drawingVisual.RenderOpen();
// Create a rectangle and draw it in the DrawingContext.
Rect rect = new Rect(new System.Windows.Point(160, 100), new System.Windows.Size(320, 80));
drawingContext.DrawRectangle(System.Windows.Media.Brushes.LightBlue, (System.Windows.Media.Pen)null, rect);
// Persist the drawing content.
drawingContext.Close();
return drawingVisual;
}
Criação de Substituições para Elementos FrameworkElement
O objeto contêiner host é responsável pelo gerenciamento de sua coleção de objetos visuais. Isto requer que o contêiner host implemente substituição de membros para a classe FrameworkElement derivada.
A lista a seguir descreve os dois membros que você deve substituir:
GetVisualChild: Retorna um filho no índice especificado da coleção de elementos filhos.
VisualChildrenCount: Obtém o número de elementos filhos visuais dentro deste elemento.
No exemplo a seguir, implementa-se substituições para os dois membros de FrameworkElement.
// Provide a required override for the VisualChildrenCount property.
protected override int VisualChildrenCount
{
get { return _children.Count; }
}
// Provide a required override for the GetVisualChild method.
protected override Visual GetVisualChild(int index)
{
if (index < 0 || index >= _children.Count)
{
throw new ArgumentOutOfRangeException();
}
return _children[index];
}
Oferecimento de Suporte a Teste de Clique
O objeto contêiner host pode fornecer manipulação de eventos mesmo que ele não exiba nenhuma propriedade visível—no entanto, sua propriedade Visibility deve ser definida como Visible. Isto permite que você crie uma rotina de manipulação de eventos para o contêiner host que pode capturar eventos de mouse, tais como o soltar do botão esquerdo do mouse. A rotina de manipulação de eventos pode, então, implementar o teste de clique ao invocar o método HitTest. O parâmetro HitTestResultCallback do método refere-se ao procedimento definido pelo usuário que você pode usar para determinar a ação que resulta de um teste de clique.
No exemplo a seguir, implementa-se suporte a teste de clique para o objeto contêiner host e seus filhos.
// Capture the mouse event and hit test the coordinate point value against
// the child visual objects.
void MyVisualHost_MouseLeftButtonUp(object sender, System.Windows.Input.MouseButtonEventArgs e)
{
// Retreive the coordinates of the mouse button event.
System.Windows.Point pt = e.GetPosition((UIElement)sender);
// Initiate the hit test by setting up a hit test result callback method.
VisualTreeHelper.HitTest(this, null, new HitTestResultCallback(myCallback), new PointHitTestParameters(pt));
}
// If a child visual object is hit, toggle its opacity to visually indicate a hit.
public HitTestResultBehavior myCallback(HitTestResult result)
{
if (result.VisualHit.GetType() == typeof(DrawingVisual))
{
if (((DrawingVisual)result.VisualHit).Opacity == 1.0)
{
((DrawingVisual)result.VisualHit).Opacity = 0.4;
}
else
{
((DrawingVisual)result.VisualHit).Opacity = 1.0;
}
}
// Stop the hit test enumeration of objects in the visual tree.
return HitTestResultBehavior.Stop;
}
Consulte também
Conceitos
Visão Geral sobre Renderização de Gráficos do Windows Presentation Foundation
Hit Testing in the Visual Layer