在开发Windows 8 Store应用程序时处理不同的方向

时间:2013-05-10 19:42:17

标签: xaml windows-store-apps winrt-xaml

我已经编写了多年的Android应用程序,现在我正在开发一个Windows应用商店/ Windows 8应用程序。

我对如何为横向和纵向方向编写不同的屏幕布局感到很困惑。

在Android中,我们所要做的就是编写2个布局,一个用于纵向,另一个用于横向,遵循文件名的一些名称约定,当我们旋转设备时,平台会自动更改屏幕布局。

我一直在谷歌搜索一些解决方案,在我的Windows 8应用程序中做同样的事情,我发现的只是一个使用Visual State Groups和Visual States的解决方案,在我们的小部件中添加了一些相同的XAML修改当我们旋转设备时。

例如,当我将设备旋转为纵向时,使文本块更改其位置:

<VisualState x:Name="FullScreenPortrait" >
    <Storyboard>
        <ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="(Grid.ColumnSpan)" Storyboard.TargetName="GridViewTitle">
            <DiscreteObjectKeyFrame KeyTime="0">
                <DiscreteObjectKeyFrame.Value>
                    <x:Int32>3</x:Int32>
                </DiscreteObjectKeyFrame.Value>
            </DiscreteObjectKeyFrame>
        </ObjectAnimationUsingKeyFrames>
        <ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="(FrameworkElement.Margin)" Storyboard.TargetName="GridViewTitle">
            <DiscreteObjectKeyFrame KeyTime="0">
                <DiscreteObjectKeyFrame.Value>
                    <Thickness>0,10,10,807</Thickness>
                </DiscreteObjectKeyFrame.Value>
            </DiscreteObjectKeyFrame>
        </ObjectAnimationUsingKeyFrames>
    </Storyboard>
</VisualState>

对我来说它看起来不是很干净和简单,甚至使用Visual Studio拖放小部件来生成代码的方法我觉得必须有一些比我更简单,更清晰的解决方案做。

所以我的问题是:是否有更简单的解决方案为每个方向编写XAML布局,或者我是否正确,但很难?

谢谢!

3 个答案:

答案 0 :(得分:2)

处理不同方向的一种方法是创建两个Grid元素及其子元素,并根据方向更改网格的可见性。

要检测方向更改,您还可以使用SimpleOrientation传感器,如下面的代码:

    public sealed partial class MainPage : Page
    {
        private SimpleOrientationSensor _oSensor;

        public MainPage()
        {
            this.InitializeComponent();

            _oSensor = SimpleOrientationSensor.GetDefault();

        }

        protected override void OnNavigatedTo(NavigationEventArgs e)
        {
            if (_oSensor != null)
                _oSensor.OrientationChanged += (s, a) =>
                {
                    Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal, () =>
                    {
                        switch (a.Orientation)
                        {
                            case SimpleOrientation.NotRotated:
                            case SimpleOrientation.Rotated180DegreesCounterclockwise:
                                currentOrientation.Text = "Landscape";
                                break;
                            case SimpleOrientation.Rotated270DegreesCounterclockwise:
                            case SimpleOrientation.Rotated90DegreesCounterclockwise:
                                currentOrientation.Text = "Portrait";
                                break;
                            default:
                                currentOrientation.Text = "N/A";
                                break;
                        }
                    });
                };
        }

    }

或者最简单的方法是处理SizeChanged事件,如下面的代码:

public sealed partial class MainPage : Page
{
    public MainPage()
    {
        this.InitializeComponent();

        mainGrid.SizeChanged += mainGrid_SizeChanged;
    }

    void mainGrid_SizeChanged(object sender, SizeChangedEventArgs e)
    {
        if (mainGrid.ActualHeight > mainGrid.ActualWidth)
            currentOrientation.Text = "Portrait";
        else
            currentOrientation.Text = "Landscape";
    }

}

希望这有帮助!

答案 1 :(得分:1)

Esdras - 你没错,应该有一个更简单的方法,但唯一的另一个选择是Expression Blend软件。我会承认,有一个学习曲线可以启动和运行。

对于用Xaml编写的方向更改,父控件必须从可以扩展(不是内部密封)的控件驱动,并且必须能够识别布局。因此,例如,如果您在布局感知页面上放置一个文本框,其方向将会改变,但如果您在布局识别页面上放置一个网格,并在网格中放置一个文本框...默认行为是网格将响应但是文本框不会。

您可能还会注意到,虽然它很乱,并且每个控件都需要一个控件修饰符,就像您为应对方向更改的每个元素提供的那样...好处是它不需要本机代码来定义状态或转换,所以设计师能够使用xml看起来像xaml来描述视图中的变化,无论是方向还是其他控件的状态。

如果您可以开始使用Expression Blend程序,那就是为此目的而制作的。

答案 2 :(得分:0)

我已经在一段时间后写了一篇关于stackoverflow的帖子,这可能对你有用。 提供了一些示例和代码:

[在Windows 8应用上处理方向] [1] Handling Orientation in Windows 8.1 Store app

发布我,如果你有更多问题。

谢谢, Ambuj