WindowChrome 利用時に アプリ を 最大化 したときの 問題 と 対策方法

0 件のコメント

WPF で フラットデザイン(メトロデザイン) っぽい ウィンドウ を作成しようとすると WindowChrome を利用することになります。 WindowChrome を使うときに発生する問題点とその対処方法をここではまとめます。

目次

問題点

WindowChrome を利用して最大化したときの問題点は2点あります。

  1. タスクバーの上に被ってしまう

    ウィンドウを最大化するとタスクバー上まで被ってしまい、タスクバーの操作ができなくなってしまいます。 ストアアプリや全画面表示するゲームであれば良いでしょうが…、通常業務で使うアプリだと不便です。

  2. ウィンドウ枠が画面外にはみ出る

    ウィンドウを最大化すると画面領域外にウィンドウ枠がはみ出てしまいます。 以下の画像ではウィンドウタイトルに指定している左上の「MainWindow」という文字が見切れてしまっています。

対応策

上述問題点のそれぞれに対して対策を行っていきます。

  1. タスクバー上へ被らないようにする

    これは WindowChromeGlassFrameThickness属性 を "0" に設定することで解決できます。

      ...
                        <WindowChrome CornerRadius="0"
                                      GlassFrameThickness="0"
                                      ResizeBorderThickness="8" />
      ...
    
  2. ウィンドウ枠が画面外にはみ出ないようにする

    これは最大化時、「外枠に指定している BorderThickness の値」を「WindowChromeResizeBorderThickness の値」に設定することで解決できます。 最大化を解除するときは「外枠に指定している BorderThickness の値」元に戻すことを忘れないようにします。 以下のコードでは ResizeBorderThickness が "8" なので、 BorderThickness も "8" に設定します。

      ...
                        <WindowChrome CornerRadius="0"
                                      GlassFrameThickness="0"
                                      ResizeBorderThickness="8" />
      ...
                            <ControlTemplate.Triggers>
                                <Trigger Property="WindowState" Value="Maximized">
                                    <Setter TargetName="border" Property="BorderThickness" Value="8" />
                                </Trigger>
                                <Trigger Property="WindowState" Value="Normal">
                                    <Setter TargetName="border" Property="BorderThickness" Value="1" />
                                </Trigger>
                            </ControlTemplate.Triggers>
      ...
    

[まとめ] サンプルコード

WindowChrome を利用したウィンドウを作成する、できるだけ単純なサンプルコードを以下に載せます。 「できるだけ単純な…」としながらそれなりのコードになってしまいましたが、ポイントとなる箇所はハイライトしておきました。

<Window x:Name="window"
        x:Class="WpfApplication.Views.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="MainWindow" Height="350" Width="525"
        WindowStyle="None">
    <Window.Style>
        <Style TargetType="Window">
            <Setter Property="WindowChrome.WindowChrome">
                <Setter.Value>
                    <WindowChrome CornerRadius="0"
                                  GlassFrameThickness="0"
                                  ResizeBorderThickness="8" />
                </Setter.Value>
            </Setter>
            <Setter Property="Template">
                <Setter.Value>
                    <ControlTemplate TargetType="Window">
                        <Border x:Name="border"
                                Background="#ffffff"
                                BorderBrush="#cccccc"
                                BorderThickness="1">
                            <Grid>
                                <Grid.RowDefinitions>
                                    <RowDefinition Height="Auto" />
                                    <RowDefinition Height="*" />
                                </Grid.RowDefinitions>
                                <Grid Grid.Row="0" HorizontalAlignment="Stretch" VerticalAlignment="Top">
                                    <TextBlock Text="{Binding ElementName=window, Path=Title}" />
                                    <StackPanel Orientation="Horizontal" HorizontalAlignment="Right" VerticalAlignment="Stretch">
                                        <Button Content="_" Width="{x:Static SystemParameters.WindowCaptionButtonWidth}" Height="{x:Static SystemParameters.WindowCaptionButtonHeight}" />
                                        <Button Content="□" Width="{x:Static SystemParameters.WindowCaptionButtonWidth}" Height="{x:Static SystemParameters.WindowCaptionButtonHeight}" />
                                        <Button Content="×" Width="{x:Static SystemParameters.WindowCaptionButtonWidth}" Height="{x:Static SystemParameters.WindowCaptionButtonHeight}" />
                                    </StackPanel>
                                </Grid>
                                <Grid Grid.Row="1">
                                    <ContentPresenter HorizontalAlignment="Stretch"
                                                      VerticalAlignment="Stretch" />                                   
                                </Grid>
                            </Grid>
                        </Border>
                        <ControlTemplate.Triggers>
                            <Trigger Property="WindowState" Value="Maximized">
                                <Setter TargetName="border" Property="BorderThickness" Value="8" />
                            </Trigger>
                            <Trigger Property="WindowState" Value="Normal">
                                <Setter TargetName="border" Property="BorderThickness" Value="1" />
                            </Trigger>
                        </ControlTemplate.Triggers>
                    </ControlTemplate>
                </Setter.Value>
            </Setter>
        </Style>            
    </Window.Style>
    <Grid>
        <Button Content="Button"
                HorizontalAlignment="Center"
                VerticalAlignment="Center" />
    </Grid>
</Window>

参考記事