爱气象,爱气象家园! 

气象家园

 找回密码
 立即注册

QQ登录

只需一步,快速开始

新浪微博登陆

只需一步, 快速开始

搜索
查看: 10226|回复: 15

MeteoInfo二次开发教程(十一)

[复制链接]

新浪微博达人勋

发表于 2012-11-12 13:18:13 | 显示全部楼层 |阅读模式

登录后查看更多精彩内容~

您需要 登录 才可以下载或查看,没有帐号?立即注册 新浪微博登陆

x
这一讲介绍一下如何在状态栏中显示MapView和MapLayout中鼠标所在位置的地理坐标。已在MeteoInfo网站上更新了Demo程序(http://www.meteothinker.com/Downloads.aspx),效果如下:

Image00273.png
Image00274.png

1、首先在状态栏中增加一个ToolStripStatusLabel控件,命名为TSSL_Coord用了显示鼠标所在地理坐标。

2、增加MapView_MouseMove和Layout_MouseMove两个鼠标事件函数来获取鼠标所在位置的地理坐标。如果是经纬度投影,直接用ScreenToProj就可以获得鼠标所在位置的经纬度;如果是其它投影,ScreenToProj获得的是该投影下的坐标位置(以米为单位),想要得到经纬度需要进行投影变换,定义投影前后的ProjectionInfo(fromProj即当前投影,toProj设为经纬度投影),用Reproject.ReprojectPoints方法可将当前投影中鼠标所在点的坐标投影为经纬度坐标,详见以下代码:
  1. private void MapView_MouseMove(object sender, MouseEventArgs e)
  2.         {
  3.             double ProjX, ProjY;
  4.             ProjX = 0;
  5.             ProjY = 0;
  6.             layersLegend1.ActiveMapFrame.MapView.ScreenToProj(ref ProjX, ref ProjY, e.X, e.Y);
  7.             if (layersLegend1.ActiveMapFrame.MapView.Projection.IsLonLatMap)
  8.             {
  9.                 this.TSSL_Coord.Text = "Lon: " + ProjX.ToString("0.00") + "; Lat: " + ProjY.ToString("0.00");
  10.             }
  11.             else
  12.             {
  13.                 string theText = this.TSSL_Coord.Text = "X: " + ProjX.ToString("0.0") + "; Y: " + ProjY.ToString("0.0");
  14.                 if (layersLegend1.ActiveMapFrame.MapView.Projection.ProjInfo.Transform.ProjectionName == ProjectionNames.Robinson)
  15.                     return;

  16.                 ProjectionInfo toProj = KnownCoordinateSystems.Geographic.World.WGS1984;
  17.                 ProjectionInfo fromProj = layersLegend1.ActiveMapFrame.MapView.Projection.ProjInfo;
  18.                 double[][] points = new double[1][];
  19.                 points[0] = new double[] { ProjX, ProjY };
  20.                 //double[] Z = new double[1];
  21.                 try
  22.                 {
  23.                     Reproject.ReprojectPoints(points, fromProj, toProj, 0, 1);
  24.                     this.TSSL_Coord.Text = theText + " (Lon: " + points[0][0].ToString("0.00") + "; Lat: " +
  25.                         points[0][1].ToString("0.00") + ")";
  26.                 }
  27.                 catch
  28.                 {
  29.                     //this.TSSL_Coord.Text = "X: " + ProjX.ToString("0.0") + "; Y: " + ProjY.ToString("0.0");
  30.                 }
  31.             }            
  32.         }
复制代码
  1. private void Layout_MouseMove(object sender, MouseEventArgs e)
  2.         {
  3.             Point pageP = layersLegend1.MapLayout.ScreenToPage(e.X, e.Y);
  4.             foreach (MapFrame mf in layersLegend1.MapFrames)
  5.             {
  6.                 Rectangle rect = mf.LayoutBounds;
  7.                 if (MIMath.PointInRectangle(pageP, rect))
  8.                 {
  9.                     double ProjX, ProjY;
  10.                     ProjX = 0;
  11.                     ProjY = 0;
  12.                     mf.MapView.ScreenToProj(ref ProjX, ref ProjY, pageP.X - rect.Left, pageP.Y - rect.Top, layersLegend1.MapLayout.Zoom);
  13.                     //ProjX = ProjX * MapDocument.MapLayout.Zoom;
  14.                     //ProjY = ProjY / MapDocument.MapLayout.Zoom;
  15.                     if (mf.MapView.Projection.IsLonLatMap)
  16.                     {
  17.                         this.TSSL_Coord.Text = "Lon: " + ProjX.ToString("0.00") + "; Lat: " + ProjY.ToString("0.00");
  18.                     }
  19.                     else
  20.                     {
  21.                         string theText = this.TSSL_Coord.Text = "X: " + ProjX.ToString("0.0") + "; Y: " + ProjY.ToString("0.0");
  22.                         if (mf.MapView.Projection.ProjInfo.Transform.ProjectionName == ProjectionNames.Robinson)
  23.                             return;

  24.                         ProjectionInfo toProj = KnownCoordinateSystems.Geographic.World.WGS1984;
  25.                         ProjectionInfo fromProj = mf.MapView.Projection.ProjInfo;
  26.                         double[][] points = new double[1][];
  27.                         points[0] = new double[] { ProjX, ProjY };
  28.                         //double[] Z = new double[1];
  29.                         try
  30.                         {
  31.                             Reproject.ReprojectPoints(points, fromProj, toProj, 0, 1);
  32.                             this.TSSL_Coord.Text = theText + " (Lon: " + points[0][0].ToString("0.00") + "; Lat: " +
  33.                                 points[0][1].ToString("0.00") + ")";
  34.                         }
  35.                         catch
  36.                         {
  37.                             //this.TSSL_Coord.Text = "X: " + ProjX.ToString("0.0") + "; Y: " + ProjY.ToString("0.0");
  38.                         }
  39.                     }

  40.                     break;
  41.                 }
  42.             }
  43.         }
复制代码

3、在SetMapView()函数中将MapView_MouseMove事件函数增加到mapView1的MouseMove事件中,在frmMain_Load函数中将Layout_MouseMove事件函数增加到layersLegend的MapLayout的MouseMove事件中,代码如下:
  1. private void SetMapView()
  2.         {
  3.             //Add map view
  4.             tabControl1.TabPages[0].Controls.Clear();
  5.             tabControl1.TabPages[0].Controls.Add(mapView1);
  6.             mapView1.Dock = DockStyle.Fill;
  7.             mapView1.MouseMove += new MouseEventHandler(this.MapView_MouseMove);
  8.             //mapView1.MouseDown += new MouseEventHandler(this.MapView_MouseDown);
  9.             //mapView1.GraphicSeleted += new EventHandler(this.MapView_GraphicSelected);            
  10.         }
复制代码
  1. private void frmMain_Load(object sender, EventArgs e)
  2.         {
  3.             //Set width and height
  4.             this.Width = 1000;
  5.             this.Height = 625;

  6.             //Load layers
  7.             LoadLayers();

  8.             //Add title
  9.             AddTitle();

  10.             //Add South China Sea map frame
  11.             AddMapFrame_ChinaSouthSea();

  12.             //Set map view
  13.             SetMapView();

  14.             //Set map layout mouse move event
  15.             layersLegend1.MapLayout.MouseMove += new MouseEventHandler(Layout_MouseMove);

  16.             //Add ActiveMapFrameChanged event
  17.             layersLegend1.ActiveMapFrameChanged += new EventHandler(ActiveMapFrameChanged);

  18.             //Set initial tool
  19.             TSB_Pan.PerformClick();            
  20.         }
复制代码




本帖被以下淘专辑推荐:

密码修改失败请联系微信:mofangbao

新浪微博达人勋

发表于 2012-11-14 21:04:21 | 显示全部楼层
最新的meteoinfo.dll的版本是什么啊?
密码修改失败请联系微信:mofangbao

新浪微博达人勋

发表于 2012-11-14 21:06:10 | 显示全部楼层
苹果电脑的系统下面能装vs2010么,能用meteoinfo么
密码修改失败请联系微信:mofangbao

新浪微博达人勋

 楼主| 发表于 2012-11-14 21:08:37 | 显示全部楼层
密码修改失败请联系微信:mofangbao

新浪微博达人勋

 楼主| 发表于 2012-11-14 21:21:52 | 显示全部楼层
本帖最后由 MeteoInfo 于 2012-11-14 22:34 编辑
西山守望 发表于 2012-11-14 21:06
苹果电脑的系统下面能装vs2010么,能用meteoinfo么

vs2010应该是不行。MeteoInfo是可以的,需要先安装Mono(http://www.go-mono.com/mono-downloads/download.html),在mono 2.6.7版是可以运行的,不过mono的最新版本我没测试过,你可以试试。很早以前用Mac系统运行MeteoInfo的一张截图:

Apple.jpg

mono平台距.Net还有很大差距,MeteoInfo虽然可以不做任何修改就可以在mono的支持下在linux等平台下运行,但速度比较慢且不稳定,部分功能也不能实现,比如读写NetCDF数据。由于缺乏大公司的支持,mono前景堪忧,我对于利用mono跨平台也没有太大信心,所以一直也没下功夫去做跨平台。最近想用Java重新开发MeteoInfo(已经完成了wContour的Java版),不过困难还是有很多(Java和C#不像想象中那么相似)且工作量巨大(MeteoInfo已经是一个比较庞大的系统了)。也没有任何项目支持,完全是凭个人兴趣来做,进度难以保障。
密码修改失败请联系微信:mofangbao

新浪微博达人勋

发表于 2012-11-15 10:35:26 | 显示全部楼层
好东西,学习
密码修改失败请联系微信:mofangbao

新浪微博达人勋

发表于 2012-11-15 18:12:13 | 显示全部楼层
能否显示鼠标所在点的数据的数值?好像在哪个帖子里看到过,但是找不到了。再有就是用getgriddata_levlon读数据和用dimensionset中的.lenlon设置再用getgriddata读数据有什么区别。
密码修改失败请联系微信:mofangbao

新浪微博达人勋

 楼主| 发表于 2012-11-15 20:50:56 | 显示全部楼层
西山守望 发表于 2012-11-15 18:12
能否显示鼠标所在点的数据的数值?好像在哪个帖子里看到过,但是找不到了。再有就是用getgriddata_levlon读 ...

用Identifer工具就可以了。

二者是一回事。
密码修改失败请联系微信:mofangbao

新浪微博达人勋

发表于 2012-11-15 22:14:58 | 显示全部楼层
MeteoInfo 发表于 2012-11-15 20:50
用Identifer工具就可以了。

二者是一回事。

如果是1°*1°的数据,用GridData.Data[]来读取数据,怎么读1.5°或者其他非整数点的数据呢?
密码修改失败请联系微信:mofangbao

新浪微博达人勋

 楼主| 发表于 2012-11-15 22:35:37 | 显示全部楼层
西山守望 发表于 2012-11-15 22:14
如果是1°*1°的数据,用GridData.Data[]来读取数据,怎么读1.5°或者其他非整数点的数据呢?

GridData有ToStation(double x, double y)方法,用的双线性插值。
密码修改失败请联系微信:mofangbao
您需要登录后才可以回帖 登录 | 立即注册 新浪微博登陆

本版积分规则

Copyright ©2011-2014 bbs.06climate.com All Rights Reserved.  Powered by Discuz! (京ICP-10201084)

本站信息均由会员发表,不代表气象家园立场,禁止在本站发表与国家法律相抵触言论

快速回复 返回顶部 返回列表