Programming

StackPanel의 아이들이 최대 공간을 아래쪽으로 채우도록하는 방법은 무엇입니까?

procodes 2020. 3. 4. 07:50
반응형

StackPanel의 아이들이 최대 공간을 아래쪽으로 채우도록하는 방법은 무엇입니까?


왼쪽에는 텍스트가 흐르고 오른쪽에는 도움말 상자가 필요합니다.

도움말 상자가 맨 아래까지 뻗어 있어야합니다.

아래의 외부 StackPanel을 꺼내면 훌륭하게 작동합니다.

그러나 레이아웃의 이유로 (UserControls를 동적으로 삽입하고 있습니다) 줄 바꿈 StackPanel이 필요합니다.

내가 시도한 것처럼 GroupBox를 StackPanel의 맨 아래로 확장하려면 어떻게해야합니까?

  • VerticalAlignment = "스트레치"
  • VerticalContentAlignment = "Stretch"
  • Height = "자동"

XAML :

<Window x:Class="TestDynamic033.Test3"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="Test3" Height="300" Width="600">
    <StackPanel 
        VerticalAlignment="Stretch" 
        Height="Auto">

        <DockPanel 
            HorizontalAlignment="Stretch" 
            VerticalAlignment="Stretch" 
            Height="Auto" 
            Margin="10">

            <GroupBox 
                DockPanel.Dock="Right" 
                Header="Help" 
                Width="100" 
                Background="Beige" 
                VerticalAlignment="Stretch" 
                VerticalContentAlignment="Stretch" 
                Height="Auto">
                <TextBlock Text="This is the help that is available on the news screen." TextWrapping="Wrap" />
            </GroupBox>

            <StackPanel DockPanel.Dock="Left" Margin="10" Width="Auto" HorizontalAlignment="Stretch">
                <TextBlock Text="Here is the news that should wrap around." TextWrapping="Wrap"/>
            </StackPanel>

        </DockPanel>
    </StackPanel>
</Window>

대답:

감사합니다 Mark, StackPanel 대신 DockPanel을 사용하여 정리했습니다. 일반적으로 WPF 레이아웃에 DockPanel을 점점 더 많이 사용하고 있습니다. 고정 XAML은 다음과 같습니다.

<Window x:Class="TestDynamic033.Test3"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="Test3" Height="300" Width="600" MinWidth="500" MinHeight="200">
    <DockPanel 
        VerticalAlignment="Stretch" 
        Height="Auto">

        <DockPanel 
            HorizontalAlignment="Stretch" 
            VerticalAlignment="Stretch" 
            Height="Auto" 
            MinWidth="400"
            Margin="10">

            <GroupBox 
                DockPanel.Dock="Right" 
                Header="Help" 
                Width="100" 
                VerticalAlignment="Stretch" 
                VerticalContentAlignment="Stretch" 
                Height="Auto">
                <Border CornerRadius="3" Background="Beige">
                    <TextBlock Text="This is the help that is available on the news screen." TextWrapping="Wrap" 

                Padding="5"/>
                </Border>
            </GroupBox>

            <StackPanel DockPanel.Dock="Left" Margin="10" Width="Auto" HorizontalAlignment="Stretch">
                <TextBlock Text="Here is the news that should wrap around." TextWrapping="Wrap"/>
            </StackPanel>

        </DockPanel>
    </DockPanel>
</Window>

StackPanel최종 요소가 나머지 공간을 모두 사용 하는 처럼 들립니다 . 그러나 왜 DockPanel?를 사용하지 않습니까? DockPanelwith 의 다른 요소를 장식하면 DockPanel.Dock="Top"도움말 컨트롤이 나머지 공간을 채울 수 있습니다.

XAML :

<DockPanel Width="200" Height="200" Background="PowderBlue">
    <TextBlock DockPanel.Dock="Top">Something</TextBlock>
    <TextBlock DockPanel.Dock="Top">Something else</TextBlock>
    <DockPanel
        HorizontalAlignment="Stretch" 
        VerticalAlignment="Stretch" 
        Height="Auto" 
        Margin="10">

      <GroupBox 
        DockPanel.Dock="Right" 
        Header="Help" 
        Width="100" 
        Background="Beige" 
        VerticalAlignment="Stretch" 
        VerticalContentAlignment="Stretch" 
        Height="Auto">
        <TextBlock Text="This is the help that is available on the news screen." 
                   TextWrapping="Wrap" />
     </GroupBox>

      <StackPanel DockPanel.Dock="Left" Margin="10" 
           Width="Auto" HorizontalAlignment="Stretch">
          <TextBlock Text="Here is the news that should wrap around." 
                     TextWrapping="Wrap"/>
      </StackPanel>
    </DockPanel>
</DockPanel>

DockPanel사용 가능한 플랫폼이없는 플랫폼 (예 : WindowsStore) 인 경우 그리드를 사용하여 동일한 효과를 만들 수 있습니다. 다음은 그리드를 대신 사용하여 수행 한 위의 예입니다.

<Grid Width="200" Height="200" Background="PowderBlue">
    <Grid.RowDefinitions>
        <RowDefinition Height="Auto"/>
        <RowDefinition Height="*"/>
    </Grid.RowDefinitions>
    <StackPanel Grid.Row="0">
        <TextBlock>Something</TextBlock>
        <TextBlock>Something else</TextBlock>
    </StackPanel>
    <Grid Height="Auto" Grid.Row="1" Margin="10">
        <Grid.ColumnDefinitions>
            <ColumnDefinition Width="*"/>
            <ColumnDefinition Width="100"/>
        </Grid.ColumnDefinitions>
        <GroupBox
            Width="100"
            Height="Auto"
            Grid.Column="1"
            Background="Beige"
            Header="Help">
            <TextBlock Text="This is the help that is available on the news screen." 
              TextWrapping="Wrap"/>
        </GroupBox>
        <StackPanel Width="Auto" Margin="10" DockPanel.Dock="Left">
            <TextBlock Text="Here is the news that should wrap around." 
              TextWrapping="Wrap"/>
        </StackPanel>
    </Grid>
</Grid>

이런 일이 발생하는 이유는 스택 패널이 요소를 스태킹하는 축의 제약 조건으로 양의 무한대를 가진 모든 자식 요소를 측정하기 때문입니다. 자식 컨트롤은 원하는 크기를 반환해야합니다 (양의 무한대는 어느 축의 MeasureOverride 에서 유효한 반환 값이 아님 ). 따라서 모든 것이 들어갈 수있는 가장 작은 크기를 반환합니다. 그들은 실제로 얼마나 많은 공간을 채워야하는지 알 방법이 없습니다.

뷰에 스크롤 기능이 필요하지 않고 위의 답변이 필요에 맞지 않으면 자신의 패널을 구현하는 것이 좋습니다. 아마도 StackPanel에서 직접 파생 될 수 있으며 ArrangeOverride 메소드를 변경 하여 나머지 요소를 하위 요소간에 나눕니다 (각각 동일한 양의 추가 공간을 제공). 원하는 것보다 더 많은 공간이 주어지면 요소가 제대로 렌더링되어야하지만, 더 적게 주면 글리치를 볼 수 있습니다.

전체를 스크롤 할 수 있기를 원한다면 ScrollViewer가 작업 할 무한한 공간을 제공하므로 하위 요소와 동일한 위치에 배치 할 수 있기 때문에 일이 조금 더 어려울 것입니다. 원래. 이 상황에서 새 패널에 뷰포트 크기를 지정할 수있는 새 속성을 만들려면이 속성을 ScrollViewer의 크기에 바인딩 할 수 있어야합니다. 이상적으로는 IScrollInfo를 구현 하지만 모든 것을 올바르게 구현하면 복잡해지기 시작합니다.


다른 방법은 하나의 열과 n 개의 행이 있는 Grid를 사용하는 것 입니다. 모든 행 높이를로 설정 Auto하고 맨 아래 행 높이를로 설정하십시오 1*.

그리드가 DockPanels, StackPanels 및 WrapPanels보다 레이아웃 성능이 우수하다는 것을 알았 기 때문에이 방법을 선호합니다. 그러나 많은 수의 항목에 대해 레이아웃이 수행되는 ItemTemplate에서 사용하지 않으면 아마 눈치 채지 못할 것입니다.


수정 된 버전 의 StackPanel을 사용할 수 있습니다 .

<st:StackPanel Orientation="Horizontal" MarginBetweenChildren="10" Margin="10">
   <Button Content="Info" HorizontalAlignment="Left" st:StackPanel.Fill="Fill"/>
   <Button Content="Cancel"/>
   <Button Content="Save"/>
</st:StackPanel>

첫 번째 버튼이 채워집니다.

Nuget을 통해 설치할 수 있습니다.

Install-Package SpicyTaco.AutoGrid

또한 wpf-autogrid를 살펴 보는 것이 좋습니다 . DockPanel, StackPanel 및 Grid 대신 WPF 양식에 매우 유용하며 매우 쉽고 우아하게 스트레칭으로 문제를 해결합니다. github에서 readme를 살펴보십시오.

<st:AutoGrid Columns="160,*" ChildMargin="3">
    <Label Content="Name:"/>
    <TextBox/>

    <Label Content="E-Mail:"/>
    <TextBox/>

    <Label Content="Comment:"/>
    <TextBox/>
</st:AutoGrid>

할 수있는 몇 가지 :

1 : Orientation세로로 설정하십시오 .

<StackPanel Orientation="Vertical"></StackPanel>
  1. 세트 Height의를 StackPanel윈도우와 동일로 :

물론 이러한 속성을 결합 할 수 있습니다 .

<StackPanel Orientation="Vertical" Height="600"></StackPanel>

NuGets를 설치하고 다른 작업을 수행하지 않고도 추가 작업을 수행 할 필요가 없습니다 ....

편집하다

StackPanel을 ScrollViewer 안에 넣을 수도 있습니다. 그러면 컨텐츠 가시성을 유지하면서 GroupBox의 높이를 제어 할 수 있습니다.

<GroupBox>
    <ScrollViewer>
        <StackPanel Orientation="Vertical>
              <!-- Place Children Objects here-->
        <StackPanel>
    <ScrollViewer>
<GroupBox>

참고 URL : https://stackoverflow.com/questions/569095/how-to-get-stackpanels-children-to-fill-maximum-space-downward



반응형