在Bing Maps Silverlight Control中以及为我们提供了地图图钉控件pushpin,我曾经在《使用图钉层(Pushpin layer)及地图图层(MapLayer)》一文中介绍过他的使用方法,本篇主要介绍如何自定义图钉标注控件以及对他的一些扩展,比如实现图钉的动态ToolPanel。
关于图钉的UI外观的设计这里就不详细介绍了,通过Blend可以快速的构建UI界面。首先介绍下我的实现思想,通过Path构建图钉标注控件的UI外观,控件整体布局使用GrID布局,分别在GrID容器里设计好图钉UI外观效果和需要动态提示的ToolPanel(使用border布局设计),默认将ToolPanel隐藏,在后台代码中通过鼠标事件进行控制其是否出现;另外还布局了一个TextBlock控件,用于出现图钉标注上的内容。下面是定义好的图钉风格的样式:
自定义图钉样式 < Style x:name ="pushpinStyle" targettype ="Controls:pushpinControl" >< Setter Property ="Template" >
< Setter.Value >
< ControlTemplate targettype ="Controls:pushpinControl" >
< GrID x:name ="GrdRoot" Height ="auto" WIDth ="auto" HorizontalAlignment ="Stretch" RendertransformOrigin ="0,0" >
< GrID.Rendertransform >
< transformGroup >
< Scaletransform x:name ="_Scaletransform" ScaleX ="1" ScaleY ="1" />
< Skewtransform />
< Rotatetransform />
< Translatetransform />
</ transformGroup >
</ GrID.Rendertransform >
< Path Stretch ="Fill" Opacity ="1" RendertransformOrigin ="0.501,0.281" Data ="M0,-250L6.09909264359567,
-250C7.86508433137037,-249.883679757668 9.5771753004554,-249.696968148304 11.2361413649071,
-249.457603405072 24.5078612249376,-247.542676877067 34.3794798686271,
-242.257907887612 41.2465583494687,-237.283319185337 44.6800986937064,
-234.796020219885 47.3625022581612,-232.386267374123 49.3432151487858,
-230.514059732522 50.3335754087938,-229.577954004373 51.1485091856508,
-228.776236246195 51.7942001036199,-228.166407297221 56.0964631917223,
-224.103097789728 68.1963801884179,-208.309435634954 69.289336364603,
-191.492424677005 70.6231971699074,-170.968460931381 68.290878635012,
-158.519576085084 59.6252929380878,-143.46295614065 52.4136905999628,
-130.932641056522 38.9633656169578,-121.172558189545 25.9663459471247,
-99.9756667119496 22.717070324265,-94.6763733347819 19.5096780307535,
-85.8535122559554 16.5262691191198,-75.6002242070549 15.0345529933047,
-70.4735161130636 13.5988258504601,-64.9891717094285 12.2418500593682,
-59.4087874394669 8.8494006958964,-45.4578438671403 0.658368923825747,
-0.264830522697093 0.658368923825747,-0.264830522697093L0.658368923825747,
-0.264830522697093C0.658368923825747,-0.264830522697093 -6.20713033738298,
-39.8775058725022 -10.9565428086754,-59.4087721806768 -13.6705143479304,
-70.5696227914182 -16.6994467050881,-81.3462113972954 -19.8613212892067,
-89.645756433626 -21.4422436994774,-93.7955199281247 -23.0564059677924,
-97.3260283129902 -24.6810425111283,-99.9756667119496 -37.6780541099905,
-121.172569912188 -51.1284623692131,-130.932797619228 -58.3399704286158,
-143.462940881861 -67.0055167526496,-158.519492415143 -69.3378901087436,
-170.968446571251 -68.0040291139176,-191.492413232913 -66.9110789415046,
-208.309331812531 -54.8111481537909,-224.103105568266 -50.508885223533,
-228.166399667826 -47.9261288596012,-230.605716191039 -42.6354741589363,
-236.115224319832 -34.2414024659624,-241.014917085726 -30.0443655550756,
-243.464752007233 -25.0714708225116,-245.762135285075 -19.2732761689687,
-247.447058389738 -16.3741806336881,-248.289518545224 -13.2687567063844,
-248.978864381863 -9.95082648482475, -249.457595894886 -8.29186423506778,
-249.6969603997 -6.57977326598088,-249.883671889854 -4.81378157820587,-250z"
strokeThickness ="2.5" margin ="-28.398,-30.999,0" WIDth ="35" Height ="30.754" VerticalAlignment ="top"
Fill ="#59000000" HorizontalAlignment ="left" d:LayoutOverrIDes ="WIDth, Height" IsHitTestVisible ="False" >
< Path.Rendertransform >
< transformGroup >
< Scaletransform ScaleX ="1" ScaleY ="1" />
< Skewtransform AngleX ="-57.547" AngleY ="0" />
< Rotatetransform Angle ="0" />
< Translatetransform X ="45.252" Y ="0" />
</ transformGroup >
</ Path.Rendertransform >
</ Path >
< Path Stretch ="Fill" stroke ="#FF000000" Opacity ="1" RendertransformOrigin ="0.501,0.281"
Data ="M0,-250C7.86508433137037,
-249.696968148304 11.2361413649071,-249.457603405072 24.5078612249376,
-247.542676877067 34.3794798686271,-242.257907887612 41.2465583494687,
-237.283319185337 44.6800986937064,-234.796020219885 47.3625022581612,
-232.386267374123 49.3432151487858,-230.514059732522 50.3335754087938,
-229.577954004373 51.1485091856508,-228.776236246195 51.7942001036199,
-228.166407297221 56.0964631917223,-224.103097789728 68.1963801884179,
-208.309435634954 69.289336364603,-191.492424677005 70.6231971699074,
-170.968460931381 68.290878635012,-158.519576085084 59.6252929380878,
-143.46295614065 52.4136905999628,-130.932641056522 38.9633656169578,
-121.172558189545 25.9663459471247,-99.9756667119496 22.717070324265,
-94.6763733347819 19.5096780307535,-85.8535122559554 16.5262691191198,
-75.6002242070549 15.0345529933047,-70.4735161130636 13.5988258504601,
-64.9891717094285 12.2418500593682,-59.4087874394669 8.8494006958964,
-45.4578438671403 0.658368923825747,-0.264830522697093 0.658368923825747,
-0.264830522697093L0.658368923825747,-0.264830522697093C0.658368923825747,
-0.264830522697093 -6.20713033738298,-39.8775058725022 -10.9565428086754,
-59.4087721806768 -13.6705143479304,-70.5696227914182 -16.6994467050881,
-81.3462113972954 -19.8613212892067,-89.645756433626 -21.4422436994774,
-93.7955199281247 -23.0564059677924,-97.3260283129902 -24.6810425111283,
-99.9756667119496 -37.6780541099905,-121.172569912188 -51.1284623692131,
-130.932797619228 -58.3399704286158,-143.462940881861 -67.0055167526496,
-158.519492415143 -69.3378901087436,-170.968446571251 -68.0040291139176,
-191.492413232913 -66.9110789415046,-208.309331812531 -54.8111481537909,
-224.103105568266 -50.508885223533,-228.166399667826 -47.9261288596012,
-230.605716191039 -42.6354741589363,-236.115224319832 -34.2414024659624,
-241.014917085726 -30.0443655550756,-243.464752007233 -25.0714708225116,
-245.762135285075 -19.2732761689687,-247.447058389738 -16.3741806336881,
-248.289518545224 -13.2687567063844,-248.978864381863 -9.95082648482475,
-249.457595894886 -8.29186423506778,-249.6969603997 -6.57977326598088,
-249.883671889854 -4.81378157820587,-250z"
strokeThickness ="2.5" HorizontalAlignment ="left" margin ="-18,-63.25,0" x:name ="shppushpin"
WIDth ="35" d:LayoutOverrIDes ="WIDth" Height ="63"
VerticalAlignment ="top" Cursor ="Hand" >
< Path.Rendertransform >
< transformGroup >
< Scaletransform ScaleX ="1" ScaleY ="1" />
< Skewtransform AngleX ="0" AngleY ="0" />
< Rotatetransform Angle ="0" />
< Translatetransform X ="0" Y ="0" />
</ transformGroup >
</ Path.Rendertransform >
< Path.Fill >
< linearGradIEntBrush EndPoint ="0.5,1" StartPoint ="0.5,0" >
< GradIEntStop color ="#FFFFF77F" Offset ="0" />
< GradIEntStop color ="#FFFCF14E" Offset ="1" />
</ linearGradIEntBrush >
</ Path.Fill >
</ Path >
< TextBlock textwrapPing ="Wrap" d:LayoutOverrIDes ="Height, GrIDBox" RendertransformOrigin ="0.51,0.491" VerticalAlignment ="top"
TextAlignment ="Center" margin ="-15.55,-60,0" x:name ="txtTitle"
WIDth ="30" FontSize ="24" Visibility ="Visible" FontFamily ="Verdana" HorizontalAlignment ="left" IsHitTestVisible ="False" >
< TextBlock.Rendertransform >
< transformGroup >
< Scaletransform />
< Skewtransform AngleX ="0" AngleY ="0" />
< Rotatetransform Angle ="0" />
< Translatetransform X ="0" Y ="0" />
</ transformGroup >
</ TextBlock.Rendertransform >
</ TextBlock >
< border x:name ="ToolPanel" VerticalAlignment ="Stretch" Background ="#A82D2D2D" CornerRadius ="8,8,8" Visibility ="Collapsed"
borderBrush ="#FF626262" borderThickness ="2,2,2" ScrollVIEwer.HorizontalScrollbarVisibility ="Visible"
RendertransformOrigin ="0.5,0.5" GrID.Row ="0" WIDth ="300" Height ="200" >
< border.Rendertransform >
< transformGroup >
< Scaletransform />
< Skewtransform />
< Rotatetransform />
< Translatetransform X ="20" Y ="-75" />
</ transformGroup >
</ border.Rendertransform >
< StackPanel VerticalAlignment ="top" margin ="5,10, 5, 10" >
< GrID Height ="29" VerticalAlignment ="top" >
< TextBlock Height ="25" WIDth ="346" Text ="标题内容" textwrapPing ="Wrap" Foreground ="#FFF0E7E7" FontSize ="16"
HorizontalAlignment ="left" margin ="12,3,1" />
</ GrID >
< StackPanel VerticalAlignment ="top" >
< border x:name ="Contentborder" Background ="#FF000000" CornerRadius ="8,8" VerticalAlignment ="top"
margin ="0,3" padding ="0,8" Opacity ="0.68" MinHeight ="200" >
< TextBlock Text ="显示内容" Foreground ="White" margin ="3" ></ TextBlock >
</ border >
</ StackPanel >
</ StackPanel >
</ border >
</ GrID >
</ ControlTemplate >
</ Setter.Value >
</ Setter >
</ Style >
接下来要做的就是实现图标注控件的定义以及动态控制ToolPanel控件的显示与否了,主要思路就是通过引用上面定义的样式,以模板的方式从样式里获取到相应的控件元素进行动态控制,详细见如下代码:
/// @H_301_1247@ <summary> @H_301_1247@/// @H_301_1247@ 自定义图钉控件
/// @H_301_1247@ </summary>
public class pushpinControl : ContentControl
{
private string Text;
public pushpinControl(String text)
{
@H_301_1247@// @H_301_1247@设置图钉标注控件的标注内容 @H_301_1247@
this .Text = text == "" ? " M " : text;
DefaultStyleKey = typeof (pushpinControl);
@H_301_1247@// @H_301_1247@为当前对象引用样式,从全局资源里读取 @H_301_1247@
this .Style = Application.Current.Resources[ " pushpinStyle " ] as Style;
}
public overrIDe voID OnApplyTemplate()
{
base .OnApplyTemplate();
@H_301_1247@// @H_301_1247@从样式模板中获取TextBlock控件 @H_301_1247@
var textBlock = GetTemplateChild( " txtTitle " ) as TextBlock;
textBlock.Text = this .Text;
@H_301_1247@// @H_301_1247@从样式模板中获取ToolPanel(既border布局实现的,详细见样式的定义)控件 @H_301_1247@
var ToolPanelborder = GetTemplateChild( " ToolPanel " ) as border;
@H_301_1247@// @H_301_1247@通过事件动态控制ToolPanel的显示和隐藏 @H_301_1247@
this .MouseEnter += (mes, meo) => { ToolPanelborder.Visibility = Visibility.Visible; };
this .MouseLeave += (mls, mlo) => { ToolPanelborder.Visibility = Visibility.Collapsed; };
}
}
到这里就成功的完成了图钉标注控件的自定义了,接下来看看如何使用这个自定义的图钉标注控件,详见如下代码块:
private voID Addpushpin(){
@H_301_1247@// @H_301_1247@添加Bing Maps Silverlight Control自带的图钉
@H_301_1247@// @H_301_1247@var pushpin = new pushpin();
@H_301_1247@// @H_301_1247@pushpin.Location = new Location(29.5076372217973, 106.489384971208);
@H_301_1247@// @H_301_1247@添加自定义的图钉 @H_301_1247@
var pushpin = new pushpinControl( " D " );
MapLayer.AddChild(pushpin, new Location( 29.5076372217973 , 106.489384971208 ));
}
或许会有人问道,如何动态的实现ToolPanel里显示的内容?要实现这个功能也是非常简单的,首先我们来分析下上面定义的样式里对ToolPanel部分的定义:
< border x:name ="ToolPanel" VerticalAlignment ="Stretch" Background ="#A82D2D2D" CornerRadius ="8,8" Visibility ="Collapsed"borderBrush ="#FF626262" borderThickness ="2,2" ScrollVIEwer.HorizontalScrollbarVisibility ="Visible"
RendertransformOrigin ="0.5,0.5" GrID.Row ="0" WIDth ="300" Height ="200" >
< border.Rendertransform >
< transformGroup >
< Scaletransform />
< Skewtransform />
< Rotatetransform />
< Translatetransform X ="20" Y ="-75" />
</ transformGroup >
</ border.Rendertransform >
< StackPanel VerticalAlignment ="top" margin ="5, 10" >
< GrID Height ="29" VerticalAlignment ="top" >
< TextBlock Height ="25" WIDth ="346" Text ="标题内容" textwrapPing ="Wrap" Foreground ="#FFF0E7E7" FontSize ="16"
HorizontalAlignment ="left" margin ="12,1" />
</ GrID >
< StackPanel VerticalAlignment ="top" >
< border x:name ="Contentborder" Background ="#FF000000" CornerRadius ="8,8" VerticalAlignment ="top"
margin ="0,3" padding ="0,8" Opacity ="0.68" MinHeight ="200" >
< TextBlock Text ="显示内容" Foreground ="White" margin ="3" ></ TextBlock >
</ border >
</ StackPanel >
</ StackPanel >
</ border >
使用了border进行圆角布局,在其内部通过StackPanel垂直布局实现了ToolPanel的的标题和内容两大部分,内容部分并通过border进行设计,取名为Contentborder,这是为了实现动态呈现显示内容而设计,整体border通过Translatetransform进行一个偏移的处理,也就是让ToolPanel始终显示在图钉标注的右边相应的位置,详细见本文前面提供的截图。
从上面的实现知道ToolPanel是在鼠标的MouseEnter事件执行的时候才会显示的,当鼠标离开就会将其可见性设置为隐藏。了解了这个原理后就可以想到,是否可以从MouseEnter事件中通过某种方法去处理?事件是个非常强大的技术点,这里我们就可以通过事件,将显示内容的border容器派发处理,通过事件的监听来动态更新其显示内容。首先需要扩展一个事件类:
public delegate voID pushpinContentChangedHandler( object sender,pushpinContentChangedEvantAgrs e);public class pushpinContentChangedEvantAgrs : EventArgs
{
public border Contentborder { get ; set ; }
public pushpinContentChangedEvantAgrs() { }
public pushpinContentChangedEvantAgrs(border Contentborder)
{
this .Contentborder = Contentborder;
}
}
接下来为自定义的图钉标注类定义一个事件,事件类型就为上面所定义好的委托类型,传递的事件为pushpinContentChangedEventArgs.
/// @H_301_1247@ <summary> @H_301_1247@/// @H_301_1247@ 自定义图钉控件
/// @H_301_1247@ </summary>
public class pushpinControl : ContentControl
{
public event pushpinContentChangedHandler ContentChangedEvent;
现在需要做的就是在当前对象的MouseEnter事件中去触发这个事件,将样式里所定义好的用于显示内容的border对象获取出来,通过事件参数传递派发出去,让事件监听段可以通过该事件获取事件参数进行ToolPanel内容的呈现更新。所有我们需要改写pushpinControl的OnApplyTemplate方法:
public overrIDe voID OnApplyTemplate(){
base .OnApplyTemplate();
@H_301_1247@// @H_301_1247@从样式模板中获取TextBlock控件 @H_301_1247@
var textBlock = GetTemplateChild( " txtTitle " ) as TextBlock;
textBlock.Text = this .Text;
@H_301_1247@// @H_301_1247@从样式模板中获取ToolPanel(既border布局实现的,详细见样式的定义)控件 @H_301_1247@
var ToolPanelborder = GetTemplateChild( " ToolPanel " ) as border;
@H_301_1247@// @H_301_1247@获取内容border对象,通过事件将该对象派发出去,在使用段可以通过监听这个事件而获取到内容border @H_301_1247@
var Contentborder = GetTemplateChild( " Contentborder " ) as border;
@H_301_1247@// @H_301_1247@通过事件动态控制ToolPanel的显示和隐藏 @H_301_1247@
this .MouseEnter += (mes, meo) =>
{
ToolPanelborder.Visibility = Visibility.Visible;
if (ContentChangedEvent != null )
{
ContentChangedEvent( this , new pushpinContentChangedEvantAgrs(Contentborder));
}
};
this .MouseLeave += (mls, mlo) => { ToolPanelborder.Visibility = Visibility.Collapsed; };
}
通过ContentChangedEvent事件的监听动态的去改变ToolPanel里的显示内容就可以达到我们的目的了,比如我们动态的将ToolPanel里的显示内容更改为一张图片,上面使用自定义图钉标注的代码将变成下面这样的。
private voID Addpushpin()
{
@H_301_1247@// @H_301_1247@添加Bing Maps Silverlight Control自带的图钉
@H_301_1247@// @H_301_1247@var pushpin = new pushpin();
@H_301_1247@// @H_301_1247@pushpin.Location = new Location(29.5076372217973, 106.489384971208);
@H_301_1247@// @H_301_1247@添加自定义的图钉 @H_301_1247@
var pushpin = new pushpinControl( " D " );
pushpin.ContentChangedEvent += (sender, o) =>
{
@H_301_1247@// @H_301_1247@构造Image对象 用于显示在ToolPanel中 @H_301_1247@
var image = new Image { WIDth = 100 , Height = 100 , margin = new Thickness( 8 ) };
image.source = new BitmAPImage( new Uri( " Resources/Smbecker.png " , UriKind.relativeOrabsolute));
border border = o.Contentborder;
border.Child = image;
};
MapLayer.AddChild(pushpin, 106.489384971208 ));
}
之前有网友问到如何实现可拖拽的图钉标注控件,鉴于篇幅的原因这里就不做介绍,不清楚的朋友可以留言讨论。本篇就介绍到这里,欢迎大家前来交流、讨论、拍砖。
更多学习资料:
MSDN:http://msdn.microsoft.com/en-us/library/ee681890.aspx
官方:http://www.microsoft.com/maps
中国Bing Maps:http://cn.bing.com/ditu/
官方SDK:http://www.microsoft.com/maps/isdk/silverlight/
总结以上是内存溢出为你收集整理的【Silverlight】Bing Maps开发应用与技巧二:自定义图钉标注控件和动态ToolPanel全部内容,希望文章能够帮你解决【Silverlight】Bing Maps开发应用与技巧二:自定义图钉标注控件和动态ToolPanel所遇到的程序开发问题。
如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)