From 47645ec815da840254ca79a106f112734ffc715c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?An=C5=BEe=20Vodovnik?= Date: Thu, 13 May 2021 19:18:56 +0200 Subject: [PATCH] docs(dotnet): Frame examples (#6555) --- docs/src/api/class-frame.md | 158 ++++++++++++++++++++++++++++++++++++ 1 file changed, 158 insertions(+) diff --git a/docs/src/api/class-frame.md b/docs/src/api/class-frame.md index 2f3d097612..a5baf5561b 100644 --- a/docs/src/api/class-frame.md +++ b/docs/src/api/class-frame.md @@ -97,6 +97,32 @@ with sync_playwright() as playwright: run(playwright) ``` +```csharp +using Microsoft.Playwright; +using System; +using System.Threading.Tasks; + +class FrameExamples +{ + public static async Task Main() + { + using var playwright = await Playwright.CreateAsync(); + await using var browser = await playwright.Firefox.LaunchAsync(); + var page = await browser.NewPageAsync(); + + await page.GoToAsync("https://www.bing.com"); + DumpFrameTree(page.MainFrame, string.Empty); + } + + private static void DumpFrameTree(IFrame frame, string indent) + { + Console.WriteLine($"{indent}{frame.Url}"); + foreach (var child in frame.ChildFrames) + DumpFrameTree(child, indent + " "); + } +} +``` + ## async method: Frame.addScriptTag - returns: <[ElementHandle]> @@ -282,6 +308,10 @@ await frame.dispatch_event("button#submit", "click") frame.dispatch_event("button#submit", "click") ``` +```csharp +await frame.DispatchEventAsync("button#submit", "click"); +``` + Under the hood, it creates an instance of an event based on the given [`param: type`], initializes it with [`param: eventInit`] properties and dispatches it on the element. Events are `composed`, `cancelable` and bubble by default. @@ -324,6 +354,12 @@ data_transfer = frame.evaluate_handle("new DataTransfer()") frame.dispatch_event("#source", "dragstart", { "dataTransfer": data_transfer }) ``` +```csharp +// Note you can only create DataTransfer in Chromium and Firefox +var dataTransfer = await frame.EvaluateHandleAsync("() => new DataTransfer()"); +await frame.DispatchEventAsync("#source", "dragstart", new { dataTransfer }); +``` + ### param: Frame.dispatchEvent.selector = %%-input-selector-%% ### param: Frame.dispatchEvent.type @@ -379,6 +415,12 @@ preload_href = frame.eval_on_selector("link[rel=preload]", "el => el.href") html = frame.eval_on_selector(".main-container", "(e, suffix) => e.outerHTML + suffix", "hello") ``` +```csharp +var searchValue = await frame.EvalOnSelectorAsync("#search", "el => el.value"); +var preloadHref = await frame.EvalOnSelectorAsync("link[rel=preload]", "el => el.href"); +var html = await frame.EvalOnSelectorAsync(".main-container", "(e, suffix) => e.outerHTML + suffix", "hello"); +``` + ### param: Frame.evalOnSelector.selector = %%-query-selector-%% ### param: Frame.evalOnSelector.expression = %%-evaluate-expression-%% @@ -421,6 +463,10 @@ divs_counts = await frame.eval_on_selector_all("div", "(divs, min) => divs.lengt divs_counts = frame.eval_on_selector_all("div", "(divs, min) => divs.length >= min", 10) ``` +```csharp +var divsCount = await frame.EvalOnSelectorAllAsync("div", "(divs, min) => divs.length >= min", 10); +``` + ### param: Frame.evalOnSelectorAll.selector = %%-query-selector-%% ### param: Frame.evalOnSelectorAll.expression = %%-evaluate-expression-%% @@ -466,6 +512,11 @@ result = frame.evaluate("([x, y]) => Promise.resolve(x * y)", [7, 8]) print(result) # prints "56" ``` +```csharp +var result = await frame.EvaluateAsync("([x, y]) => Promise.resolve(x * y)", new[] { 7, 8 }); +Console.WriteLine(result); +``` + A string can also be passed in instead of a function. ```js @@ -488,6 +539,10 @@ x = 10 print(frame.evaluate(f"1 + {x}")) # prints "11" ``` +```csharp +Console.WriteLine(await frame.EvaluateAsync("1 + 2")); // prints "3" +``` + [ElementHandle] instances can be passed as an argument to the [`method: Frame.evaluate`]: ```js @@ -514,6 +569,12 @@ html = frame.evaluate("([body, suffix]) => body.innerHTML + suffix", [body_handl body_handle.dispose() ``` +```csharp +var bodyHandle = await frame.QuerySelectorAsync("body"); +var html = await frame.EvaluateAsync("([body, suffix]) => body.innerHTML + suffix", new object [] { bodyHandle, "hello" }); +await bodyHandle.DisposeAsync(); +``` + ### param: Frame.evaluate.expression = %%-evaluate-expression-%% ### param: Frame.evaluate.arg @@ -552,6 +613,11 @@ a_window_handle = frame.evaluate_handle("Promise.resolve(window)") a_window_handle # handle for the window object. ``` +```csharp +// Handle for the window object. +var aWindowHandle = await frame.EvaluateHandleAsync("() => Promise.resolve(window)"); +``` + A string can also be passed in instead of a function. ```js @@ -570,6 +636,10 @@ a_handle = await page.evaluate_handle("document") # handle for the "document" a_handle = page.evaluate_handle("document") # handle for the "document" ``` +```csharp +var docHandle = await frame.EvalueHandleAsync("document"); // Handle for the `document` +``` + [JSHandle] instances can be passed as an argument to the [`method: Frame.evaluateHandle`]: ```js @@ -600,6 +670,13 @@ print(result_handle.json_value()) result_handle.dispose() ``` +```csharp +var handle = await frame.EvaluateHandleAsync("() => document.body"); +var resultHandle = await frame.EvaluateHandleAsync("([body, suffix]) => body.innerHTML + suffix", new object[] { handle, "hello" }); +Console.WriteLine(await resultHandle.JsonValueAsync()); +await resultHandle.DisposeAsync(); +``` + ### param: Frame.evaluateHandle.expression = %%-evaluate-expression-%% ### param: Frame.evaluateHandle.arg @@ -669,6 +746,12 @@ content_frame = frame_element.content_frame() assert frame == content_frame ``` +```csharp +var frameElement = await frame.FrameElementAsync(); +var contentFrame = await frameElement.ContentFrameAsync(); +Console.WriteLine(frame == contentFrame); // -> True +``` + ## async method: Frame.getAttribute - returns: <[null]|[string]> @@ -964,6 +1047,15 @@ frame.select_option("select#colors", label="blue") frame.select_option("select#colors", value=["red", "green", "blue"]) ``` +```csharp +// single selection matching the value +await frame.SelectOptionAsync("select#colors", new[] { "blue" }); +// single selection matching both the value and the label +await frame.SelectOptionAsync("select#colors", new[] { new SelectOptionValue() { Label = "blue" } }); +// multiple selection +await frame.SelectOptionAsync("select#colors", new[] { "red", "green", "blue" }); +``` + ### param: Frame.selectOption.selector = %%-query-selector-%% ### param: Frame.selectOption.values = %%-select-options-values-%% @@ -1074,6 +1166,11 @@ frame.type("#mytextarea", "hello") # types instantly frame.type("#mytextarea", "world", delay=100) # types slower, like a user ``` +```csharp +await frame.TypeAsync("#mytextarea", "hello"); // types instantly +await frame.TypeAsync("#mytextarea", "world", delay: 100); // types slower, like a user +``` + ### param: Frame.type.selector = %%-input-selector-%% ### param: Frame.type.text @@ -1194,6 +1291,23 @@ with sync_playwright() as playwright: run(playwright) ``` +```csharp +using Microsoft.Playwright; +using System.Threading.Tasks; + +class FrameExamples +{ + public static async Task Main() + { + using var playwright = await Playwright.CreateAsync(); + await using var browser = await playwright.Firefox.LaunchAsync(); + var page = await browser.NewPageAsync(); + await page.SetViewportSizeAsync(50, 50); + await page.MainFrame.WaitForFunctionAsync("window.innerWidth < 100"); + } +} +``` + To pass an argument to the predicate of `frame.waitForFunction` function: ```js @@ -1216,6 +1330,11 @@ selector = ".foo" frame.wait_for_function("selector => !!document.querySelector(selector)", selector) ``` +```csharp +var selector = ".foo"; +await page.MainFrame.WaitForFunctionAsync("selector => !!document.querySelector(selector)", selector); +``` + ### param: Frame.waitForFunction.expression = %%-evaluate-expression-%% ### param: Frame.waitForFunction.arg @@ -1256,6 +1375,11 @@ frame.click("button") # click triggers navigation. frame.wait_for_load_state() # the promise resolves after "load" event. ``` +```csharp +await frame.ClickAsync("button"); +await frame.WaitForLoadStateAsync(); // Defaults to LoadState.Load +``` + ### param: Frame.waitForLoadState.state = %%-wait-for-load-state-state-%% ### option: Frame.waitForLoadState.timeout = %%-navigation-timeout-%% @@ -1299,6 +1423,12 @@ with frame.expect_navigation(): # Resolves after navigation has finished ``` +```csharp +Task.WaitAll(frame.WaitForNavigationAsync(), + frame.ClickAsync("a.delayed-navigation")); // clicking the link will indirectly cause a navigation +// Resolves after navigation has finished +``` + :::note Usage of the [History API](https://developer.mozilla.org/en-US/docs/Web/API/History_API) to change the URL is considered a navigation. @@ -1395,6 +1525,29 @@ with sync_playwright() as playwright: run(playwright) ``` +```csharp +using Microsoft.Playwright; +using System; +using System.Threading.Tasks; + +class FrameExamples +{ + public static async Task Main() + { + using var playwright = await Playwright.CreateAsync(); + await using var browser = await playwright.Chromium.LaunchAsync(); + var page = await browser.NewPageAsync(); + + foreach (var currentUrl in new[] { "https://www.google.com", "https://bbc.com" }) + { + await page.GoToAsync(currentUrl); + element = await page.MainFrame.WaitForSelectorAsync("img"); + Console.WriteLine($"Loaded image: {await element.GetAttributeAsync("src")}"); + } + } +} +``` + ### param: Frame.waitForSelector.selector = %%-query-selector-%% ### option: Frame.waitForSelector.state = %%-wait-for-selector-state-%% @@ -1437,6 +1590,11 @@ frame.click("a.delayed-navigation") # clicking the link will indirectly cause a frame.wait_for_url("**/target.html") ``` +```csharp +await frame.ClickAsync("a.delayed-navigation"); // clicking the link will indirectly cause a navigation +await frame.WaitForURLAsync("**/target.html"); +``` + ### param: Frame.waitForURL.url = %%-wait-for-navigation-url-%% ### option: Frame.waitForURL.timeout = %%-navigation-timeout-%% ### option: Frame.waitForURL.waitUntil = %%-navigation-wait-until-%%