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

Xaml 在开发Windows 8应用商店应用程序时处理不同的方向,xaml,windows-store-apps,winrt-xaml,Xaml,Windows Store Apps,Winrt Xaml,我已经写了几年Android应用程序,现在我正在开发一个Windows应用商店/Windows 8应用程序 我很困惑如何为横向和纵向编写不同的屏幕布局 在Android中,我们所要做的就是编写两个布局,一个用于纵向,另一个用于横向,遵循文件名的一些名称约定,当我们旋转设备时,平台会自动更改屏幕布局 我一直在用谷歌搜索一些解决方案,以便在我的Windows8应用程序中实现同样的功能,我所发现的只是一个使用可视状态组和可视状态的解决方案,在相同的XAML中加入一些在旋转设备时发生在小部件上的修改 例

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

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

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

我一直在用谷歌搜索一些解决方案,以便在我的Windows8应用程序中实现同样的功能,我所发现的只是一个使用可视状态组和可视状态的解决方案,在相同的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>

3.
0,10,10,807
对我来说,它看起来不是很干净和简单,即使使用VisualStudio的拖放小部件的方法来生成代码,我仍然觉得一定有比我现在所做的更简单的解决方案

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


谢谢

处理不同方向的一种方法是创建两个栅格元素,其中包含子元素,并根据方向更改栅格的可见性

要检测方向变化,还可以使用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;
                        }
                    });
                };
        }

    }
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";
    }

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

    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;
                        }
                    });
                };
        }

    }
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";
    }

}

希望这有帮助

Esdras-你没有错,应该有一种更简单的方法,但唯一的其他选择是软件表达式混合。我要承认,站起来跑步有一条学习曲线

此外,对于用Xaml编写的方向更改,父控件必须从可以扩展(非内部密封)且必须具有布局意识的控件驱动。例如,如果你把一个文本框放在一个布局感知页面上,它的方向会改变,但是如果你把一个网格放在布局感知页面上,把一个文本框放在网格中。。。默认行为是网格将响应,但文本框不会响应

您可能还注意到,尽管它很混乱,而且每个控件都需要一个控件修饰符,就像您为每个元素提供的那样,这些元素应该响应方向更改……好处是它不需要本机代码来定义状态或转换,因此设计人员可以使用类似于xaml的xml来描述控件中的更改查看它是方向还是其他控件的状态


如果你能得到你的手上的程序表达式混合它是为了这个目的。

我写了一篇关于stackoverflow的文章,一段时间以前,这可能对你有用。 提供了一些示例和代码:

[在Windows 8应用程序上处理方向信息][1]

如果您有更多问题,请发邮件给我

谢谢,
Ambuj

Hmm.听起来不错,但是在我的代码中,我必须处理一些gridview的选定内容,我应该做一些类似于
if(肖像){handle_my_gridview_ratio();}或者{handle_my_gridview_landscape()}
。无论如何,这比我目前的解决方案要好。谢谢上面的示例只是展示了如何以不同的方式检测方向变化。但是,您可以在DataContext中更改值并使用绑定来避免代码隐藏。这两个问题的答案都很好,但您的答案更适合我的问题。谢谢,抱歉耽搁了!此处有一个快速添加:由于此处的上下文是Windows 8,Blend已经在Visual Studio 2012的“盒子中”,因此请参阅本文: