WPF 中Canvas图形绘制之DrawingContext绘图(二)

图形的绘制有多种,本文采用DrawingContext。

1、定义接口

public interface iDrawingVisualSignal
{
	/// <summary>
	/// 基点
	/// </summary>
	Point ptBase { get; set; }
}

2、定义图元类,实现图元内部图形的绘制

public class DV_TrackLine : FrameworkElement, iDrawingVisualSignal
{
    #region 接口属性
    public Point ptBase { get; set; }
    #endregion
    private double iLength = 40;
    private double iScale = 1;
    public bool bSelected = false;
    public bool bHit = false;
    int iMarginX = 10;  
    TrackLine _trackLine = new TrackLine();
    public DV_TrackLine(TrackLine signalLamp)
    {
        _trackLine = signalLamp;
        iLength = Convert.ToInt32(ConfigurationManager.AppSettings["TrackLineLength"]);
        iScale = Convert.ToInt32(ConfigurationManager.AppSettings["TrackLineScale"]);
    }
    protected override void OnRender(DrawingContext drawingContext)
    {
        base.OnRender(drawingContext); 

        Pen pen1 = new Pen(bSelected || bHit ? Brushes.White : Brushes.Red, bSelected || bHit ? 4f : 1f);
        pen1.Freeze();  //冻结画笔,这样能加快绘图速度

		// 绘制直线
        drawingContext.DrawLine(pen1, new Point(0, 0), ptConnect);
		// 绘制文本
        FormattedText text = new FormattedText("S1", CultureInfo.CurrentCulture, FlowDirection.LeftToRight, new Typeface("Tahoma"), 16 * 1, Brushes.White, 1);
        double de = text.Width / 2.0;
        double dew = text.Height + 4;

        Point ptT = new Point(ptConnect.X/2 - de, -dew);
        drawingContext.DrawText(text, ptT);

    }
}

图元类的图形绘制,在OnRender重载函数中实现,绘制的坐标系与canvas相同。接口中定义的ptBase,主要是用于确定图元对象在canvas画布中的位置。

3、图元类的实例化

定义了一个单体类,用于存放所有的图元,下面的代码作为示例,只是创建一个图元。

public class TrainSingalService : SingletonNetcore<TrainSingalService>
{
	public TrainSingalService()
	{
		lstSignal.Clear();
	}
	public void Regen(Canvas canvas, double dpi)
	{
		var t12 = new DV_TrackLine(new TrackLine());
		t12.ptBase = new Point(100, 100);
		canvas.Children.Add(t12);

		Canvas.SetTop(t12, t12.ptBase.X);
		Canvas.SetLeft(t12, t12.ptBase.Y);
	}
}

创建DV_TrackLine类实例后,将其在Canvas中的定位坐标保存在ptBase中,并通过SetTop和SetLeft函数定位。

在MainWindow类中,调用单体类,传入canvas对象,实现图元的绘制。

 private void RegenGeometry()
        {
            canvas.Reset();
            double dpi = VisualTreeHelper.GetDpi(this).PixelsPerDip;
            TrainSingalService.Instance.Regen(canvas, dpi);
        }

4、图元类的复位

图元移动后,其在canvas中的位置也需要复位,在PanAndZoomCanvas类的Reset()函数改造如下

public void Reset()
{
    Zoomfactor = 1.1f;

    foreach (UIElement child in this.Children)
    {
        // 恢复缩放比例
        child.RenderTransform = Transform.Identity;
        // 恢复初始位置
        iDrawingVisualSignal iDrawing = child as iDrawingVisualSignal;
        Canvas.SetTop(child, iDrawing.ptBase.X);
        Canvas.SetLeft(child, iDrawing.ptBase.Y);
    }
}

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值