Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/wpf/14.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 如何在数据库中保存WPF RichTextBox而不丢失链接?_C#_Wpf_Hyperlink_Richtextbox - Fatal编程技术网

C# 如何在数据库中保存WPF RichTextBox而不丢失链接?

C# 如何在数据库中保存WPF RichTextBox而不丢失链接?,c#,wpf,hyperlink,richtextbox,C#,Wpf,Hyperlink,Richtextbox,我在Richtextbox中有一个链接,它运行良好,但如果我将该Richtextbox保存到数据库中,然后将其加载到要删除的链接中,我就可以看到该链接的文本 例如,my Richtextbox具有底部文本: 但在再次保存和加载后,我只能看到文本: 这是一个链接 从所选文本动态创建的超链接如下: RichTextBox.IsDocumentEnabled = true; RichTextBox.IsReadOnly = true;

我在Richtextbox中有一个链接,它运行良好,但如果我将该Richtextbox保存到数据库中,然后将其加载到要删除的链接中,我就可以看到该链接的文本

例如,my Richtextbox具有底部文本:

但在再次保存和加载后,我只能看到文本:

这是一个链接

从所选文本动态创建的超链接如下:

            RichTextBox.IsDocumentEnabled = true;

            RichTextBox.IsReadOnly = true;

            Run run = new Run(RichTextBox.Selection.Text);
            Hyperlink hyp = new Hyperlink(run) { TargetName = run.Text };
            TERM.WordMain main = new TERM.WordMain();

            hyp.Click += new RoutedEventHandler(main.hyperLink_Click);
            hyp.NavigateUri = new Uri("http://search.msn.com");
            RichTextBox.Cut();

            var container = new InlineUIContainer(new TextBlock(hyp), RichTextBox.Selection.Start);
            RichTextBox.IsDocumentEnabled = true;
            RichTextBox.IsReadOnly = false;
将richtextbox内容以RTF格式保存到文本字段:

 public static string ToStringFromBytes(System.Windows.Controls.RichTextBox richTextBox)
    {
        if (richTextBox.Document.Blocks.Count == 0)
        {
            return null;
        }

        MemoryStream memoryStream = new MemoryStream();

        TextRange textRange = new TextRange(richTextBox.Document.ContentStart, richTextBox.Document.ContentEnd);

        textRange.Save(memoryStream, System.Windows.DataFormats.Rtf);

        return Encoding.UTF8.GetString(memoryStream.ToArray());
    }
并从数据库加载到流程文档

public static FlowDocument LoadFromString(string s)
    {
        try
        {
            byte[] byteArray = Encoding.UTF8.GetBytes(s);

            MemoryStream stream = new MemoryStream(System.Text.Encoding.UTF8.GetBytes(s));

            FlowDocument doc = new FlowDocument();

            TextRange textRange = new TextRange(doc.ContentStart, doc.ContentEnd);

            textRange.Load(stream, System.Windows.DataFormats.Rtf);

            return doc;
        }
        catch (Exception ex)
        {
            throw;
        }
    }

下面的示例似乎可以做到这一点

在这里,我加载并保存
XAML
,而不是rtf格式的文本。还请注意,您需要在加载后将超链接的处理程序添加回元素,因为它们不会被序列化

public partial class MainWindow : Window
{
    private const string _stateFile = "state.xaml";
    public MainWindow()
    {
        InitializeComponent();
        richTextBox.IsReadOnly = false;
    }

    private void createLinkButton_Click(object sender, RoutedEventArgs e)
    {
        richTextBox.IsDocumentEnabled = false;
        richTextBox.IsReadOnly = true;
        var textRange = richTextBox.Selection;
        var hyperlink = new Hyperlink(textRange.Start, textRange.End);
        hyperlink.TargetName = "value";
        hyperlink.NavigateUri = new Uri("http://search.msn.com");
        hyperlink.RequestNavigate += HyperlinkOnRequestNavigate;
        richTextBox.IsDocumentEnabled = true;
        richTextBox.IsReadOnly = false;
    }

    private void HyperlinkOnRequestNavigate(object sender,
        RequestNavigateEventArgs args)
    {
        // Outputs: "Requesting: http://search.msn.com, target=value" 
        Console.WriteLine("Requesting: {0}, target={1}", args.Uri, args.Target);
    }

    private void SaveXamlPackage(string filePath)
    {
        var range = new TextRange(richTextBox.Document.ContentStart,
            richTextBox.Document.ContentEnd);
        var fStream = new FileStream(filePath, FileMode.Create);
        range.Save(fStream, DataFormats.XamlPackage);
        fStream.Close();
    }

    void LoadXamlPackage(string filePath)
    {
        if (File.Exists(filePath))
        {
            var range = new TextRange(richTextBox.Document.ContentStart,
                richTextBox.Document.ContentEnd);
            var fStream = new FileStream(filePath, FileMode.OpenOrCreate);
            range.Load(fStream, DataFormats.XamlPackage);
            fStream.Close();
        }

        // Reapply event handling to hyperlinks after loading, since these are not saved:
        foreach (var paragraph in richTextBox.Document.Blocks.OfType<Paragraph>())
        {
            foreach (var hyperlink in paragraph.Inlines.OfType<Hyperlink>())
            {
                hyperlink.RequestNavigate += HyperlinkOnRequestNavigate;
            }
        }
    }

    private void saveButton_Click(object sender, RoutedEventArgs e)
    {
        SaveXamlPackage(_stateFile);
    }

    private void loadButton_Click(object sender, RoutedEventArgs e)
    {
        LoadXamlPackage(_stateFile);
    }
}
公共部分类主窗口:窗口
{
私有常量字符串_stateFile=“state.xaml”;
公共主窗口()
{
初始化组件();
richTextBox.IsReadOnly=false;
}
私有void createLinkButton_单击(对象发送者,路由目标e)
{
richTextBox.IsDocumentEnabled=false;
richTextBox.IsReadOnly=true;
var textRange=richTextBox.Selection;
var hyperlink=新的超链接(textRange.Start、textRange.End);
hyperlink.TargetName=“值”;
hyperlink.NavigateUri=新Uri(“http://search.msn.com");
hyperlink.RequestNavigate+=HyperlinkOnRequestNavigate;
richTextBox.IsDocumentEnabled=true;
richTextBox.IsReadOnly=false;
}
私有无效HyperlinkOnRequestNavigate(对象发送方,
RequestNavigateEventArgs(参数)
{
//产出:“请求:http://search.msn.com,目标=价值“
WriteLine(“请求:{0},目标={1}”,args.Uri,args.target);
}
私有void SaveXamlPackage(字符串文件路径)
{
变量范围=新的文本范围(richTextBox.Document.ContentStart,
richTextBox.Document.ContentEnd);
var fStream=newfilestream(filePath,FileMode.Create);
Save(fStream、DataFormats.XamlPackage);
fStream.Close();
}
无效LoadXamlPackage(字符串文件路径)
{
if(File.Exists(filePath))
{
变量范围=新的文本范围(richTextBox.Document.ContentStart,
richTextBox.Document.ContentEnd);
var fStream=newfilestream(filePath,FileMode.OpenOrCreate);
Load(fStream、DataFormats.XamlPackage);
fStream.Close();
}
//加载后重新将事件处理应用于超链接,因为这些超链接不会保存:
foreach(richTextBox.Document.Blocks.OfType()中的变量段落)
{
foreach(类型()的段落.Inlines.OfType()中的变量超链接)
{
hyperlink.RequestNavigate+=HyperlinkOnRequestNavigate;
}
}
}
私有无效保存按钮\u单击(对象发送方,路由目标)
{
SaveXamlPackage(_stateFile);
}
私有无效加载按钮\u单击(对象发送者,路由目标e)
{
LoadXamlPackage(_stateFile);
}
}

例如,我添加了一些代码。
段落
对象是否与
超链接
一起存储在集合中,以及其他
运行
对象?这将告诉您是保存还是加载代码失败。@ChrisF,我无法理解这个问题。您是只存储文本还是同时存储XAML标记?首先,我保存为XAML格式,但在此之后,我丢失了超链接。然后我搜索并发现,为了将超链接或图像保存到数据库中,它必须以RTF格式保存为字符串,但在此之后,我失去了超链接的链接能力,并在@steinar处进行了大量更改。如何将TargetName添加到超链接?因为我在click Event中使用它,所以您只需添加
hyperlink.TargetName=“…”
在方法
createLinkButton\中单击
。然后在保存时序列化该值,以便加载时不需要重新应用它。我添加它,但它返回空字符串值(现在我使用另一种方法,将其添加到Navigateuri,然后获取值)))。但是我不明白为什么TargetName是emply这很奇怪,看看编辑后的答案,我在那里添加了
TargetName
,它在我的案例中确实起到了预期的作用。也许你的代码有些不同。