As we all know that one of the primary purposes of automation testing is to reduce manual effort. Hence, the use of a screenshot captured during the execution of automated test becomes very useful. You will not want to monitor your application every time the tests are executed. The script can take a screenshot helping to check the application functionality/state when the test execution completes. Screenshots also help when your test case fails so that you can easily identify what went wrong in your script or your application.
Screenshots are beneficial, specifically in case of headless test execution, where you are not able to see the GUI of the application. Still, Selenium will capture it with the help of a screenshot and store it in a file so that you can verify it later.
They also help distinguish whether the failures are due to application failure or test script failure. The given scenarios will be the significant use cases, where a screenshot is useful to debug the automated test cases failures caused:
- When the application issues occur.
- When an assertion failure occurs.
- When there is some difficulty while finding a web element on a page.
- When there is a Timeout while finding a web element on a web page.
So, considering the above cases, capturing screenshots has become an important part of all the UI automation tools.
How to take a screenshot in Selenium?
For taking a screenshot in Selenium, we use an interface called Takes Screenshot that enables the Selenium WebDriver to capture a screenshot and store it in several different ways. It has a method, “getScreenshotAs(), ” that captures the screenshot and stores it in the specified location.
Below is a syntax of capturing a screenshot, using Selenium WebDriver, of the currently visible part of the Web page:
File screenshotFile = ((TakesScreenshot) driver).getScreenshotAs(OutputType.FILE);
In this code, we are converting the WebDriver object (driver) to TakeScreenshot. And call the getScreenshotAs() method for creating an image file by providing the parameter OutputType.FILE.
Now you can use this File object to copy the image at your desired location, as shown below, using the FileUtils Class.
FileUtils.copyFile(screenshotFile , new File("D:\\temp\\screenshot.png));
Example:
import org.apache.commons.io.FileUtils;
import org.openqa.selenium.OutputType;
import org.openqa.selenium.TakesScreenshot;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.chrome.ChromeDriver;
import java.io.File;
import java.io.IOException;
public class ScreenshotDemo {
    public static void main(String[] args) {
        //set the location of chrome browser
        System.setProperty("webdriver.chrome.driver", "D:\\chromedriver.exe");Â
        // Initialize browser
        WebDriver driver = new ChromeDriver();       Â
        //navigate to url
        driver.get("https://google.com");Â
       //Take the screenshot
        String screens = System.getProperty("user.dir") + "\homePageScreenshot.png";
        File screenshot = ((TakesScreenshot) driver).getScreenshotAs(OutputType.FILE);Â
        try {
            FileUtils.copyFile(screenshot, new File(screens));
        } catch (IOException e) {
            System.out.println(e.getMessage());
        }       Â
        //closing the webdriver
        driver.close();
    }
}
In this way, Selenium WebDriver will only capture the screenshot of part of the web page, which was visible. You are not able to capture the screenshot of the full page using this method.
How to capture a screenshot of the full page in Selenium?
Selenium WebDriver does not provide the inherent capability to capture screenshot of the whole page. For capturing the full page screenshot, you have to use a third-party library named Ashot that provides the ability for capturing a screenshot of a particular WebElement as well as a full-page screenshot. You can download the Ashot library’s jar file from "https://jar-download.com/artifacts/ru.yandex.qatools.ashot/ashot "
or “https://mvnrepository.com/artifact/ru.yandex.qatools.ashot/ashot/1.5.4 “
and then you can add the same as an external dependency. Once the Ashot library gets added to the Eclipse project, you can use the below methods for capturing the screenshots of the web page:
- Capture the screen size image that is the viewable part of the screen. Then we create an Ashot object and call the takeScreenshot() method:
Screenshot screenshot = new Ashot().takeScreenshot(driver);
- Capture the full page screenshot that is more than the currently visible part on the screen. After creating the AShot object, you need to call the shootingStrategy() method before calling the takeScreenshot() method for setting up the policy. You can write the below code to do so:
Screenshot s1=new AShot().shootingStrategy(ShootingStrategies.viewportPasting(1000)).takeScreenshot(driver);
ImageIO.write(s1.getImage(),"PNG",new File("<< file path>>"));
In this code, 1000 is scrolled out time in milliseconds. In other words, it simply means that the program will scroll for each 1000 msec to take a screenshot.
Example:
import org.apache.commons.io.FileUtils;
import org.openqa.selenium.OutputType;
import org.openqa.selenium.TakesScreenshot;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.chrome.ChromeDriver;
import ru.yandex.qatools.ashot.AShot;
import ru.yandex.qatools.ashot.Screenshot;
import ru.yandex.qatools.ashot.shooting.ShootingStrategies;
import javax.imageio.ImageIO;
import java.io.File;
import java.io.IOException;
public class ScreenshotDemo {
    public static void main(String arg[]) throws IOException {
        //set the location of chrome browser
        System.setProperty("webdriver.chrome.driver", "D:\\chromedriver.exe");       Â
        // Initialize browser
        WebDriver driver = new ChromeDriver();       Â
        //navigate to url
        driver.get("https://google.com");
        String screens = System.getProperty("user.dir") + "\fullPageScreenshot.png";
        Screenshot s1=new AShot().shootingStrategy(ShootingStrategies.viewportPasting(1000)).takeScreenshot(driver);
        ImageIO.write(s1.getImage(),"PNG", new File(screens));       Â
        //closing the webdriver
        driver.close();
    }
}
How to catch the screenshot of a particular element in Selenium?
Sometimes, you need a screenshot of a particular element on a page. There are two ways for capturing the screenshot of a web element in Selenium
- Take the fullscreen image and crop the image according to the dimensions of the web element.
- Using the method getScreenshotAs() on the web element. (Only available in selenium version 4.X).
How to catch the screenshot of a particular element by cropping the full page screenshot?
You can follow the given steps to take the screenshot of the logo of Google.
- Capture viewport screenshot as a buffered Image.
- Get the element’s height and width using getSize() method.
- Get the element’s X Y coordinates using Point class.
- Read the buffered Image.
- Crop the buffered Image using element’s x, y coordinate position, and height, width parameters.
- Save cropped Image at destination location physically.
Example:
import org.apache.commons.io.FileUtils;
import org.openqa.selenium.*;
import org.openqa.selenium.chrome.ChromeDriver;
import javax.imageio.ImageIO;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
public class ScreenshotDemo {
    public static void main(String arg[]) throws IOException {
        //set the location of chrome browser
        System.setProperty("webdriver.chrome.driver", "D:\\chromedriver.exe");       Â
        // Initialize browser
        WebDriver driver = new ChromeDriver();       Â
        //navigate to url
        driver.get("https://google.com");       Â
        WebElement google_logo = driver.findElement(By.xpath("//*[@id=\"app\"]/header/a/img"));       Â
String screens = System.getProperty("user.dir") + "\particularElementScreenshot.png";
        File screenshot = ((TakesScreenshot) driver).getScreenshotAs(OutputType.FILE);       Â
        BufferedImage fullScreen = ImageIO.read(screenshot);Â
        Point location = google_logo.getLocation();       Â
        int width = google_logo.getSize().getWidth();
        int height = google_logo.getSize().getHeight();
        BufferedImage logo_image = fullScreen.getSubimage(location.getX(), location.getY(),
                width, height);
        ImageIO.write(logo_image, "png", screenshot);       Â
        FileUtils.copyFile(screenshot, new File(screens));
        driver.quit();
    }
}
In this way, you can easily crop any of the existing screenshots. It will help you to get a portion or screenshot of a specific web element.
How to take the screenshot of a particular element by using the getScreenshotAs() method?
You can capture screenshots of a particular element in Selenium 4.0 using the getScreenshotAs (OutputType.File) method of the WebElement class. So, the method getScreenshotAs() can be directly called on the WebElement, for which you want to capture the screenshot:
import org.apache.commons.io.FileUtils;
import org.openqa.selenium.*;
import org.openqa.selenium.chrome.ChromeDriver;
import java.io.File;
import java.io.IOException;
public class ScreenshotDemo {
    public static void main(String arg[]) throws IOException {
        //set the location of chrome browser
        System.setProperty("webdriver.chrome.driver", "D:\\chromedriver.exe");       Â
        // Initialize browser
        WebDriver driver = new ChromeDriver();       Â
        //navigate to url
        driver.get("https://google.com");  Â
String screens = System.getProperty("user.dir") + "\logoScreeshot.png";
        WebElement google_logo = driver.findElement(By.xpath("//*[@id=\"app\"]/header/a/img"));     Â
        File f = google_logo.getScreenshotAs(OutputType.FILE);       Â
        FileUtils.copyFile(f, new File(screens));       Â
        driver.close();
    }
}