我正在构建一个电子阅读器类型的应用程序作为 Windows 8.1/WP8.1 通用应用程序。我的文本包含在FlipView
使用 anObservableCollection<FrameworkElement>
作为其来源的 a 中。每个FrameworkElement
都是 RichTextBlock 或 RichTextBlockOverflow。我的问题是FlipView
在第三个元素之后停止显示任何东西。
我在 MDSN 论坛上发现了一个有类似问题的人。他们的解决方案似乎表明问题在于RichTextBlock/Overflows
不在可视树中。但是,当我尝试RichTextBlock/Overflows
通过StackPanel
手动ObservableCollection
将)。
我怎样才能解决这个问题?我的 RichTextBlocks 和它们的溢出不应该是树的一部分,因为它们在 FlipView 的 ItemSource 中吗?
我的 ViewModel 代码如下。我可以通过命令从我的视图中访问元素,但我希望将其保持在最低限度。
编辑
我已经用一种解决方法“修复”了这个问题。这里的问题是 FlipView 虚拟化了它的子元素,因此在从第一页滚动到足够远之后,原始的 RichTextBlock 被虚拟化了,这导致所有依赖它的 RichTextBlockOverflow 丢失了它们的内容。我的解决方案是将我的 FlipView 的 ItemsPanelTemplate 从 VirtualizingStackPanel 更改为 StackPanel。这里明显的缺点是我失去了虚拟化的性能优势。我想我会将此作为自我回答发布,除非我找到或收到很快效果更好的东西。
private void BuildPagesNew()
{
//CurrentPage is a public property. It's the ObservableCollection<FrameworkElement>
CurrentPage.Clear();
RichTextBlockOverflow lastOverflow;
lastOverflow = AddOnePage(null);
CurrentPage.Add(lastOverflow);
while(lastOverflow.HasOverflowContent)
{
lastOverflow = AddOnePage(lastOverflow);
}
}
private RichTextBlockOverflow AddOnePage(RichTextBlockOverflow lastOverflow)
{
bool isFirstPage = lastOverflow == null;
RichTextBlockOverflow rtbo = new RichTextBlockOverflow();
if (isFirstPage)
{
RichTextBlock pageOne = new RichTextBlock();
pageOne.Width = double.NaN;
pageOne.Height = double.NaN;
pageOne.FontSize = 16.00;
pageOne.MaxWidth = this.TextboxMaxWidth;
pageOne.MaxHeight = this.TextboxMaxHeight;
pageOne.HorizontalAlignment = HorizontalAlignment.Left;
pageOne.VerticalAlignment = VerticalAlignment.Top;
pageOne.IsDoubleTapEnabled = false;
pageOne.IsHitTestVisible = false;
pageOne.IsHoldingEnabled = false;
pageOne.IsTextSelectionEnabled = false;
pageOne.IsTapEnabled = false;
pageOne.SetValue(Helpers.Properties.HtmlProperty, CurrentBook.Pages[0].PageContent);
pageOne.SetBinding(RichTextBlock.MaxWidthProperty, new Binding
{
Source = TextboxMaxWidth,
Path = new PropertyPath("MaxWidth")
});
pageOne.SetBinding(RichTextBlock.MaxHeightProperty, new Binding
{
Source = TextboxMaxHeight,
Path = new PropertyPath("MaxHeight")
});
pageOne.Measure(new Size(this.TextboxMaxWidth, this.TextboxMaxHeight));
CurrentPage.Add(pageOne);
if (pageOne.HasOverflowContent)
{
pageOne.OverflowContentTarget = rtbo;
//set width and height here?
rtbo.Measure(new Size(this.TextboxMaxWidth, this.TextboxMaxHeight));
}
}
else
{
//set rtbo width and height here?
//Maybe set maxheight and maxwidth bindings too
if (lastOverflow.HasOverflowContent)
{
lastOverflow.OverflowContentTarget = rtbo;
lastOverflow.Measure(new Size(this.TextboxMaxWidth, this.TextboxMaxHeight));
rtbo.Measure((new Size(this.TextboxMaxWidth, this.TextboxMaxHeight)));
}
this.CurrentPage.Add(rtbo);
}
return rtbo;
}