ArcGIS AddIN开发,winform的样式确实不太好看,而且高清屏上老是出现缩放问题。最近在转WPF,WPF的界面确实美观了不少,最近发现了一个WPF开源UI ,能否使用该类库制作更酷炫的AddIN界面呢?
地址:https://github.com/MaterialDesignInXAML/MaterialDesignInXamlToolkit
简易教程:https://github.com/MaterialDesignInXAML/MaterialDesignInXamlToolkit/wiki/Super-Quick-Start
下面介绍一下如何在ArcGIS AddIN项目中使用该类库
1.Nuget中添加MaterialDesign类库
在管理NuGet程序包界面中,搜索MaterialDesign,点击安装即可将MaterialDesignXamlToolkit相关类库添加至项目中。
2.在WPF窗体中配置资源
官网的教程是在App.xaml中配置MaterialDesign相关资源,而ArcMap AddIN项目是无App.xaml文件,查阅相关资料,可以在具体窗体的.xaml文件中增加
其他界面代码:。。。。
美化前后的界面:
3.其他处理
上述配置编译后,弹出界面时,出现如下异常:
大体问题是 没有找到MaterialDesign相关类库
百度、Google了一大堆帖子,没有找到有价值的解决方案。
之后经过测试发现,ArcGIS AddIN插件的运行环境与WPF的运行环境存在一些区别,相当于ArcGIS AddIn的运行类库是在ArcGIS的安装目录下,默认的是C:\Program Files (x86)\ArcGIS\Desktop10.3\bin,而ArcGIS AddIN在安装的时候,安装的路劲为 C:\Users\<用户名>\AppData\Local\ESRI\Desktop10.3\AssemblyCache\{插件Guid},包括AddIN项目编译的类库以及添加的第三方类库。因此,ArcGIS AddIN插件中的WPF窗体,在显示的时候,无法获取到MaterialDesign类库,导致产生上述异常。
解决方法:将MaterialDesign相关类库拷贝到ArcGIS的安装目录下,即可解决上述问题。可以在InitialComponent()方法之前,判断MaterialDesign类库是否存在,如果不存在,去AddIN的目录中将这些类库拷贝至运行目录即可。代码如下:
public class LibraryBaseHelper
{
///
/// 类库初始化
///
///
public static void Initial(LibraryEnum le)
{
//获取ArcGIS安装路径
string targetPath = ESRI.ArcGIS.RuntimeManager.ActiveRuntime.Path;
targetPath = targetPath+"\\bin";
Type tp = typeof(LibraryBaseHelper);
string location = tp.Assembly.Location;
location = System.IO.Path.GetDirectoryName(location);
DirectoryInfo di = new DirectoryInfo(location);
FileInfo[] fis = di.GetFiles();
for (int i = 0; i < fis.Length; i++)
{
string dllpath = System.IO.Path.Combine(targetPath, fis[i].Name);
if (!File.Exists(dllpath))
{
if (detect(fis[i], le))
{
fis[i].CopyTo(dllpath);
}
}
}
}
private static bool detect(FileInfo fi, LibraryEnum le)
{
bool re=false;
switch (le)
{
case LibraryEnum.MaterialDesign:
if (fi.Name.Contains("MaterialDesign"))
{
re = true;
}
break;
}
return re;
}
public enum LibraryEnum
{
MaterialDesign = 0
}
}
在WPF窗体的构造函数中增加对上述方法的引用即可。
public RemoveAttrSpecialStrFrm()
{
GISCommonHelper.LibraryBaseHelper.Initial(GISCommonHelper.LibraryBaseHelper.LibraryEnum.MaterialDesign);
InitializeComponent();
}