我有点陌生TChromium
。我收集了具体的示例代码,制作了自己的测试程序。现在我遇到了一些问题,希望有人可以帮助我解决它:
首先。我习惯于OnLoadEnd
捕捉页面加载的那一刻,但它不能正常工作。至少在我下面的代码中。如何正确捕捉那一刻?
只要VisitDom
是异步的,我就无法在页面加载后和下一页将在循环内加载之前立即调用它。或者!如果每个页面都被一个一个地加载,并且VisitDom
为每个加载的页面的 DOM 快照准确地执行异步就可以了
比。脚本的类似情况(尚未在我的测试程序中实现)。在加载后的每个页面上都会执行脚本,并且 DOM 将被更改,因此我也需要对其进行解析。请帮助我解决任何解决方案:在脚本完成时捕获,然后在它完成后立即解析页面或捕获脚本并针对此脚本产生的 DOM 解析页面异步精确。
更短的周期看起来像: 加载页面
加载页面
解析这个DOM执行
脚本
执行的脚本
解析这个DOM可以在循环的时刻执行,也可以在特定时刻与确切的 DOM 异步执行
。parse DOM
简化的问题看起来像:如何捕获事件“页面加载”和“脚本完成”,以及如何访问在这个特定时刻准确生成的 DOM 快照(同步或异步)
谢谢您的帮助!
type
TElementNameVisitor = class(TCefDomVisitorOwn)
private
FMemo: TMemo;
protected
procedure visit(const document: ICefDomDocument); override;
public
constructor Create(AMemo:TMemo); reintroduce;
end;
implementation
constructor TElementNameVisitor.Create(AMemo:TMemo);
begin
inherited Create;
FMemo := AMemo;
end;
procedure TElementNameVisitor.Visit(const document: ICefDomDocument);
procedure ProcessNode(ANode: ICefDomNode);
var
Node: ICefDomNode;
begin
if Assigned(ANode) then
begin
Node := ANode.FirstChild;
while Assigned(Node) do
begin
if Node.ElementTagName='DIV' then
begin
if Node.GetElementAttribute('id')='type-tabs' then
FMemo.Lines.Add('FOUND');
end;
ProcessNode(Node);
Node := Node.NextSibling;
end;
end;
end;
begin
FMemo.Lines.Add('START');
ProcessNode(document.Body);
end;
procedure ProcessElementsByName(const AFrame: ICefFrame; AMemo:TMemo);
var
Visitor: TElementNameVisitor;
begin
if Assigned(AFrame) then
begin
Visitor := TElementNameVisitor.Create(AMemo);
AFrame.VisitDom(Visitor);
end;
end;
procedure TForm1.Button1Click(Sender: TObject);
var Links:TStringList;
i:integer;
begin
Links:=TStringList.Create;
Memo1.Lines.Clear;
Links.Add('www.link1.com');
Links.Add('www.link2.com');
Links.Add('www.link3.com');
for i:=0 to Links.Count-1 do begin
Chromium1.Load(Links.Strings[i]);
repeat Application.ProcessMessages until FLoaded;
Memo1.Lines.Add('Loaded #'+IntToStr(i));
for j := 0 to 20 do begin
Sleep(100); Application.ProcessMessages;
end;
ProcessElementsByName(Chromium1.Browser.MainFrame, Memo1);
for j := 0 to 20 do begin
Sleep(100); Application.ProcessMessages;
end;
end;
Memo1.Lines.Add('end of btnClick');
end;
procedure TForm1.Chromium1LoadEnd(Sender: TObject; const browser: ICefBrowser;
const frame: ICefFrame; httpStatusCode: Integer; out Result: Boolean);
begin
FLoaded:=True;
end;
procedure TForm1.Chromium1LoadStart(Sender: TObject; const browser: ICefBrowser;
const frame: ICefFrame);
begin
FLoaded:=False;
end;