読者です 読者をやめる 読者になる 読者になる

かずきのBlog@hatena

日本マイクロソフトに勤めています。XAML + C#の組み合わせをメインに、たまにASP.NETやJavaなどの.NET系以外のことも書いています。掲載内容は個人の見解であり、所属する企業を代表するものではありません。

Windows 10 TPのUAPのVisualStateManagerの新しい機能

Win10 XAML UWP
Windows 10 TP段階の情報です

Windows 10 TPのUAPのVisualStateManagerが強化されてました。簡単に言うと、以下の2点が追加されています。

  • 画面のサイズに応じてVisualStateを自動で切り替える機能
  • プロパティを設定するためのSetter機能

順番に見ていきます。

画面のサイズに応じてVisualStateを自動で切り替える機能

これはVisualStateに新しくStateTriggersというプロパティが追加されていて、ここにAdaptiveTriggerを設定することで実現できます。因みにTriggerはAdaptiveTriggerしか無さそうです。

AdaptiveTriggerにはMinWindowWidthとMinWindowHeightというプロパティがあって、ここに設定した幅や高さよりも大きい時にそのVisualStateに遷移します。条件を満たすAdaptiveTriggerが設定されたVisualStateが複数ある場合は、より大きい値が設定されているほうが優先されるっぽいです。

プロパティを設定するためのSetter機能

今までVSMでは、Storyboardを使って頑張ってプロパティの値を書き換えてきました。アニメーションが必要じゃない時も必要なときも。アニメーションがないときに、ただ単に値を書き換えるだけってケースではオーバースペックだったりしたのですが、StyleでおなじみのSetterを使ってプロパティを書き換えることが出来るようになっています。

ただ、罠があってSetterのTargetの指定の仕方が特殊です。以下のように書きます。

<Setter Target="コントロール名.プロパティ名" Value="値" />

Propertyという名前の属性もあるのですが、これを設定するとコンパイルに失敗します。罠です気を付けましょう。

動作確認

ということで簡単なサンプルです。TextBlockの値を画面の大きさに応じて書き換えてみます。XAMLは以下の通りです。

<Page
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local="using:App11"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    xmlns:Interactivity="using:Microsoft.Xaml.Interactivity" xmlns:Core="using:Microsoft.Xaml.Interactions.Core"
    x:Class="App11.MainPage"
    mc:Ignorable="d">

    <Grid Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
        <VisualStateManager.VisualStateGroups>
            <VisualStateGroup x:Name="SizeStateGroup">
                <VisualState x:Name="Min">
                    <VisualState.StateTriggers>
                        <AdaptiveTrigger MinWindowWidth="0" />
                    </VisualState.StateTriggers>
                    <VisualState.Setters>
                        <Setter Target="text.Text" Value="狭い" />
                    </VisualState.Setters>
                </VisualState>
                <VisualState x:Name="Middle">
                    <VisualState.StateTriggers>
                        <AdaptiveTrigger MinWindowWidth="651" />
                    </VisualState.StateTriggers>
                    <VisualState.Setters>
                        <Setter Target="text.Text" Value="ふつう" />
                    </VisualState.Setters>
                </VisualState>
                <VisualState x:Name="Wide">
                    <VisualState.StateTriggers>
                        <AdaptiveTrigger MinWindowWidth="1000" />
                    </VisualState.StateTriggers>
                    <VisualState.Setters>
                        <Setter Target="text.Text" Value="すげーひろい" />
                    </VisualState.Setters>
                </VisualState>
            </VisualStateGroup>
        </VisualStateManager.VisualStateGroups>
        <TextBlock x:Name="text" HorizontalAlignment="Center" VerticalAlignment="Center" />
    </Grid>
</Page>

textという名前のTextBlockのTextプロパティを1000ピクセルより幅があるときは「すげーひろい」として、651ピクセルより幅があるときは「普通」として、それより狭いときは「狭い」としています。

実行すると以下のようになります。

f:id:okazuki:20150325211859p:plain

f:id:okazuki:20150325211935p:plain

f:id:okazuki:20150325212014p:plain

MSさんとしては、こいつを使ってPhoneでもTabletでもDesktopでもOne XAMLで書いてくれHAHAHAという感じみたいです。うん。