UtilityAction扩展
在我们的帮助文档中提供了一个测距的例子,能测量 长度,面积。只需要写几行简单的代码就能使用了 地址http://resources.arcgis.com/en/help/silverlight-api/samples/start.htm#UtilityActions
但是我们发现当测量完毕之后双击鼠标发现 结果立刻从地图上消失了,如果我们要把结果保存在 地图上怎么办呢,然后猜测在测量完的事件里获取 相应的属性,加载到地图上,但是这个工具并没有暴露出来类似 MeasureEnd的事件,我们是无法直接获得这个结果的,于是还要想其他的办法来解决了。
事实上在我们测量过程中我们看到的绘出的这个面以及测量结果是保存在一个Graphicslayer中的,当我们激活测量工具的时候就会自动滴向Map 控件中添加一个Graphicslayer,当我们测量完双击鼠标之后,会自动将那个Graphicslayer 删除,于是我们就看不到测量的结果了,知道了原理就容易解决了。因为当向地图中添加Graphicslayer Layer的时候地图控件的Layes集合就会发生变化,就会触发了Map.Layers.CollectionChanged 这个事件。我们可以在这个事件里获得测量工具为我们添加的GraphicslayerLayer,在测量的时候,由于GraphicsLayer里面的要素会发生变化 同时也会触发GraphicsLayer.Graphics.CollectionChanged的事件,我们可以获得新增加的Graphic,包括面,线,以及显示的文本都是graphic,于是我们可以new一个Graphicslayer的变量graphicsLayer或者在XAML里面添加也行,在测量绘制开始 到结束之前,我们自己定义的GraphicsLayer设置为不可见状态,将测量工具创建的GraphicsLayer中的Graphics 添加到我们自己定义的graphicslayer里面。当绘制结束双击鼠标我们就把GraphicsLayer的Visible属性设置为true。说了这么多,还是代码最有说服力
1 <UserControl 2 xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 3 xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 4 xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 5 xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 6 xmlns:esri="http://schemas.esri.com/arcgis/client/2009" 7 xmlns:sdk="http://schemas.microsoft.com/winfx/2006/xaml/presentation/sdk" 8 xmlns:esriBehaviors="clr-namespace:ESRI.ArcGIS.Client.Behaviors;assembly=ESRI.ArcGIS.Client.Behaviors" 9 xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactivity" 10 x:Class="UtilityAction.MainPage" 11 mc:Ignorable="d" 12 d:DesignHeight="300" d:DesignWidth="400"> 13 14 <Grid x:Name="LayoutRoot" Background="White"> 15 16 <Grid.Resources> 17 <LinearGradientBrush x:Key="CommonGradient" StartPoint="0.5,0" EndPoint="0.5,1"> 18 <GradientStop Offset="0" Color="#99919191"/> 19 <GradientStop Offset="0.25" Color="#aa919191"/> 20 <GradientStop Offset="0.75" Color="#cc919191"/> 21 </LinearGradientBrush> 22 <Style x:Key="CommonBorder" TargetType="Border"> 23 <Setter Property="BorderBrush" Value="White" /> 24 <Setter Property="BorderThickness" Value="1" /> 25 <Setter Property="CornerRadius" Value="5" /> 26 <Setter Property="Background" Value="{StaticResource CommonGradient}" /> 27 <Setter Property="Opacity" Value="1" /> 28 </Style> 29 <Style x:Key="MenuItem" TargetType="Button"> 30 <Setter Property="Foreground" Value="White"/> 31 <Setter Property="HorizontalAlignment" Value="Left"/> 32 <Setter Property="VerticalAlignment" Value="Center"/> 33 <Setter Property="HorizontalContentAlignment" Value="Left"/> 34 <Setter Property="FontSize" Value="12" /> 35 <Setter Property="Template"> 36 <Setter.Value> 37 <ControlTemplate TargetType="Button"> 38 <Grid> 39 <VisualStateManager.VisualStateGroups> 40 <VisualStateGroup x:Name="CommonStates"> 41 <VisualState x:Name="Normal"> 42 <Storyboard> 43 <DoubleAnimation To="0" FillBehavior="HoldEnd" 44 Storyboard.TargetName="menuItemHighlight" 45 Storyboard.TargetProperty="Opacity" 46 Duration="0:0:0.3" /> 47 </Storyboard> 48 </VisualState> 49 <VisualState x:Name="MouseOver"> 50 <Storyboard> 51 <DoubleAnimation To="0.15" FillBehavior="HoldEnd" 52 Storyboard.TargetName="menuItemHighlight" 53 Storyboard.TargetProperty="Opacity" 54 Duration="0:0:0.3" /> 55 </Storyboard> 56 </VisualState> 57 </VisualStateGroup> 58 </VisualStateManager.VisualStateGroups> 59 <Rectangle x:Name="menuItemHighlight" Fill="#FFFFFFFF" 60 Opacity="0" Margin="0" /> 61 <ContentPresenter 62 Content="{TemplateBinding Content}" 63 ContentTemplate="{TemplateBinding ContentTemplate}" 64 VerticalAlignment="{TemplateBinding VerticalContentAlignment}" 65 HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" 66 Margin="{TemplateBinding Padding}" /> 67 </Grid> 68 </ControlTemplate> 69 </Setter.Value> 70 </Setter> 71 </Style> 72 <esri:SimpleFillSymbol x:Key="DefaultFillSymbol" Fill="#4400FF00" BorderBrush="Red" 73 BorderThickness="1" /> 74 </Grid.Resources> 75 76 <esri:Map x:Name="MyMap" WrapAround="True"> 77 <esri:ArcGISTiledMapServiceLayer ID="MyBaseLayer" 78 Url="http://services.arcgisonline.com/ArcGIS/rest/services/World_Street_Map/MapServer" /> 79 <esri:GraphicsLayer ID="MeasureGraphicsLayer"></esri:GraphicsLayer> 80 </esri:Map> 81 82 <Grid HorizontalAlignment="Right" VerticalAlignment="Top" Width="Auto" Height="Auto" Margin="10" > 83 <Border Style="{StaticResource CommonBorder}" Padding="10,3,10,3"> 84 <Border.Effect> 85 <DropShadowEffect /> 86 </Border.Effect> 87 <StackPanel> 88 <TextBlock Text="Utility Actions" Foreground="White" FontSize="14" FontWeight="Bold" Margin="4" /> 89 90 <Button Style="{StaticResource MenuItem}" 91 Content="Polygon Measure" > 92 <i:Interaction.Triggers> 93 <i:EventTrigger EventName="Click"> 94 <esri:MeasureAction 95 AreaUnit="SquareMiles" 96 DisplayTotals="True" 97 DistanceUnit="Miles" 98 MapUnits="Meters" 99 MeasureMode="Polygon" 100 FillSymbol="{StaticResource DefaultFillSymbol}" 101 TargetName="MyMap"/> 102 </i:EventTrigger> 103 </i:Interaction.Triggers> 104 </Button> 105 <Button Style="{StaticResource MenuItem}" 106 Content="Polyline Measure" > 107 <i:Interaction.Triggers> 108 <i:EventTrigger EventName="Click"> 109 <esri:MeasureAction 110 AreaUnit="SquareMiles" 111 DisplayTotals="True" 112 DistanceUnit="Miles" 113 MapUnits="Meters" 114 MeasureMode="Polyline" 115 FillSymbol="{StaticResource DefaultFillSymbol}" 116 TargetName="MyMap"/> 117 </i:EventTrigger> 118 </i:Interaction.Triggers> 119 </Button> 120 <Button Style="{StaticResource MenuItem}" 121 Content="Radius Measure" > 122 <i:Interaction.Triggers> 123 <i:EventTrigger EventName="Click"> 124 <esri:MeasureAction 125 AreaUnit="SquareMiles" 126 DisplayTotals="True" 127 DistanceUnit="Miles" 128 MapUnits="Meters" 129 MeasureMode="Radius" 130 FillSymbol="{StaticResource DefaultFillSymbol}" 131 TargetName="MyMap"/> 132 </i:EventTrigger> 133 </i:Interaction.Triggers> 134 </Button> 135 136 </StackPanel> 137 </Border> 138 </Grid> 139 140 141 142 143 144 145 </Grid> 146 </UserControl>
1 using ESRI.ArcGIS.Client; 2 using System; 3 using System.Collections.Generic; 4 using System.Collections.Specialized; 5 using System.Linq; 6 using System.Net; 7 using System.Windows; 8 using System.Windows.Controls; 9 using System.Windows.Documents; 10 using System.Windows.Input; 11 using System.Windows.Media; 12 using System.Windows.Media.Animation; 13 using System.Windows.Shapes; 14 15 namespace UtilityAction 16 { 17 public partial class MainPage : UserControl 18 { 19 public MainPage() 20 { 21 InitializeComponent(); 22 this.MyMap.Layers.CollectionChanged += new NotifyCollectionChangedEventHandler(Layers_CollectionChanged); 23 } 24 private GraphicsLayer addedLayer; 25 private GraphicsLayer graphicsLayer; 26 bool isDrawOver = true; 27 void Layers_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e) 28 { 29 30 if (e.Action == NotifyCollectionChangedAction.Add) 31 { 32 foreach (var item in e.NewItems) 33 if (item is GraphicsLayer) 34 { 35 addedLayer = item as GraphicsLayer; 36 graphicsLayer = this.MyMap.Layers["MeasureGraphicsLayer"] as GraphicsLayer; 37 graphicsLayer.Visible = false; 38 39 (item as GraphicsLayer).Graphics.CollectionChanged += new NotifyCollectionChangedEventHandler(Graphics_CollectionChanged); 40 } 41 } 42 43 if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Remove) 44 { 45 if (addedLayer != null) 46 { 47 isDrawOver = true; 48 graphicsLayer.Visible = true; 49 } 50 } 51 } 52 void Graphics_CollectionChanged(object sender, System.Collections.Specialized.NotifyCollectionChangedEventArgs e) 53 { 54 55 if (e.Action == NotifyCollectionChangedAction.Add) 56 { 57 58 if (isDrawOver == false) 59 { 60 graphicsLayer.ClearGraphics(); 61 } 62 else 63 { 64 isDrawOver = false; 65 66 } 67 if (graphicsLayer != null) 68 { 69 foreach (Graphic item in addedLayer.Graphics) 70 { 71 Graphic g = item as Graphic; 72 graphicsLayer.Graphics.Add(new Graphic() { Geometry = g.Geometry, Symbol = g.Symbol }); 73 } 74 } 75 } 76 } 77 } 78 }