C#Winform程序制作仿真地平仪,磁罗盘飞行仪表盘

因为项目需要做一个电子飞行仪表盘包括地平仪和磁罗盘,网上找了很久,没有找到一个合适的控件,就学习了一些图形处理的开源代码做一个简陋的仪表盘来使用,希望对其他人有帮助,如果有好的建议不妨留言

源程序代码https://download.csdn.net/download/qq_42237381/10877536

目录

一、效果示意

二、原理说明

三、代码参考


一、效果示意

飞行仪表应用于飞行器上主要是飞行姿态角的监测

包括俯仰角,偏航角和滚动角

点击开始按钮,随机生成姿态角

二、原理说明

既然要仿真一些,先从网上找几个机械仪表的样式来学习,再从网上找些图片当做背景来使用

好了,这个就是俯仰角的表盘背景,需要将将它切割成一个圆,通过移动图片的位置在图片框的显示,不同的角度,滚动角可以和这个表放一起,滚动了多少度将图片旋转多少度,在写一圈的刻度值即可。

再找一个磁罗盘的图片,需要代码将它切割成一个圆,里面的表盘也用个截图工具截下来,只需要代码让里面的表盘转动既可以达到效果

三、代码参考

开始编程,创建WINFORM程序,添加两个图片框控件,一个按钮控件,一个时间控件。

程序如下,

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;

namespace Dashboard
{
    public partial class Form1 : Form
    {


        public Image imgtmp;
        public Image imgori;
        public Bitmap bitmp;
        public Bitmap bm;
        public bool IsSure = false;

        double DbPitchAngle = new double(); //俯仰角度[-90,90]
        double DbRowAngle = new double();   //滚转角度[-180,180]
        double DbYawAngle = new double();    //航向角度[-45,45]
        public Form1()
        {
            InitializeComponent();
        }
        //重绘旋转后的仪表盘图片 
        public void Overlap(Bitmap btm, int x, int y, int w, int h)
        {
            Bitmap image = new Bitmap(btm);
            Bitmap hi = new Bitmap(bm);
            Graphics g = Graphics.FromImage(hi);
            g.DrawImage(image, new Rectangle(x, y, w, h));
            bm = hi;
        }



        //-------------------磁罗盘显示函数-------------------//
        //入口参数:
        //航向角 dir_angle 范围0~360 度 
        private void Compass_Disp(double dir_angle)
        {
            string file = System.IO.Path.Combine(Environment.CurrentDirectory, @"point.jpg");
            bitmp = new Bitmap(file);
            Bitmap pointImage = new Bitmap(250, 250);
            System.Drawing.Graphics gPoint = System.Drawing.Graphics.FromImage(pointImage);
            gPoint.InterpolationMode = System.Drawing.Drawing2D.InterpolationMode.Bilinear;
            gPoint.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.HighQuality;
            //计算偏移量
            Rectangle rectPoint = new Rectangle(0, 0, 250, 250);
            gPoint.TranslateTransform(125, 125);
            //g.RotateTransform(360 - row_angle);
            gPoint.RotateTransform((float)dir_angle);
            //恢复图像在水平和垂直方向的平移 
            gPoint.TranslateTransform(-125, -125);
            gPoint.DrawImage(bitmp, rectPoint);
            //重至绘图的所有变换  
            gPoint.ResetTransform();
            gPoint.Dispose();
            //保存旋转后的图片
            bm = pointImage;
            Overlap(pointImage, 0, 0, 250, 250);
            CompointBox.Image = bm;

            // 刻度盘截圆
            System.Drawing.Drawing2D.GraphicsPath gp = new System.Drawing.Drawing2D.GraphicsPath();
            gp.FillMode = 0;
            gp.AddEllipse(new Rectangle(0, 0, 350, 350));
            ComshellBox.Region = new Region(gp);
            //表盘截圆
            System.Drawing.Drawing2D.GraphicsPath gp1 = new System.Drawing.Drawing2D.GraphicsPath();
            gp1.FillMode = 0;
            gp1.AddEllipse(new Rectangle(0, 0, 250, 250));
            CompointBox.Region = new Region(gp1);
            gp1.Dispose();
            gp.Dispose();
            gPoint.Dispose();
            bitmp.Dispose();
            //Graphics gp1 = CompointBox.CreateGraphics();
            //gp1.DrawEllipse()
        }

        //-------------------地平仪刻度划线函数-------------------//
        //入口参数:无       
        public Image Hori_Line()
        {
            bitmp = new Bitmap(350, 350);
            System.Drawing.Graphics gscale = System.Drawing.Graphics.FromImage(bitmp);
            Pen p1 = new Pen(Color.Red, 4);
            Pen p2 = new Pen(Color.Green, 3);

            //准心绘线
            //gscale.DrawEllipse(Pens.Red ,165, 165, 20, 20);
            gscale.DrawLine(p2, 145, 175, 205, 175);
            gscale.DrawLine(p1, 145, 185, 175, 175);
            gscale.DrawLine(p1, 205, 185, 175, 175);
            //滚转刻度线
            gscale.DrawEllipse(Pens.White, 35, 35, 280, 280);
            int i, i1, j, j1, k;
            for (k = 0; k < 73; k++)
            {
                i = Convert.ToInt32(140 * Math.Cos(k * Math.PI / 36) + 175);
                j = Convert.ToInt32(140 * Math.Sin(k * Math.PI / 36) + 175);
                if (k % 2 == 0)
                {
                    i1 = Convert.ToInt32(155 * Math.Cos(k * Math.PI / 36) + 175);
                    j1 = Convert.ToInt32(155 * Math.Sin(k * Math.PI / 36) + 175);
                }
                else
                {
                    i1 = Convert.ToInt32(150 * Math.Cos(k * Math.PI / 36) + 175);
                    j1 = Convert.ToInt32(150 * Math.Sin(k * Math.PI / 36) + 175);
                }
                gscale.DrawLine(Pens.White, i, j, i1, j1);
            }
            gscale.Dispose();
            return bitmp;
        }
        //-------------------地平仪显示函数-------------------//
        //入口参数:
        //俯仰角 pitch_angle 范围-90~90 度 
        //滚动角 row_angle   范围-90~90 度
        private void Hori_Disp(double pitch_angle, double row_angle)
        {
            //1地平仪图像载入带平移
            int pic_position;
            pic_position = Convert.ToInt32(pitch_angle * 3.86);
            string file = System.IO.Path.Combine(Environment.CurrentDirectory, @"11.jpg");
            try
            {
                imgtmp = new Bitmap(file);
                row_angle = row_angle % 360;
                //弧度转换  
                double ar = 2;
                double radian = (row_angle - 90) * Math.PI / 180.0;
                double radiana = (row_angle - 90 - ar) * Math.PI / 180.0;
                double radianc = (row_angle - 90 + ar) * Math.PI / 180.0;
                double cos = Math.Cos(radian);
                double cosa = Math.Cos(radiana);
                double cosc = Math.Cos(radianc);
                double sin = Math.Sin(radian);
                double sina = Math.Sin(radiana);
                double sinc = Math.Sin(radianc);
                //目标位图
                Bitmap dsImage = new Bitmap(350, 350);
                System.Drawing.Graphics g = System.Drawing.Graphics.FromImage(dsImage);
                g.InterpolationMode = System.Drawing.Drawing2D.InterpolationMode.Bilinear;
                g.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.HighQuality;
                //计算偏移量
                Rectangle rect = new Rectangle(-175, -175 + pic_position, 700, 700);
                g.TranslateTransform(175, 175);
                g.RotateTransform((float)row_angle);
                //恢复图像在水平和垂直方向的平移 
                g.TranslateTransform(-175, -175);
                g.DrawImage(imgtmp, rect);
                //重至绘图的所有变换  
                g.ResetTransform();
                g.Dispose();
                //保存旋转后的图片
                bm = dsImage;
                //调用imgori 已经是画好的刻度盘
                Bitmap bitmp = new Bitmap(imgori);
                Overlap(bitmp, 0, 0, 350, 350);
                Bitmap pointImage = new Bitmap(350, 350);
                // 指针设计 ;
                System.Drawing.Graphics gPoint = System.Drawing.Graphics.FromImage(pointImage);
                SolidBrush h = new SolidBrush(Color.Red);
                Point a = new Point(Convert.ToInt32(175 + 131 * cosa), Convert.ToInt32(180 + 131 * sina));
                Point b = new Point(Convert.ToInt32(141 * cos + 175), Convert.ToInt32(141 * sin + 175));
                Point c = new Point(Convert.ToInt32(175 + 131 * cosc), Convert.ToInt32(180 + 131 * sinc));
                Point[] pointer = { a, b, c };
                gPoint.FillPolygon(h, pointer);

                Overlap(pointImage, 0, 0, 350, 350);
                HoriBox.Image = bm;
                g.Dispose();
                imgtmp.Dispose();
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message);
            }
            System.Drawing.Drawing2D.GraphicsPath gp = new System.Drawing.Drawing2D.GraphicsPath();
            gp.FillMode = 0;
            gp.AddEllipse(new Rectangle(0, 0, 350, 350));
            HoriBox.Region = new Region(gp);
            gp.Dispose();
        }
        /// <summary>
        /// 开始按钮点击
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void button1_Click(object sender, EventArgs e)
        {
            if (IsSure == false)
            {
                timer1.Enabled = true;
                IsSure = true;
                button1.Text = "停止";
            }
            else
            {
                timer1.Enabled = false;
                IsSure = false;
                button1.Text = "开始";
            }
        }

        private void timer1_Tick(object sender, EventArgs e)
        {
              double DbPitchAngle = 0; //俯仰角度[-90,90]
              double DbRowAngle = 0;   //滚转角度[-180,180]
              double DbYawAngle = 0;   //航向角度[-45,45]
              Random pR = new Random();
              Random rR = new Random();
              Random yR = new Random();
              DbPitchAngle = pR.Next(0, 90);
              DbRowAngle = rR.Next(-180, 180);
              DbYawAngle = yR.Next(-45,45);
              Hori_Disp(DbPitchAngle, DbRowAngle);
              Compass_Disp(DbYawAngle);
              Hori_Line();

        }

        private void Form1_Load(object sender, EventArgs e)
        {
            imgori = Hori_Line();
        }

    }
}

 

  • 8
    点赞
  • 47
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值