1. 上文中介绍了怎么使用selenium及设置手机模式浏览,但发现只能截取屏幕部分图片,而之前网页端用webbrowser截图还可以,但手机端的话因为webbrowser是ie内核,导致页面样式杂乱。现改用selenium下面介绍整理的几种方式
1.) selenium有默认的较为简单截图方式,只能截图屏幕区域,可满足简单的需求。
//截图
Screenshot screenShotFile = ((ITakesScreenshot)driver).GetScreenshot();
string img_url = Environment.CurrentDirectory + @"\\test.jpg";
screenShotFile.SaveAsFile(img_url, OpenQA.Selenium.ScreenshotImageFormat.Jpeg);
2.) 创建继承ChromeDriver的类,执行js获取参数
public class ChromeDriverEx : ChromeDriver
{
private const string SendChromeCommandWithResult = "sendChromeCommandWithResponse";
private const string SendChromeCommandWithResultUrlTemplate = "/session/{sessionId}/chromium/send_command_and_get_result";
public ChromeDriverEx(string chromeDriverDirectory, ChromeOptions options)
: base(chromeDriverDirectory, options)
{
CommandInfo commandInfoToAdd = new CommandInfo(CommandInfo.PostCommand, SendChromeCommandWithResultUrlTemplate);
this.CommandExecutor.CommandInfoRepository.TryAddCommand(SendChromeCommandWithResult, commandInfoToAdd);
}
public ChromeDriverEx(ChromeDriverService service, ChromeOptions options)
: base(service, options)
{
CommandInfo commandInfoToAdd = new CommandInfo(CommandInfo.PostCommand, SendChromeCommandWithResultUrlTemplate);
this.CommandExecutor.CommandInfoRepository.TryAddCommand(SendChromeCommandWithResult, commandInfoToAdd);
}
public Screenshot GetFullPageScreenshot()
{
string metricsScript = @"({
width: Math.max(window.innerWidth,document.body.scrollWidth,document.documentElement.scrollWidth)|0,
height: Math.max(window.innerHeight,document.body.scrollHeight,document.documentElement.scrollHeight)|0,
deviceScaleFactor: window.devicePixelRatio || 1,
mobile: typeof window.orientation !== 'undefined'
})";
Dictionary<string, object> metrics = this.EvaluateDevToolsScript(metricsScript);
this.ExecuteChromeCommand("Emulation.setDeviceMetricsOverride", metrics);
Dictionary<string, object> parameters = new Dictionary<string, object>();
parameters["format"] = "png";
parameters["fromSurface"] = true;
object screenshotObject = this.ExecuteChromeCommandWithResult("Page.captureScreenshot", parameters);
Dictionary<string, object> screenshotResult = screenshotObject as Dictionary<string, object>;
string screenshotData = screenshotResult["data"] as string;
this.ExecuteChromeCommand("Emulation.clearDeviceMetricsOverride", new Dictionary<string, object>());
Screenshot screenshot = new Screenshot(screenshotData);
return screenshot;
}
public object ExecuteChromeCommandWithResult(string commandName, Dictionary<string, object> commandParameters)
{
if (commandName == null)
{
throw new ArgumentNullException("commandName", "commandName must not be null");
}
Dictionary<string, object> parameters = new Dictionary<string, object>();
parameters["cmd"] = commandName;
parameters["params"] = commandParameters;
Response response = this.Execute(SendChromeCommandWithResult, parameters);
return response.Value;
}
private Dictionary<string, object> EvaluateDevToolsScript(string scriptToEvaluate)
{
Dictionary<string, object> parameters = new Dictionary<string, object>();
parameters["returnByValue"] = true;
parameters["expression"] = scriptToEvaluate;
object evaluateResultObject = this.ExecuteChromeCommandWithResult("Runtime.evaluate", parameters);
Dictionary<string, object> evaluateResultDictionary = evaluateResultObject as Dictionary<string, object>;
Dictionary<string, object> evaluateResult = evaluateResultDictionary["result"] as Dictionary<string, object>;
Dictionary<string, object> evaluateValue = evaluateResult["value"] as Dictionary<string, object>;
return evaluateValue;
}
}
此种调用方式为
//cdSvc参数为对象ChromeDriverService,也可直接将d://chromedriver/驱动所在地址作为参数传递
ChromeDriverEx driver = new ChromeDriverEx(cdSvc, options);
driver1.Url = "http://m.baidu.com";
Screenshot screenshot = driver1.GetFullPageScreenshot();
screenshot.SaveAsFile(Environment.CurrentDirectory + @"\FullPageScreenshot.png");
3.) 在上面的方法的前提下,另一种GetFullPageScreenshot方式
var filePath = Environment.CurrentDirectory + @"\FullPageScreenshot11.png";
Dictionary<string, Object> metrics = new Dictionary<string, Object>();
metrics["width"] = driver.ExecuteScript("return Math.max(window.innerWidth,document.body.scrollWidth,document.documentElement.scrollWidth)");
metrics["height"] = driver.ExecuteScript("return Math.max(window.innerHeight,document.body.scrollHeight,document.documentElement.scrollHeight)");
//返回当前显示设备的物理像素分辨率与 CSS 像素分辨率的比率
metrics["deviceScaleFactor"] = driver.ExecuteScript("return window.devicePixelRatio");
metrics["mobile"] = driver.ExecuteScript("return typeof window.orientation !== 'undefined'");
driver.ExecuteChromeCommand("Emulation.setDeviceMetricsOverride", metrics);
driver.GetScreenshot().SaveAsFile(filePath, ScreenshotImageFormat.Png);
参考:https://stackoverflow.com/questions/52043197/c-sharp-selenium-full-page-screenshot