web-dev-qa-db-ja.com

WPFシェル統合ライブラリを使用して最大化するとウィンドウが画面から消える

WPF Shell Integration Library を使用してwpfアプリのカスタムchromeを作成しています。すべて問題ありませんが、アプリを最大化すると、6または7ピクセルになります。画面から。

これは私が使用しているコードです:

<Style TargetType="{x:Type local:MainWindow}">
        <Setter Property="Shell:WindowChrome.WindowChrome">
            <Setter.Value>
                <Shell:WindowChrome
                    ResizeBorderThickness="6"
                    CaptionHeight="10"
                    CornerRadius="0"
                    GlassFrameThickness="1"/>
            </Setter.Value>
        </Setter>
        <Setter Property="Template">
            <Setter.Value>
                <ControlTemplate TargetType="{x:Type local:MainWindow}">
                    <Grid>
                        <Border BorderThickness="1" BorderBrush="#389FD1" Background="#389FD1">
                            <ContentPresenter Margin="0,22,0,0" Content="{TemplateBinding Content}"/>
                        </Border>
                        <StackPanel Orientation="Horizontal" HorizontalAlignment="Right" VerticalAlignment="Top" >
                            <TextBlock Text="{Binding NombreUsuario}" Foreground="White" Margin="5,5,20,5" Opacity=".8" />
                            <Button Style="{StaticResource ImageButton}" Height="20" Width="20" Margin="0" Click="WindowMinimize" Shell:WindowChrome.IsHitTestVisibleInChrome="True">
                                <Image Height="10" Width="10" Source="/Resources/Images/minimize.png" />
                            </Button>
                            <Button Style="{StaticResource ImageButton}" Height="20" Width="20" Margin="0" Click="WindowMaximizeRestore" Shell:WindowChrome.IsHitTestVisibleInChrome="True" >
                                <Image Height="10" Width="10" Source="/Resources/Images/maximize.png" />
                            </Button>
                            <Button Style="{StaticResource ImageButton}" Height="20" Width="20" Margin="0" Click="WindowClose" Shell:WindowChrome.IsHitTestVisibleInChrome="True">
                                <Image Height="10" Width="10" Source="/Resources/Images/close.png" />
                            </Button>
                        </StackPanel>

                    </Grid>
                </ControlTemplate>
            </Setter.Value>
        </Setter>
    </Style>
40
Eduardo Molteni

Windowsは、ウィンドウが最大化されたときにウィンドウのエッジをトリミングして、通常はサイズ変更のエッジになるものを不明瞭にします。ウィンドウとコンテンツの間にプロキシ境界線を配置し、最大化されたときに厚さを膨らませることで、これを回避できます。

これを行うためにlibに付属の例を変更しました。同じ基本的な変更を、サンプルに加えることができます。

<ControlTemplate TargetType="{x:Type local:SelectableChromeWindow}">
  <Border BorderBrush="Green">
    <Border.Style>
      <Style TargetType="{x:Type Border}">
        <Setter Property="BorderThickness" Value="0"/>
        <Style.Triggers>
          <DataTrigger Binding="{Binding ElementName=ThisWindow, Path=WindowState}" Value="Maximized">
            <Setter Property="BorderThickness" Value="{Binding Source={x:Static Shell:SystemParameters2.Current}, Path=WindowResizeBorderThickness}"/>
          </DataTrigger>
        </Style.Triggers>
      </Style>
    </Border.Style>
    <Grid [...]/>
  </Border>
</ControlTemplate>

それがお役に立てば幸いです。

。net 4.5以降の場合 SystemParametersは少し異なります(例:

<DataTrigger Binding="{Binding RelativeSource={RelativeSource AncestorType={x:Type local:MainWindow}}, Path=WindowState}" Value="Maximized">
    <Setter Property="BorderThickness" Value="{Binding Source={x:Static SystemParameters.WindowResizeBorderThickness}}"/>
</DataTrigger>
47
Joe Castro

これは私のために働いた:

<ResourceDictionary xmlns="http://schemas.Microsoft.com/winfx/2006/xaml/presentation"
                xmlns:x="http://schemas.Microsoft.com/winfx/2006/xaml"
                xmlns:Shell="clr-namespace:Microsoft.Windows.Shell;Assembly=Microsoft.Windows.Shell"
                xmlns:Views="clr-namespace:BorderLessWpf.Views">

<Style TargetType="{x:Type Views:ShellView}" >
    <Setter Property="Shell:WindowChrome.WindowChrome">
        <Setter.Value>
            <Shell:WindowChrome
                ResizeBorderThickness="6"
                CaptionHeight="10"
                CornerRadius="0"
                GlassFrameThickness="1"/>
        </Setter.Value>
    </Setter>
    <Style.Triggers>
        <Trigger Property="WindowState" Value="Maximized">
            <Setter Property="BorderThickness" Value="6" />
        </Trigger>
    </Style.Triggers>
</Style>
7
Bas

ウィンドウが画面から出る問題を解決するには、次のように設定します。

this.ResizeMode = System.Windows.ResizeMode.NoResize;

詳細については、 JAPFの「WPFプロジェクトのメインウィンドウのセットアップ」の投稿 を参照してください。

2
Ayo

私のプロジェクトでは、CaptionHeightを0に設定し、ResizeModeをCanResizeWithGripに設定しています。これは私が適切な厚さのために思いついたコードです。

            Thickness maximizeFix = new Thickness(SystemParameters.WindowNonClientFrameThickness.Left +
                SystemParameters.WindowResizeBorderThickness.Left,
                SystemParameters.WindowNonClientFrameThickness.Top +
                SystemParameters.WindowResizeBorderThickness.Top
                - SystemParameters.CaptionHeight,
                SystemParameters.WindowNonClientFrameThickness.Right +
                SystemParameters.WindowResizeBorderThickness.Right,
                SystemParameters.WindowNonClientFrameThickness.Bottom +
                SystemParameters.WindowResizeBorderThickness.Bottom);

Joe Castroが行ったように境界線を使用し、ウィンドウの状態が変化したときに更新するプロパティに太さをバインドします。

コードはぎこちないようですが、私はまだ別の解決策を見つけていません。

2
Shaun Lammers

ここ から、WindowChrome.NonClientFrameEdgesを設定してみようと思いました。

いくつかの実験で、最大化されたときにNonClientFrameEdges.Bottomに設定し、最大化されていないときにNonClientFrameEdges.Noneに戻すことで、目的の効果を得ることができることがわかりました。

これにより、下部を除くすべてのエッジでマージンが消えますが、タスクバーの下での重なりが発生しなくなります。

WindowChromeがWindowStateにpriorに設定されていることが重要です。そのため、私のコードビハインドには関数があります(MainGrid2はすべてのウィンドウコンテンツを保持します。ステータスバー、およびStatusGridはステータスバーを保持します):

    private void Maximise()
    {
        StatusGrid.Margin = new Thickness(7, 0, 7, 0);
        MainGrid2.Margin = new Thickness(12, 12, 12, 0);            
        chrome.NonClientFrameEdges = NonClientFrameEdges.Bottom;
        WindowChrome.SetWindowChrome(this, chrome); 
        WindowState = System.Windows.WindowState.Maximized;
    }

    private void Restore()
    {
        StatusGrid.Margin = new Thickness(0);
        MainGrid2.Margin = new Thickness(5, 5, 5, 0);
        chrome.NonClientFrameEdges = NonClientFrameEdges.None;
        WindowChrome.SetWindowChrome(this, chrome);
        WindowState = System.Windows.WindowState.Normal;
    }
1
Ben Sewell

ウィンドウのメインコンテンツの周囲に境界線を追加し、ViewModelのプロパティにバインドすることで、問題を解決することができました。ユーザーが最大化ボタンを押すと、BorderThicknessを7に設定するコマンドがトリガーされます。最大化ボタンをもう一度押すと、BorderThicknessが0に設定されます。

    <!-- Content of my window -->
    <Border BorderThickness="{Binding BorderThickness}" BorderBrush="{StaticResource OffsetBlackBrush}">
            <Grid>
<StackPanel Grid.Column="2" Orientation="Horizontal">
                    <Button Content="-" Command="{Binding MinimizeCommand}" Style="{StaticResource WindowControlButton}" />
                    <Button Content="[ ]" Command="{Binding MaximizeCommand}" Style="{StaticResource WindowControlButton}" />
                    <Button Content="X" Command="{Binding CloseCommand}" Style="{StaticResource WindowCloseButton}" />
                </StackPanel>
            </Grid>
    </Border>


<!-- BorderThickness property in VM -->
public int BorderThickness { get; set; } = 0;


    /// <summary>
    /// Maximizes the current window
    /// </summary>
    public RelayCommand MaximizeCommand
    {
        get => new RelayCommand(param =>
        {
            if (!_view.GetWindowState())
            {
                BorderThickness = 7;
                _view.SetWindowState("Maximize"); // Change window state to maximized using interface passed into ctor
            }
            else
            {
                BorderThickness = 0;
                _view.SetWindowState("Normal");
            }
        });
    }
0
Craig Martin