2010-11-18 73 views
5

我有一个自定义的线型,使用装饰者在该线中间显示一个数组和一些文本。装饰元素上的装饰者和事件

alt text

的问题是,所述装饰行为独立于佐餐的元素,并且不“转移”事件给它。在下面的代码中,我不得不手动将装饰元素重新链接到装饰元素(ta.MouseLeftButtonDown += Adorner_MouseLeftButtonDown;),但不幸的是,即使这不起作用... 有人可能会建议什么是错误的时候调用this.OnMouseLeftButtonDown,为什么我没有收到各自的事件?

public class SegmentLine : Shape 
{ 
    AdornerLayer aLayer; 

    public static readonly DependencyProperty X1Property; 
    public static readonly DependencyProperty X2Property; 
    public static readonly DependencyProperty Y1Property; 
    public static readonly DependencyProperty Y2Property; 
    ... 

    static SegmentLine() { 
     X1Property = DependencyProperty.Register("X1", typeof(double), typeof(SegmentLine), new FrameworkPropertyMetadata(double.NaN, 
      FrameworkPropertyMetadataOptions.AffectsRender)); 
     X2Pro... 
    } 

    public SegmentLine() 
     : base() 
    { 
     this.Loaded += SegmentLine_Loaded; 
    } 

    void SegmentLine_Loaded(object sender, RoutedEventArgs e) 
    { 
     aLayer = AdornerLayer.GetAdornerLayer(this); 
     if (aLayer != null) 
     { 
      TextAdorner ta = new TextAdorner(this); 
      //ta.IsHitTestVisible = false; 
      ta.MouseLeftButtonDown += Adorner_MouseLeftButtonDown; 
      aLayer.Add(ta); 
     } 
    } 

    void Adorner_MouseLeftButtonDown(object sender, System.Windows.Input.MouseButtonEventArgs e) 
    { 
     // !! try to rise the MouseLeftButtonDown event 
     this.OnMouseLeftButtonDown(e); 
    } 

    protected override void OnRender(DrawingContext drawingContext) 
    { 
     base.OnRender(drawingContext); 
     if (aLayer != null) 
      aLayer.Update(); 
    } 

    class TextAdorner : Adorner 
    { 
     public TextAdorner(UIElement adornedElement) 
      : base(adornedElement) { } 

     protected override void OnRender(DrawingContext drawingContext) 
     { 
      // ADD LABEL ... 
      FormattedText ft = new FormattedText(...); 
      drawingContext.DrawText(ft, midPoint); 

      // Add ARROW ... 
      var myPathGeometry = new PathGeometry { Figures = myPathFigureCollection };    
      drawingContext.DrawGeometry(Brushes.Black, null, myPathGeometry); 
     } 
    } 

    protected override System.Windows.Media.Geometry DefiningGeometry 
    { 
     get 
     { 
      var geometryGroup = new GeometryGroup(); 
      // Add line 
      geometryGroup.Children.Add(new LineGeometry(new Point(X1, Y1), new Point(X2, Y2))); 
      return geometryGroup; 
     } 
    }  
} 
+1

只需将'IsHitTestVisible'设置为false,即可禁用adorner上的所有事件。或者你想让一些事件由'SegmentLine'由adorner和其他人处理? – 2010-11-18 12:56:14

+0

@ alpha-mouse:不,任何事件我都想要由adorner来处理,但是如果我只是设置IsHitTestVisible = false(因为您可以在代码中看到它的评论),我根本没有收到任何事件。 – serhio 2010-11-18 16:26:27

回答

5

你应该叫的this.RaiseEvent(e);,而不是this.OnMouseLeftButtonDown(e);的事件转移到佐餐元素。
顺便说一句,你可以只用一个事件处理程序来传输多个事件类型

void SegmentLine_Loaded(object sender, RoutedEventArgs e) 
{ 
    .. 
    ta.MouseLeftButtonDown += Adorner_AnyEvent; 
    ta.MouseRightButtonDown += Adorner_AnyEvent; 
} 

void Adorner_AnyEvent(object sender, RoutedEventArgs e) 
{ 
    this.RaiseEvent(e); 
} 
1

我知道这是旧的,但我也有类似的问题(不接收装饰器事件),我固定通过绘制在我的OnRender中透明背景()

drawingContext.DrawRectangle(Brushes.Transparent, null, viewRect); 

没有背景=没有事件。