需求:
在CAD内实现两个坐标系的转换。
转换方式为文件内的所有图形从一个坐标系下的坐标,转换到另一个坐标系下的坐标。
进行坐标转换后,仅仅是坐标发生改变,图层、样式等等不会发生变化。
示例:如图一、二

图 1 国家2000坐标系
转换后坐标:
图 2 广州城建坐标系
坐标转换:
空间实体的位置描述,从一种坐标系统变换到另一种坐标系统的过程。通过建立两个坐标系统之间一一对应关系来实现。是各种比例尺地图测量和编绘中建立地图数学基础必不可少的步骤。两个及以上的坐标转换时由极坐标相对参照确定维数空间。
一个点在一个坐标系的(一组)坐标,到新坐标系的(另一组)坐标的改变。新坐标系可以是与原坐标系同类型的(通过坐标轴的平移或旋转等得出);也可以是不同类型的(例如由直角坐标系变为极坐标系等)。
X1与Y1代表原平面坐标下的坐标, X2与Y2代表目标平面坐标下的坐标,二者转换需要四个参数,分别为x、y两个坐标的偏移,以及旋转角度和尺度因子等。
,
通常平面直角坐标系转换,需要两步:
- 计算四参数
- 通过四参数计算转换后的坐标
第一步中四参数我们会提供,可以不用计算,提供的四参数有两套。
需要利用编程实现的就是第二步,即利用四参数计算坐标。
页面布局:
图 3 页面布局
选择国家2000转广州城建的单选框时,左边显示出四参数,但是不可更改。
选择广州城建转国家2000的单选框时,左边显示出四参数,但是不可更改。
选择自定义单选框时,左边四参数可输入。
参考资料:坐标转换 - 四参数求解_四参数转换_尘埃里的邂逅的博客-CSDN博客
结果:
源码:
Form1.Cs:
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
namespace WindowsFormsApp1
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void Closebtn_Click(object sender, EventArgs e)
{
this.Close();
}
private void button1_Click_1(object sender, EventArgs e)
{
}
private void button2_Click(object sender, EventArgs e)
{
}
private void button3_Click(object sender, EventArgs e)
{
}
//自定义参数
private void mybtn_Click(object sender, EventArgs e)
{
x = 386471.785949509;
y = -2529992.86170142;
m = -0.00483892522831;
alpha = 1.00002783953692;
// this.textBoxX.Text = " ";
// this.textBoxY.Text = " ";
// this.textBoxm.Text = " ";
// this.textBoxAlpha.Text = " ";
this.textBoxX.ReadOnly = false;
this.textBoxY.ReadOnly = false;
this.textBoxm.ReadOnly = false;
this.textBoxAlpha.ReadOnly = false;
//输入参数
string strX = this.textBoxX.Text;
x = double.Parse(strX);//将输入的参数传给变量
string strY = this.textBoxY.Text;
y = double.Parse(strX);//将输入的参数传给变量
string strm = this.textBoxm.Text;
m = double.Parse(strm);//将输入的参数传给变量
string strAlpha = this.textBoxAlpha.Text;
alpha = double.Parse(strAlpha);//将输入的参数传给变量
//坐标转换公式:
// X2 = x + m * cos(alpha) * X1 - m * sin(alpha) * Y1
// Y2 = x + m * sin(alpha) * X1 - m * cos(alpha) * Y1
//坐标转换
double X1 = 1, X2, Y1 = 1, Y2;
//设置原坐标:X1,Y1
string strx = this.textBoxX1.Text;
X1 = double.Parse(strx);
string stry = this.textBoxY1.Text;
Y1 = double.Parse(stry);
X2 = x + m * Math.Cos(alpha) * X1 - m * Math.Sin(alpha) * Y1;
Y2 = x + m * Math.Sin(alpha) * X1 - m * Math.Cos(alpha) * Y1;
string str = "X:" + X2.ToString() + " Y:" + Y2.ToString();
string strxy1 = "X:" + X1.ToString() + " Y:" + Y1.ToString();
this.textBoxXY1.Text = strxy1;
this.textBoxXY.Text = str;
}
private void Guangzhoubtn_Click(object sender, EventArgs e)
{
//设置广州城建参数
x = 386471.785949509;
y = -2529992.86170142;
m = -0.00483892522831;
alpha = 1.00002783953692;
this.textBoxX.Text = " ";
this.textBoxY.Text = " ";
this.textBoxm.Text = " ";
this.textBoxAlpha.Text = " ";
this.textBoxX.ReadOnly = true;
this.textBoxY.ReadOnly = true;
this.textBoxm.ReadOnly = true;
this.textBoxAlpha.ReadOnly = true;
this.textBoxXY.ReadOnly = true;
this.textBoxX.Text = "386471.785949509";
this.textBoxY.Text = "-2529992.86170142";
this.textBoxm.Text = "-0.00483892522831";
this.textBoxAlpha.Text = " 1.00002783953692";
//坐标转换公式:
// X2 = x + m * cos(alpha) * X1 - m * sin(alpha) * Y1
// Y2 = x + m * sin(alpha) * X1 - m * cos(alpha) * Y1
//坐标转换
double X1 = 1, X2, Y1 = 1, Y2;
//设置原坐标:X1,Y1
string strx = this.textBoxX1.Text;
X1 = double.Parse(strx);
string stry = this.textBoxY1.Text;
Y1 = double.Parse(stry);
X2 = x + m * Math.Cos(alpha) * X1 - m * Math.Sin(alpha) * Y1;
Y2 = x + m * Math.Sin(alpha) * X1 - m * Math.Cos(alpha) * Y1;
string str = "X:"+X2.ToString()+" Y:"+Y2.ToString();
string strxy1 = "X:" + X1.ToString() + " Y:" + Y1.ToString();
this.textBoxXY1.Text = strxy1;
this.textBoxXY.Text = str;
}
//国家2000单选框
private void Guojiabtn_Click(object sender, EventArgs e)
{
//国家参数
x = -374214.444824699;
y = -2531762.85922438;
m = 0.00483892522819;
alpha = 0.99997216121273;
this.textBoxX.Text = " ";
this.textBoxY.Text = " ";
this.textBoxm.Text = " ";
this.textBoxAlpha.Text = " ";
this.textBoxX.ReadOnly = true;
this.textBoxY.ReadOnly = true;
this.textBoxm.ReadOnly = true;
this.textBoxAlpha.ReadOnly = true;
this.textBoxX.Text = "-386471.785949509";
this.textBoxY.Text = "-2531762.85922438";
this.textBoxm.Text = "0.00483892522819";
this.textBoxAlpha.Text = "0.99997216121273";
//坐标转换
double X1 = 1, X2, Y1 = 1, Y2;
//设置原坐标:X1,Y1
string strx = this.textBoxX1.Text;
X1 = double.Parse(strx);
string stry = this.textBoxY1.Text;
Y1 = double.Parse(stry);
X2 = x + m * Math.Cos(alpha) * X1 - m * Math.Sin(alpha) * Y1;
Y2 = x + m * Math.Sin(alpha) * X1 - m * Math.Cos(alpha) * Y1;
string str = "X:" + X2.ToString() + " Y:" + Y2.ToString();
string strxy1 = "X:" + X1.ToString() + " Y:" + Y1.ToString();
this.textBoxXY1.Text = strxy1;
this.textBoxXY.Text = str;
}
private void listBox1_SelectedIndexChanged(object sender, EventArgs e)
{
}
}
}
Form1.Desiger.cs:
namespace WindowsFormsApp1
{
partial class Form1
{
/// <summary>
/// 必需的设计器变量。
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// 清理所有正在使用的资源。
/// </summary>
/// <param name="disposing">如果应释放托管资源,为 true;否则为 false。</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
//默认国家2000转广州城建参数
public double x = -374214.444824699;
public double y = -2531762.85922438;
public double m = 0.00483892522819;
public double alpha = 0.99997216121273;
#region Windows 窗体设计器生成的代码
/// <summary>
/// 设计器支持所需的方法 - 不要修改
/// 使用代码编辑器修改此方法的内容。
/// </summary>
private void InitializeComponent()
{
this.labX = new System.Windows.Forms.Label();
this.Closebtn = new System.Windows.Forms.Button();
this.Guobtn = new System.Windows.Forms.Button();
this.Guangbtn = new System.Windows.Forms.Button();
this.button = new System.Windows.Forms.Button();
this.Guojiabtn = new System.Windows.Forms.Button();
this.Guangzhoubtn = new System.Windows.Forms.Button();
this.mybtn = new System.Windows.Forms.Button();
this.labm = new System.Windows.Forms.Label();
this.labY = new System.Windows.Forms.Label();
this.labAlpha = new System.Windows.Forms.Label();
this.groupBox1 = new System.Windows.Forms.GroupBox();
this.textBoxAlpha = new System.Windows.Forms.TextBox();
this.textBoxm = new System.Windows.Forms.TextBox();
this.textBoxY = new System.Windows.Forms.TextBox();
this.textBoxX = new System.Windows.Forms.TextBox();
this.groupBox2 = new System.Windows.Forms.GroupBox();
this.textBoxXY1 = new System.Windows.Forms.TextBox();
this.textBoxY1 = new System.Windows.Forms.TextBox();
this.label3 = new System.Windows.Forms.Label();
this.label4 = new System.Windows.Forms.Label();
this.textBoxX1 = new System.Windows.Forms.TextBox();
this.label2 = new System.Windows.Forms.Label();
this.label1 = new System.Windows.Forms.Label();
this.textBoxXY = new System.Windows.Forms.TextBox();
this.groupBox1.SuspendLayout();
this.groupBox2.SuspendLayout();
this.SuspendLayout();
//
// labX
//
this.labX.AutoSize = true;
this.labX.Location = new System.Drawing.Point(23, 36);
this.labX.Name = "labX";
this.labX.Size = new System.Drawing.Size(17, 12);
this.labX.TabIndex = 0;
this.labX.Text = "X:";
//
// Closebtn
//
this.Closebtn.AutoSize = true;
this.Closebtn.Location = new System.Drawing.Point(501, 240);
this.Closebtn.Name = "Closebtn";
this.Closebtn.Size = new System.Drawing.Size(77, 22);
this.Closebtn.TabIndex = 1;
this.Closebtn.Text = "Close";
this.Closebtn.UseVisualStyleBackColor = true;
this.Closebtn.Click += new System.EventHandler(this.Closebtn_Click);
//
// Guobtn
//
this.Guobtn.Location = new System.Drawing.Point(269, 62);
this.Guobtn.Name = "Guobtn";
this.Guobtn.Size = new System.Drawing.Size(183, 23);
this.Guobtn.TabIndex = 2;
this.Guobtn.Text = "国家2000转广州城建";
this.Guobtn.UseVisualStyleBackColor = true;
this.Guobtn.Click += new System.EventHandler(this.button1_Click_1);
//
// Guangbtn
//
this.Guangbtn.Location = new System.Drawing.Point(269, 107);
this.Guangbtn.Name = "Guangbtn";
this.Guangbtn.Size = new System.Drawing.Size(183, 23);
this.Guangbtn.TabIndex = 3;
this.Guangbtn.Text = "广州城建转国家2000";
this.Guangbtn.UseVisualStyleBackColor = true;
this.Guangbtn.Click += new System.EventHandler(this.button2_Click);
//
// button
//
this.button.Location = new System.Drawing.Point(269, 149);
this.button.Name = "button";
this.button.Size = new System.Drawing.Size(183, 23);
this.button.TabIndex = 4;
this.button.Text = "自定义";
this.button.UseVisualStyleBackColor = true;
this.button.Click += new System.EventHandler(this.button3_Click);
//
// Guojiabtn
//
this.Guojiabtn.Location = new System.Drawing.Point(480, 62);
this.Guojiabtn.Name = "Guojiabtn";
this.Guojiabtn.Size = new System.Drawing.Size(101, 23);
this.Guojiabtn.TabIndex = 5;
this.Guojiabtn.Text = "国家转广州结果";
this.Guojiabtn.UseVisualStyleBackColor = true;
this.Guojiabtn.Click += new System.EventHandler(this.Guojiabtn_Click);
//
// Guangzhoubtn
//
this.Guangzhoubtn.Location = new System.Drawing.Point(480, 102);
this.Guangzhoubtn.Name = "Guangzhoubtn";
this.Guangzhoubtn.Size = new System.Drawing.Size(101, 23);
this.Guangzhoubtn.TabIndex = 6;
this.Guangzhoubtn.Text = "广州转国家结果";
this.Guangzhoubtn.UseVisualStyleBackColor = true;
this.Guangzhoubtn.Click += new System.EventHandler(this.Guangzhoubtn_Click);
//
// mybtn
//
this.mybtn.Location = new System.Drawing.Point(480, 152);
this.mybtn.Name = "mybtn";
this.mybtn.Size = new System.Drawing.Size(98, 23);
this.mybtn.TabIndex = 7;
this.mybtn.Text = "自定义转换结果";
this.mybtn.UseVisualStyleBackColor = true;
this.mybtn.Click += new System.EventHandler(this.mybtn_Click);
//
// labm
//
this.labm.AutoSize = true;
this.labm.Location = new System.Drawing.Point(17, 125);
this.labm.Name = "labm";
this.labm.Size = new System.Drawing.Size(17, 12);
this.labm.TabIndex = 8;
this.labm.Text = "m:";
//
// labY
//
this.labY.AutoSize = true;
this.labY.Location = new System.Drawing.Point(23, 80);
this.labY.Name = "labY";
this.labY.Size = new System.Drawing.Size(17, 12);
this.labY.TabIndex = 9;
this.labY.Text = "Y:";
//
// labAlpha
//
this.labAlpha.AutoSize = true;
this.labAlpha.Location = new System.Drawing.Point(17, 168);
this.labAlpha.Name = "labAlpha";
this.labAlpha.Size = new System.Drawing.Size(23, 12);
this.labAlpha.TabIndex = 10;
this.labAlpha.Text = "α:";
//
// groupBox1
//
this.groupBox1.Controls.Add(this.textBoxAlpha);
this.groupBox1.Controls.Add(this.textBoxm);
this.groupBox1.Controls.Add(this.textBoxY);
this.groupBox1.Controls.Add(this.textBoxX);
this.groupBox1.Controls.Add(this.labX);
this.groupBox1.Controls.Add(this.labm);
this.groupBox1.Controls.Add(this.labY);
this.groupBox1.Controls.Add(this.labAlpha);
this.groupBox1.Location = new System.Drawing.Point(33, 38);
this.groupBox1.Name = "groupBox1";
this.groupBox1.Size = new System.Drawing.Size(230, 192);
this.groupBox1.TabIndex = 19;
this.groupBox1.TabStop = false;
//
// textBoxAlpha
//
this.textBoxAlpha.Location = new System.Drawing.Point(47, 159);
this.textBoxAlpha.Name = "textBoxAlpha";
this.textBoxAlpha.Size = new System.Drawing.Size(139, 21);
this.textBoxAlpha.TabIndex = 14;
this.textBoxAlpha.Text = "1";
//
// textBoxm
//
this.textBoxm.Location = new System.Drawing.Point(47, 116);
this.textBoxm.Name = "textBoxm";
this.textBoxm.Size = new System.Drawing.Size(139, 21);
this.textBoxm.TabIndex = 13;
this.textBoxm.Text = "1";
//
// textBoxY
//
this.textBoxY.Location = new System.Drawing.Point(47, 71);
this.textBoxY.Name = "textBoxY";
this.textBoxY.Size = new System.Drawing.Size(139, 21);
this.textBoxY.TabIndex = 12;
this.textBoxY.Text = "1";
//
// textBoxX
//
this.textBoxX.Location = new System.Drawing.Point(47, 26);
this.textBoxX.Name = "textBoxX";
this.textBoxX.Size = new System.Drawing.Size(139, 21);
this.textBoxX.TabIndex = 11;
this.textBoxX.Text = "1";
//
// groupBox2
//
this.groupBox2.Controls.Add(this.textBoxXY1);
this.groupBox2.Controls.Add(this.textBoxY1);
this.groupBox2.Controls.Add(this.label3);
this.groupBox2.Controls.Add(this.label4);
this.groupBox2.Controls.Add(this.textBoxX1);
this.groupBox2.Controls.Add(this.label2);
this.groupBox2.Controls.Add(this.label1);
this.groupBox2.Controls.Add(this.textBoxXY);
this.groupBox2.Controls.Add(this.groupBox1);
this.groupBox2.Controls.Add(this.Closebtn);
this.groupBox2.Controls.Add(this.Guobtn);
this.groupBox2.Controls.Add(this.mybtn);
this.groupBox2.Controls.Add(this.Guangbtn);
this.groupBox2.Controls.Add(this.Guangzhoubtn);
this.groupBox2.Controls.Add(this.button);
this.groupBox2.Controls.Add(this.Guojiabtn);
this.groupBox2.Location = new System.Drawing.Point(58, 33);
this.groupBox2.Name = "groupBox2";
this.groupBox2.Size = new System.Drawing.Size(599, 321);
this.groupBox2.TabIndex = 20;
this.groupBox2.TabStop = false;
//
// textBoxXY1
//
this.textBoxXY1.Location = new System.Drawing.Point(80, 246);
this.textBoxXY1.Name = "textBoxXY1";
this.textBoxXY1.Size = new System.Drawing.Size(283, 21);
this.textBoxXY1.TabIndex = 24;
//
// textBoxY1
//
this.textBoxY1.Location = new System.Drawing.Point(340, 203);
this.textBoxY1.Name = "textBoxY1";
this.textBoxY1.Size = new System.Drawing.Size(138, 21);
this.textBoxY1.TabIndex = 23;
this.textBoxY1.Text = "1";
//
// label3
//
this.label3.AutoSize = true;
this.label3.Location = new System.Drawing.Point(269, 184);
this.label3.Name = "label3";
this.label3.Size = new System.Drawing.Size(65, 12);
this.label3.TabIndex = 21;
this.label3.Text = "原X 坐 标:";
//
// label4
//
this.label4.AutoSize = true;
this.label4.Location = new System.Drawing.Point(269, 206);
this.label4.Name = "label4";
this.label4.Size = new System.Drawing.Size(65, 12);
this.label4.TabIndex = 22;
this.label4.Text = "原Y 坐 标:";
//
// textBoxX1
//
this.textBoxX1.Location = new System.Drawing.Point(340, 175);
this.textBoxX1.Name = "textBoxX1";
this.textBoxX1.Size = new System.Drawing.Size(138, 21);
this.textBoxX1.TabIndex = 21;
this.textBoxX1.Text = "1";
//
// label2
//
this.label2.AutoSize = true;
this.label2.Location = new System.Drawing.Point(14, 250);
this.label2.Name = "label2";
this.label2.Size = new System.Drawing.Size(59, 12);
this.label2.TabIndex = 20;
this.label2.Text = "原 坐 标:";
//
// label1
//
this.label1.AutoSize = true;
this.label1.Location = new System.Drawing.Point(6, 282);
this.label1.Name = "label1";
this.label1.Size = new System.Drawing.Size(71, 12);
this.label1.TabIndex = 15;
this.label1.Text = "转换后坐标:";
//
// textBoxXY
//
this.textBoxXY.Location = new System.Drawing.Point(80, 273);
this.textBoxXY.Name = "textBoxXY";
this.textBoxXY.Size = new System.Drawing.Size(283, 21);
this.textBoxXY.TabIndex = 16;
//
// Form1
//
this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 12F);
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
this.ClientSize = new System.Drawing.Size(763, 412);
this.Controls.Add(this.groupBox2);
this.Name = "Form1";
this.Text = "Form1";
this.groupBox1.ResumeLayout(false);
this.groupBox1.PerformLayout();
this.groupBox2.ResumeLayout(false);
this.groupBox2.PerformLayout();
this.ResumeLayout(false);
}
#endregion
private System.Windows.Forms.Label labX;
private System.Windows.Forms.Button Closebtn;
private System.Windows.Forms.Button Guobtn;
private System.Windows.Forms.Button Guangbtn;
private System.Windows.Forms.Button button;
private System.Windows.Forms.Button Guojiabtn;
private System.Windows.Forms.Button Guangzhoubtn;
private System.Windows.Forms.Button mybtn;
private System.Windows.Forms.Label labm;
private System.Windows.Forms.Label labY;
private System.Windows.Forms.Label labAlpha;
private System.Windows.Forms.GroupBox groupBox1;
private System.Windows.Forms.GroupBox groupBox2;
private System.Windows.Forms.TextBox textBoxAlpha;
private System.Windows.Forms.TextBox textBoxm;
private System.Windows.Forms.TextBox textBoxY;
private System.Windows.Forms.TextBox textBoxX;
private System.Windows.Forms.Label label1;
private System.Windows.Forms.TextBox textBoxXY;
private System.Windows.Forms.TextBox textBoxX1;
private System.Windows.Forms.Label label2;
private System.Windows.Forms.TextBox textBoxXY1;
private System.Windows.Forms.TextBox textBoxY1;
private System.Windows.Forms.Label label3;
private System.Windows.Forms.Label label4;
}
}
Program.cs:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using System.Windows.Forms;
namespace WindowsFormsApp1
{
static class Program
{
/// <summary>
/// 应用程序的主入口点。
/// </summary>
[STAThread]
static void Main()
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new Form1());
}
}
}