[wpf] HorizontalAlignment = Stretch, MaxWidth 및 Left를 동시에 정렬 하시겠습니까?

이것은 쉬울 것 같지만 나는 어리둥절합니다. WPF에서는 부모의 너비로 늘어나지 만 최대 너비로만 늘어나는 TextBox를 원합니다. 문제는 부모 내에서 정당화되기를 원한다는 것입니다. 늘이기 위해서는 HorizontalAlignment = “Stretch”를 사용해야하지만 결과는 중앙에 위치합니다. HorizontalContentAlignment로 실험 해 보았지만 아무것도하지 않는 것 같습니다.

이 파란색 텍스트 상자가 창 크기에 따라 커지고 최대 너비가 200 픽셀이고 왼쪽 정렬되도록하려면 어떻게해야합니까?

<Page
  xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
  xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
  <StackPanel>
    <TextBox Background="Azure" Text="Hello" HorizontalAlignment="Stretch" MaxWidth="200" />
  </StackPanel>
</Page>

속임수는 무엇입니까?



답변

당신은 설정할 수 있습니다 HorizontalAlignment귀하의 설정, 왼쪽에 MaxWidth바인드 다음과 Width받는 ActualWidth부모 요소의 :

<Page
  xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
  xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
  <StackPanel Name="Container">
    <TextBox Background="Azure"
    Width="{Binding ElementName=Container,Path=ActualWidth}"
    Text="Hello" HorizontalAlignment="Left" MaxWidth="200" />
  </StackPanel>
</Page>


답변

<Grid>
    <Grid.ColumnDefinitions>
        <ColumnDefinition Width="*" MaxWidth="200"/>
    </Grid.ColumnDefinitions>

    <TextBox Background="Azure" Text="Hello" />
</Grid>


답변

주어진 두 답변 모두 내가 말한 문제에 효과적이었습니다. 감사합니다!

하지만 실제 응용 프로그램에서는 ScrollViewer 내부에 패널을 제한하려고했지만 Kent의 메서드는 추적 할 필요가없는 어떤 이유로 그렇게 잘 처리하지 못했습니다. 기본적으로 컨트롤은 MaxWidth 설정 이상으로 확장되어 내 의도를 무너 뜨릴 수 있습니다.

Nir의 기술은 잘 작동했고 ScrollViewer에 문제가 없었지만주의해야 할 사소한 것이 하나 있습니다. TextBox의 오른쪽 및 왼쪽 여백이 0으로 설정되어 있는지 확인해야합니다. 그렇지 않으면 방해가됩니다. 또한 세로 스크롤 막대가 나타날 때 문제를 방지하기 위해 ActualWidth 대신 ViewportWidth를 사용하도록 바인딩을 변경했습니다.


답변

DataTemplate의 너비에 사용할 수 있습니다.

Width="{Binding ActualWidth,RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type ScrollContentPresenter}}}"

DataTemplate 루트에 Margin = “0”이 있는지 확인합니다 (일부 패널을 루트로 사용하고 Margin을 해당 루트의 자식으로 설정할 수 있음).


답변

허용되는 답변과 기능적으로 유사하지만 부모 요소를 지정할 필요가 없습니다.

<TextBox
    Width="{Binding ActualWidth, RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type FrameworkElement}}}"
    MaxWidth="500"
    HorizontalAlignment="Left" />


답변

이 질문에 부딪히는 사람을 여전히 도울 수있을 것입니다. 왜냐하면 이것은 매우 오래된 문제이기 때문입니다.

나는 이것도 필요했고 이것을 처리하기 위해 행동을 썼다. 따라서 여기에 동작이 있습니다.

public class StretchMaxWidthBehavior : Behavior<FrameworkElement>
{
    protected override void OnAttached()
    {
        base.OnAttached();
        ((FrameworkElement)this.AssociatedObject.Parent).SizeChanged += this.OnSizeChanged;
    }

    protected override void OnDetaching()
    {
        base.OnDetaching();
        ((FrameworkElement)this.AssociatedObject.Parent).SizeChanged -= this.OnSizeChanged;
    }

    private void OnSizeChanged(object sender, SizeChangedEventArgs e)
    {
        this.SetAlignments();
    }

    private void SetAlignments()
    {
        var slot = LayoutInformation.GetLayoutSlot(this.AssociatedObject);
        var newWidth = slot.Width;
        var newHeight = slot.Height;

        if (!double.IsInfinity(this.AssociatedObject.MaxWidth))
        {
            if (this.AssociatedObject.MaxWidth < newWidth)
            {
                this.AssociatedObject.HorizontalAlignment = HorizontalAlignment.Left;
                this.AssociatedObject.Width = this.AssociatedObject.MaxWidth;
            }
            else
            {
                this.AssociatedObject.HorizontalAlignment = HorizontalAlignment.Stretch;
                this.AssociatedObject.Width = double.NaN;
            }
        }

        if (!double.IsInfinity(this.AssociatedObject.MaxHeight))
        {
            if (this.AssociatedObject.MaxHeight < newHeight)
            {
                this.AssociatedObject.VerticalAlignment = VerticalAlignment.Top;
                this.AssociatedObject.Height = this.AssociatedObject.MaxHeight;
            }
            else
            {
                this.AssociatedObject.VerticalAlignment = VerticalAlignment.Stretch;
                this.AssociatedObject.Height = double.NaN;
            }
        }
    }
}

그런 다음 다음과 같이 사용할 수 있습니다.

<Grid>
    <Grid.ColumnDefinitions>
        <ColumnDefinition Width="Auto" />
        <ColumnDefinition />
    </Grid.ColumnDefinitions>

    <TextBlock Grid.Column="0" Text="Label" />
    <TextBox Grid.Column="1" MaxWidth="600">
          <i:Interaction.Behaviors>
               <cbh:StretchMaxWidthBehavior/>
          </i:Interaction.Behaviors>
    </TextBox>
</Grid>

마지막으로 System.Windows.Interactivity네임 스페이스를 사용하여 동작을 사용하는 것을 잊습니다 .


답변

나는 사용할 것이다 SharedSizeGroup

<Grid>
    <Grid.ColumnDefinition>
        <ColumnDefinition SharedSizeGroup="col1"></ColumnDefinition>
        <ColumnDefinition SharedSizeGroup="col2"></ColumnDefinition>
    </Grid.ColumnDefinition>
    <TextBox Background="Azure" Text="Hello" Grid.Column="1" MaxWidth="200" />
</Grid>