我在研究生院写了许多ArcGIS VBA自动化程序。但是,它们完全依赖于ArcGIS Spatial Analyst扩展,该扩展不仅是闭源的,而且在威慑方面也很昂贵。
由于不赞成使用VBA,并且由于U的一些研究人员仍在使用我的VBA工具,所以我认为用.Net重写它们会很有趣。但是现在,有了更多经验,我进一步意识到,如果那些实用程序使用了开放算法,则将更适合于学术用途。
考虑到这一点,我正在考虑将Whitebox GAT视为Spatial Analyst水文学工具的潜在替代者,并且我很好奇是否存在与ArcGIS / Whitebox集成相关的成功案例或省时的“难题”。
我预计会有几个人会反对Saga,GRASS,R等的建议。如果这是您的职位,请说明为什么进行Whitebox集成是不明智的。例如,它是否仅支持几种输入格式,对大文件(1-2 GB以上)的处理不佳等?
我在Whitebox UI上进行了一些操作,并在他们的教程的帮助下,对放置的30米DEM进行了预处理并不困难。接下来,排列水力栅格后,我创建了一个倾泻点并绘制了分水岭。这足以让您感受到Whitebox的用户体验。
Whitebox可使用.Net或Python进行扩展和/或使用。在Whitebox UI中完成了一些基础知识之后,我认为我已经将典型的DEM预处理任务与简单的.Net自动化(目前还没有ArcMap)链接在一起。DEM预处理通常意味着以下内容:
- 不设置数据值(Whitebox需要此值,但Arc从来不需要)
- 填充水槽
- 创建流向栅格
- 创建流量累积栅格
我将以下Windows窗体“应用程序”(aka WhiteboxDaisyChain
)放在一起。它需要一个包含ArcGIS Grid(.FLT)的系统目录,并执行上述任务。如果您想尝试此操作,则需要下载已编译的二进制文件,解压缩,然后将所有.dll
文件从其中复制..\WhiteboxGAT_1_0_7\Plugins
到您的项目中-我将所有内容都放入..\WhiteboxDaisyChain\Whitebox
。但是,此示例仅需要DLLs
在代码示例顶部提到的四个。
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;
// 1) Create a new Windows Form
// 2) Put all these in a Whitebox folder in the C# project root.
// 3) Add project references to the following and create using statements:
using Interfaces; // requires Add Reference: Interfaces.dll
using ImportExport; // requires Add Reference: ImportExport.dll
using ConversionTools; // requires Add Reference: ConversionTools.dll
using flow; // requires Add Reference: flow.dll
namespace WhiteboxDaisyChain
{
// 4) Prepare to implement the IHost interface.
// 5) Right-click IHost, select "Implement interface.."
public partial class UI : Form, IHost
{
// 6) Add a BackgroundWorker object.
private BackgroundWorker worker;
public UI()
{
InitializeComponent();
// 7) Instantiate the worker and set "WorkerReportsProgress".
worker = new BackgroundWorker();
worker.WorkerReportsProgress = true;
}
// 8) Use some event to set things in motion.. i.e. Button click.
private void button1_Click(object sender, EventArgs e)
{
progressLabel.Text = "Running..";
// This is the path containing my ArcGrid .FLT.
// All processing will unfold to this directory.
string path = "C:\\xData\\TutorialData\\DemWhitebox\\";
string[] fltArgs = new string[1];
fltArgs[0] = path + "greene30.flt"; // in: Arc floating point grid
// creates a raster in Whitebox data model
ImportArcGrid importAG = new ImportArcGrid();
importAG.Initialize(this as IHost);
importAG.Execute(fltArgs, worker); // out: path + "greene30.dep"
// set the nodata value on the DEM
string[] noDataArgs = new string[2];
noDataArgs[0] = path + "greene30.dep"; // in: my raw DEM
noDataArgs[1] = "-9999"; // mine used -9999 as nodata value
SetNoData setNoData = new SetNoData();
setNoData.Initialize(this as IHost);
setNoData.Execute(noDataArgs, worker); // out: path + "greene30.dep"
// fill sinks in the DEM
string[] fillSinksArgs = new string[4];
fillSinksArgs[0] = path + "greene30.dep"; // in: my DEM with NoData Fixed
fillSinksArgs[1] = path + "greene30_fill.dep"; // out: my DEM filled
fillSinksArgs[2] = "50"; // the dialog default
fillSinksArgs[3] = "0.01"; // the dialog default
FillDepsBySize fillSinks = new FillDepsBySize();
fillSinks.Initialize(this as IHost);
fillSinks.Execute(fillSinksArgs, worker);
// create a flow direction raster
string[] flowDirArgs = new string[2];
flowDirArgs[0] = path + "greene30_fill.dep"; // in: my Filled DEM
flowDirArgs[1] = path + "greene30_dir.dep"; // out: flow direction raster
FlowPointerD8 flowDirD8 = new FlowPointerD8();
flowDirD8.Initialize(this as IHost);
flowDirD8.Execute(flowDirArgs, worker);
// create a flow accumulation raster
string[] flowAccArgs = new string[4];
flowAccArgs[0] = path + "greene30_dir.dep"; // in: my Flow Direction raster
flowAccArgs[1] = path + "greene30_acc.dep"; // out: flow accumulation raster
flowAccArgs[2] = "Specific catchment area (SCA)"; // a Whitebox dialog input
flowAccArgs[3] = "false"; // a Whitebox dialog input
FlowAccumD8 flowAccD8 = new FlowAccumD8();
flowAccD8.Initialize(this as IHost);
flowAccD8.Execute(flowAccArgs, worker);
progressLabel.Text = "";
progressLabel.Text = "OLLEY-OLLEY-OXEN-FREE!";
}
/* IHost Implementation Methods Below Here */
public string ApplicationDirectory
{
get { throw new NotImplementedException(); }
}
public void ProgressBarLabel(string label)
{
this.progressLabel.Text = "";
this.progressLabel.Text = label; // This is the only one I used.
}
public string RecentDirectory
{
get
{
throw new NotImplementedException();
}
set
{
throw new NotImplementedException();
}
}
public bool RunInSynchronousMode
{
get
{
throw new NotImplementedException();
}
set
{
throw new NotImplementedException();
}
}
public void RunPlugin(string PluginClassName)
{
throw new NotImplementedException();
}
public void SetParameters(string[] ParameterArray)
{
throw new NotImplementedException();
}
public void ShowFeedback(string strFeedback, string Caption = "GAT Message")
{
throw new NotImplementedException();
}
}
}
到目前为止,我正在对此进行挖掘,但是我还没有一个真正的成功故事或任何可以描述的秀场表演者。.我的下一个目标是交互式地从ArcMap提交倾点。基本上,我想单击地图..获取分水岭。