2 回答

TA貢獻(xiàn)1827條經(jīng)驗(yàn) 獲得超8個(gè)贊
首先,重要的是要了解它Javascript
是在渲染過程中執(zhí)行的。結(jié)果EvaluateScriptAsync
實(shí)際上是一個(gè)DTO
,我們創(chuàng)建一個(gè)對象來表示執(zhí)行腳本的結(jié)果。
目前無法返回 HTMLElement或任何具有循環(huán)引用的對象。
如果我們將 `HTMLElement 作為一個(gè)特定的例子來看,它將有一個(gè) parentElement/parentNode 并且父元素有包含節(jié)點(diǎn)本身的子元素。您最終也會遍歷整個(gè) DOM 樹。
CEF 對其CefV8Value
類型的類型支持非常有限,因此很難做任何太花哨的事情。
我們可能會添加一個(gè)擴(kuò)展方法,將用戶腳本包裝在 中 IIFE
并進(jìn)行一些instanceof HTMLElement
樣式類型檢查以返回 HTML 元素的精簡表示。

TA貢獻(xiàn)1831條經(jīng)驗(yàn) 獲得超10個(gè)贊
作為使用 JavaScript 的替代方法,您現(xiàn)在可以使用CefSharp.Dom,這是一個(gè)用于訪問 DOM 的異步庫。
它是免費(fèi)提供的
// Add using CefSharp.Dom to access CreateDevToolsContextAsync and related extension methods.
await using var devToolsContext = await chromiumWebBrowser.CreateDevToolsContextAsync();
// Get element by Id
// https://developer.mozilla.org/en-US/docs/Web/API/Document/querySelector
var element = await devToolsContext.QuerySelectorAsync<HtmlElement>("#myElementId");
//Strongly typed element types (this is only a subset of the types mapped)
var htmlDivElement = await devToolsContext.QuerySelectorAsync<HtmlDivElement>("#myDivElementId");
var htmlSpanElement = await devToolsContext.QuerySelectorAsync<HtmlSpanElement>("#mySpanElementId");
var htmlSelectElement = await devToolsContext.QuerySelectorAsync<HtmlSelectElement>("#mySelectElementId");
var htmlInputElement = await devToolsContext.QuerySelectorAsync<HtmlInputElement>("#myInputElementId");
var htmlFormElement = await devToolsContext.QuerySelectorAsync<HtmlFormElement>("#myFormElementId");
var htmlAnchorElement = await devToolsContext.QuerySelectorAsync<HtmlAnchorElement>("#myAnchorElementId");
var htmlImageElement = await devToolsContext.QuerySelectorAsync<HtmlImageElement>("#myImageElementId");
var htmlTextAreaElement = await devToolsContext.QuerySelectorAsync<HtmlImageElement>("#myTextAreaElementId");
var htmlButtonElement = await devToolsContext.QuerySelectorAsync<HtmlButtonElement>("#myButtonElementId");
var htmlParagraphElement = await devToolsContext.QuerySelectorAsync<HtmlParagraphElement>("#myParagraphElementId");
var htmlTableElement = await devToolsContext.QuerySelectorAsync<HtmlTableElement>("#myTableElementId");
// Get a custom attribute value
var customAttribute = await element.GetAttributeAsync<string>("data-customAttribute");
//Set innerText property for the element
await element.SetInnerTextAsync("Welcome!");
//Get innerText property for the element
var innerText = await element.GetInnerTextAsync();
//Get all child elements
var childElements = await element.QuerySelectorAllAsync("div");
//Change CSS style background colour
await element.EvaluateFunctionAsync("e => e.style.backgroundColor = 'yellow'");
//Type text in an input field
await element.TypeAsync("Welcome to my Website!");
//Click The element
await element.ClickAsync();
// Simple way of chaining method calls together when you don't need a handle to the HtmlElement
var htmlButtonElementInnerText = await devToolsContext.QuerySelectorAsync<HtmlButtonElement>("#myButtonElementId")
? ? .AndThen(x => x.GetInnerTextAsync());
//Event Handler
//Expose a function to javascript, functions persist across navigations
//So only need to do this once
await devToolsContext.ExposeFunctionAsync("jsAlertButtonClick", () =>
{
? ? _ = devToolsContext.EvaluateExpressionAsync("window.alert('Hello! You invoked window.alert()');");
});
var jsAlertButton = await devToolsContext.QuerySelectorAsync<HtmlButtonElement>("#jsAlertButton");
//Write up the click event listner to call our exposed function
_ = jsAlertButton.AddEventListenerAsync("click", "jsAlertButtonClick");
//Get a collection of HtmlElements
var divElements = await devToolsContext.QuerySelectorAllAsync<HtmlDivElement>("div");
foreach (var div in divElements)
{
? ? // Get a reference to the CSSStyleDeclaration
? ? var style = await div.GetStyleAsync();
? ? //Set the border to 1px solid red
? ? await style.SetPropertyAsync("border", "1px solid red", important: true);
? ? await div.SetAttributeAsync("data-customAttribute", "123");
? ? await div.SetInnerTextAsync("Updated Div innerText");
}
//Using standard array
var tableRows = await htmlTableElement.GetRowsAsync().ToArrayAsync();
foreach (var row in tableRows)
{
? ? var cells = await row.GetCellsAsync().ToArrayAsync();
? ? foreach (var cell in cells)
? ? {
? ? ? ? var newDiv = await devToolsContext.CreateHtmlElementAsync<HtmlDivElement>("div");
? ? ? ? await newDiv.SetInnerTextAsync("New Div Added!");
? ? ? ? await cell.AppendChildAsync(newDiv);
? ? }
}
//Get a reference to the HtmlCollection and use async enumerable
//Requires Net Core 3.1 or higher
var tableRowsHtmlCollection = await htmlTableElement.GetRowsAsync();
await foreach (var row in tableRowsHtmlCollection)
{
? ? var cells = await row.GetCellsAsync();
? ? await foreach (var cell in cells)
? ? {
? ? ? ? var newDiv = await devToolsContext.CreateHtmlElementAsync<HtmlDivElement>("div");
? ? ? ? await newDiv.SetInnerTextAsync("New Div Added!");
? ? ? ? await cell.AppendChildAsync(newDiv);
? ? }
}
添加回答
舉報(bào)