WPF中的可视化对象

1. 绘制可视化对象

using System.Collections.Generic;
using System.Windows.Controls;
using System.Windows.Media;

namespace 项目10 {
    class MyPanel:Panel
    {
        private List<Visual> visuals=new List<Visual>();

        protected override Visual GetVisualChild(int index)
        {
            return visuals[index];
        }

        protected override int VisualChildrenCount
        {
            get { return visuals.Count; }
        }

        public void AddVisual(Visual visual)
        {
            visuals.Add(visual);
            base.AddLogicalChild(visual);
            base.AddVisualChild(visual);
        }
    }
}
  1. 在XAML中调用MyPanel
<Window x:Class="项目10.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:sys="clr-namespace:System;assembly=mscorlib"
        xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactivity"
        xmlns:local="clr-namespace:项目10"
        mc:Ignorable="d"
        Title="MainWindow" Width="750" Height="350"  WindowStartupLocation="CenterScreen"
        Loaded="Window_Loaded">
    <local:MyPanel x:Name="MyPanel1">

    </local:MyPanel>
</Window>
  1. 添加Loaded事件

    using System.Windows;
    using System.Windows.Media;
    
    namespace 项目10 {
        /// <summary>
        /// MainWindow.xaml 的交互逻辑
        /// </summary>
        public partial class MainWindow : Window {
            public MainWindow()
            {
                InitializeComponent();
    
            }
    
            private void Window_Loaded(object sender, RoutedEventArgs e)
            {
                DrawingVisual dv=new DrawingVisual();
                DrawingContext dc = dv.RenderOpen();
                Brush brush = Brushes.LightGreen;
                Pen drawingPen=new Pen(Brushes.SteelBlue,3);
                dc.DrawRectangle(brush,drawingPen,new Rect(new Point(100,100),new Size(50,100)));
                dc.DrawEllipse(brush, drawingPen, new Point(400,150), 100,120);
                dc.DrawLine(drawingPen,new Point(0,50), new Point(50,0) );
                dc.DrawLine(drawingPen,new Point(50,0), new Point(100,50) );
                dc.DrawLine(drawingPen,new Point(0,50), new Point(100,50) );
                dc.Close();
                MyPanel1.AddVisual(dv);
            }
        }
    }
    

WPF中的命中测试

using System.Collections.Generic;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Media;

namespace 项目10 {
    class MyPanel:Panel
    {
        private List<Visual> visuals=new List<Visual>();

        protected override Visual GetVisualChild(int index)
        {
            return visuals[index];
        }

        protected override int VisualChildrenCount
        {
            get { return visuals.Count; }
        }

        public void AddVisual(Visual visual)
        {
            visuals.Add(visual);
            base.AddLogicalChild(visual);
            base.AddVisualChild(visual);
        }

        public void DeleteVisual(Visual visual)
        {
            visuals.Remove(visual);
            base.RemoveVisualChild(visual);
            base.RemoveLogicalChild(visual);
        }
        public DrawingVisual GetVisual(Point point)
        {
            HitTestResult hitTestResult = VisualTreeHelper.HitTest(this, point);
            if (hitTestResult != null)
                return hitTestResult.VisualHit as DrawingVisual;
            return null;
        }
    }
}
  using System.Windows;
  using System.Windows.Media;

  namespace 项目10 {
      /// <summary>
      /// MainWindow.xaml 的交互逻辑
      /// </summary>
      public partial class MainWindow : Window {
          public MainWindow()
          {
              InitializeComponent();

          }

          private void Window_MouseLeftButtonDown(object sender, System.Windows.Input.MouseButtonEventArgs e)
          {
              Point pointClicked = e.GetPosition(MyPanel1);
              DrawingVisual visual=new DrawingVisual();
              DrawSquare(visual,pointClicked);
              MyPanel1.AddVisual(visual);
          }

          private void DrawSquare(DrawingVisual visual, Point topleftCorner)
          {
              DrawingContext dc = visual.RenderOpen();
              Brush brush = Brushes.LightGreen;
              Pen dPen=new Pen(Brushes.SteelBlue,3);
              dc.DrawRectangle(brush,dPen,new Rect(topleftCorner,new Size(150,150)));
              dc.Close();
          }

          private void Window_MouseRightButtonDown(object sender, System.Windows.Input.MouseButtonEventArgs e)
          {
              Point pointClicked = e.GetPosition(MyPanel1);
              DrawingVisual visual = MyPanel1.GetVisual(pointClicked);
              if (visual!=null)
              {
                  MyPanel1.DeleteVisual(visual);
              }
          }
      }
  }