首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> 更多程式語言 >> Delphi

Delphi TWebBrowser 實作網頁編輯器:contentEditable 與 designMode 雙模式切換

     編輯:Delphi

前言

TWebBrowser 封裝 MSHTML (Trident/EdgeHTML),支援將網頁內容切換為可編輯模式。本文示範兩種標準編輯模式:contentEditable (元素級) 與 designMode (文檔級),並提供完整的編輯器原型程式碼。

核心程式碼實作

unit Unit1;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, OleCtrls, SHDocVw, StdCtrls, ExtCtrls;

type
  TForm1 = class(TForm)
    WebBrowser1: TWebBrowser;
    Panel1: TPanel;
    BtnEdit: TButton;
    ChkEditable: TCheckBox;
    BtnShowText: TButton;
    procedure FormCreate(Sender: TObject);
    procedure ChkEditableClick(Sender: TObject);
    procedure BtnShowTextClick(Sender: TObject);
  private
    { Private declarations }
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

procedure TForm1.FormCreate(Sender: TObject);
begin
  // 介面佈局
  Panel1.Align := alTop;
  Panel1.Height := 40;
  
  ChkEditable.Parent := Panel1;
  ChkEditable.Anchor := [akTop, akRight];
  ChkEditable.Caption := '編輯模式';
  ChkEditable.OnClick := ChkEditableClick;
  
  BtnShowText.Parent := Panel1;
  BtnShowText.Anchor := [akTop, akRight];
  BtnShowText.Left := ChkEditable.Left - BtnShowText.Width - 10;
  BtnShowText.Caption := '顯示純文字';
  BtnShowText.OnClick := BtnShowTextClick;
  
  WebBrowser1.Align := alClient;
  WebBrowser1.Navigate('https://example.com'); // 載入測試頁面
end;

procedure TForm1.ChkEditableClick(Sender: TObject);
var
  Doc: IHTMLDocument2;
begin
  // 取得 MSHTML 文檔介面
  Doc := WebBrowser1.Document as IHTMLDocument2;
  if not Assigned(Doc) then Exit;
  
  // 模式 1: contentEditable (元素級,推薦)
  // 僅讓 body 可編輯,保留其他結構
  Doc.body.contentEditable := IfThen(ChkEditable.Checked, 'true', 'false');
  
  // 模式 2: designMode (文檔級,舊標準)
  // 整個文檔可編輯,某些瀏覽器引擎需要此模式
  // Doc.designMode := IfThen(ChkEditable.Checked, 'On', 'Off');
end;

procedure TForm1.BtnShowTextClick(Sender: TObject);
var
  Doc: IHTMLDocument2;
  BodyText: string;
begin
  Doc := WebBrowser1.Document as IHTMLDocument2;
  if Assigned(Doc) and Assigned(Doc.body) then
  begin
    // 取得可見文字 (不含 HTML 標籤)
    BodyText := Doc.body.innerText;
    ShowMessage(BodyText);
  end;
end;

end.

兩種編輯模式差異對照

特性contentEditabledesignMode
作用範圍單一元素及其子樹整個文檔
屬性值'true'/'false'/'inherit' (字串)'On'/'Off' (字串)
標準HTML5 標準舊版 IE 專有,後被標準化
巢狀控制可在可編輯區域內設 contentEditable='false' 禁用子區全域開關,難以局部控制
相容性現代瀏覽器完美支援舊版 IE/EdgeHTML 必須用此模式
推薦度⭐⭐⭐⭐⭐⭐⭐ (相容舊專案)

進階編輯功能實作

1. 執行編輯命令 (加粗、斜體、插入連結等)

uses MSHTML;

procedure TForm1.ExecEditCommand(const CmdID: string; const Value: OleVariant = EmptyParam);
var
  Doc: IHTMLDocument2;
begin
  Doc := WebBrowser1.Document as IHTMLDocument2;
  if Assigned(Doc) then
    Doc.execCommand(CmdID, False, Value);
end;

// 使用範例
ExecEditCommand('Bold');           // 加粗
ExecEditCommand('Italic');         // 斜體
ExecEditCommand('Underline');      // 底線
ExecEditCommand('CreateLink', 'https://example.com'); // 插入連結
ExecEditCommand('InsertImage', 'https://example.com/img.png'); // 插入圖片
ExecEditCommand('ForeColor', '#FF0000'); // 字體顏色
ExecEditCommand('BackColor', '#FFFF00'); // 背景色
ExecEditCommand('FontName', '微軟正黑體'); // 字型
ExecEditCommand('FontSize', '3');  // 字號 (1-7)
ExecEditCommand('JustifyCenter');  // 置中
ExecEditCommand('InsertOrderedList'); // 有序清單
ExecEditCommand('InsertUnorderedList'); // 無序清單
ExecEditCommand('Undo');           // 復原
ExecEditCommand('Redo');           // 重做
ExecEditCommand('SelectAll');      // 全選
ExecEditCommand('Delete');         // 刪除選取
ExecEditCommand('Unlink');         // 移除連結

2. 取得/設定 HTML 內容

function GetHTMLContent: string;
var
  Doc: IHTMLDocument2;
begin
  Result := '';
  Doc := WebBrowser1.Document as IHTMLDocument2;
  if Assigned(Doc) and Assigned(Doc.body) then
    Result := Doc.body.innerHTML;
end;

procedure SetHTMLContent(const HTML: string);
var
  Doc: IHTMLDocument2;
begin
  Doc := WebBrowser1.Document as IHTMLDocument2;
  if Assigned(Doc) and Assigned(Doc.body) then
    Doc.body.innerHTML := HTML;
end;

3. 監聽內容變更事件

uses MSHTML, ActiveX;

type
  TForm1 = class(TForm)
  private
    FDocEvents: IHTMLDocumentEvents2;
    FCookie: DWORD;
    procedure DocOnClick(Sender: TObject);
  end;

procedure TForm1.FormCreate(Sender: TObject);
var
  Doc: IHTMLDocument2;
  ConnPt: IConnectionPointContainer;
  ConnPt2: IConnectionPoint;
begin
  // ... 原有初始化 ...
  
  // 事件連接 (需在 DocumentComplete 後)
  Doc := WebBrowser1.Document as IHTMLDocument2;
  if Supports(Doc, IConnectionPointContainer, ConnPt) then
  begin
    ConnPt.FindConnectionPoint(DIID_HTMLDocumentEvents2, ConnPt2);
    if Assigned(ConnPt2) then
      ConnPt2.Advise(Self as IHTMLDocumentEvents2, FCookie);
  end;
end;

procedure TForm1.DocOnClick(Sender: TObject);
begin
  // 處理文檔點擊事件
  Caption := '內容已變更';
end;

常見問題排查

問題原因解決
編輯模式不生效Document 尚未載入完成在 OnDocumentComplete 事件中啟用編輯
中文輸入法異常Trident 引擎 IME 整合問題嘗試 designMode='On'、或改用 Edge WebView2
execCommand 無效命令字串拼寫錯誤、選取範圍無效確認選取非空、命令 ID 大小寫正確
CSS 樣式不生效編輯器產生 inline style 覆蓋使用 styleWithCSS 命令控制
記憶體洩漏介面參考未釋放表單銷毀時 ConnPt2.Unadvise(FCookie)

現代替代方案:Edge WebView2

Microsoft 現推薦使用 WebView2 (基於 Chromium Edge) 替代 TWebBrowser:

  • 渲染引擎現代、支援最新 HTML/CSS/JS
  • contentEditable 體驗更佳、IME 完美支援
  • Delphi 11+ 內建 TEdgeBrowser 元件
  • 需部署 WebView2 Runtime (常駐系統)

結語

TWebBrowser 配合 contentEditable 可快速構建輕量級網頁編輯器。掌握 execCommand 命令集、innerHTML/innerText 內容存取、事件連接機制,即能實現格式工具列、原始碼檢視、內容同步等核心功能。新專案強烈建議遷移至 TEdgeBrowser 獲得現代瀏覽器級編輯體驗。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved