首页 > 其他分享 >WPF customize line with sharp arrow and direction

WPF customize line with sharp arrow and direction

时间:2024-08-16 20:26:54浏览次数:5  
标签:direction customize double System typeof arrow new using public

//Customize LineArrow
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Media;
using System.Windows.Shapes;
using System.Windows;

namespace WpfApp249
{
    public sealed class LineArrow : Shape
    {
        public static readonly DependencyProperty X1Property = 
            DependencyProperty.Register("X1", typeof(double), typeof(LineArrow), new PropertyMetadata(0.0));
        public static readonly DependencyProperty Y1Property =
            DependencyProperty.Register("Y1", typeof(double), typeof(LineArrow), new PropertyMetadata(0.0));
        public static readonly DependencyProperty X2Property =
            DependencyProperty.Register("X2", typeof(double), typeof(LineArrow), new PropertyMetadata(0.0));
        public static readonly DependencyProperty Y2Property =
            DependencyProperty.Register("Y2", typeof(double), typeof(LineArrow), new PropertyMetadata(0.0));
        public static readonly DependencyProperty HeadHeightProperty =
            DependencyProperty.Register("HeadHeight", typeof(double), typeof(LineArrow), new PropertyMetadata(0.0));
        public static readonly DependencyProperty HeadWidthProperty =
            DependencyProperty.Register("HeadWidth", typeof(double), typeof(LineArrow), new PropertyMetadata(0.0)); 


        [TypeConverter(typeof(LengthConverter))]
        public double X1
        {
            get { return (double)base.GetValue(X1Property); }
            set { base.SetValue(X1Property, value); }
        }

        [TypeConverter(typeof(LengthConverter))]
        public double X2
        {
            get { return (double)base.GetValue(X2Property); }
            set { base.SetValue(X2Property, value); }
        }

        [TypeConverter(typeof(LengthConverter))]
        public double Y1
        {
            get { return (double)base.GetValue(Y1Property); }
            set { base.SetValue(Y1Property, value); }
        }

        [TypeConverter(typeof(LengthConverter))]
        public double Y2
        {
            get { return (double)base.GetValue(Y2Property); }
            set { base.SetValue(Y2Property, value); }
        }

        [TypeConverter(typeof(LengthConverter))]
        public double HeadHeight
        {
            get { return (double)base.GetValue(HeadHeightProperty); }
            set { base.SetValue(HeadHeightProperty, value); }
        }

        [TypeConverter(typeof(LengthConverter))]
        public double HeadWidth
        {
            get { return (double)base.GetValue(HeadWidthProperty); }
            set { base.SetValue(HeadWidthProperty, value); }
        }

        protected override Geometry DefiningGeometry
        {
            get
            {
                // Create a StreamGeometry for describing the shape
                StreamGeometry geometry = new StreamGeometry();
                geometry.FillRule = FillRule.EvenOdd;

                using (StreamGeometryContext context = geometry.Open())
                {
                    InternalDrawArrowGeometry(context);
                }

                // Freeze the geometry for performance benefits
                geometry.Freeze();

                return geometry;
            }
        }

        /// <summary>
        /// Draws an Arrow
        /// </summary>
        private void InternalDrawArrowGeometry(StreamGeometryContext context)
        {
            double theta = Math.Atan2(Y1 - Y2, X1 - X2);
            double sint = Math.Sin(theta);
            double cost = Math.Cos(theta);

            Point pt1 = new Point(X1, this.Y1);
            Point pt2 = new Point(X2, this.Y2);

            Point pt3 = new Point(
                X2 + (HeadWidth * cost - HeadHeight * sint),
                Y2 + (HeadWidth * sint + HeadHeight * cost));

            Point pt4 = new Point(
                X2 + (HeadWidth * cost + HeadHeight * sint),
                Y2 - (HeadHeight * cost - HeadWidth * sint));

            context.BeginFigure(pt1, true, false);
            context.LineTo(pt2, true, true);
            context.LineTo(pt3, true, true);
            context.LineTo(pt2, true, true);
            context.LineTo(pt4, true, true);
        }
    }
}

 

 

 

 

//Customize control
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Media;
using System.Windows.Shapes;
using System.Windows;

namespace WpfApp249
{
    public sealed class LineArrow : Shape
    {
        public static readonly DependencyProperty X1Property = 
            DependencyProperty.Register("X1", typeof(double), typeof(LineArrow), new PropertyMetadata(0.0));
        public static readonly DependencyProperty Y1Property =
            DependencyProperty.Register("Y1", typeof(double), typeof(LineArrow), new PropertyMetadata(0.0));
        public static readonly DependencyProperty X2Property =
            DependencyProperty.Register("X2", typeof(double), typeof(LineArrow), new PropertyMetadata(0.0));
        public static readonly DependencyProperty Y2Property =
            DependencyProperty.Register("Y2", typeof(double), typeof(LineArrow), new PropertyMetadata(0.0));
        public static readonly DependencyProperty HeadHeightProperty =
            DependencyProperty.Register("HeadHeight", typeof(double), typeof(LineArrow), new PropertyMetadata(0.0));
        public static readonly DependencyProperty HeadWidthProperty =
            DependencyProperty.Register("HeadWidth", typeof(double), typeof(LineArrow), new PropertyMetadata(0.0)); 


        [TypeConverter(typeof(LengthConverter))]
        public double X1
        {
            get { return (double)base.GetValue(X1Property); }
            set { base.SetValue(X1Property, value); }
        }

        [TypeConverter(typeof(LengthConverter))]
        public double X2
        {
            get { return (double)base.GetValue(X2Property); }
            set { base.SetValue(X2Property, value); }
        }

        [TypeConverter(typeof(LengthConverter))]
        public double Y1
        {
            get { return (double)base.GetValue(Y1Property); }
            set { base.SetValue(Y1Property, value); }
        }

        [TypeConverter(typeof(LengthConverter))]
        public double Y2
        {
            get { return (double)base.GetValue(Y2Property); }
            set { base.SetValue(Y2Property, value); }
        }

        [TypeConverter(typeof(LengthConverter))]
        public double HeadHeight
        {
            get { return (double)base.GetValue(HeadHeightProperty); }
            set { base.SetValue(HeadHeightProperty, value); }
        }

        [TypeConverter(typeof(LengthConverter))]
        public double HeadWidth
        {
            get { return (double)base.GetValue(HeadWidthProperty); }
            set { base.SetValue(HeadWidthProperty, value); }
        }

        protected override Geometry DefiningGeometry
        {
            get
            {
                // Create a StreamGeometry for describing the shape
                StreamGeometry geometry = new StreamGeometry();
                geometry.FillRule = FillRule.EvenOdd;

                using (StreamGeometryContext context = geometry.Open())
                {
                    InternalDrawArrowGeometry(context);
                }

                // Freeze the geometry for performance benefits
                geometry.Freeze();

                return geometry;
            }
        }

        /// <summary>
        /// Draws an Arrow
        /// </summary>
        private void InternalDrawArrowGeometry(StreamGeometryContext context)
        {
            double theta = Math.Atan2(Y1 - Y2, X1 - X2);
            double sint = Math.Sin(theta);
            double cost = Math.Cos(theta);

            Point pt1 = new Point(X1, this.Y1);
            Point pt2 = new Point(X2, this.Y2);

            Point pt3 = new Point(
                X2 + (HeadWidth * cost - HeadHeight * sint),
                Y2 + (HeadWidth * sint + HeadHeight * cost));

            Point pt4 = new Point(
                X2 + (HeadWidth * cost + HeadHeight * sint),
                Y2 - (HeadHeight * cost - HeadWidth * sint));

            context.BeginFigure(pt1, true, false);
            context.LineTo(pt2, true, true);
            context.LineTo(pt3, true, true);
            context.LineTo(pt2, true, true);
            context.LineTo(pt4, true, true);
        }
    }
}




//mainwindow.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.CompilerServices;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;

namespace WpfApp249
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        private Random rnd { get; set; }
        private double width { get; set; }
        private double height { get; set; }

        private int xDelta = 100;

        private int yDelta = 50;
        private Canvas cvs { get; set; }

        private ScaleTransform cvsScaler { get; set; }

        public MainWindow()
        {
            InitializeComponent();
            this.MouseWheel += Window_MouseWheel;
            this.Loaded += MainWindow_Loaded;            
        }

        private void MainWindow_Loaded(object sender, RoutedEventArgs e)
        {
            rnd = new Random();
            width = this.ActualWidth;
            height = this.ActualHeight;
            cvs = new Canvas();
            TransformGroup tg = new TransformGroup();
            cvsScaler = new ScaleTransform();
            if(!tg.Children.Contains(cvsScaler))
            {
                tg.Children.Add(cvsScaler);
            }
            cvs.RenderTransform = tg;
            DrawLineArrows();
        }

        private void DrawLineArrows()
        {
             for(int i=0;i<5;i++)
            {
                LineArrow la = new LineArrow();
                la.X1=rnd.Next(0,(int)width);
                la.Y1= rnd.Next(0, (int)height);
                la.X2 = la.X1 + 100;
                la.Y2 = la.Y1 + 100;
                la.HeadHeight = 10;
                la.HeadWidth = 10;
                la.Stroke = new SolidColorBrush(Colors.Red);
                la.StrokeThickness = 4;
                if(!cvs.Children.Contains(la))
                {
                    cvs.Children.Add(la);
                }
            }

            for (int i = 0; i < 5; i++)
            {
                LineArrow la = new LineArrow();
                la.X1 = rnd.Next(0, (int)width);
                la.Y1 = rnd.Next(0, (int)height);
                la.X2 = la.X1 - 100;
                la.Y2 = la.Y1 - 100;
                la.HeadHeight = 10;
                la.HeadWidth = 10;
                la.Stroke = new SolidColorBrush(Colors.Green);
                la.StrokeThickness = 4;
                if (!cvs.Children.Contains(la))
                {
                    cvs.Children.Add(la);
                }
            }

            for (int i = 0; i < 5; i++)
            {
                LineArrow la = new LineArrow();
                la.X1 = rnd.Next(0, (int)width);
                la.Y1 = rnd.Next(0, (int)height);
                la.X2 = la.X1 + 100;
                la.Y2 = la.Y1 - 100;
                la.HeadHeight = 10;
                la.HeadWidth = 10;
                la.Stroke = new SolidColorBrush(Colors.Blue);
                la.StrokeThickness = 4;
                if (!cvs.Children.Contains(la))
                {
                    cvs.Children.Add(la);
                }
            }

            for (int i = 0; i < 5; i++)
            {
                LineArrow la = new LineArrow();
                la.X1 = rnd.Next(0, (int)width);
                la.Y1 = rnd.Next(0, (int)height);
                la.X2 = la.X1 -100;
                la.Y2 = la.Y1 + 100;
                la.HeadHeight = 10;
                la.HeadWidth = 10;
                la.Stroke = new SolidColorBrush(Colors.Orange);
                la.StrokeThickness = 4;
                if (!cvs.Children.Contains(la))
                {
                    cvs.Children.Add(la);
                }
            }

            this.Content = cvs;
        }

        
        private void Window_MouseWheel(object sender, MouseWheelEventArgs e)
        {
            if (e.Delta > 0)
            {
                cvsScaler.ScaleX *= 1.2;
                cvsScaler.ScaleY *= 1.2;
            }
            else
            {
                cvsScaler.ScaleX /= 1.2;
                cvsScaler.ScaleY /= 1.2;
            }
            cvsScaler.CenterX = 0;
            cvsScaler.CenterY = 0;
        }
    }
}

 

标签:direction,customize,double,System,typeof,arrow,new,using,public
From: https://www.cnblogs.com/Fred1987/p/18363580

相关文章

  • Make Them Narrow
    题目大意:给你一个\(n\)和\(k\),再给你一个长度为\(N\)的序列\(A\),从\(A\)中任意选择\(K\)个元素并将其删除,然后按原来的顺序将剩余的元素连接起来,形成一个新的序列\(B\),然后求这个序列的极差。解题思路错误解法一开始我想到了贪心:把\(A\)数组排个序,然后把开头......
  • WPF Customize control
    //xaml<UserControlx:Class="WpfApp246.EllipseTbk"xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"xmlns:mc=&q......
  • Fotify扫描结果Open Redirection解决方案
    URL任意跳转漏洞,又叫开放重定向漏洞,是一种常见的安全漏洞。当访问时用widow.href或者window.localtion指定跳转地址时,会报此漏洞。网上的解决方案大致分为两种。方法一:种是对跳转URL进行加密,使用方法functionvalidateURL(surl){varurl......
  • Time flies like an arrow. 光阴不仅似箭。
    做semantics练习的时候做到的。发现有四种解释,挺有趣的,遂分享。第一种,光阴似箭。最平凡的理解,time指时间(是一个施事),flies指流逝,likeanarrow修饰流逝的速度。第二种,考虑time作为动词!解释是measurethetimetakenby(aprocess,activity,etc.,orapersondoingit......
  • Farrow滤波器-数字信号的任意速率变换
    前言:本文是Farrow滤波器相关三篇论文的学习笔记,介绍用于数字信号任意速率转化的Farrow滤波器,主要包括原理与架构,文章分为三个部分(1)重采样过程的数学建模;(2)Farrow算法推导;(3)Farrow滤波器实现架构。Farrow架构的两种理解:(1)对数模混合重采样过程用全数字滤波器形式近似,并基于多......
  • 来自 PyArrow ChunkedArray 的虚拟编码 PyArrow 表,无需通过 pandas?
    假设我importpyarrowaspaca=pa.chunked_array([['a','b','b','c']])print(ca)<pyarrow.lib.ChunkedArrayobjectat0x7fc938bcea70>[["a","b","b","......
  • C++ 列式内存布局数据存储格式 Arrow
    ApacheArrow优点:   高性能数据处理:Arrow使用列式内存布局,这特别适合于数据分析和查询操作,因为它允许对数据进行高效批量处理,减少CPU缓存未命中,从而提升处理速度。   零拷贝数据共享:Arrow允许不同系统和进程之间直接共享内存中的数据而无需复制,这对于提高数据......
  • pyarrow ipc 流 - 如何使用它进行通信?
    阅读pyarrowIPC文档后,我的印象是RecordBatchStreamReader会读取流直到完成(最后的0-s,是通过关闭流编写器写入的)。但是我看到reader很快就停止了,这不是我期望看到的。下面的示例开始在一个进程中写入文件流,并在延迟后开始在另一个进程中读取该文件流。我希望读者能......
  • WPF customize DelegateCommand via implementation interface System.Windows.Input.
    publicclassDelCmd:ICommand{privatereadonlyAction<Object>execute;privatereadonlyPredicate<Object>canExecute;publicDelCmd(Action<object>executeValue,Predicate<object>canExecuteValue){execut......
  • "No Directionality widget found." 在使用cupertino的时候出现了这个问题
    在使用cupertino的时候出现了这个问题,不过使用其他组件库也是类似的原代码:import'package:flutter/cupertino.dart';voidmain()=>runApp(constCupertinoTestRoute());classCupertinoTestRouteextendsStatelessWidget{constCupertinoTestRoute({Key?key}):s......