【问题标题】:Set Font Size in TWebBrowser Selection在 TWebBrowser 选择中设置字体大小
【发布时间】:2016-10-18 00:42:47
【问题描述】:

我有一个电子邮件客户端,它允许用户更改字体、字体大小、粗体、斜体等。

我遇到的问题是,当我尝试向上或向下更改选择的字体大小时,我得到一个 “EVariantTypeCastError”,并显示“无法将 Null 类型的变体转换为 OleStr 类型”的消息。 TextRange.queryCommandValue('FONTSIZE') 会引发此异常。

procedure TForm1.act_FontIncreaseExecute(Sender: TObject);
var
    Selection: IHTMLSelectionObject;
    HtmlPage: IHTMLDocument2;
    TextRange: IHTMLTxtRange;
    Parent: IHTMLElement2;
    s: string;
    i, mode: Integer;
begin

    HtmlPage := self.HtmlEditor.Document as IHTMLDocument2;
    Selection := HtmlPage.Selection;

    TextRange := Selection.createRange as IHTMLTxtRange;
    if (TextRange <> nil) then
    begin
        s := TextRange.queryCommandValue('FONTSIZE');
        val(s, i, mode);
        if mode = 0 then
            HtmlPage.execCommand('FONTSIZE', False, inttostr(i + 1))
    end;
end;

这是增加所选字体大小的正确方法吗?

编辑 1:

示例 HTML:

<HTML><HEAD></HEAD>
<BODY>
<P>
    <SPAN style='FONT-SIZE: 7pt;'>
        Test Text
    </SPAN>
</P>
</BODY></HTML>

看起来问题出在 FONT-SIZE 样式上。当它被取出时,不会抛出异常。我的最终目标是能够从 Outlook 复制和粘贴,这是一个精简的示例。当我使用其他样式(例如颜色:红色)时,不会引发异常。所以看起来它只是 FONT-SIZE 有问题。

编辑 2

异常堆栈跟踪

【问题讨论】:

  • Query/Exec 的参数是 Olevariant。 FontSize 不会总是返回一个整数,在你的情况下它似乎什么都不返回(null)。但是我无法重现您的错误,您可以编辑问题并包含一段重现错误的 html 吗?
  • 感谢您的帮助,我会用示例更新问题
  • FONTSIZE 命令指的是围绕文本范围的FONT 标记:例如&lt;FONT size=1&gt;Test Text&lt;/FONT&gt;。在您的 HTML 示例中,您需要处理样式属性/元素。
  • @kobik 谢谢你的帮助。当我将跨度切换为字体并将属性更改为您提到的大小时,我不再遇到异常。此 HTML 是直接从 Outlook 签名粘贴的。 Outlook 签名是否有理由将 FONT-SIZE 放在一个跨度中?从 Word 复制时也遇到同样的错误
  • html5 不支持 FONT 标签。 Outlook/Word 使用 CSS,这是现代 HTML 中的首选方式。

标签: delphi twebbrowser


【解决方案1】:

这是增加字体大小的正确方法吗? 选择?

.queryCommandValue('FONTSIZE') 指的是围绕文本范围的FONT 标签(字体大小为 1-7):例如

<FONT size=1>Test Text</FONT>

在您的 HTML 示例中,没有 FONT 标记。您需要处理周围SPAN 的FONT-SIZE Style 属性(CSS)。

例如(没有错误检查以简化示例):

if (TextRange <> nil) then
begin
  ...
  ShowMessage(TextRange.parentElement.style.fontSize);
end;

这将显示7pt。 @whosrdaddy answer 解释了您的具体异常原因(queryCommandValue 因我解释的原因返回 null)

【讨论】:

    【解决方案2】:

    如您所见,在某些情况下查询将返回 NULL,然后 Val() 命令将失败。

    解决方法很简单,当你得到 null 时假设标准字体大小:

    procedure TForm1.FontIncreaseExecute;
    
    var
        Selection: IHTMLSelectionObject;
        HtmlPage: IHTMLDocument2;
        TextRange: IHTMLTxtRange;
        s: OleVariant;
        i, mode: Integer;
    
     begin  
      HtmlPage := WebBrowser1.Document as IHTMLDocument2;
      Selection := HtmlPage.Selection;
      TextRange := Selection.createRange as IHTMLTxtRange;
      if (TextRange <> nil) then
       begin
        s := TextRange.queryCommandValue('FONTSIZE');
        if VarisNull(s) then
         s := 0; // fall back to standard font size
        Val(s, i, mode);
        if mode = 0 then
        HtmlPage.execCommand('FONTSIZE', False, inttostr(i + 1))
       end;
    end;
    

    【讨论】:

    • 感谢您的帮助。 queryCommandValue 引发异常,因此 VarisNull 在这种情况下无济于事。我必须使用 try except 语句。知道为什么在这种情况下它为空吗?
    • @MattLaza:那么您没有使用您在此处发布的代码。调试您的应用程序并提供堆栈跟踪...
    • 我肯定在使用我提供的代码。我还附上了堆栈跟踪的屏幕截图。可以看到 System.Variants 中抛出了异常
    • @MattLaza,请注意 whosrdaddy 使用 s: OleVariant 而您使用 s: string。你试过用VarisNull检查他的代码吗?在任何情况下,您都可以处理异常,但 queryCommandValue 不会像我在 cmets 中解释的那样为您提供您正在寻找的字体大小。
    • @Kobik 这确实解释了为什么由于从空变量到字符串的隐式转换,他在查询中出现异常。
    猜你喜欢
    • 2012-06-29
    • 2012-05-27
    • 2011-07-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-03-01
    • 1970-01-01
    • 2020-06-12
    相关资源
    最近更新 更多