6

为了保存和加载我的布局,我按照这里的说明进行操作,但它对我不起作用。

我在XAML里面有这个MainWindow

<StackPanel Orientation="Vertical">
    <Button Content="Save"
            Click="SaveButton_Click"/>
    <Button Content="Load"
            Click="LoadButton_Click"/>
    <ad:DockingManager x:Name="myDM">
        <ad:LayoutRoot>
            <ad:LayoutPanel>
                <ad:LayoutDocumentPane>
                    <ad:LayoutDocument Title="Document">
                        <TextBox />
                    </ad:LayoutDocument>
                </ad:LayoutDocumentPane>
            </ad:LayoutPanel>
            <ad:LayoutRoot.LeftSide>
                <ad:LayoutAnchorSide>
                    <ad:LayoutAnchorGroup>
                        <ad:LayoutAnchorable Title="Left">
                            <TextBox/>
                        </ad:LayoutAnchorable>
                    </ad:LayoutAnchorGroup>
                </ad:LayoutAnchorSide>
            </ad:LayoutRoot.LeftSide>
        </ad:LayoutRoot>
    </ad:DockingManager>
</StackPanel>

这些是按钮单击的事件处理程序:

private void SaveButton_Click(object sender, RoutedEventArgs e)
{
    XmlLayoutSerializer layoutSerializer = new XmlLayoutSerializer(myDM);
    using (var writer = new StreamWriter("test"))
    {
        layoutSerializer.Serialize(writer);
    }
}

private void LoadButton_Click(object sender, RoutedEventArgs e)
{
    XmlLayoutSerializer layoutSerializer = new XmlLayoutSerializer(myDM);
    using (var reader = new StreamReader("test"))
    {
        layoutSerializer.Deserialize(reader);
    }
}

显示窗口后,我点击保存“测试”文件的内容是:

<?xml version="1.0" encoding="utf-8"?>
<LayoutRoot xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <RootPanel Orientation="Horizontal">
    <LayoutDocumentPane>
      <LayoutDocument Title="Document" IsSelected="True" IsLastFocusedDocument="True" LastActivationTimeStamp="04/12/2013 14:50:38" />
    </LayoutDocumentPane>
  </RootPanel>
  <TopSide />
  <RightSide />
  <LeftSide>
    <LayoutAnchorGroup>
      <LayoutAnchorable AutoHideMinWidth="100" AutoHideMinHeight="100" Title="Left" />
    </LayoutAnchorGroup>
  </LeftSide>
  <BottomSide />
  <FloatingWindows />
  <Hidden />
</LayoutRoot>

问题来了 - 在我单击加载按钮后,文档和可锚定项消失了,我在窗口中看到的只有 2 个按钮和一个空矩形,我的布局应该是。此时,当我单击保存按钮时,这是写入“测试”文件的内容:

<?xml version="1.0" encoding="utf-8"?>
<LayoutRoot xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <RootPanel Orientation="Horizontal">
    <LayoutDocumentPane />
  </RootPanel>
  <TopSide />
  <RightSide />
  <LeftSide>
    <LayoutAnchorGroup Id="d3710e74-e6b5-4541-8b6f-554197c29dd6" />
  </LeftSide>
  <BottomSide />
  <FloatingWindows />
  <Hidden>
    <LayoutAnchorable AutoHideMinWidth="100" AutoHideMinHeight="100" Title="Left" IsSelected="True" LastActivationTimeStamp="04/12/2013 14:53:56" PreviousContainerId="d3710e74-e6b5-4541-8b6f-554197c29dd6" PreviousContainerIndex="0" />
  </Hidden>
</LayoutRoot>

我正在使用 AvalonDock 2.0.1746.0。任何人都知道如何解决它?

4

1 回答 1

22

编辑:

我尝试了您的代码,并将其输出与我的进行了比较,发现您的序列化文件缺少ContentId您的LayoutDocumentLayoutAnchorable. 这个属性是 AvalonDock 在内部用来匹配现有DockingManager面板和序列化版本的属性,没有它,如您所见,没有任何效果。

还有 2 种方法可用于设置ContentId属性,或者显式作为特定 AvalonDock 面板的属性,或者通过Name在面板的直接子级上设置属性来隐式设置。这是使用两种方式的修改后的主窗口 XAML 代码。

<StackPanel Orientation="Vertical">
    <Button Content="Save"
    Click="SaveButton_Click"/>
    <Button Content="Load"
    Click="LoadButton_Click"/>
    <ad:DockingManager x:Name="myDM">
        <ad:LayoutRoot>
            <ad:LayoutPanel>
                <ad:LayoutDocumentPane>
                    <ad:LayoutDocument Title="Document" ContentId="IHaveContent">
                        <TextBox />
                    </ad:LayoutDocument>
                </ad:LayoutDocumentPane>
            </ad:LayoutPanel>
            <ad:LayoutRoot.LeftSide>
                <ad:LayoutAnchorSide>
                    <ad:LayoutAnchorGroup>
                        <ad:LayoutAnchorable Title="Left">
                            <TextBox x:Name="IAmTextBoxContent"/>
                        </ad:LayoutAnchorable>
                    </ad:LayoutAnchorGroup>
                </ad:LayoutAnchorSide>
            </ad:LayoutRoot.LeftSide>
        </ad:LayoutRoot>
    </ad:DockingManager>
</StackPanel>

如果您现在使用保存和加载按钮,您将看到ContentId现在在测试文件中设置了属性,如下所示。

<?xml version="1.0" encoding="utf-8"?>
<LayoutRoot xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <RootPanel Orientation="Horizontal">
    <LayoutDocumentPane>
      <LayoutDocument Title="Document" 
          IsSelected="True" 
          IsLastFocusedDocument="True" 
          ContentId="IHaveContent" 
          LastActivationTimeStamp="04/17/2013 09:13:35" />
    </LayoutDocumentPane>
  </RootPanel>
  <TopSide />
  <RightSide />
  <LeftSide>
    <LayoutAnchorGroup>
      <LayoutAnchorable AutoHideMinWidth="100" 
          AutoHideMinHeight="100" 
          Title="Left" 
          ContentId="IAmTextBoxContent" />
    </LayoutAnchorGroup>
  </LeftSide>
  <BottomSide />
  <FloatingWindows />
  <Hidden />
</LayoutRoot>

为了将来如何调试此问题的参考,我确实使用下面的回调来调试和检查反序列化过程返回的值,其中e参数包含属性中 AvalonDock 面板的反序列化版本Model,(在您的case 最初为 null),如果ContentId属性正确,将在其属性中包含您面板的内容(由于 的属性中Content的 null 值,这也是 null )。ContentIdModel

s回调处理程序中的 包含引用XmlLayoutSerializer,它还包含对 的引用DockingManager,通过它您可以检查其中包含的当前项。

老的:

我记得早期版本的 AvalonDock 也有类似的问题,但我认为为我解决的问题是升级到最新版本(您已经拥有),因为有一个内部部分没有正确反序列化。

LayoutSerializer但是,要尝试查找反序列化过程的问题,您可以尝试在回调中放置断点。希望这将为您提供有关特定问题的更多信息。

layoutSerializer.LayoutSerializationCallback += (s, e) =>
{
    object o = e.Content;
};
于 2013-04-15T23:19:39.243 回答