GIS二次开发之缩小
前一篇随笔中记录了地图放大功能的实现,其中很多方法和这篇中要说的缩小很像,比如ControlsMapZoomOutTool和ControlsMapZoomOutFixedCommand。那在这篇中就忽略掉这两个方法的实现了,直接看看自定义缩小功能的实现代码
代码
public MapZoomOut()
{
string[] res = GetType().Assembly.GetManifestResourceNames();
base.m_bitmap = new System.Drawing.Bitmap(GetType().Assembly.GetManifestResourceStream("Commands.zoomout.bmp"));
base.m_caption = "缩小地图";
base.m_category = "ToolBar";
base.m_message = "缩小地图";
base.m_name = "ToolBar_MapPan";
base.m_toolTip = "缩小";
m_ZoomOutStart = true;
m_feedBack = null;
try
{
base.m_cursor = new System.Windows.Forms.Cursor(GetType().Assembly.GetManifestResourceStream("Commands.ZoomOut.CUR"));
}
catch (Exception ex)
{
}
}
public override void OnCreate(object hook)
{
m_HookHelper.Hook = hook;
try
{
m_pActiveView = m_HookHelper.ActiveView;
}
catch { }
}
public override void OnMouseDown(int Button, int Shift, int X, int Y)
{
if (null == m_pActiveView) return;
m_pPoint = m_pActiveView.ScreenDisplay.DisplayTransformation.ToMapPoint(X, Y);
m_ZoomOutStart = true;
m_feedBack = null;
}
public override void OnMouseMove(int Button, int Shift, int X, int Y)
{
if (null == m_pActiveView) return;
if (!m_ZoomOutStart) return;
if (m_feedBack == null)
{
m_feedBack = new NewEnvelopeFeedbackClass();
if (Button == 1)
{
m_feedBack.Display = m_pActiveView.ScreenDisplay;
m_feedBack.Start(m_pPoint);
}
}
m_feedBack.MoveTo(m_pActiveView.ScreenDisplay.DisplayTransformation.ToMapPoint(X, Y));
}
public override void OnMouseUp(int Button, int Shift, int X, int Y)
{
if (null == m_pActiveView) return;
if (!m_ZoomOutStart) return;
IEnvelope m_pEnvelope = new EnvelopeClass();
if (null == m_feedBack) //点击缩小
{
m_pEnvelope = m_pActiveView.Extent;
m_pEnvelope.Expand(2, 2, true);
m_pActiveView.Extent.CenterAt(m_pPoint);
}
else //拉框缩小
{
IEnvelope m_pFeedEnvelope = new EnvelopeClass();
m_pFeedEnvelope = m_feedBack.Stop();
try
{
{
string[] res = GetType().Assembly.GetManifestResourceNames();
base.m_bitmap = new System.Drawing.Bitmap(GetType().Assembly.GetManifestResourceStream("Commands.zoomout.bmp"));
base.m_caption = "缩小地图";
base.m_category = "ToolBar";
base.m_message = "缩小地图";
base.m_name = "ToolBar_MapPan";
base.m_toolTip = "缩小";
m_ZoomOutStart = true;
m_feedBack = null;
try
{
base.m_cursor = new System.Windows.Forms.Cursor(GetType().Assembly.GetManifestResourceStream("Commands.ZoomOut.CUR"));
}
catch (Exception ex)
{
}
}
public override void OnCreate(object hook)
{
m_HookHelper.Hook = hook;
try
{
m_pActiveView = m_HookHelper.ActiveView;
}
catch { }
}
public override void OnMouseDown(int Button, int Shift, int X, int Y)
{
if (null == m_pActiveView) return;
m_pPoint = m_pActiveView.ScreenDisplay.DisplayTransformation.ToMapPoint(X, Y);
m_ZoomOutStart = true;
m_feedBack = null;
}
public override void OnMouseMove(int Button, int Shift, int X, int Y)
{
if (null == m_pActiveView) return;
if (!m_ZoomOutStart) return;
if (m_feedBack == null)
{
m_feedBack = new NewEnvelopeFeedbackClass();
if (Button == 1)
{
m_feedBack.Display = m_pActiveView.ScreenDisplay;
m_feedBack.Start(m_pPoint);
}
}
m_feedBack.MoveTo(m_pActiveView.ScreenDisplay.DisplayTransformation.ToMapPoint(X, Y));
}
public override void OnMouseUp(int Button, int Shift, int X, int Y)
{
if (null == m_pActiveView) return;
if (!m_ZoomOutStart) return;
IEnvelope m_pEnvelope = new EnvelopeClass();
if (null == m_feedBack) //点击缩小
{
m_pEnvelope = m_pActiveView.Extent;
m_pEnvelope.Expand(2, 2, true);
m_pActiveView.Extent.CenterAt(m_pPoint);
}
else //拉框缩小
{
IEnvelope m_pFeedEnvelope = new EnvelopeClass();
m_pFeedEnvelope = m_feedBack.Stop();
try
{
//这里是与放大代码不同的地方
double newWidth = m_pActiveView.Extent.Width * (m_pActiveView.Extent.Width / m_pFeedEnvelope.Width);
double newHeight = m_pActiveView.Extent.Height * (m_pActiveView.Extent.Height / m_pFeedEnvelope.Height);
double newXmin = m_pActiveView.Extent.XMin - ((m_pFeedEnvelope.XMin - m_pActiveView.Extent.XMin) * (m_pActiveView.Extent.Width / m_pFeedEnvelope.Width));
double newYmin = m_pActiveView.Extent.YMin - ((m_pFeedEnvelope.YMin - m_pActiveView.Extent.YMin) * (m_pActiveView.Extent.Height / m_pFeedEnvelope.Height));
m_pEnvelope.PutCoords(newXmin, newYmin, newXmin + newWidth, newYmin + newHeight);
}
catch
{
m_pEnvelope = m_pActiveView.Extent;
m_pEnvelope.Expand(2, 2, true);
m_pActiveView.Extent.CenterAt(m_pPoint);
m_feedBack = null;
m_ZoomOutStart = false;
}
}
m_pActiveView.Extent = m_pEnvelope;
m_pActiveView.PartialRefresh(esriViewDrawPhase.esriViewGeography, null, null);
m_feedBack = null;
Marshal.ReleaseComObject(m_feedBack);
m_ZoomOutStart = false;
}
public override void OnKeyDown(int keyCode, int Shift)
{
if (keyCode == 27)
{
m_ZoomOutStart = false;
base.m_cursor = System.Windows.Forms.Cursors.Default;
}
}
double newWidth = m_pActiveView.Extent.Width * (m_pActiveView.Extent.Width / m_pFeedEnvelope.Width);
double newHeight = m_pActiveView.Extent.Height * (m_pActiveView.Extent.Height / m_pFeedEnvelope.Height);
double newXmin = m_pActiveView.Extent.XMin - ((m_pFeedEnvelope.XMin - m_pActiveView.Extent.XMin) * (m_pActiveView.Extent.Width / m_pFeedEnvelope.Width));
double newYmin = m_pActiveView.Extent.YMin - ((m_pFeedEnvelope.YMin - m_pActiveView.Extent.YMin) * (m_pActiveView.Extent.Height / m_pFeedEnvelope.Height));
m_pEnvelope.PutCoords(newXmin, newYmin, newXmin + newWidth, newYmin + newHeight);
}
catch
{
m_pEnvelope = m_pActiveView.Extent;
m_pEnvelope.Expand(2, 2, true);
m_pActiveView.Extent.CenterAt(m_pPoint);
m_feedBack = null;
m_ZoomOutStart = false;
}
}
m_pActiveView.Extent = m_pEnvelope;
m_pActiveView.PartialRefresh(esriViewDrawPhase.esriViewGeography, null, null);
m_feedBack = null;
Marshal.ReleaseComObject(m_feedBack);
m_ZoomOutStart = false;
}
public override void OnKeyDown(int keyCode, int Shift)
{
if (keyCode == 27)
{
m_ZoomOutStart = false;
base.m_cursor = System.Windows.Forms.Cursors.Default;
}
}
可以看到缩小与放大不同之处
①:在点击缩放的时候m_pEnvelope.Expand(0.5,0.5,true) 和m_pEnvelope.Expand(2,2,true)的不同,应该很容易理解,打个比方,比如把当前的地图比作为1m*1m的标准地图,Expand(0.5,0.5,true),相当于是说将0.5m*0.5m的地图视图放大1m*1m的“地图框架”中,为了充满这个“地图框架”,应该要放大。(哈哈,应该可以这样理解),同样,缩小也就好理解了。
②:在拉框缩放的时候,放大中直接按照绘制的矩形框的大小进行放大,在缩小的时候,需要set new coordinate,就像屏幕的分辨率一样,重置到当前“屏幕”的大小(就是重定义ActiveView.Extent的Xmin,Ymin,Xmax,Ymax)。