1

简单的问题,我有一个 Windows Phone 页面,其中包含 a ,其中包含 a scrollviewerimageatextblock和 a richtextbox

现在,当用户开始滚动时,我想在页面滚动到页面外textblock时将视图保持在顶部image

所以效果是,用户开始向上滚动,一切都向上滚动,当图像在页面之外时,文本块停留在页面顶部,但richtextbox继续向上滚动。

有什么想法吗?

4

2 回答 2

1

我自己找到了一个可行的解决方案……完整的详细信息可在我的博客上找到……它还包含指向我在 GitHub 上的演示项目的链接。

诀窍是抓住VerticallScrollBar内部ScrollViewer并将其设置为ManipulationModeControlUI 线程上获得足够的反馈。使用滚动条的滚动偏移信息,我们可以为要保持在视图中的特定 ui 元素设置动画。

于 2013-08-27T12:13:57.553 回答
1

这是达到此结果的一种方法:

一是布局。我设置了一个网格,有两行。第一个是空的,当我们需要冻结它时将托管标题。第二行包含滚动查看器。

在滚动查看器中,我将控件放在网格中,但您可以使用任何适合您的容器。

<ScrollViewer Grid.Row="1"
                Margin="0"
                Padding="0"
                x:Name="ParentScroll"
                ManipulationMode="Control"
                MouseMove="ParentScroll_MouseMove">
    <Grid x:Name="ChildGrid">
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto" />
            <RowDefinition Height="Auto" />
            <RowDefinition />
        </Grid.RowDefinitions>

        <Image Source="Picture.jpg" Grid.Row="0"/>
        <TextBlock Text="Header" Grid.Row="1" x:Name="TextHeader" />
        <RichTextBox Grid.Row="2" x:Name="RichText">
            <Paragraph>
                <Bold>RichTextBox</Bold>
                <!-- More stuff -->
            </Paragraph>
        </RichTextBox>
    </Grid>
</ScrollViewer>

我使用MouseMove事件来通知滚动事件。您还可以深入了解模板、提取ScrollBar控件并订阅ValueChanged事件,如下所述:http: //social.msdn.microsoft.com/Forums/wpapps/en-US/81fcd34e-6ec9-48d0-891e- c53a53344553/scrollviewer-同步

请注意,您需要设置ManipulationMode为,Control否则控件的位置将不会以平滑的速率更新。我想这是由于一些内部优化。

在后面的代码中,我使用该TransformToVisual方法来计算控件与 ScrollViewer 的相对位置。这样,我可以知道标题何时消失。当它发生时,我将其从子网格中删除,并将其放在父网格中的 ScrollViewer 之外。当 RichTextBox 的顶部看不见时,我将标题放回 ScrollViewer:

private void ParentScroll_MouseMove(object sender, System.Windows.Input.MouseEventArgs e)
{
    if (Grid.GetRow(this.TextHeader) == 1)
    {
        var generalTransform = TextHeader.TransformToVisual(ParentScroll);
        var childToParentCoordinates = generalTransform.Transform(new Point(0, 0));

        if (childToParentCoordinates.Y < 0)
        {
            this.ChildGrid.Children.Remove(this.TextHeader);
            this.ParentGrid.Children.Add(this.TextHeader);

            Grid.SetRow(this.TextHeader, 0);
        }
    }
    else
    {
        var generalTransform = RichText.TransformToVisual(ParentScroll);
        var childToParentCoordinates = generalTransform.Transform(new Point(0, 0));

        if (childToParentCoordinates.Y > 0)
        {
            this.ParentGrid.Children.Remove(this.TextHeader);
            this.ChildGrid.Children.Add(this.TextHeader);

            Grid.SetRow(this.TextHeader, 1);
        }
    }

可能有一些不那么棘手的方法可以达到相同的结果,但这个解决方案似乎在模拟器中运行顺利。

于 2013-08-26T19:53:36.757 回答