当前位置: 首页 > news >正文

C# DrawArc(画弧)

2020/6/12
最近用到C# 的 pictureBox 画圆弧,设计者的脑回路和我们平常的脑回路有点不太一样,所以刚上来就给整懵逼了,这篇博客就简单介绍一下如何调用这个 DrawArc
2020/6/13
其实昨天并没有达到想要的效果,画出来的弧为啥都是优弧呢?经过一些思考,我想我找到了原因,下面更正一下


1.理解设计者的脑回路

1.首先新建个窗体:
在这里插入图片描述
名字啥的随便区,但是要拉的大一点(不然一会画不下)
2.添加 Paint 响应事件:
在这里插入图片描述
3.找到

private void Draft_Paint(object sender, PaintEventArgs e)
{
}

在里面添加:

        private void Draft_Paint(object sender, PaintEventArgs e)
        {
            // Create pen.
            Pen blackPen = new Pen(Color.Black, 3);

            // Create coordinates of rectangle to bound ellipse.
            int x = 30;//包裹圆弧矩形的左上角x,y 坐标
            int y = 30;
            int width = 200;//包裹矩形的大小
            int height = 200;

            // Create start and sweep angles on ellipse.
            int startAngle = 45;//起始角
            int sweepAngle = 270;//逆时针转过这么多

            // Draw arc to screen.
            e.Graphics.DrawArc(blackPen, x, y, width, height, startAngle, sweepAngle);
        }

4.点击调式运行:
在这里插入图片描述
注:只有黑色的是程序运行出的结果。
这个DrawArc 和pictureBox 的DrawArc 调用方法是一样的

2.将我们的脑回路转化成设计者的脑回路

我们画圆弧的时候(不知道各位读者是不是,反正我是,嘿嘿),通常是已知起始点、终止点、半径,来画的,如何将这些信息转化成上面的那些信息呢?
1.根据起止点和终止点求出圆心坐标:
我们都知道,两点确定不出来唯一一个圆,但是加上起止点到终止点是逆时针方向这个约束条件就可以唯一确定一个圆了,(扯,还得 在加上一个是优弧还是劣弧的条件)怎么做到的呢?
首先由两个点搞出来第三个点:
在这里插入图片描述
之后三个点就确定出来圆心坐标了。
2.得到圆心坐标,有半径,包裹矩形大小以及包裹矩形左上角坐标即可知

3.有圆心坐标,有起终点坐标,起始方位角,弧角即可知

综上,关键就是求出圆心坐标。

3.C# 代码实现

		/*此函数用来在画布上画圆弧1
         * 输入:p 笔, g 画布, R 半径, p1 起点, p2 终点, k 优1劣2 顺时针画的
         * 注意,这里的p1 p2 是在画布坐标系下的坐标
         */ 
        public static void DrawArc(Pen p,Graphics g,double R,Point p1,Point p2,int k=1)
        {
            Point cen = GetCenter.Ycenter(R, p1, p2,k);
            // Create coordinates of rectangle to bound ellipse.
            float x = (float)(cen.x-R),//包裹圆弧矩形的左上角x,y 坐标
                y = (float)(cen.y-R),  //由于系统的 DrawArc 不支持double 故强制类型转化一下
                width=(float)(2*R),
                height=(float)(2*R);
            Angle
                PI=new Angle(Math.PI/2),
                AstartAngle = cen.getAn(p1),//起始角,以度为单位
                a = cen.getAn(p2),
                AsweepAngle = a - AstartAngle;//逆时针转过这么多
            float startAngle = AstartAngle.d+180,
                sweepAngle = AsweepAngle.d;
            // Draw arc to screen.
            g.DrawArc(p, x, y, width, height, startAngle, sweepAngle);  
        }

其所依附的类:

https://blog.csdn.net/Gou_Hailong/article/details/106686355
https://blog.csdn.net/Gou_Hailong/article/details/88989274
https://blog.csdn.net/Gou_Hailong/article/details/95803595

4.使用示例

在刚才的paint 中加入代码,点击运行

		private void Draft_Paint(object sender, PaintEventArgs e)
        {
            // create pen.
            Pen p = new Pen(Color.Black, 2);
            PointF p1 = new PointF(120, 140),
            p2 = new PointF(200, 110);
            double r = 50;
            Graphics g = e.Graphics;
            Draw.DrawArc(p, g, r, p1, p2);//优1劣2,直观顺
            p.Color = Color.Red;
            Draw.DrawArc(p, g, r, p2, p1,2);

            PointF p3 = new PointF(),
                p4 = new PointF();
            p3.X = p1.X + 200; p4.X = p2.X + 200;
            p3.Y = p1.Y; p4.Y = p2.Y;
            p.Color = Color.Blue;
            Draw.DrawArc(p, g, r, p4, p3);//优1劣2
            p.Color = Color.Yellow;
            Draw.DrawArc(p, g, r, p3, p4, 2);
            g.DrawLine(p, p1,p3);
            g.DrawLine(p, p2, p4);
            Point[] pt = new Point[4];
            pt[0] = new Point(p1); pt[0].name = "p1";
            pt[1] = new Point(p2); pt[1].name = "p2";
            pt[2] = new Point(p3); pt[2].name = "p3";
            pt[3] = new Point(p4); pt[3].name = "p4";
            Font f = new Font("宋体", 10);
            for(int i=0;i<4;i++)
            {
                g.FillEllipse(Brushes.Black, (float)(pt[i].X - 5), (float)(pt[i].Y) - 5, 10, 10);
                g.DrawString(pt[i].name, f, Brushes.Black, (float)(pt[i].X - 5), (float)(pt[i].Y + 5));
            }
        }

结果:
在这里插入图片描述
欧了!
【注1】其中的代码也许并不完整,您可以作为伪码参看,或者您可以去我主博客逛逛,也许有意外之喜!
【注2】此篇博客是 C# 编程笔记 的子博客。
【注3】由于博主水平有限,程序可能存在漏洞或bug, 如有发现,请尽快与博主联系!
回到 主博客

相关文章:

  • 模式识别 这些干货你都 get 了吗?
  • 用MATLAB 读写各种文件 ∈ Matlab 使用笔记
  • Matlab 求矩阵均值和协方差矩阵 ∈ Matlab 使用笔记
  • 常用遥感卫星数据汇总
  • 遥感图像分类领域的混淆矩阵
  • 模式识别+Matlab 最大似然分类(MLC)【贝叶斯(Bayes)分类法】
  • “北斗”知多少?
  • 2坐标格式转换 ∈ C# 编程笔记
  • 1坐标格式转换 ∈ C# 编程笔记
  • 2坐标转换 四参数/七参数/正形变换 ∈ C# 编程笔记
  • 闭合附和导线近似平差 ∈ C# 编程笔记
  • #快捷键# 大学四年我常用的软件快捷键大全,教你成为电脑高手!!
  • Matlab 各种画图 ∈ Matlab 使用笔记
  • C#一个解决方案创建多个项目
  • 夜光遥感卫星调研
  • [js高手之路]搞清楚面向对象,必须要理解对象在创建过程中的内存表示
  • 「前端」从UglifyJSPlugin强制开启css压缩探究webpack插件运行机制
  • 【Leetcode】104. 二叉树的最大深度
  • 【剑指offer】让抽象问题具体化
  • 【译】React性能工程(下) -- 深入研究React性能调试
  • conda常用的命令
  • Linux后台研发超实用命令总结
  • Python_网络编程
  • SpringBoot 实战 (三) | 配置文件详解
  • unity如何实现一个固定宽度的orthagraphic相机
  • Vue 重置组件到初始状态
  • 浮动相关
  • 机器人定位导航技术 激光SLAM与视觉SLAM谁更胜一筹?
  • 基于 Babel 的 npm 包最小化设置
  • 看域名解析域名安全对SEO的影响
  • 聊聊sentinel的DegradeSlot
  • 码农张的Bug人生 - 见面之礼
  • 三栏布局总结
  • 学习Vue.js的五个小例子
  • 一些css基础学习笔记
  • 06-01 点餐小程序前台界面搭建
  • 选择阿里云数据库HBase版十大理由
  • #前后端分离# 头条发布系统
  • (06)金属布线——为半导体注入生命的连接
  • (10)ATF MMU转换表
  • (4) PIVOT 和 UPIVOT 的使用
  • (C语言)二分查找 超详细
  • (Pytorch框架)神经网络输出维度调试,做出我们自己的网络来!!(详细教程~)
  • (七)Java对象在Hibernate持久化层的状态
  • (区间dp) (经典例题) 石子合并
  • (十二)devops持续集成开发——jenkins的全局工具配置之sonar qube环境安装及配置
  • (十六)串口UART
  • (转)Android中使用ormlite实现持久化(一)--HelloOrmLite
  • (转)ORM
  • .Net 知识杂记
  • .Net7 环境安装配置
  • .NET多线程执行函数
  • .net开发时的诡异问题,button的onclick事件无效
  • .pings勒索病毒的威胁:如何应对.pings勒索病毒的突袭?
  • .pyc文件是什么?