You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Delphi 10.3中TJvRichEdit文本设置异常问题求助

Delphi 10.3中TJvRichEdit加载RTF文本后Text属性返回完整RTF的解决方法

问题概述

从Delphi 2007迁移至10.3(同版本JVCL),Firebird 3.0/64的BLOB文本字段存储RTF内容。使用非数据库版TJvRichEdit加载table.BLOBField.AsString后,Delphi 2007中JvRichEditcontrol.Text返回解析后的纯文本,而10.3中返回完整RTF源码,导致ConvertToHtmlStrings生成的HTML嵌入RTF标签。但子类TJvDBRichEdit可正常解析显示,说明存在正确的加载逻辑。

核心原因

Delphi 2007使用ANSI字符串,TJvRichEdit的Text属性赋值时会自动识别ANSI编码的RTF内容并解析为富文本;而Delphi 10.3采用UnicodeString,直接赋值Text时,控件将内容视为纯文本而非RTF格式,因此不会触发解析逻辑,直接保留原始RTF代码。

TJvDBRichEdit的正常工作,是因为它并非直接赋值Text,而是通过数据库字段的专用加载流程,调用了RTF解析的底层接口。

解决方案

方法1:通过流加载RTF内容

将BLOB字段内容存入内存流,再用LoadFromStream指定RTF格式加载:

Var
  HTML : TStringList;
  MS: TMemoryStream;
begin
  MS := TMemoryStream.Create;
  try
    table.BLOBField.SaveToStream(MS);
    MS.Position := 0;
    JvRichEditcontrol.PlainText := False;
    JvRichEditcontrol.LoadFromStream(MS, TStreamFormat.sfRTF);
    JvRichEditToHtml.ConvertToHtmlStrings(JvRichEditcontrol, HTML);
  finally
    MS.Free;
  end;
end;

方法2:调用RichEdit底层API加载

使用EM_STREAMIN消息直接传入RTF内容,绕过Text属性的赋值逻辑:

Var
  HTML : TStringList;
  EditStream: TEditStream;
  RtfContent: string;
  
  function EditStreamCallback(dwCookie: DWORD_PTR; pbBuff: PByte; cb: LongInt; var pcb: LongInt): DWORD; stdcall;
  begin
    pcb := Min(cb, Length(RtfContent) - dwCookie);
    if pcb > 0 then
    begin
      Move(PByte(@RtfContent[dwCookie + 1])^, pbBuff^, pcb);
      Result := 0;
    end
    else
      Result := 1;
  end;

begin
  RtfContent := table.BLOBField.AsString;
  EditStream.dwCookie := 0;
  EditStream.pfnCallback := @EditStreamCallback;
  
  JvRichEditcontrol.PlainText := False;
  SendMessage(JvRichEditcontrol.Handle, EM_STREAMIN, SF_RTF, LPARAM(@EditStream));
  
  JvRichEditToHtml.ConvertToHtmlStrings(JvRichEditcontrol, HTML);
end;

方法3:模拟TJvDBRichEdit的加载逻辑

复用JVCL内部的加载逻辑,直接操作控件的Lines流:

Var
  HTML : TStringList;
begin
  JvRichEditcontrol.PlainText := False;
  
  if table.BLOBField.IsBlob then
  begin
    JvRichEditcontrol.Lines.BeginUpdate;
    try
      JvRichEditcontrol.Clear;
      table.BLOBField.SaveToStream(JvRichEditcontrol.Lines.LoadedStream);
      JvRichEditcontrol.Lines.LoadedStream.Position := 0;
      JvRichEditcontrol.Lines.LoadFromStream(JvRichEditcontrol.Lines.LoadedStream, TStreamFormat.sfRTF);
    finally
      JvRichEditcontrol.Lines.EndUpdate;
    end;
  end;
  
  JvRichEditToHtml.ConvertToHtmlStrings(JvRichEditcontrol, HTML);
end;

验证结果

采用上述任意方法后,TJvRichEdit会正确解析RTF内容,JvRichEditcontrol.Text返回纯文本,ConvertToHtmlStrings生成带<b>、<i>等格式标签的预期HTML。

内容的提问来源于stack exchange,提问作者alvaroc

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.04 07:45:36