【问题标题】:Why won't Grid rows with height Auto resize with scale-transformed content?为什么不使用高度转换的内容自动调整高度的网格行?
【发布时间】:2015-06-05 15:04:12
【问题描述】:

鉴于下面的代码,我原以为红色和绿色框最终会彼此相邻,但正如您在结果的屏幕截图中看到的那样,它们并没有。相反,网格行的大小可以适应它们的完整大小,即使有一个渲染变换将它们缩放到它们的一半高度。

有没有办法让网格行真正调整自己的大小并适应它们的内容?

我想要这个,因为我无法为行的高度设置动画,所以我想为其内容的高度设置动画。

<Grid>
    <Grid.RowDefinitions>
        <RowDefinition Height="Auto" />
        <RowDefinition Height="Auto" />
    </Grid.RowDefinitions>

    <Border Height="300"
                Grid.Row="0"
                Background="Red">
        <Border.RenderTransform>
            <ScaleTransform ScaleY="0.5" />
        </Border.RenderTransform>
    </Border>
    <Border Height="200"
                Grid.Row="1"
                Background="Green">
        <Border.RenderTransform>
            <ScaleTransform ScaleY=".5" />
        </Border.RenderTransform>
    </Border>
</Grid>

【问题讨论】:

  • 如果您只是使用对象进行大小调整,只需将 Grid 换成 StackPanel。

标签: xaml windows-phone-8.1


【解决方案1】:

正如 Sheridan 所说,RenderTransform 只是在移动东西——独立于其他元素。巧妙的是,它是完全硬件加速的。

让系统执行动画并影响布局有点棘手。您可能希望不进行纯粹的调整大小,而是使用渲染变换让一个元素在另一个元素之上移动,从而隐藏它。

但是,如果您确实想要真正调整内容大小,这里有一种方法。

首先,我在底部添加了一个高度为 * 的行,以允许您的自动行仅使用他们需要的大小。 其次,我创建了一个动画(当然是使用 Blend :)) - 并命名了其中的关键帧,以便能够从后面的代码中访问它们。

最后我修改了 .cs 文件中的动画,然后运行动画 - 瞧!请注意,这不会是硬件加速的,但应该适用于简单的 UI。

代码也可以在:https://github.com/andyhammar/Wp81ResizeRowsTestApp

.xaml

<Page.Resources>
    <Storyboard x:Name="AnimateRed">
        <DoubleAnimationUsingKeyFrames EnableDependentAnimation="True" Storyboard.TargetProperty="(FrameworkElement.Height)" Storyboard.TargetName="_redBorder">
            <EasingDoubleKeyFrame KeyTime="0" x:Name="redAnimationFromKeyFrame" Value="300"/>
            <EasingDoubleKeyFrame KeyTime="0:0:0.5" x:Name="redAnimationToKeyFrame" Value="200">
                <EasingDoubleKeyFrame.EasingFunction>
                    <CubicEase EasingMode="EaseOut"/>
                </EasingDoubleKeyFrame.EasingFunction>
            </EasingDoubleKeyFrame>
        </DoubleAnimationUsingKeyFrames>
    </Storyboard>
</Page.Resources>

<Grid>
    <Grid.RowDefinitions>
        <RowDefinition Height="Auto" />
        <RowDefinition Height="Auto" />
        <RowDefinition Height="*" />
    </Grid.RowDefinitions>

    <Border 
        x:Name="_redBorder" 
        Height="300"
        Grid.Row="0"
        Background="Red">
    </Border>
    <Border 
        x:Name="_greenBorder" 
        Height="200"
        Grid.Row="1"
        Background="Green">
    </Border>

    <StackPanel 
        Grid.Row="2"
        VerticalAlignment="Bottom"
        HorizontalAlignment="Center"
        Orientation="Horizontal">
        <Button 
            x:Name="redSmallButton"
            Content="red small"
            Click="RedSmallButton_OnClick"/>
        <Button 
            x:Name="redLargeButton"
            Content="red large"
            Click="RedLargeButton_OnClick"/>
    </StackPanel>

</Grid>

.xaml.cs

    private void RedSmallButton_OnClick(object sender, RoutedEventArgs e)
    {
        redAnimationFromKeyFrame.Value = 300;
        redAnimationToKeyFrame.Value = 200;
        AnimateRed.Begin();
    }

    private void RedLargeButton_OnClick(object sender, RoutedEventArgs e)
    {
        redAnimationFromKeyFrame.Value = 200;
        redAnimationToKeyFrame.Value = 300;
        AnimateRed.Begin();
    }

【讨论】:

    【解决方案2】:

    确实如此,但我建议您改用LayoutTransform Property。不同之处在于LayoutTransform 在调用ArrangeMeasure 方法之前 执行,因此会考虑新的大小并在之后执行RenderTransform,因此它忽略了任何维度变化。

    您可以在 Scott Logic 网站上的 LayoutTransform vs. RenderTransform - What's the Difference? 页面中找到有关差异的完整说明。

    <Grid>
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto" />
            <RowDefinition Height="Auto" />
        </Grid.RowDefinitions>
    
        <Border Height="300"
                    Grid.Row="0"
                    Background="Red">
            <Border.LayoutTransform>
                <ScaleTransform ScaleY="0.5" />
            </Border.LayoutTransform>
        </Border>
        <Border Height="200"
                    Grid.Row="1"
                    Background="Green">
            <Border.LayoutTransform>
                <ScaleTransform ScaleY=".5" />
            </Border.LayoutTransform>
        </Border>
    </Grid>
    

    【讨论】:

    • 对不起,我没有注意到那个标签……还是一样的,你仍然可以使用它。查看LayoutTransform not in Windows Phone Toolkit 问题的答案。
    • 我试过了,但我无法让它正确地制作动画;我不知道如何在情节提要中指定目标属性以获取自定义转换器中的比例。
    猜你喜欢
    • 1970-01-01
    • 2017-08-25
    • 1970-01-01
    • 2014-11-06
    • 2016-06-13
    • 1970-01-01
    • 1970-01-01
    • 2010-11-28
    • 1970-01-01
    相关资源
    最近更新 更多