Skip to content

Commit

Permalink
Introducing Burst mode (#705)
Browse files Browse the repository at this point in the history
* Burst mode

* CodeFactor

* Ops

* cr

* cr
  • Loading branch information
kblok authored and Meir017 committed Oct 19, 2018
1 parent 7a5b155 commit f764ff3
Show file tree
Hide file tree
Showing 4 changed files with 130 additions and 57 deletions.
10 changes: 10 additions & 0 deletions lib/PuppeteerSharp/Messaging/PageCaptureScreenshotResponse.cs
@@ -0,0 +1,10 @@
using Newtonsoft.Json;

namespace PuppeteerSharp.Messaging
{
internal class PageCaptureScreenshotResponse
{
[JsonProperty("data")]
public string Data { get; set; }
}
}
18 changes: 18 additions & 0 deletions lib/PuppeteerSharp/Messaging/PageGetLayoutMetricsResponse.cs
@@ -0,0 +1,18 @@
using Newtonsoft.Json;

namespace PuppeteerSharp.Messaging
{
internal class PageGetLayoutMetricsResponse
{
[JsonProperty("contentSize")]
public LayourContentSize ContentSize { get; set; }

public class LayourContentSize
{
[JsonProperty("width")]
public decimal Width { get; set; }
[JsonProperty("height")]
public decimal Height { get; set; }
}
}
}
151 changes: 95 additions & 56 deletions lib/PuppeteerSharp/Page.cs
Expand Up @@ -43,6 +43,9 @@ public class Page : IDisposable
private readonly Dictionary<string, Worker> _workers;
private readonly ILogger _logger;
private bool _ensureNewDocumentNavigation;
private PageGetLayoutMetricsResponse _burstModeMetrics;
private bool _screenshotBurstModeOn;
private ScreenshotOptions _screenshotBurstModeOptions;

private static readonly Dictionary<string, decimal> _unitToPixels = new Dictionary<string, decimal> {
{"px", 1},
Expand Down Expand Up @@ -1565,6 +1568,20 @@ void responseEventListener(object sender, ResponseCreatedEventArgs e)
/// <param name="options">Navigation parameters.</param>
public Task<Response> GoForwardAsync(NavigationOptions options = null) => GoAsync(1, options);

/// <summary>
/// Resets the background color and Viewport after taking Screenshots using BurstMode.
/// </summary>
/// <returns>The burst mode off.</returns>
public Task SetBurstModeOff()
{
_screenshotBurstModeOn = false;
if (_screenshotBurstModeOptions != null)
{
ResetBackgroundColorAndViewport(_screenshotBurstModeOptions);
}

return Task.CompletedTask;
}
#endregion

#region Private Method
Expand Down Expand Up @@ -1645,72 +1662,86 @@ private async Task<Response> GoAsync(int delta, NavigationOptions options)

private async Task<string> PerformScreenshot(ScreenshotType type, ScreenshotOptions options)
{
await Client.SendAsync("Target.activateTarget", new
if (!_screenshotBurstModeOn)
{
targetId = Target.TargetId
}).ConfigureAwait(false);
await Client.SendAsync("Target.activateTarget", new
{
targetId = Target.TargetId
}).ConfigureAwait(false);
}

var clip = options.Clip?.Clone();
if (clip != null)
{
clip.Scale = 1;
}

if (options != null && options.FullPage)
if (!_screenshotBurstModeOn)
{
var metrics = await Client.SendAsync("Page.getLayoutMetrics").ConfigureAwait(false);
var contentSize = metrics[MessageKeys.ContentSize];

var width = Convert.ToInt32(Math.Ceiling(contentSize[MessageKeys.Width].Value<decimal>()));
var height = Convert.ToInt32(Math.Ceiling(contentSize[MessageKeys.Height].Value<decimal>()));

// Overwrite clip for full page at all times.
clip = new Clip
if (options != null && options.FullPage)
{
X = 0,
Y = 0,
Width = width,
Height = height,
Scale = 1
};

var isMobile = Viewport?.IsMobile ?? false;
var deviceScaleFactor = Viewport?.DeviceScaleFactor ?? 1;
var isLandscape = Viewport?.IsLandscape ?? false;
var screenOrientation = isLandscape ?
new ScreenOrientation
var metrics = _screenshotBurstModeOn
? _burstModeMetrics :
await Client.SendAsync<PageGetLayoutMetricsResponse>("Page.getLayoutMetrics").ConfigureAwait(false);

if (options.BurstMode)
{
Angle = 90,
Type = ScreenOrientationType.LandscapePrimary
} :
new ScreenOrientation
_burstModeMetrics = metrics;
}

var contentSize = metrics.ContentSize;

var width = Convert.ToInt32(Math.Ceiling(contentSize.Width));
var height = Convert.ToInt32(Math.Ceiling(contentSize.Height));

// Overwrite clip for full page at all times.
clip = new Clip
{
Angle = 0,
Type = ScreenOrientationType.PortraitPrimary
X = 0,
Y = 0,
Width = width,
Height = height,
Scale = 1
};

await Client.SendAsync("Emulation.setDeviceMetricsOverride", new
{
mobile = isMobile,
width,
height,
deviceScaleFactor,
screenOrientation
}).ConfigureAwait(false);
}
var isMobile = Viewport?.IsMobile ?? false;
var deviceScaleFactor = Viewport?.DeviceScaleFactor ?? 1;
var isLandscape = Viewport?.IsLandscape ?? false;
var screenOrientation = isLandscape ?
new ScreenOrientation
{
Angle = 90,
Type = ScreenOrientationType.LandscapePrimary
} :
new ScreenOrientation
{
Angle = 0,
Type = ScreenOrientationType.PortraitPrimary
};

await Client.SendAsync("Emulation.setDeviceMetricsOverride", new
{
mobile = isMobile,
width,
height,
deviceScaleFactor,
screenOrientation
}).ConfigureAwait(false);
}

if (options != null && options.OmitBackground)
{
await Client.SendAsync("Emulation.setDefaultBackgroundColorOverride", new
if (options != null && options.OmitBackground)
{
color = new
await Client.SendAsync("Emulation.setDefaultBackgroundColorOverride", new
{
r = 0,
g = 0,
b = 0,
a = 0
}
}).ConfigureAwait(false);
color = new
{
r = 0,
g = 0,
b = 0,
a = 0
}
}).ConfigureAwait(false);
}
}

dynamic screenMessage = new ExpandoObject();
Expand All @@ -1727,19 +1758,27 @@ private async Task<string> PerformScreenshot(ScreenshotType type, ScreenshotOpti
screenMessage.clip = clip;
}

JObject result = await Client.SendAsync("Page.captureScreenshot", screenMessage).ConfigureAwait(false);
var result = await Client.SendAsync<PageCaptureScreenshotResponse>("Page.captureScreenshot", screenMessage).ConfigureAwait(false);

if (options != null && options.OmitBackground)
if (options.BurstMode)
{
await Client.SendAsync("Emulation.setDefaultBackgroundColorOverride").ConfigureAwait(false);
_screenshotBurstModeOptions = options;
_screenshotBurstModeOn = true;
}

if (options?.FullPage == true && Viewport != null)
else
{
await SetViewportAsync(Viewport).ConfigureAwait(false);
await ResetBackgroundColorAndViewport(options);
}
return result.Data;
}

return result.GetValue(MessageKeys.Data).AsString();
private Task ResetBackgroundColorAndViewport(ScreenshotOptions options)
{
var omitBackgroundTask = options?.OmitBackground == true ?
Client.SendAsync("Emulation.setDefaultBackgroundColorOverride") : Task.CompletedTask;
var setViewPortTask = (options?.FullPage == true && Viewport != null) ?
SetViewportAsync(Viewport) : Task.CompletedTask;
return Task.WhenAll(omitBackgroundTask, setViewPortTask);
}

private decimal ConvertPrintParameterToInches(object parameter)
Expand Down
8 changes: 7 additions & 1 deletion lib/PuppeteerSharp/ScreenshotOptions.cs
Expand Up @@ -49,7 +49,13 @@ public class ScreenshotOptions
/// <value>The quality.</value>
[JsonProperty("quality")]
public int? Quality { get; set; }

/// <summary>
/// When BurstMode is <c>true</c> the screenshot process will only execute all the screenshot setup actions (background and metrics overrides)
/// before the first screenshot call and it will ignore the reset actions after the screenshoot is taken.
/// <see cref="Page.SetBurstModeOff"/> needs to be called after the last screenshot is taken.
/// </summary>
[JsonIgnore]
public bool BurstMode { get; set; } = false;
internal static ScreenshotType? GetScreenshotTypeFromFile(string file)
{
var extension = new FileInfo(file).Extension.Replace(".", string.Empty);
Expand Down

0 comments on commit f764ff3

Please sign in to comment.