我希望能够利用文本块的顶部,并找到了一种方法,但是一旦图纸就无法删除。这是代码。

   public class DerivedTextBlock : TextBlock {

      public Boolean DrawExtra {
         get { return (Boolean)GetValue(DrawExtraProperty); }
         set { SetValue(DrawExtraProperty, value); }
      }

      // Using a DependencyProperty as the backing store for DrawExtra.  This enables animation, styling, binding, etc...
      public static readonly DependencyProperty DrawExtraProperty =
          DependencyProperty.Register("DrawExtra", typeof(Boolean), typeof(DerivedTextBlock), new FrameworkPropertyMetadata(false, FrameworkPropertyMetadataOptions.AffectsRender | FrameworkPropertyMetadataOptions.AffectsArrange));

      public DrawingVisual DrawingVisual { get; set; }

      public DerivedTextBlock() {
         DrawingVisual = this.CreateDrawingVisualRectangle();
      }

      protected override int VisualChildrenCount {
         get {
            //if we want to draw our extra info, add one to
            // our visualChildrenCount, usually with a textblock it is 0
            if (DrawExtra) {
               return base.VisualChildrenCount + 1;
            }
            else {
               return base.VisualChildrenCount;
            }
         }
      }

      protected override Visual GetVisualChild(int index) {
         return DrawingVisual;
      }

      // 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 Point(10.0, 0), new Size(10.0 / 2.0, 10));
         drawingContext.DrawRectangle(Brushes.LightBlue, (Pen)null, rect);

         // Persist the drawing content.
         drawingContext.Close();

         return drawingVisual;
      }
   }

我要这样做的原因:我们有一个带有许多单元格的数据,每个单元格显示了文本。我们在单元格上显示了一些验证信息,并通过使用带有文本块的模板和网格中的一些hosten路径来执行此操作。它的开销为视觉树增添了额外的元素,当我们必须重新绘制(在加载,切换窗口或某种方面)时,它需要更长的时间,而视觉树中的元素越多。当它只是一个文本块时,它比拥有网格的控件快于1/3-1/2。因此,我们想在文本框顶部绘制验证内容。

有帮助吗?

解决方案

您的问题是:

  1. getVisualChild()应返回base.getVisualChild(index),除非index == base.visualChildRencount。
  2. 您忘了在DrawsExtra变为true或DrawsVisual更改时忘记调用AddVisualChild()
  3. 您忘了调用dracterextra变为false或drausthvisual更改时调用removevisualChild()

您可以通过在DrawingExtra上设置属性ChangedCallback并将代码添加到DrawsVisual的设置中来修复#2和#3。

说明:实际上将视觉添加到树上的是AddVisualChild()调用。发生的事情是,由于您在getVisualChild()中的错误,您的视觉效果被发现并显示出“偶然”,但是它没有正确地链接到视觉树中,因此您会遇到许多问题。

更新

我如上所述编辑了您的代码,并且效果很好。这是更改:

...
      {
        PropertyChangedCallback = (obj, e) =>
          {
            var textBlock = (DerivedTextBlock)obj;
            if((bool)e.OldValue) textBlock.RemoveVisualChild(textBlock.DrawingVisual);
            if((bool)e.NewValue) textBlock.AddVisualChild(textBlock.DrawingVisual);
          }
      });

  public DrawingVisual DrawingVisual
  {
    get { return _drawingVisual; }
    set
    {
      if(DrawExtra) RemoveVisualChild(_drawingVisual);
      _drawingVisual = value;
      if(DrawExtra) AddVisualChild(_drawingVisual);
    }
  }
  private DrawingVisual _drawingVisual;

...

  protected override int VisualChildrenCount
  {
    get { return base.VisualChildrenCount + (DrawExtra ? 1 : 0); }
  }

  protected override Visual GetVisualChild(int index)
  {
    return index==base.VisualChildrenCount ? DrawingVisual : base.GetVisualChild(index);
  }
许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top