介绍
在ArcEngine实际开发过程中,经常会使用事件执行某项操作,比如更换地图后修改地图引用,添加图层后将添加的图层自动更新到combox控件中。本文以实例形式探讨ArcEngine事件的使用方式。主要使用的接口为IActiveViewEvents_Event接口以及AxMapControl类。
IActiveViewEvents_Event接口
IActiveViewEvents_Event接口中包含11个事件(注意是IActiveViewEvents_Event接口不是IActiveViewEvents接口,AE中的事件接口后面都带有"_Event"),11个事件的触发条件如下:
事件 | 描述 |
AfterDraw | 在指定的阶段被绘制后触发 |
AfterItemDraw | 在绘制单个视图项后触发。示例:视图项包括地图中的图层或页面布局中的元素 |
ContentsChanged | 当视图的内容改变时触发 |
ContentsCleared | 视图内容被清除后触发 |
FocusMapChanged | 激活新地图时触发 |
ItemAdded | 将项添加到视图时触发 |
ItemDeleted | 从视图中删除项时触发 |
ItemReordered | 当视图项被重新排序时触发 |
SelectionChanged | 选择集变化后触发 |
SpatialReferenceChanged | 当空间参考改变时触发 |
ViewRefreshed | 在绘制之前刷新视图时触发 |
使用此接口监听与活动视图相关的特定事件,如AfterDraw和SelectionChanged。许多类实现这个接口,每个类触发不同的事件。例如,Map对象不会触发FocusMapChanged事件,而PageLayout对象会。类似地,Map对象在从Map中删除一个层时触发ItemDeleted事件,而PageLayout在删除Map Frame或图形等元素时触发相同的事件。
注意您正在监听的特定对象的事件。例如,仅在FocusMap对象上编写侦听SelectionChanged事件的代码将不会通过更改布局视图中的选择触发事件。此外,如果FocusMap更改,则必须重置客户端。
AfterItemDraw事件只有在IViewManager::VerboseEvents属性设置为True时才会触发。默认情况下,此属性设置为False。
示例
本示例使用AxMapControl::OnMapReplaced事件和IActiveViewEvents_Event::ItemAdded、IActiveViewEvents_Event::ItemDeleted事件实现当主窗体中图层发生变化时,子窗体combox控件中的图层列表自动变化。
主窗体样式及代码
namespace WindowsFormsApplication1 { public partial class FrmMain : Form { public FrmMain() { InitializeComponent(); } private void btnChild_Click(object sender, EventArgs e) { FrmChild frm = new FrmChild(axMapControl1); frm.Show(); } private void btnMXD_Click(object sender, EventArgs e) { ICommand cmd = new ControlsOpenDocCommand(); cmd.OnCreate(axMapControl1.Object); cmd.OnClick(); } private void btnAdd_Click(object sender, EventArgs e) { ICommand cmd = new ControlsAddDataCommand(); cmd.OnCreate(axMapControl1.Object); cmd.OnClick(); } private void btnDelete_Click(object sender, EventArgs e) { if (axMapControl1.LayerCount > 0) { axMapControl1.DeleteLayer(0); } } } }
子窗体样式及代码
namespace WindowsFormsApplication1 { public partial class FrmChild : Form { IActiveViewEvents_Event pEvent; IMapControl2 mapCon; AxMapControl pAxMapCon; public FrmChild(AxMapControl axMapCon) { InitializeComponent(); pAxMapCon = axMapCon; //注册地图更换事件 pAxMapCon.OnMapReplaced += pAxMapCon_OnMapReplaced; //注册项目添加和删除事件 mapCon = axMapCon.Object as IMapControl2; pEvent = mapCon.Map as IActiveViewEvents_Event; pEvent.ItemAdded += pEvent_ItemAdded; pEvent.ItemDeleted += pEvent_ItemDeleted; } private void pAxMapCon_OnMapReplaced(object sender, IMapControlEvents2_OnMapReplacedEvent e) { IMap pMap = e.newMap as IMap; pEvent = pMap as IActiveViewEvents_Event; pEvent.ItemAdded += pEvent_ItemAdded; pEvent.ItemDeleted += pEvent_ItemDeleted; comboBox1.Items.Clear(); for (int i = 0; i < pMap.LayerCount; i++) { comboBox1.Items.Add(mapCon.get_Layer(i).Name); } if (comboBox1.Items.Count > 0) { comboBox1.SelectedIndex = 0; } } private void pEvent_ItemAdded(object Item) { ILayer pLayer = Item as ILayer; comboBox1.Items.Add(pLayer.Name); comboBox1.SelectedIndex = comboBox1.Items.Count - 1; } private void pEvent_ItemDeleted(object Item) { ILayer pLayer = Item as ILayer; comboBox1.Items.Remove(pLayer.Name); if (comboBox1.Items.Count > 0) { comboBox1.SelectedIndex = 0; } else { comboBox1.Text = ""; } } private void FrmChild_Load(object sender, EventArgs e) { for (int i = 0; i < mapCon.LayerCount; i++) { comboBox1.Items.Add(mapCon.get_Layer(i).Name); } if (comboBox1.Items.Count > 0) { comboBox1.SelectedIndex = 0; } } } }