注意:初次使用時請測試結果是否滿足要求
此工具基於arcgis軟件使用,較適用於計算地塊數量較多的四至座標,批量獲取每個地塊最北、最東、最西、最南四個方位的座標點,適用於林地用地範圍描敘,獲取座標點後,導出屬性表直接獲得四至點的座標。
下載地址 鏈接: https://pan.baidu.com/s/19_tya6hQ_YTzaTD2CfFMPQ 提取碼: 5na9
使用方式 雙擊安裝後,工具條中自定義>加載項管理器>自定義
將工具拖動到工具條中即可使用
工具界面如下:
插件代碼:
form窗體代碼
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;
using GISCommonHelper;
using ESRI.ArcGIS.Carto;
using ESRI.ArcGIS.Geodatabase;
using ESRI.ArcGIS.Geometry;
namespace SiZhiCoordinate
{
public partial class frmSet : Form
{
public frmSet()
{
InitializeComponent();
}
private IMap pMap = null;
private IFeatureLayer pftlyr;
private string sx;
public string Sx
{
get { return sx; }
set { sx = value; }
}
private string sy;
public string Sy
{
get { return sy; }
set { sy = value; }
}
private string ex;
public string Ex
{
get { return ex; }
set { ex = value; }
}
private string ey;
public string Ey
{
get { return ey; }
set { ey = value; }
}
private string nx;
public string Nx
{
get { return nx; }
set { nx = value; }
}
private string ny;
public string Ny
{
get { return ny; }
set { ny = value; }
}
private string wx;
public string Wx
{
get { return wx; }
set { wx = value; }
}
private string wy;
public string Wy
{
get { return wy; }
set { wy = value; }
}
public IFeatureLayer Pftlyr
{
get { return pftlyr; }
set { pftlyr = value; }
}
private void frmSet_Load(object sender, EventArgs e)
{
pMap = ArcMap.Document.FocusMap;
GISCommonHelper.CartoLyrHelper.setFeatureLyrCombox(ref cmbLayer, pMap, esriGeometryType.esriGeometryPolygon);
}
private void cmbLayer_SelectedIndexChanged(object sender, EventArgs e)
{
if (cmbLayer.SelectedIndex == -1)
return;
pftlyr = cmbLayer.SelectedValue as IFeatureLayer;
IFields pFields = pftlyr.FeatureClass.Fields;
CartoFieldHelper.setFieldCombox(ref cmbNX, pFields);
CartoFieldHelper.setFieldCombox(ref cmbNY, pFields);
CartoFieldHelper.setFieldCombox(ref cmbSX, pFields);
CartoFieldHelper.setFieldCombox(ref cmbSY, pFields);
CartoFieldHelper.setFieldCombox(ref cmbEX, pFields);
CartoFieldHelper.setFieldCombox(ref cmbEY, pFields);
CartoFieldHelper.setFieldCombox(ref cmbWX, pFields);
CartoFieldHelper.setFieldCombox(ref cmbWY, pFields);
}
private void btnOK_Click(object sender, EventArgs e)
{
if (cmbNX.SelectedIndex == -1 || cmbNY.SelectedIndex==-1 || cmbSX.SelectedIndex==-1 || cmbSY.SelectedIndex==-1||
cmbEX.SelectedIndex==-1 || cmbEY.SelectedIndex==-1 || cmbWX.SelectedIndex==01 || cmbWY.SelectedIndex==-1)
return;
nx = cmbNX.SelectedValue.ToString();
ny = cmbNY.SelectedValue.ToString();
sx = cmbSX.SelectedValue.ToString();
sy = cmbSY.SelectedValue.ToString();
wx = cmbWX.SelectedValue.ToString();
wy = cmbWY.SelectedValue.ToString();
ex = cmbEX.SelectedValue.ToString();
ey = cmbEY.SelectedValue.ToString();
this.DialogResult = DialogResult.OK;
}
private void btnCancel_Click(object sender, EventArgs e)
{
this.DialogResult = DialogResult.Cancel;
}
}
}
tool代碼
using System;
using System.Collections.Generic;
using System.Text;
using System.IO;
using GISCommonHelper;
using System.Windows.Forms;
using ESRI.ArcGIS.Carto;
using ESRI.ArcGIS.Geometry;
using ESRI.ArcGIS.Geodatabase;
namespace SiZhiCoordinate
{
public class btnSiZhiCmd : ESRI.ArcGIS.Desktop.AddIns.Button
{
public btnSiZhiCmd()
{
}
protected override void OnClick()
{
//
// TODO: Sample code showing how to access button host
//
ArcMap.Application.CurrentTool = null;
try
{
frmSet fs = new frmSet();
if (fs.ShowDialog() == DialogResult.OK)
{
Excute(fs);
MessageBox.Show("處理完成");
}
}
catch (System.Exception ex)
{
MessageBox.Show("發生異常:"+ex.Message);
}
}
protected override void OnUpdate()
{
Enabled = ArcMap.Application != null;
}
private void Excute(frmSet fs)
{
IFeatureClass pftcls = fs.Pftlyr.FeatureClass;
IDataset pds = pftcls as IDataset;
IWorkspaceEdit pwsEdit = pds.Workspace as IWorkspaceEdit;
pwsEdit.StartEditing(true);
pwsEdit.StartEditOperation();
IFeatureCursor pftCursor = pftcls.Update(null, true);
IFeature pFeature = pftCursor.NextFeature();
while (pFeature != null)
{
IPolygon pPolygon = pFeature.ShapeCopy as IPolygon;
NSEW nw = getNSEW(pPolygon);
pFeature.set_Value(pFeature.Fields.FindField(fs.Nx), nw.nx);
pFeature.set_Value(pFeature.Fields.FindField(fs.Ny), nw.ny);
pFeature.set_Value(pFeature.Fields.FindField(fs.Sx), nw.sx);
pFeature.set_Value(pFeature.Fields.FindField(fs.Sy), nw.sy);
pFeature.set_Value(pFeature.Fields.FindField(fs.Wx), nw.wx);
pFeature.set_Value(pFeature.Fields.FindField(fs.Wy), nw.wy);
pFeature.set_Value(pFeature.Fields.FindField(fs.Ex), nw.ex);
pFeature.set_Value(pFeature.Fields.FindField(fs.Ey), nw.ey);
pftCursor.UpdateFeature(pFeature);
pFeature = pftCursor.NextFeature();
}
pwsEdit.StopEditOperation();
pwsEdit.StopEditing(true);
}
private NSEW getNSEW(IPolygon pPolygon)
{
NSEW nw = new NSEW();
IPointCollection pntCol = pPolygon as IPointCollection;
int ni=-1, si=-1, wi=-1, ei=-1;
double nflag=0, sflag=0, wflag=0, eflag=0;
for (int i = 0; i < pntCol.PointCount; i++)
{
double x = pntCol.get_Point(i).X;
double y = pntCol.get_Point(i).Y;
if (i == 0)
{
//獲取初值
nflag = y;
sflag = y;
wflag = x;
eflag = x;
ni = i; si = i; wi = i; ei = i;
}
else
{
if (x > eflag)
{
//更東
eflag = x;
ei = i;
}
if (x < wflag)
{
//更西
wflag = x;
wi = i;
}
if (y > nflag)
{
//更北
nflag=y;
ni = i;
}
if (y < sflag)
{
//更南
sflag=y;
si = i;
}
}
}
nw.ex = pntCol.get_Point(ei).X;
nw.ey = pntCol.get_Point(ei).Y;
nw.wx = pntCol.get_Point(wi).X;
nw.wy = pntCol.get_Point(wi).Y;
nw.sx = pntCol.get_Point(si).X;
nw.sy = pntCol.get_Point(si).Y;
nw.nx = pntCol.get_Point(ni).X;
nw.ny = pntCol.get_Point(ni).Y;
return nw;
}
}
class NSEW
{
public double nx, ny, sx, sy, wx, wy, ex, ey;
}
}
程序中用到的其他類
winform字段設置輔助類
public class CartoFieldHelper
{
/// <summary>
/// 匹配模式
/// </summary>
public enum NAmode
{
NameEqual,
AliasNameEqual,
NAEqual,
NameLike,
AliasNameLike,
NALike
}
/// <summary>
///
/// </summary>
/// <param name="cmb"></param>
/// <param name="pFields"></param>
/// <param name="mode"></param>
/// <param name="kstr"></param>
/// <param name="useBlank"></param>
/// <param name="ets"></param>
public static void setFieldCombox(ref ComboBox cmb, IFields pFields, NAmode mode, string kstr, bool useBlank = false, params esriFieldType[] ets)
{
setFieldCombox(ref cmb, pFields, useBlank, ets);
for (int i = 0; i < cmb.Items.Count; i++)
{
Name_AliasName na = cmb.SelectedItem as Name_AliasName;
if (na == null)
continue;
bool b_get = false;
switch (mode)
{
case NAmode.NALike:
if (na.name.Contains(kstr) || na.alias_name.Contains(kstr))
{
cmb.SelectedIndex = i;
b_get = true;
}
break;
case NAmode.NameLike:
if (na.name.Contains(kstr))
{
cmb.SelectedIndex = i;
b_get = true;
}
break;
case NAmode.AliasNameLike:
if ( na.alias_name.Contains(kstr))
{
cmb.SelectedIndex = i;
b_get = true;
}
break;
case NAmode.NAEqual:
if (na.name==kstr || na.alias_name==kstr)
{
cmb.SelectedIndex = i;
b_get = true;
}
break;
case NAmode.NameEqual:
if (na.name == kstr)
{
cmb.SelectedIndex = i;
b_get = true;
}
break;
case NAmode.AliasNameEqual:
if (na.alias_name==kstr)
{
cmb.SelectedIndex = i;
b_get = true;
}
break;
}
if (b_get)
{
break;//中斷循環
}
}
}
public static void setFieldCombox(ref ComboBox cmb,IFields pFields,bool useBlank=false)
{
cmb.DisplayMember = "alias_name";
cmb.ValueMember = "name";
List<Name_AliasName> list = getLyrFields(pFields);
if (useBlank)
{
Name_AliasName na = new Name_AliasName("", "");
list.Insert(0, na);
}
//list.Insert(0, new Name_AliasName("",""));
cmb.DataSource = list;
cmb.SelectedIndex = -1;
cmb.DropDownStyle = ComboBoxStyle.DropDownList;
}
public static void setFieldCombox(ref ComboBox cmb, IFields pFields,bool useBlank=false,params esriFieldType[] ets)
{
cmb.DisplayMember = "alias_name";
cmb.ValueMember = "name";
List<Name_AliasName> list = getLyrFields(pFields,ets);
if(useBlank)
{
Name_AliasName na = new Name_AliasName("", "");
list.Insert(0, na);
}
cmb.DataSource = list;
cmb.SelectedIndex = -1;
cmb.DropDownStyle = ComboBoxStyle.DropDownList;
}
/// <summary>
/// 獲取特定字段類型的字段名與假名集合
/// </summary>
/// <param name="pFields"></param>
/// <param name="et">字段類型</param>
/// <returns></returns>
public static List<Name_AliasName> getLyrFields(IFields pFields,params esriFieldType[] ets)
{
List<Name_AliasName> list = new List<Name_AliasName>();
for (int i = 0; i < pFields.FieldCount; i++)
{
IField pfd = pFields.get_Field(i);
if (ets.Length == 0)
{
list.Add(new Name_AliasName(pfd.Name, pfd.AliasName));
}
else
{
if (ets.Contains(pfd.Type))
{
list.Add(new Name_AliasName(pfd.Name, pfd.AliasName));
}
}
}
return list;
}
/// <summary>
/// 獲取所有字段名與假名集合
/// </summary>
/// <param name="pFields"></param>
/// <returns></returns>
public static List<Name_AliasName> getLyrFields(IFields pFields)
{
List<Name_AliasName> list = new List<Name_AliasName>();
for (int i = 0; i < pFields.FieldCount; i++)
{
IField pfd = pFields.get_Field(i);
list.Add(new Name_AliasName(pfd.Name, pfd.AliasName));
}
return list;
}
}
winform中圖層輔助類
public class CartoLyrHelper
{
#region 設置要素圖層Combox
/// <summary>
/// 設置要素圖層Combox
/// </summary>
/// <param name="cmb"></param>
/// <param name="pMap"></param>
/// <param name="tp"></param>
/// <param name="nl">默認選中的圖層</param>
/// <param name="useBlank"></param>
/// <returns></returns>
public static List<name_Layer> setFeatureLyrCombox(ref ComboBox cmb, IMap pMap, esriGeometryType tp,name_Layer nl,bool useBlank = false)
{
List<name_Layer> lyrlist = setFeatureLyrCombox(ref cmb, pMap, tp, useBlank);
for (int i = 0; i < cmb.Items.Count; i++)
{
name_Layer nltmp = cmb.Items[i] as name_Layer;
if (nltmp.id == nl.id)
{
cmb.SelectedIndex = i;
break;
}
}
return lyrlist;
}
/// <summary>
/// 設置圖要素層Combox
/// </summary>
/// <param name="cmb"></param>
/// <param name="pMap"></param>
/// <param name="tp">幾何類型</param>
/// <param name="useBlank">使用默認的空白項</param>
/// <returns></returns>
public static List<name_Layer> setFeatureLyrCombox(ref ComboBox cmb, IMap pMap,esriGeometryType tp,bool useBlank=false)
{
cmb.DisplayMember = "name";
cmb.ValueMember = "layer";
List<name_Layer> lyrlist = new List<name_Layer>();
if (useBlank)
{
name_Layer nl = new name_Layer("", null);
lyrlist.Insert(0, nl);
}
getAllFtlyr(ref lyrlist, pMap,tp);
cmb.DataSource = lyrlist;
cmb.DropDownStyle = ComboBoxStyle.DropDownList;
cmb.SelectedIndex = -1;
return lyrlist;
}
#endregion
#region 設置圖層Combox
public static List<name_Layer> setLyrCombox<T>(ref ComboBox cmb, IMap pMap,name_Layer nl, bool useBlank)
{
List<name_Layer> nllist = setLyrCombox<T>(ref cmb, pMap, useBlank);
for (int i = 0; i < cmb.Items.Count; i++)
{
name_Layer nlTmp = cmb.Items[i] as name_Layer;
if (nlTmp.id == nl.id)
{
cmb.SelectedIndex = i;
break;
}
}
return nllist;
}
/// <summary>
/// 設置圖層Combox
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="cmb"></param>
/// <param name="pMap"></param>
/// <returns></returns>
public static List<name_Layer> setLyrCombox<T>(ref ComboBox cmb,IMap pMap,bool useBlank=false)
{
cmb.DisplayMember = "name";
cmb.ValueMember = "layer";
List<name_Layer> lyrlist = new List<name_Layer>();
if (useBlank)
{
name_Layer nl = new name_Layer("", null);
lyrlist.Insert(0, nl);
}
getAllLayer<T>(ref lyrlist, pMap);
cmb.DataSource = lyrlist;
cmb.DropDownStyle = ComboBoxStyle.DropDownList;
cmb.SelectedIndex = -1;
return lyrlist;
}
#endregion
#region 獲取所有圖層
public static List<T> getAllLayer<T>(IMap pMap)
{
List<name_Layer> nllist = new List<name_Layer>();
getAllLayer<T>(ref nllist, pMap);
List<T> lyrlist = new List<T>();
for (int i = 0; i < nllist.Count; i++)
{
lyrlist.Add((T)nllist[i].layer);
}
return lyrlist;
}
#endregion
#region 獲取所有圖層集合,適用於Combox
/// <summary>
/// 獲取圖層集合,適用於combox
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="nllist"></param>
/// <param name="pMap"></param>
public static void getAllLayer<T>(ref List<name_Layer> nllist, IMap pMap)
{
for (int i = 0; i < pMap.LayerCount; i++)
{
ILayer plyr = pMap.get_Layer(i);
if (plyr is T)
{
nllist.Add(new name_Layer(plyr.Name, plyr));
}
else if (plyr is IGroupLayer)
{
getGroupLayer<T>(ref nllist, (IGroupLayer)plyr);
}
}
}
#endregion
#region 獲取所有要素圖層
/// <summary>
/// 獲取所有要素圖層
/// </summary>
/// <param name="nllist"></param>
/// <param name="pMap"></param>
/// <param name="tp"></param>
public static void getAllFtlyr(ref List<name_Layer> nllist, IMap pMap, ESRI.ArcGIS.Geometry.esriGeometryType tp)
{
for (int i = 0; i < pMap.LayerCount; i++)
{
ILayer plyr = pMap.get_Layer(i);
if (plyr is IFeatureLayer)
{
if (((IFeatureLayer)plyr).FeatureClass != null) //避免圖層感嘆號時,可能存在的問題
{
if (tp == esriGeometryType.esriGeometryAny)
{
nllist.Add(new name_Layer(plyr.Name, plyr));
}
else
{
if (((IFeatureLayer)plyr).FeatureClass.ShapeType == tp)
nllist.Add(new name_Layer(plyr.Name, plyr));
}
}
}
else if (plyr is IGroupLayer)
{
getGroupLayer(ref nllist, (IGroupLayer)plyr,tp);
}
}
}
#endregion
#region 獲取圖層組的子圖層
/// <summary>
/// 獲取圖層組的子圖層
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="nllist"></param>
/// <param name="pGroupLyr"></param>
private static void getGroupLayer<T>(ref List<name_Layer> nllist, IGroupLayer pGroupLyr)
{
ICompositeLayer pCmsLyr = pGroupLyr as ICompositeLayer;
for (int i = 0; i < pCmsLyr.Count; i++)
{
ILayer plyr = pCmsLyr.get_Layer(i);
if (plyr is T)
{
nllist.Add(new name_Layer(plyr.Name, plyr));
}
if (plyr is IGroupLayer)
{
getGroupLayer<T>(ref nllist, (IGroupLayer)plyr);
}
}
}
/// <summary>
/// 獲取圖層組的子圖層,只針對於FeatureLayer
/// </summary>
/// <param name="nllist"></param>
/// <param name="pGroupLyr"></param>
/// <param name="tp"></param>
private static void getGroupLayer(ref List<name_Layer> nllist, IGroupLayer pGroupLyr,esriGeometryType tp)
{
ICompositeLayer pCmsLyr = pGroupLyr as ICompositeLayer;
for (int i = 0; i < pCmsLyr.Count; i++)
{
ILayer plyr = pCmsLyr.get_Layer(i);
if (plyr is IFeatureLayer)
{
if(((IFeatureLayer)plyr).FeatureClass!=null){
if (((IFeatureLayer)plyr).FeatureClass.ShapeType == tp)
nllist.Add(new name_Layer(plyr.Name, plyr));
}
}
if (plyr is IGroupLayer)
{
getGroupLayer(ref nllist, (IGroupLayer)plyr,tp);
}
}
}
#endregion
#region 圖層更改數據源
/// <summary>
/// 根據圖層中的數據源的數據集名稱設置數據源
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="pLyr"></param>
/// <param name="pWs"></param>
public static void setDataSourceByDsname<T>(ILayer pLyr, IWorkspace pWs,string pnm="")
{
string dsName;
if (string.IsNullOrEmpty(pnm))
{
dsName = (((IDataLayer)pLyr).DataSourceName as IDatasetName).Name;
}
else
{
dsName = pnm;
}
try
{
if (typeof(T) == typeof(IFeatureLayer))
{
IFeatureWorkspace pfws = pWs as IFeatureWorkspace;
IFeatureLayer pftLyr = pLyr as IFeatureLayer;
pftLyr.FeatureClass = pfws.OpenFeatureClass(dsName);
}
else if (typeof(T) == typeof(IRasterLayer))
{
IRasterWorkspace2 prstWorkspace = pWs as IRasterWorkspace2;
IRasterLayer prstLyr = pLyr as IRasterLayer;
IRasterDataset rasterDataset = prstWorkspace.OpenRasterDataset(dsName);
prstLyr.CreateFromDataset(rasterDataset);
}
}
catch (System.Exception ex)
{
//可能會有未知的名稱問題導致圖層名稱更改而無法獲取名稱的問題
}
}
public static void setDataSourceByDsnameTwice<T>(ILayer pLyr, IWorkspace pWs)
{
IWorkspace2 pws2 = pWs as IWorkspace2;
string dsName;
dsName = (((IDataLayer)pLyr).DataSourceName as IDatasetName).Name;
esriDatasetType edt;
if (typeof(T) == typeof(IFeatureLayer))
{
edt = esriDatasetType.esriDTFeatureClass;
}
else if (typeof(T) == typeof(IRasterLayer))
{
edt = esriDatasetType.esriDTRasterDataset;
}
else
edt = esriDatasetType.esriDTAny;
if(pws2.get_NameExists(edt,dsName))
{
setDataSourceByDsname<T>(pLyr, pWs);
}
else
{
dsName = "_" + dsName;
if (pws2.get_NameExists(edt, dsName))
setDataSourceByDsname<T>(pLyr, pWs,dsName);
else
{
//不存在,不處理
}
}
}
/// <summary>
/// 根據圖層的名稱設置數據源
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="pLyr"></param>
/// <param name="pWs"></param>
public static void setDataSourceByLayerName<T>(ILayer pLyr, IWorkspace pWs)
{
string dsName = pLyr.Name;
if (typeof(T) == typeof(IFeatureLayer))
{
IFeatureWorkspace pfws = pWs as IFeatureWorkspace;
IFeatureLayer pftLyr = pLyr as IFeatureLayer;
pftLyr.FeatureClass = pfws.OpenFeatureClass(dsName);
}
else if (typeof(T) == typeof(IRasterLayer))
{
if (dsName.Contains("."))
dsName = dsName.Substring(0, dsName.LastIndexOf("."));
IRasterWorkspace2 prstWorkspace = pWs as IRasterWorkspace2;
IRasterLayer prstLyr = pLyr as IRasterLayer;
IRasterDataset rasterDataset = prstWorkspace.OpenRasterDataset(dsName);
prstLyr.CreateFromDataset(rasterDataset);
}
}
#endregion
}