---------------------------------------------------------------------------------------------------------
●·● 目录:
A0 ………… 64位windows 7 + Visual Studio 2010 + ArcGIS Engine 10.0 操作问题 & 解决
A1 ………… Dock 在布局控件时的使用技巧
Anchor 在布局控件时的使用技巧
A2 ………… ToolbarControl 的属性设置
A3 ………… TOCControl 的属性设置
A4 ………… MapControl 的属性设置
A5 ………… PageLayoutControl 的属性设置
A6 ………… VS2008打开VS2010项目
A7 ………… Visual Studio 2008“分析 EntityName 时出错。 行 2,位置 81。”报错解决!
A8 ………… 类、接口等的引用传递的理解
A9 ………… DrawShape 与 AddElement 显示图形的区别
G1 ………… Type.Missing 的含义
G2 ………… C# /// 注释 & C# 书签设置
---------------------------------------------------------------------------------------------------------
╔════════╗
╠════╣ 第A0个 ╠══════════════════════════════════════════════════╣
╚════════╝
●·● 64位windows 7 + Visual Studio 2010 + ArcGIS Engine 10.0 操作问题 & 解决:
参考:http://www.cnblogs.com/Joetao/articles/3415356.html
许多版友在刚刚使用ArcGIS 10做开发的时候,都会遇到这样那样的问题。在担任实习版主的这一个多月里,看到了这么几个与开发环境相关的问题,重复被提到相当多,于是我就做了这个FAQ。
Q:哪儿有10的ArcGIS Engine SDK? A:ArcGIS 10不需要安装单独的Engine开发包,在Desktop的镜像中,安装ArcObjects SDK就可以使用Engine的那些控件做开发了。只在部署的时候还需要Engine Runtime。
Q:为什么在9.3中执行正常的代码,在10中会执行出错,抛出异常COMException A:是如下图这个异常么?
10新增了一个dll,ESRI.ArcGIS.Version,添加这个引用。然后在Main方法中,在窗体启动之前,添加这么一行代码:
- RuntimeManager.Bind(ProductCode.EngineOrDesktop);
重新编译执行即可。
Q:为什么以前正常的代码,现在都编译都通不过了,提示什么“无法嵌入互操作类型...”
A:你用的是Visual Studio 2010和C# 4吧?如果是,那就对了。这个问题和Engine本身无关。 这是C# 4对COMInterop的一个改进,把创建CoClass时的类名的Class后缀去掉即可。不允许用CoClass本身,而必须用相应的接口来创建对象。 比如,
- IPoint p = new PointClass()
改为:
- IPoint p = new Point()
详细的解释可以看这里的:嵌入的互操作类型(如果尝试使用 CoClass 创建嵌入的 COM 类型的实例,则会导致编译器错误)
Q:为什么以前正常的代码,现在一运行就报错,抛出异常BadImageFormatException
A:你的操作系统是64位的Windows吧?可是ArcGIS现在只有32位的,所以必须用X86平台生成项目。 打开项目属性,在“生成”选项卡中找到目标平台,把Any CPU改为x86,重新生成即可。
Q:我要用ArcGIS Engine 10,一定要用Visual Studio 2010吗?
A: 不一定,不论什么版本的Visual Studio和什么版本ArcGIS Engine SDK,都是可以组合的。 因为ArcGIS Engine的SDK是一些COM组件,而C#、VB、VC++对COM的支持一直是有的。
注:Engine SDK可能会检查系统已安装的VisualStudio版本,比如ArcObjects 10 SDK(内含Engine)只在已有10或者08SP1的系统完成安装。当然,如果有办法绕过去,就没问题了。
可能你装上之后工具箱里面的神马MapControl,SceneControl、LicenseControl都没有出来。 这个没关系,添加工具箱项,找到Engine的dll,添加进来,一切Ok
这个问题还是补充地具体一些吧: 1、在VS工具箱内右键,添加选项卡,取名ArcGIS Windows Form 2、在新选项卡上右键,选择项... 3、点浏览,找到ESRI.ArcGIS.AxControls.dll(缺省安装在"C:\Program Files\ArcGIS\DotNet\ESRI.ArcGIS.AxControls.dll"),打开。
4、勾选中新出现的那几个ArcGIS的控件,点确定。
---------------------------------------------------------------------------------------------------------
╔════════╗
╠════╣ 第A1个 ╠══════════════════════════════════════════════════╣
╚════════╝
●·● Dock 在布局控件时的使用技巧:
在布局控件的时候使用 Dock 是很省事的,可以令控件很完美,在使用 Dock 的时候要注意下面几点:
- Dock 包括 Top、Left、Fill、Right、Bottom,按要求选择!
- 有的时候Dock不会按照自己的想法去实现,主要原因是控件的层次关系,Dock会优先考虑放在更低下的控件,如下所示,为了让 MapControl 控件可以以 Fill 形式呈现,必须将其放在最顶层,若是放在最底层,则会铺满整个界面,像是 MenuStrip 和 StatusStrip 则要放在最底层,否则就不能完全占据 Top 和 Bottom 了,反正就是优先考虑地层的,然后再考虑顶层的!
●·● Anchor 在布局控件时的使用技巧:
直接看下面的例子,Anchor中的Left、Right、Top、Bottom是指与这些边的距离保持不变!
最大化!
设置:
左边的 webBrowser Anchor 设置:Top, Bottom, Left, Right
右上角控件的 Anchor 设置:Top, Right
右下角的 dataGridView Anchor 设置:Top, Bottom, Right
---------------------------------------------------------------------------------------------------------
╔════════╗
╠════╣ 第A2个 ╠══════════════════════════════════════════════════╣
╚════════╝
●·● ToolbarControl 的属性设置:
1. General:
- Border:边框,0 —— 没有边框、1 —— 有边框。
- Appearance:外观,0 —— 普通、1 —— 3D效果。
- Mouse:鼠标样式。
- Orientation:水平显示 or 垂直显示。
- Buddy:伙伴控件。
- Enable:是否可用。
- Preview in Design Mode:是否在设计视图预览控件。
- Menu Tracking:选中时,鼠标点击一个 Menu 后,移动鼠标,其他的 Menu 自动被展开!
2. Items:
- Item:0 —— 普通、1 —— 3D效果。
- Text:文本显示样式。
- Update:更新时间。
- Icon:图标大小。
- ToolTips:是否显示标记。
- Themed Drawing:是否有后面的圆角矩形。
- Show Hidden Item:是否显示隐藏项。
- Add:增加项。
- Remove All:删除所有项。
Add 分项:
- Commands:一些基本的命令和工具!
- ToolSets:分类!
- Menus:以菜单形式存在!
- Palettes:以板的形式存在!
menu 和 palette 如下所示!
3. Color:
- Transparent:工具栏是透明的。
- Background Color:设置背景颜色。
- Fade Color:与上面的 Background Color 建立渐变色。
- Fill Direction:渐变的方向:水平 or 垂直!
4. 效果预览:
添加 Menu 代码:
//Add existing menus to ToolbarControl. axToolbarControl1.AddMenuItem("esriControls.ControlsMapViewMenu", -1, false, 0); axToolbarControl1.AddMenuItem("esriControls.ControlsFeatureSelectionMenu", -1, false, 0); //Create a new file menu. IToolbarMenu toolbarMenu = new ToolbarMenuClass(); toolbarMenu.Caption = "Map Document"; toolbarMenu.AddItem("esriControls.ControlsOpenDocCommand", -1, 0, false, esriCommandStyles.esriCommandStyleIconAndText); toolbarMenu.AddItem("esriControls.ControlsSaveAsDocCommand", -1, 1, false, esriCommandStyles.esriCommandStyleIconAndText); axToolbarControl1.AddMenuItem(toolbarMenu, -1, false, 0); axToolbarControl1.MenuTracking = true;
※ 参考:http://blog.163.com/hnhanpeng@126/blog/static/264189020069108522553/
---------------------------------------------------------------------------------------------------------
╔════════╗
╠════╣ 第A3个 ╠══════════════════════════════════════════════════╣
╚════════╝
●·● TOCControl 的属性设置:
1. TOCControl 控件:
- 相同的如上面所述。
- Label:
- Layer:选择 1 后,复选框没办法选!
- Enable Layer Drag and Drop:是否允许用鼠标拖拽图层。
- Arrow Key Intercept:是否拦截按键,若选中,则按键仅影响 TOCControl,若不选中,方向键会不自觉地影响 MapControl。
---------------------------------------------------------------------------------------------------------
╔════════╗
╠════╣ 第A4个 ╠══════════════════════════════════════════════════╣
╚════════╝
●·● MapControl 的属性设置:
1. MapControl 控件:
- Available Maps:可以选择显示的 Data Frame。
- Scale:初始比例尺。
- Rotation:初始旋转角度。
---------------------------------------------------------------------------------------------------------
╔════════╗
╠════╣ 第A5个 ╠══════════════════════════════════════════════════╣
╚════════╝
●·● PageLayoutControl 的属性设置:
1. PageLayoutControl 控件:
- 显示设置。
- 页面设置。
---------------------------------------------------------------------------------------------------------
╔════════╗
╠════╣ 第A6个 ╠══════════════════════════════════════════════════╣
╚════════╝
●·● VS2008打开VS2010项目:
第一步,修改解决方案后缀为sln的文件
Microsoft Visual Studio Solution File, Format Version 11.00
# Visual Studio 2010
修改为:
Microsoft Visual Studio Solution File, Format Version 10.00
# Visual Studio 2008
第二步,修改项目后缀为csproj的文件,找到第一个4.0改成3.5就好!
<Project DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003" ToolsVersion="4.0">
修改为:
<Project DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003" ToolsVersion="3.5">
删除:有的时候不存在
<TargetFrameworkVersion>v4.0</TargetFrameworkVersion>
参考:http://qqhack8.blog.163.com/blog/static/11414798520115892540805/
---------------------------------------------------------------------------------------------------------
╔════════╗
╠════╣ 第A7个 ╠══════════════════════════════════════════════════╣
╚════════╝
●·● Visual Studio 2008“分析 EntityName 时出错。 行 2,位置 81。”报错解决!:
1. 报错内容“若要在加载设计器前避免可能发生的数据丢失,必须纠正以下错误: ”
“分析 EntityName 时出错。 行 2,位置 81。”
2. 如图:
3. 原因如下:
4. 就是中间那个“&”搞的鬼,哎,我怎么就起了个这么悲催的名字呢,以前就经常出现这个问题,有的时候会报错,但有的时候不会报错,靠,原来是这个原因,果断把程序拷到外面,结果就成功了,好吧,看来起名字还是一门学问呢!
参考:http://hi.baidu.com/janic716/blog/item/59165a18073fb3ac4aedbc0a.html
另外就是,不要让路径的名称太冗长,或是夹杂太多的中文,因为我在用一本书的代码的时候都会出现这个问题,好像就是因为有太多的中文,再加之路径太长了,因为每个文件夹的名字都很长,字符又很乱,所以文件夹和文件的名字要起的简介且规范一点为好!
--------------------------------------------------------------------------------------------------------
╔════════╗
╠════╣ 第A8个 ╠══════════════════════════════════════════════════╣
╚════════╝
●·● 类、接口等的引用传递的理解:
昨天晚上睡觉的时候突然就想到了这一点,我当时在想,为什么我在另外一个窗体中操作 map(此 map 是调用地图中的 map 的)的时候,会在主窗体中发生变化,之前一直困扰我的就是怎么通过独立的窗体控制主窗体,我突然恍然大悟,当时学习的引用传递就是这个意思了。他们都是共用一个对象的,所以任何对于此对象的操作都会受影响,因为它们本身就是绑定在一起的,这就是为什么我操作独立窗体中的 map 对象的时候,会在主窗体中发生变化。
另外这也是接口查询(QI)的基石,为什么将接口转来转去的来搞,原因就是它们操作的都是一个对象,只是接口不同,具有的方法和属性不同罢了,从而实现不同的功能!
① 实例:在按钮的单击事件中新建一个 MapControl 实例,然后操作这个实例的时候,主窗体中的地图也会随之变化!
private void button2_Click(object sender, EventArgs e) { IMapControl4 pmc = axMapControl1.Object as IMapControl4; pmc.Rotation = 180; pmc.ActiveView.Refresh(); }
② 实例:将 MapControl 通过类的构造函数传递到独立窗体中,然后操作独立窗体中新建的 MapControl 也会对主窗体中的地图产生影响!
建立独立窗体:
public partial class LayerProperties : Form { IMapControl4 pMapControl; IMap pMap; IFeatureLayer pLayer; IActiveView pActiveView; public LayerProperties(IMapControl4 mapControl, IMap map,ILayer layer) //将主要的内容传递过去,其实传个 MapControl 就足够了 { InitializeComponent(); pMapControl = mapControl; pMap = map; pLayer = layer as IFeatureLayer; pActiveView = pMap as IActiveView; } private void 缩放到该要素ToolStripMenuItem_Click(object sender, EventArgs e) { if (pMapControl.Rotation == 0) //直接操作这个 pMapControl 就会直接影响主窗体的地图了! { pMapControl.Rotation = 180; } else { pMapControl.Rotation = 0; } pMapControl.ActiveView.Refresh(); } }
在主窗体中调用独立窗体:
private void button1_Click(object sender, EventArgs e) { IMap pMap = axMapControl1.Map; ILayer pLayer = pMap.get_Layer(0); LayerProperties frm = new LayerProperties(axMapControl1.Object as IMapControl4,pMap, pLayer); frm.Show(); }
③ 实例: 如下所示:
1 IPoint pPt = axMapControl2.ActiveView.ScreenDisplay.DisplayTransformation.ToMapPoint(e.x,e.y); 2 IMarkerElement pMarkerElement = new MarkerElementClass(); 3 ISimpleMarkerSymbol pMarkerSymbol = new SimpleMarkerSymbolClass(); 4 pMarkerSymbol.Color = GetColor(255, 0, 0); 5 pMarkerSymbol.Size = 10; 6 pMarkerSymbol.Style = esriSimpleMarkerStyle.esriSMSCross; 7 IElement pElement = pMarkerElement as IElement; 8 pElement.Geometry = pPt; 9 pMarkerElement.Symbol = pMarkerSymbol; //这里虽然用的是 pMarkerElement,但是效果就会直接影响 pElement! 10 IGraphicsContainer pGraphicsContainer = axMapControl2.Map as IGraphicsContainer; 11 pGraphicsContainer.AddElement(pElement, 0); 12 axMapControl2.ActiveView.Refresh();
对于第 11 句来说,下面的写法也可以!实现的效果是一样的,因为本身他们就是一个东西,不同的名字罢了!
pGraphicsContainer.AddElement(pMarkerElement as IElement, 0);
--------------------------------------------------------------------------------------------------------
╔════════╗
╠════╣ 第A9个 ╠══════════════════════════════════════════════════╣
╚════════╝
●·● DrawShape 与 AddElement 显示图形的区别:
前者在操作的时候更加方便,但是这个图形是临时的,一旦刷新地图,这些东西就没了,因此也没有办法存储,相比之下,AddElement 是实体的操作,放大地图,图形也跟着变大,而且可以存储在地图中!对比下面:
IMapControl4 m_mapControl = m_hookHelper.Hook as IMapControl4; IEnvelope pRectangle = m_mapControl.TrackRectangle(); ISimpleLineSymbol pSimpleLineSym = new SimpleLineSymbol(); pSimpleLineSym.Color = GetColor(0, 0, 0); pSimpleLineSym.Width = 2; ISimpleFillSymbol pSimpleFillSym = new SimpleFillSymbol(); pSimpleFillSym.Color = GetColor(0, 255, 0); pSimpleFillSym.Outline = pSimpleLineSym; object symbol = pSimpleFillSym; m_mapControl.DrawShape(pRectangle, ref symbol);
IMapControl4 m_mapControl = m_hookHelper.Hook as IMapControl4; IScreenDisplay pScreenDisplay = m_mapControl.ActiveView.ScreenDisplay; IGraphicsContainer pGraphicsContainer = m_mapControl.Map as IGraphicsContainer; IRubberBand pRubberPolygon = new RubberPolygon(); IPolygon pPolygon = pRubberPolygon.TrackNew(pScreenDisplay, null) as IPolygon; ISimpleLineSymbol pSimpleLineSym = new SimpleLineSymbol(); pSimpleLineSym.Color = GetColor(0, 0, 0); pSimpleLineSym.Width = 2; ISimpleFillSymbol pSimpleFillSym = new SimpleFillSymbol(); pSimpleFillSym.Color = GetColor(0, 255, 0); pSimpleFillSym.Outline = pSimpleLineSym; IElement pEle = new PolygonElement(); pEle.Geometry = pPolygon; IFillShapeElement pFillShapeEle = pEle as IFillShapeElement; pFillShapeEle.Symbol = pSimpleFillSym; pGraphicsContainer.AddElement(pEle, 0); m_mapControl.ActiveView.Refresh();
对于后者来说是增加元素,因此最后要刷新一下,否则没办法显示,前者则只是画在临时的地图表面!
--------------------------------------------------------------------------------------------------------
╔════════╗
╠════╣ 第G1个 ╠══════════════════════════════════════════════════╣
╚════════╝
●·● Type.Missing 的含义:
表示 Type 信息中的缺少值。 使用 Missing 字段通过反射进行调用,以获取参数的默认值。如果传入一个参数值的 Missing 字段,并且该参数没有默认值,则引发 ArgumentException。 一般在ComInterop使用比较多。如果接触过VSTO,就会发现有很多地方要用到Type.Missing字段。许多C++写的com组件API参数列表中有很多默认值,而C#是没有参数默认值的。使用这个字段可以直接使用API参数的默认值。
※ 官方帮助参考:http://msdn.microsoft.com/zh-cn/library/system.type.missing.aspx?TPSecNotice
--------------------------------------------------------------------------------------------------------
╔════════╗
╠════╣ 第G2个 ╠══════════════════════════════════════════════════╣
╚════════╝
●·● C# /// 注释 & C# 书签设置:
/// 的注释有特殊的作用,不仅仅是注释,通过下面的实例来体会!
/// <summary> /// shp文件的完整路劲 /// </summary> string shapeFileFullName = string.Empty;
其中中间的部分是对于变量的描述,在后面的程序中用到此变量的时候,可以显示这个描述!(错字都显示出来了!哈!)
对于函数来说,一方面可以给函数本身做注释,还可以给参数做注释!
/// <summary> /// 获取点数据 /// </summary> /// <param name="surveyDataFullName">测量数据全路径名称</param> /// <returns></returns> private List<CPoint> GetAllPoint(string surveyDataFullName) { ... }
※ 官方帮助参考:http://msdn.microsoft.com/zh-cn/library/5ast78ax.aspx
※ 书签设置参考:http://topic.csdn.net/u/20120112/12/38f1b889-0795-4f99-b0f1-1b9b2c827ba1.html