欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  移动技术

Windows Phone编程中页面间传值方法

程序员文章站 2022-04-11 15:01:21
wp开发过程中有时会遇到页面间转值的需求,如果定义两个页面,一个是初始页面source page,另外一个是跳转的页面destination page,简单地分析主要有两个方面的要求:: r2 q....

wp开发过程中有时会遇到页面间转值的需求,如果定义两个页面,一个是初始页面source page,另外一个是跳转的页面destination page,简单地分析主要有两个方面的要求:: r2 q. h% e" f4 f4 i2 t! m
•        首先是在source page跳转到destination page时给destination page页面传值的实现;
•        然后是当在destination page中调用goback函数回到source page时如何在source page传值;) c9 m. g: `: |; x3 \; r9 f7 w
) z3 a' x* g3 y; x) t
第一点本身提供了基本的实现方法,新建一个项目datapassingdemo,然后新建一个页面secondpage.xaml,我们需要实现就是从mainpage中跳转到secondpage中去,并传递参数让secendpage捕捉。首先在mainpage中增加一个textblock并且增加事件处理函数:2 o* v; x  i3 x  _
view sourceprint?: b3 y5 ^4 m  j9 k; n
<grid x:name="contentpanel" grid.row="1" margin="12,0,12,0">            
    <textblock text="navigate to 2nd page with data" horizontalalignment="center"
    verticalalignment="center" padding="0 34"               * f/ v" t% g8 r( o+ w$ k
         manipulationstarted="textblock_manipulationstarted"/>        
</grid># q2 z& x( @. g  t2 |

在mainpage的后台代码中,实现textblock_manipulationstarted方法如下:4 ]7 z) j8 b- p. w3 w! f
view sourceprint?
private void textblock_manipulationstarted(object sender, manipulationstartedeventargs args) ) b, q4 u" t" `8 ]  w( h
{            
    string destination = "/secondpage.xaml?parameter1=hello&parameter2=world";  " b( k6 }+ w3 \" c/ l  r. a: l. q
         this.navigationservice.navigate(new uri(destination, urikind.relative));             9 ?7 ^$ a- s  a% v
    args.complete();             * o' t$ i) s3 d
    args.handled = true;         0 j, k8 g$ }0 b; r% \$ ~* a1 |+ r, e
}% b& u4 o- q+ g1 p
可以看到上面的那个destination是不是很像网页间传递参数的形式呢?同理在secondpage中增加一个textblock,并给该textblock的manipulationstarted事件中增加goback()事件。同时,为了捕捉mainpage传递过来的参数,在secondpage的后台代码中实现下面的代码:
view sourceprint?
protected override void onnavigatedto(system.windows.navigation.navigationeventargs args)
        {
            idictionary<string, string> parameters = this.navigationcontext.querystring; / u1 \' j" w' `6 m9 i
            if (parameters.containskey("parameter1")) % ~( h4 i8 l7 x' ]
            { ' t, ?  o' ^0 t
                string parameter1 = parameters["parameter1"];
                string parameter2 = parameters["parameter2"]; ' n/ v% g6 k+ \
                txtblk.text = string.format("parameter1 is:{0} and parameter2 is:{1}", parameter1, parameter2); ) f8 y- v, v# c: i3 @  v
            } " \4 q0 h, u* h7 g; t
            base.onnavigatedto(args); 2 f" x; y. u* t% ^% v; f
        }
通过重载onnavigatedto函数实现获取传递过来的参数并在其中的一个textblock中显示出来。
[local]1[/loca所以实现第一个传值要求的方法很简单,只要通过给navigationservice的目标页面地址附带上参数再由目标页面获取参数即可,而我们要注意的地方是,由于移动设备设计的便捷性要求,我们应该避免那些很复杂的传递参数的设计,并且,在设计时要注意windows phone设计中的墓碑机制,才能设计出合理高效的wp应用。8 e' _) q! z6 b; f# w+ m8 l6 w
7 r+ i% l( x' [: m, s3 o, m
接着我们来考虑第二个问题,如何在页面间共享,传递数据。我们可以考虑到如果有一个是中间的“容器”可以存放一些公共的数据的话那且不是可以实现这个要求了吗?这时如果熟悉silverlight设计的话头脑里就会呈现出app这个类,由于所有的页面都可以访问到app这个类,所以我们可以把一些准备共享的数据放在app这个类中定义。就在上面那个例子中,我们在app类中增加一个公共变量:
view sourceprint?
public string sharedstring { set; get; }
7 l7 c) x- c) w, c6 g4 _
这时如果想在mainpage中给secondpage传递参数的话则需要先访问那个共享数据,这时的mainpage中的后台代码如下:
view sourceprint?5 t) m. \& ?2 h
private void textblock_manipulationstarted(object sender, manipulationstartedeventargs args) $ |8 m* h2 p) o/ p8 a5 t, c* [
{
    (application.current as app).sharedstring = "hello world";
    this.navigationservice.navigate(new uri("/secondpage.xaml", urikind.relative)); : s/ q1 q" v4 v; k3 {/ t
    args.complete(); ; h8 k. r1 n& t8 z/ o
}

即在访问secondpage前先修改那个共享数据的值,然后在secondpage的onnavigatedto事件中代码修改如下:
view sourceprint?
protected override void onnavigatedto(system.windows.navigation.navigationeventargs args) 0 m# i6 s) f3 u. _/ d  t: t# u; @
{ ! ^2 v% h8 b3 w. i' k# w+ o+ h
    string sharedstring = (application.current as app).sharedstring; # _, i+ l1 r6 r8 q
    txtblk.text = sharedstring;
    base.onnavigatedto(args);
}0 u3 k7 x0 u8 }' w7 h% g
% i5 w+ y3 q' r! ~4 k8 @
同理,如果想通过secondpage向mainpage传递数据的话,只要在调用goback函数前修改那个共享数据的值再由mainpage中的onnavigatedto函数来获取到相对应的数据即可。5 r+ a0 n) k5 f
% k3 z8 f' a9 j2 y) w
到这里我们已经基本可以实现上面的两个要求了,但第二种方法只是一种取巧的方法,在逻辑及实现上都有不合理的地方,我们应该走思考另外一种更为合理与通用的实现方式,那就是onnavigatedfrom这个函数了。大家可能会想,from不是很明显吗,我们就是通过from的原页面跳到目标页面的,那么这个from有何用处呢。其实它的用处挺大的,例如,通过这个函数我们可以很好的解决上面提到的问题。
2 k% u( n* s- g- s5 v0 s
最后用一个例子去说明这种方式的具体实现,我们定义两个页面,和之前的类似,这次我们通过secondpage返回的值去定义mainpage页面的颜色,mainpage的后台代码定义如下:! z4 x" q( n- n% i4 t
view sourceprint?$ @, g, l) d4 o$ q$ h8 k
public partial class mainpage : phoneapplicationpage
    {   b  n& s' ^; _6 j8 l
        public mainpage() + b! _1 m  a' r7 n6 {5 r7 `$ d
        {
            initializecomponent();   v, f" i: m: n3 k" q
        } - t8 \* p/ o' e* f4 z, g8 b
        public color? returnedcolor { set; get; }
  # w7 u/ v. \" l- b7 r. v
        private void textblock_manipulationstarted(object sender, manipulationstartedeventargs args)
        {
            this.navigationservice.navigate(new uri("/secondpage.xaml", urikind.relative)); - x  {$ o5 s0 a5 |& ]: o, }
 
            args.complete();
            args.handled = true; ; c" r5 y1 g% }. q/ g/ h6 a: x# ?
        } % v( c' p- l6 x$ l- ?
    }7 ^* v- _  v, i
  [+ f  m" \  {
这里定义为color?,因为返回的值有可能是非颜色的。而secondpage中的后台代码定义如下:
show sourceview sourceprint?& e8 c4 b" {( u
namespace datapassingdemo
{
    public partial class secondpage : phoneapplicationpage 8 @$ u1 k2 i& c! l0 s! y; w
    { 3 u- t- c9 y! r
        public secondpage() + v8 c. m  f. s! e& g/ m, h
        { # v5 q; w( q7 j2 @
            initializecomponent(); ; k, u  b5 h4 q7 r( l/ b, t
        } 6 w2 v) `+ a, f
        random rand = new random();
 
        private void textblock_manipulationstarted(object sender, manipulationstartedeventargs args)
        { ( q3 o8 z. p3 l. a
            this.navigationservice.goback();
            args.complete();
            args.handled = true;
        }
  * j2 v; a. t; \2 y) u9 `" f
        protected override void onnavigatedfrom(system.windows.navigation.navigationeventargs e) ' s0 n0 r, s( e; a$ q' s8 |
        {
            if (contentpanel.background is solidcolorbrush) ) p$ }/ f5 b# ?! a7 [1 j
            {
                color clr = (contentpanel.background as solidcolorbrush).color;
                if (e.content is mainpage)
                    (e.content as mainpage).returnedcolor = clr; . r2 r% u* i2 p+ c" g( e
            }
            base.onnavigatedfrom(e); 4 ]2 `1 r2 ?4 e+ o
        } ! @9 u! {5 _2 u" d( {' z
  8 s) u4 u  m( a' e+ p
        protected override void onmanipulationstarted(manipulationstartedeventargs args) ) z. t- m) g3 a2 a' a) \+ y
        {
            contentpanel.background = new solidcolorbrush( / b( \! h4 n; m, z4 p7 l+ w5 o; g
                color.fromargb(255, (byte)rand.next(255), * k! u$ ]- a" m, w
                (byte)rand.next(255),
                (byte)rand.next(255))); 5 o1 j) r% u. h; c
            base.onmanipulationstarted(args); 4 s' p& _' r, k, r2 ^7 \5 t
        }
    }   q0 k; n$ w9 o+ w% y4 f
}/ ]5 l; g9 e, r
4 g, n, o- {1 r3 f. d" k* j
我们通过获得一个随机数值组合而成的颜色设置为secondpage的背景颜色,然后通过onnavigatedfrom设置returnedcolor为当前背景颜色,所以为了获取secondpage返回的returnedcolor,在mainpage的后台代码中还需要重载onnavigatedto方法响应这个onnavigatedfrom:
view sourceprint?
protected override void onnavigatedto(system.windows.navigation.navigationeventargs args)
        {
            if (returnedcolor != null)
                contentpanel.background =
                new solidcolorbrush(returnedcolor.value);
            base.onnavigatedto(args); ( f& j8 ~  h9 s& \9 |
        }

通过onnavigatedfrom与onnavigatedto,我们就完成了数据的传递过程。l]

 
摘自 xiechengfa的专栏