Windows Phone笔记(2)方向处理之动态布局
1.动态布局
默认情况下,windows phone应用程序在竖屏模式(垂直方向)下运行,当手机改变方向时我们的应用程序也应该能够根据方向的改变做出相应的布局调整。运行之前创建的hellowindowsphone项目程序,改变模拟器中屏幕的的方向:
我们发现页面并没有做出相应的改变。让页面根据自动改变很简单。只需要把mainpage.xaml中的phoneapplicationpage标记的supportedorientations属性值更改为:portraitorlandscape即可,supportedorientations支持三个枚举值:landscape(水平方向)、portrait(竖直方向)、portraitorlandscape(根据手机具体方向自动调整)。
重新编译运行后,旋转模拟器我们会发现,页面方向也会自动根据方向改变进行调整。
这些对方向改变程序而做出的响应体现了silverlight的动态布局。所以得页面元素都改变了位置,并且有的元素还改变的自身的大小。在处理动态布局中最重要的两个属性是:horizontalalignment(水平对齐方式)和verticalalignment(垂直对齐方式) 。
下面通过在一个grid中放置9个textblock元素用来学习horizontalalignment和verticalalignment的9种不同组合下的使用方法。
mainpage.xaml
1 <phone:phoneapplicationpage
2 x:class="hellowindowsphone.mainpage"
3 xmlns=""
4 xmlns:x=""
5 xmlns:phone="clr-namespace:microsoft.phone.controls;assembly=microsoft.phone"
6 xmlns:shell="clr-namespace:microsoft.phone.shell;assembly=microsoft.phone"
7 xmlns:d=""
8 xmlns:mc=""
9 mc:ignorable="d" d:designwidth="480" d:designheight="768"
10 fontfamily="{staticresource phonefontfamilynormal}"
11 fontsize="{staticresource phonefontsizenormal}"
12 foreground="{staticresource phoneforegroundbrush}"
13 supportedorientations="portraitorlandscape" orientation="portrait"
14 shell:systemtray.isvisible="true">
15
16 <grid x:name="contentpanel" grid.row="1" margin="12,0,0,12">
17 <textblock text="top-left" verticalalignment="top" horizontalalignment="left" fontsize="22"></textblock>
18 <textblock text="top-center" verticalalignment="top" horizontalalignment="center" fontsize="22"></textblock>
19 <textblock text="top-right" verticalalignment="top" horizontalalignment="right" fontsize="22"></textblock>
20 <textblock text="center-left" verticalalignment="center" horizontalalignment="left" fontsize="22"></textblock>
21 <textblock text="center-center" verticalalignment="center" horizontalalignment="center" fontsize="22"></textblock>
22 <textblock text="center-right" verticalalignment="center" horizontalalignment="right" fontsize="22"></textblock>
23 <textblock text="bottom-left" verticalalignment="bottom" horizontalalignment="left" fontsize="22"></textblock>
24 <textblock text="bottom-center" verticalalignment="bottom" horizontalalignment="center" fontsize="22"></textblock>
25 <textblock text="bottom-right" verticalalignment="bottom" horizontalalignment="right" fontsize="22"></textblock>
26 </grid>
27
28
29 </phone:phoneapplicationpage>
运行程序,旋转模拟器方向:
我们可以看出windows phone 中有三种可能的方向:纵向(竖屏)和横向(向左或向右,横屏)。
从前面给出的代码中我们发现有一个margin属性这个属性在silverlight布局中同样很重要,有个css开发经验的都知道margin用来设置一个元素所有外边距的宽度。如果指这种一个值例如:"margin=100"那么这个值将应用于四个边,如果是两个值如:"margin=100,200"那么第一个值应用于左右,第二个值应用于上下,如果为四个值例如前面示例给出代码中的"margin="12,0,0,12""那么应用的顺序为左、上、右、下。margin属性是由frameworkelement定义的;在实际的应用中,几乎每个元素都会有一个非零的margin属性用来防止页面间的元素过于拥挤。
通过修改前面给出的代码我们进一步观察margin在布局的中作用。
mainpage.xaml
1 <phone:phoneapplicationpage
2 x:class="hellowindowsphone.mainpage"
3 xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
4 xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
5 xmlns:phone="clr-namespace:microsoft.phone.controls;assembly=microsoft.phone"
6 xmlns:shell="clr-namespace:microsoft.phone.shell;assembly=microsoft.phone"
7 xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
8 xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
9 mc:ignorable="d" d:designwidth="480" d:designheight="768"
10 fontfamily="{staticresource phonefontfamilynormal}"
11 fontsize="{staticresource phonefontsizenormal}"
12 foreground="{staticresource phoneforegroundbrush}"
13 supportedorientations="portraitorlandscape" orientation="portrait"
14 shell:systemtray.isvisible="true">
15
16 <grid x:name="contentpanel" grid.row="1" margin="12,0,0,12">
17 <textblock text="top-left" verticalalignment="top" horizontalalignment="left" fontsize="22" margin="0 50 0 0"></textblock>
18 <textblock text="top-center" verticalalignment="top" horizontalalignment="center" fontsize="22" margin="30 100 0 0"></textblock>
19 <textblock text="top-right" verticalalignment="top" horizontalalignment="right" fontsize="22" margin="0 150 0 0"></textblock>
20 <textblock text="center-left" verticalalignment="center" horizontalalignment="left" fontsize="22" margin="50 0 0 200"></textblock>
21 <textblock text="center-center" verticalalignment="center" horizontalalignment="center" fontsize="22"></textblock>
22 <textblock text="center-right" verticalalignment="center" horizontalalignment="right" fontsize="22" margin="0 200 50 0"></textblock>
23 <textblock text="bottom-left" verticalalignment="bottom" horizontalalignment="left" fontsize="22" margin="0 0 0 150"></textblock>
24 <textblock text="bottom-center" verticalalignment="bottom" horizontalalignment="center" fontsize="22" margin="0 0 0 100"></textblock>
25 <textblock text="bottom-right" verticalalignment="bottom" horizontalalignment="right" fontsize="22" margin="0 0 20 50"></textblock>
26 </grid>
27
28
29 </phone:phoneapplicationpage>
继续运行程序,我们可以看到通过margin我们可以进一步控制页面元素所在的位置。
2.方向事件
从前面我们可以看出屏幕布局是自动切换的,但是当我们在手机屏幕发生改变时需要做一些额外工作的时候该如何处理呢?那么我们就可以通过屏幕方向改变时会触发的orientationchanged事件来编写代码处理这些额外的工作。
下面我们重新创建一个新的silverlight for windows phone的项目,这个程序有三个button元素和一张图片,当屏幕为竖屏的时候图片在上面,三个按钮在图片的下面,当屏幕为横屏的时候按钮就在图片的右边。在phoneapplicationpage标记中增加一个"orientationchanged=phoneapplicationpage_orientationchanged"的声明,下面是mainpage.xaml的代码:
mainpage.xaml
1 <phone:phoneapplicationpage
2 x:class="silverlightorientationdisplay.mainpage"
3 xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
4 xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
5 xmlns:phone="clr-namespace:microsoft.phone.controls;assembly=microsoft.phone"
6 xmlns:shell="clr-namespace:microsoft.phone.shell;assembly=microsoft.phone"
7 xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
8 xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
9 mc:ignorable="d" d:designwidth="480" d:designheight="768"
10 fontfamily="{staticresource phonefontfamilynormal}"
11 fontsize="{staticresource phonefontsizenormal}"
12 foreground="{staticresource phoneforegroundbrush}"
13 supportedorientations="portraitorlandscape" orientation="portrait"
14 orientationchanged="phoneapplicationpage_orientationchanged"
15 shell:systemtray.isvisible="true">
16
17 <!--layoutroot 是包含所有页面内容的根网格-->
18 <grid x:name="layoutroot" background="transparent">
19 <grid.rowdefinitions>
20 <rowdefinition height="auto"/>
21 <rowdefinition height="*"/>
22 </grid.rowdefinitions>
23 <grid.columndefinitions>
24 <columndefinition width="auto"/>
25 <columndefinition width="*"/>
26 </grid.columndefinitions>
27
28 <!--contentpanel - 在此处放置其他内容-->
29 <grid>
30 <image x:name="image1" stretch="fill" horizontalalignment="center" verticalalignment="center" source="mm.jpg" height="468" width="333" margin="75 0" />
31 </grid>
32 <stackpanel grid.row="1" height="282" name="buttonlist" verticalalignment="center" width="456" horizontalalignment="center">
33 <button content="button" height="72" name="button1" width="160" />
34 <button content="button" height="72" name="button2" width="160" />
35 <button content="button" height="72" name="button3" width="160" />
36 </stackpanel>
37 </grid>
38
39 </phone:phoneapplicationpage>
这里是后台orientationchanged事件的c#代码:
mainpage.xaml.cs
using system;
using system.collections.generic;
using system.linq;
using system.net;
using system.windows;
using system.windows.controls;
using system.windows.documents;
using system.windows.input;
using system.windows.media;
using system.windows.media.animation;
using system.windows.shapes;
using microsoft.phone.controls;
namespace silverlightorientationdisplay
{
public partial class mainpage : phoneapplicationpage
{
// 构造函数
public mainpage()
{
initializecomponent();
}
private void phoneapplicationpage_orientationchanged(object sender, orientationchangedeventargs e)
{
if ((e.orientation & pageorientation.portrait) == (pageorientation.portrait))
{
grid.setrow(buttonlist, 1);
grid.setcolumn(buttonlist, 0);
}
else
{
grid.setrow(buttonlist, 0);
grid.setcolumn(buttonlist, 1);
}
}
}
}
运行效果如下:
竖屏,按钮始终在图片下方
横屏,按钮始终在图片右边。
当然除了像我们前面这样,直接在xaml中phoneapplicationpage标记中声明方向改变事件之外还可以通过重写基类phoneapplicationpage的虚方法onorientationchanged来实现相同的效果。该虚方法是protected的。
好了,让我们来回顾前面介绍的内容:1.把mainpage.xaml中的phoneapplicationpage标记的supportedorientations属性值更改为:portraitorlandscape页面即可实现屏幕的自动切换。2.margin在页面布局中非常重要,用来设置一个元素所有外边距的宽度。3.当屏幕方向发生改变时会触发orientationchanged事件,通过为事件添加相应代码或者重新此方法以实现相应的效果。
摘自 晴天猪の博客