小白在参阅网上各类参考资料和书籍之后,一路艰辛,终于成功实现第一个应用程序,记录遇到的问题,供参考。
关于类和接口
简单理解:类是一个对象(比如人),接口实现类的内部属性和方法的分类。一个类可以实现多个接口,一个接口也可以被多个类实现。类内显式实现的接口,不能通过类的全名进行方法的调用,只能用接口实例来访问。
例如:
注:显式接口不能用public 来修饰。
错误做法:
正确做法:
如果不是显式接口,
person A =new person();
A.start();
是可以的。
IZou pZou=new person();
pZou.start();
也是可以的。
接口本身并不提供所定义的成员的实现,而只是指定实现该接口的类或接口必须提供的成员。在可以使用类的地方,都可以使用接口来替代,除了使用类产生一个对象外。
参考:https://blog.csdn.net/lianliancf/article/details/7661323
创建工程
添加控件
-
找不到ToolbarControl,TOCControl,MapControl,PageLayoutControl等相关控件的解决办法:右键工具箱->选择项,在选择工具箱页面中勾选相关选项。
- 控件布设完毕,最后将LicenseControl控件拖入到窗体的任意地方。按F5编译运行如果不能运行,很可能是ArcEngine没有许可,解决方法:打开program.cs,把
ESRI.ArcGIS.RuntimeManager.Bind(ESRI.ArcGIS.ProductCode.EngineOrDesktop);
这句放到Application.SetCompatibleTextRenderingDefault(false);和Application.Run(new Form1());
之间。
控件绑定
右击ToolbarControl、TOCControl等控件,将Buddy设置为axMapControl1,实现绑定。
添加菜单
菜单是MenuStrip控件
添加工具
右键工具条,属性,打开界面
我添加控件后并绑定后(ToolbarControl、TOCControl分别和MapControl绑定)的界面如下
写代码实现相关功能
控件的属性中,双击事件进入相应代码段。
1. 地图浏览
不写代码,单击工具栏上第一个图标Open,打开mxd文件,即可加载浏览。
2. 添加shp、添加lyr、图层属性
为”添加shp”、“添加lyr”、“图层属性“ 编写Click事件代码,分别对应下面的menuAddShp_Click、menuAddLyr_Click、menuAttibutes_Click函数。
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;
using ESRI.ArcGIS.DataSourcesFile;
using ESRI.ArcGIS.Geodatabase;
using ESRI.ArcGIS.Carto;
namespace MapViewer
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void menuAddShp_Click(object sender, EventArgs e)
{
////1.创建工作工厂空间
//IWorkspaceFactory pWorkspaceFactory = new ShapefileWorkspaceFactory();
////2.打开文件名对应的工作空间
//IWorkspace pWorkspace1 = pWorkspaceFactory.OpenFromFile(@"E:\engineTest\data", 0);
////3.打开要素类
//IFeatureWorkspace pFeatureWorkspace = pWorkspace1 as IFeatureWorkspace;
//IFeatureClass pFC = pFeatureWorkspace.OpenFeatureClass("water.shp");
////4.创建要素图层
//IFeatureLayer pFLayer = new FeatureLayerClass();
//pFLayer.FeatureClass = pFC;
//pFLayer.Name = pFC.AliasName;
////5.关联图层和要素类
//ILayer pLayer = pFLayer as ILayer;
//IMap pMap = axMapControl1.Map;
////6.添加到地图控件中
//pMap.AddLayer(pLayer);
//axMapControl1.ActiveView.Refresh();
//上面阴影部分是加载代码指定文件的方法
//以下改进后用户自定义加载文件
IWorkspaceFactory pWorkspaceFactory = new ShapefileWorkspaceFactory();
//文件过滤器
openFileDialog1.Filter = "ShapeFile文件(*.shp)|*.shp";
//设定文件对话框的初始路径
openFileDialog1.InitialDirectory = @"E:\engineTest\data";
//不能多选
openFileDialog1.Multiselect = false;
DialogResult pDialogResult = openFileDialog1.ShowDialog() ;
if (pDialogResult != DialogResult.OK)
return;
//得到对应文件对应的路径和文件名
string pPath = openFileDialog1.FileName;
string pFolder = System.IO.Path.GetDirectoryName(pPath);
string pFileName = System.IO.Path.GetFileName(pPath);
IWorkspace pWorkspace1 = pWorkspaceFactory.OpenFromFile(pFolder, 0);
IFeatureWorkspace pFeatureWorkspace = pWorkspace1 as IFeatureWorkspace;
IFeatureClass pFC = pFeatureWorkspace.OpenFeatureClass(pFileName);
IFeatureLayer pFLayer = new FeatureLayerClass();
pFLayer.FeatureClass = pFC;
pFLayer.Name = pFC.AliasName;
ILayer pLayer = pFLayer as ILayer;
IMap pMap = axMapControl1.Map;
pMap.AddLayer(pLayer);
axMapControl1.ActiveView.Refresh();
}
private void menuAddLyr_Click(object sender, EventArgs e)
{
openFileDialog1.Filter = "lyr文件(*.lyr)|*.lyr";
openFileDialog1.InitialDirectory = @"E:\engineTest\data";
//不能多选
openFileDialog1.Multiselect = false;
DialogResult pDialogResult = openFileDialog1.ShowDialog();
if (pDialogResult != DialogResult.OK)
return;
//得到对应文件对应的路径和文件名
string pFileName = openFileDialog1.FileName;
axMapControl1.AddLayerFromFile(pFileName);
axMapControl1.ActiveView.Refresh();
}
private void menuAttibutes_Click(object sender, EventArgs e)
{
FeatAttributeTable frm = new FeatAttributeTable(axMapControl1);
frm.ShowDialog();
}
}
}
为了能够在点击图层属性时加载属性表,在现有项目之上新建一个窗体应用程序。拖入DataGridView控件,编写Load事件代码。
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;
using ESRI.ArcGIS.Geodatabase;
using ESRI.ArcGIS.Carto;
using ESRI.ArcGIS.Controls;
namespace MapViewer
{
public partial class FeatAttributeTable : Form
{
//声明地图控件
private AxMapControl axMapControl;
public FeatAttributeTable()
{
InitializeComponent(); //初始化窗体及窗体上的各种控件
}
//构造函数2,1个参数
public FeatAttributeTable(AxMapControl pMapControl)
{
InitializeComponent(); //初始化窗体及窗体上的各种控件
axMapControl = pMapControl;
}
private void FeatAttributeTable_Load(object sender, EventArgs e)
{
//得到地图控件的第0层图层
ILayer pLayer = axMapControl.get_Layer(0);
//将pLayer类型强制转换成IFeatureLayer
IFeatureLayer pFLayer = pLayer as IFeatureLayer;
IFeatureClass pFC = pFLayer.FeatureClass;//class主要是属性的接口
//获得图标
IFeatureCursor pFCursor = pFC.Search(null, false);
//获得第0图层的第一个要素,要素中包含多个属性值
IFeature pFuture = pFCursor.NextFeature();
DataTable pTable = new DataTable();
DataColumn ColName = new DataColumn("KIND");
ColName.DataType = System.Type.GetType("System.String");
pTable.Columns.Add(ColName);
//获得字段名在内存表中的字段所引
int indexOfName = pFC.FindField("KIND");
//当要素不为空时
while (pFuture != null)
{
//得到索引号
string name=pFuture.get_Value(indexOfName);
DataRow pRow = pTable.NewRow();
pRow[0] = name;
pTable.Rows.Add(pRow);
pFuture = pFCursor.NextFeature();
}
//将属性表和控件连接
dataGridView1.DataSource = pTable;
}
}
}
最后效果
参考:https://blog.csdn.net/lianliancf/article/details/7667523
《ArcGIS Engine + C#入门经典》赵银军 卢远 | 2016年编著