我正在尝试实现用户在Bing Map控件上绘制和细化多边形的功能。
我添加了一个形状图层,并覆盖了点击事件以绘制一个简单的多边形,并且一切都完美无缺。我想进一步细化控件,以便用户可以拖放绘制多边形的任何Location对象来改变它的形状,但我没有运气。
我试图添加一个MapItemControl,绑定到我的多边形的Locations属性,但没有成功 - 我没有看到引脚出现在地图上,即使我的多边形确实正确渲染。据推测,Locations集合没有通知UI对集合的任何更改,因此我可能需要为这些引脚维护一个单独的集合。
然而,一旦我开始这样做,我仍然需要能够拖放引脚来修改多边形。有人在Windows 8上实现了这个可以分享一些想法吗?
修改
我现在让我的图钉在地图上显示Locations集合。理想情况下,我希望将它们绑定到多边形的Locations集合,但是乞丐不能是选择器。我现在只需要能够拖动引脚。
答案 0 :(得分:1)
我在多边形中添加了一个拖动手柄模块,以便编辑多边形中的每个点。这是我使用的演练。
这适用于7.0版。不确定您使用的是哪个版本,但它很容易适应。
修改我是用javascript / html完成的。刚注意到你把它标记为Windows 8.好奇,你是否正在为Windows 8手机进行银光控制?
WPF C#解决方案
以下是我提出的内容,它非常容易实现,您只需将我的事件挂钩到MapPolygon
对象上即可。代码背后的想法是,一旦你点击多边形,我们在多边形的每个顶点放置一个图钉(我们创建事件以便我们可以拖动它)。当我们拖放每个图钉时,我们调整polygon.Locations(如果适用)。
polygon.MouseDown += new MouseButtonEventHandler(polygon_MouseDownResize);
作为退出调整大小事件的一种方法,我选择只关闭按键并使用'esc'停止编辑,但您可以通过右键单击或您选择的任何其他事件来执行此操作。您所做的就是清除pushPinVertices
列表并重置事件变量。
// === Editable polygon Events ===
private bool _shapeEdit;
public MapPolygon selectedPoly { get; set; }
public List<Pushpin> pushPinVertices { get; set; }
void polygon_MouseDownResize(object sender, MouseButtonEventArgs e)
{
if (!_shapeEdit && selectedPoly == null)
{
_shapeEdit = true;
selectedPoly = sender as MapPolygon;
pushPinVertices = new List<Pushpin>();
int i = 0;
foreach (Microsoft.Maps.MapControl.WPF.Location vertice in selectedPoly.Locations)
{
Pushpin verticeBlock = new Pushpin();
// I use a template to place a 'vertice marker' instead of a pushpin, il provide resource below
verticeBlock.Template = (ControlTemplate)Application.Current.Resources["PushPinTemplate"];
verticeBlock.Content = "vertice";
verticeBlock.Location = vertice;
verticeBlock.MouseDown += new MouseButtonEventHandler(pin_MouseDown);
verticeBlock.MouseUp += new MouseButtonEventHandler(pin_MouseUp);
myMap.Children.Add(verticeBlock);
pushPinVertices.Add(verticeBlock);
i++;
}
}
}
private void myMap_KeyDown(object sender, KeyEventArgs e)
{
if (e.Key == System.Windows.Input.Key.Escape)
{
if (_shapeEdit && selectedPoly != null)
{
foreach (Pushpin p in pushPinVertices)
{
myMap.Children.Remove(p);
}
_shapeEdit = false;
selectedPoly = null;
}
}
}
// Note: I needed my window to pass bing maps the keydown event
private void Window_KeyDown(object sender, KeyEventArgs e)
{
myMap_KeyDown(sender, e);
}
// === Editable polygon Events ===
// ==== Draggable pushpin events =====
Vector _mouseToMarker;
private bool _IsPinDragging;
public Pushpin SelectedPushpin { get; set; }
void pin_MouseUp(object sender, MouseButtonEventArgs e)
{
LocationCollection locCol = new LocationCollection();
foreach (Pushpin p in pushPinVertices)
{
locCol.Add(p.Location);
}
selectedPoly.Locations = locCol;
bingMapRefresh();
_IsPinDragging = false;
SelectedPushpin = null;
}
void pin_MouseDown(object sender, MouseButtonEventArgs e)
{
e.Handled = true;
SelectedPushpin = (Pushpin)sender;
_IsPinDragging = true;
_mouseToMarker = Point.Subtract(
myMap.LocationToViewportPoint(SelectedPushpin.Location),
e.GetPosition(myMap));
}
private void myMap_MouseMove(object sender, MouseEventArgs e)
{
if (e.LeftButton == MouseButtonState.Pressed)
{
if (_IsPinDragging && SelectedPushpin != null)
{
SelectedPushpin.Location = myMap.ViewportPointToLocation(Point.Add(e.GetPosition(myMap), _mouseToMarker));
e.Handled = true;
}
}
}
// ==== Draggable pushpin events =====
// Nice little maprefresh I found online since the bingmap WPF doesnt always seem to update elements after certain event orders
private void bingMapRefresh()
{
//myMap.UpdateLayout();
var mapCenter = myMap.Center;
mapCenter.Latitude += 0.00001;
myMap.SetView(mapCenter, myMap.ZoomLevel);
}
至于覆盖图钉图标的资源,我只使用ImageBrush
做了一个小的白色方块。请注意,您可能需要调整Margin
属性,具体取决于您制作标记的时间长度/宽度。这是因为默认情况下,图钉通常会固定在该位置上方。
<Application.Resources>
<ControlTemplate x:Key="PushPinTemplate">
<Grid>
<Rectangle Width="10" Height="10" Margin="0 35 0 0">
<Rectangle.Fill>
<ImageBrush ImageSource="pack://application:,,,/Images/DragIcon.gif"/>
</Rectangle.Fill>
</Rectangle>
</Grid>
</ControlTemplate>
</Application.Resources>