Best JavaScript code snippet using playwright-internal
uber-controller.js
Source:uber-controller.js
...32 delay: 1000,33 timeout: 2000034 }) => {35 console.log(`Waiting for selector (${desc}): ${selector}`);36 await _screenshot(page, `click_before_wait_${desc}_${Date.now()}`);37 await page.waitForSelector(selector, {timeout: timeout});38 await _screenshot(page, `click_after_wait_${desc}_${Date.now()}`);39 console.log(`Selector found in page`);40 await page.click(selector);41 await _screenshot(page, `click_after_click_${desc}_${Date.now()}`);42 console.log(`Clicked selector. Now waiting ${delay}ms`);43 await page.waitFor(delay);44 await _screenshot(page, `click_after_second_wait_${desc}_${Date.now()}`);45 console.log(`Done waiting.`);46}47const _wait_for_function_and_perform_func = async (page,48 wait_func,49 wait_func_params,50 exec_func = null,51 exec_func_params = null,52 {53 desc = "",54 delay = 1000,55 timeout = 2000056 } =57 {58 desc: "",59 delay: 1000,60 timeout: 2000061 }) => {62 console.log(`Waiting for function (${desc})`);63 await _screenshot(page, `before_wait_for_wait_func_${desc}_${Date.now()}`);64 await page.waitForFunction(wait_func, {timeout: timeout}, ...wait_func_params);65 await _screenshot(page, `after_wait_for_wait_func_${desc}_${Date.now()}`);66 if (!exec_func) {67 console.log("No exec function...returning.");68 return null;69 }70 const retVal = await page.evaluate(exec_func, ...exec_func_params);71 await _screenshot(page, `after_evaluate_exec_func_${desc}_${Date.now()}`);72 await page.waitFor(delay);73 await _screenshot(page, `after_wait_for_second_wait_for_wait_func_${desc}_${Date.now()}`);74 console.log(`Done waiting.`);75 return retVal;76}77const _wait_for_selector_and_select = async (page,78 selector,79 value,80 {81 desc = "",82 delay = 1000,83 timeout = 20000,84 hideValue = false,85 } =86 {87 desc: "",88 delay: 1000,89 timeout: 20000,90 hideValue: false,91 }) => {92 console.log(`Waiting for selector (${desc}): ${selector}`);93 await _screenshot(page, `select_before_wait_${desc}_${Date.now()}`);94 await page.waitForSelector(selector, {timeout: timeout});95 console.log(`Selector found in page`);96 await _screenshot(page, `select_after_wait_${desc}_${Date.now()}`);97 await page.select(selector, value);98 const redactedValue = hideValue ? "*******" : value;99 console.log(`Selected ${redactedValue} from dropdown. Now waiting ${delay}ms`);100 await _screenshot(page, `select_after_select_${desc}_${Date.now()}`);101 await page.waitFor(delay);102 await _screenshot(page, `select_after_second_wait_${desc}_${Date.now()}`);103 console.log(`Done waiting.`);104}105const _wait_for_selector_and_type = async (page,106 selector,107 value,108 {109 desc = "",110 delay = 1000,111 timeout = 10000,112 hideValue = false,113 } =114 {115 desc: "",116 delay: 1000,117 timeout: 10000,118 hideValue: false,119 }) => {120 console.log(`Waiting for selector (${desc}): ${selector}`);121 await _screenshot(page, `type_before_wait_${desc}_${Date.now()}`);122 await page.waitForSelector(selector, {timeout: timeout});123 console.log(`Selector found in page`);124 await _screenshot(page, `type_after_wait_${desc}_${Date.now()}`);125 await page.type(selector, value);126 const redactedValue = hideValue ? "*******" : value;127 await _screenshot(page, `type_after_type_${desc}_${Date.now()}`);128 console.log(`Typed ${redactedValue} into field. Now waiting ${delay}ms`);129 await page.waitFor(delay);130 await _screenshot(page, `type_after_second_wait_${desc}_${Date.now()}`);131 console.log(`Done waiting.`);132}133const _click_and_wait_ms = async (page, selector, ms) => {134 await page.click(selector);135 await page.waitFor(ms);136}137const _click_and_wait_ms_deprecated = (page, selector, ms) => Promise.all([138 page.evaluate((selector) => document.querySelector(selector).click(), selector),139 page.waitFor(ms),140]);141const _wait_for_selector = async (page, selector, delay, timeout) => {142 await page.waitForSelector(selector, {timeout: timeout});143 await page.waitFor(delay);144}...
indicator.js
Source:indicator.js
1// vi: sts=2 sw=2 et2const Lang = imports.lang;3const Signals = imports.signals;4const St = imports.gi.St;5const Cogl = imports.gi.Cogl;6const Shell = imports.gi.Shell;7const Clutter = imports.gi.Clutter;8const PanelMenu = imports.ui.panelMenu;9const PopupMenu = imports.ui.popupMenu;10const Slider = imports.ui.slider;11const Gettext = imports.gettext.domain('gnome-shell-screenshot');12const _ = Gettext.gettext;13const ExtensionUtils = imports.misc.extensionUtils;14const Local = ExtensionUtils.getCurrentExtension();15const Config = Local.imports.config.exports;16const Convenience = Local.imports.convenience.exports;17const { dump } = Local.imports.dump.exports;18const DefaultIcon = 'camera-photo-symbolic';19const settings = Convenience.getSettings();20const CaptureDelayMenu = new Lang.Class({21 Name: 'CaptureDelayMenu',22 Extends: PopupMenu.PopupMenuSection,23 createScale: function () {24 let scale = [0];25 for (let p = 1; p < 4; p ++) {26 for (let x = 1; x <= 10; x += 1) {27 scale.push(x * Math.pow(10, p));28 }29 }30 return scale;31 },32 _init: function(control) {33 this.parent();34 this.scaleMS = this.createScale();35 this.delayValueMS = settings.get_int(Config.KeyCaptureDelay);36 this.slider = new Slider.Slider(this.scaleToSlider(this.delayValueMS));37 this.slider.connect('value-changed', this.onDragEnd.bind(this));38 this.sliderItem = new PopupMenu.PopupBaseMenuItem({ activate: false });39 this.sliderItem.actor.add(this.slider.actor, { expand: true });40 this.addMenuItem(this.sliderItem);41 this.delayInfoItem = new PopupMenu.PopupMenuItem(42 '', { activate: false, hover: false, can_focus: false }43 );44 this.addMenuItem(this.delayInfoItem)45 this.updateDelayInfo();46 },47 scaleToSlider: function (ms) {48 return this.scaleMS.findIndex((v) => v >= ms) / (this.scaleMS.length-1);49 },50 sliderToScale: function (value) {51 return this.scaleMS[(value * (this.scaleMS.length-1)) | 0];52 },53 onDragEnd: function(slider, value, property) {54 const newValue = this.sliderToScale(value);55 if (newValue !== this.delayValueMS) {56 this.delayValueMS = newValue;57 settings.set_int(Config.KeyCaptureDelay, newValue);58 this.updateDelayInfo();59 }60 },61 updateDelayInfo: function() {62 const v = this.delayValueMS;63 let text;64 if (v === 0) {65 text = _('No Capture Delay');66 } else if (v < 1000) {67 text = `${v}ms ` + _('Capture Delay');68 } else {69 text = `${v / 1000}s ` + _('Capture Delay');70 }71 this.delayInfoItem.label.text = text;72 }73});74const ScreenshotSection = new Lang.Class({75 Name: "ScreenshotTool.ScreenshotSection",76 _init: function (menu) {77 this._screenshot = null;78 this._image = new PopupMenu.PopupBaseMenuItem();79 this._image.actor.content_gravity =80 Clutter.ContentGravity.RESIZE_ASPECT;81 this._clear = new PopupMenu.PopupMenuItem(_('Clear'));82 this._copy = new PopupMenu.PopupMenuItem(_('Copy'));83 this._save = new PopupMenu.PopupMenuItem(_('Save As...'));84 this._image.connect('activate', this._onImage.bind(this));85 this._clear.connect('activate', this._onClear.bind(this));86 this._copy.connect('activate', this._onCopy.bind(this));87 this._save.connect('activate', this._onSave.bind(this));88 menu.addMenuItem(this._image);89 menu.addMenuItem(this._clear);90 menu.addMenuItem(this._copy);91 menu.addMenuItem(this._save);92 // IMGUR93 menu.addMenuItem(new PopupMenu.PopupSeparatorMenuItem());94 this._imgurMenu = new PopupMenu.PopupSubMenuMenuItem(_('Imgur'), false);95 this._imgurUpload = new PopupMenu.PopupMenuItem(_('Upload'));96 this._imgurOpen = new PopupMenu.PopupMenuItem(_('Open Link'));97 this._imgurCopyLink = new PopupMenu.PopupMenuItem(_('Copy Link'));98 this._imgurDelete = new PopupMenu.PopupMenuItem(_('Delete'));99 this._imgurUpload.connect('activate', this._onImgurUpload.bind(this));100 this._imgurOpen.connect('activate', this._onImgurOpen.bind(this));101 this._imgurCopyLink.connect('activate', this._onImgurCopyLink.bind(this));102 this._imgurDelete.connect('activate', this._onImgurDelete.bind(this));103 this._imgurMenu.menu.addMenuItem(this._imgurUpload);104 this._imgurMenu.menu.addMenuItem(this._imgurOpen);105 this._imgurMenu.menu.addMenuItem(this._imgurCopyLink);106 this._imgurMenu.menu.addMenuItem(this._imgurDelete);107 menu.addMenuItem(this._imgurMenu);108 menu.connect("open-state-changed", () => {109 this._updateVisibility();110 });111 this._updateVisibility();112 },113 _updateVisibility: function () {114 let visible = !!this._screenshot;115 this._image.actor.visible = visible;116 this._clear.actor.visible = visible;117 this._copy.actor.visible = visible;118 this._save.actor.visible = visible;119 let imgurEnabled = settings.get_boolean(Config.KeyEnableUploadImgur);120 let imgurComplete =121 this._screenshot &&122 this._screenshot.imgurUpload &&123 this._screenshot.imgurUpload.responseData;124 this._imgurMenu.actor.visible =125 visible && imgurEnabled;126 this._imgurUpload.actor.visible =127 visible && imgurEnabled && !imgurComplete;128 this._imgurOpen.actor.visible =129 visible && imgurEnabled && imgurComplete;130 this._imgurCopyLink.actor.visible =131 visible && imgurEnabled && imgurComplete;132 this._imgurDelete.actor.visible =133 visible && imgurEnabled && imgurComplete;134 },135 _setImage: function (pixbuf) {136 let {width, height} = pixbuf;137 if (height == 0) {138 return;139 }140 let image = new Clutter.Image();141 let success = image.set_data(142 pixbuf.get_pixels(),143 pixbuf.get_has_alpha()144 ? Cogl.PixelFormat.RGBA_8888145 : Cogl.PixelFormat.RGB_888,146 width,147 height,148 pixbuf.get_rowstride()149 );150 if (!success) {151 throw Error("error creating Clutter.Image()");152 }153 this._image.actor.content = image;154 this._image.actor.height = 200;155 },156 setScreenshot: function (screenshot) {157 this._screenshot = screenshot;158 if (screenshot) {159 this._setImage(screenshot.gtkImage.get_pixbuf());160 this._screenshot.connect("imgur-upload", (obj, upload) => {161 upload.connect("done", (obj, data) => {162 this._updateVisibility();163 });164 });165 }166 this._updateVisibility();167 },168 _onImage: function () {169 this._screenshot.launchOpen();170 },171 _onClear: function () {172 this.setScreenshot(null);173 },174 _onCopy: function () {175 this._screenshot.copyClipboard();176 },177 _onSave: function () {178 this._screenshot.launchSave();179 },180 _onImgurUpload: function () {181 this._screenshot.imgurStartUpload();182 },183 _onImgurOpen: function () {184 this._screenshot.imgurOpenURL();185 },186 _onImgurCopyLink: function () {187 this._screenshot.imgurCopyURL();188 },189 _onImgurDelete: function () {190 this._screenshot.imgurDelete();191 }192})193const Indicator = new Lang.Class({194 Name: "ScreenshotTool.Indicator",195 Extends: PanelMenu.Button,196 _init: function (extension) {197 this.parent(null, Config.IndicatorName);198 this._extension = extension;199 this._signalSettings = [];200 this._icon = new St.Icon({201 icon_name: DefaultIcon,202 style_class: 'system-status-icon'203 });204 this.actor.add_actor(this._icon);205 this.actor.connect('button-press-event', this._onClick.bind(this));206 this._buildMenu();207 },208 _onClick: function (obj, evt) {209 // only override primary button behavior210 if (evt.get_button() !== Clutter.BUTTON_PRIMARY) {211 return;212 }213 let action = settings.get_string(Config.KeyClickAction);214 if (action === 'show-menu') {215 return;216 }217 this.menu.close();218 this._extension.onAction(action);219 },220 _buildMenu: function () {221 // These actions can be triggered via shortcut or popup menu222 const items = [223 ["select-area", _("Select Area")],224 ["select-window", _("Select Window")],225 ["select-desktop", _("Select Desktop")]226 ];227 items.forEach(([action, title]) => {228 let item = new PopupMenu.PopupMenuItem(title);229 item.connect(230 'activate', function (action) {231 this.menu.close();232 this._extension.onAction(action);233 }.bind(this, action)234 );235 this.menu.addMenuItem(item);236 })237 // Delay238 this.menu.addMenuItem(new PopupMenu.PopupSeparatorMenuItem());239 this.menu.addMenuItem(new CaptureDelayMenu());240 this.menu.addMenuItem(new PopupMenu.PopupSeparatorMenuItem());241 this._screenshotSection = new ScreenshotSection(this.menu);242 this.menu.addMenuItem(new PopupMenu.PopupSeparatorMenuItem());243 // Settings can only be triggered via menu244 let settingsItem = new PopupMenu.PopupMenuItem(_('Settings'));245 settingsItem.connect('activate', () => {246 let appSys = Shell.AppSystem.get_default();247 let prefs = appSys.lookup_app('gnome-shell-extension-prefs.desktop');248 if (prefs.get_state() == prefs.SHELL_APP_STATE_RUNNING) {249 prefs.activate();250 } else {251 prefs.get_app_info().launch_uris(252 ['extension:///' + Local.metadata.uuid], null253 );254 }255 });256 this.menu.addMenuItem(settingsItem);257 },258 setScreenshot: function (screenshot) {259 this._screenshotSection.setScreenshot(screenshot);260 },261 destroy: function () {262 this.parent();263 this._signalSettings.forEach((signal) => {264 settings.disconnect(signal);265 });266 }267});268var exports = {269 Indicator...
controller.js
Source:controller.js
1/*2 * This file is part of the ZombieBox package.3 *4 * Copyright © 2015-2020, Interfaced5 *6 * For the full copyright and license information, please view the LICENSE7 * file that was distributed with this source code.8 */9import app from 'generated/app';10import {div} from 'zb/html';11import AbstractApplication from 'zb/abstract-application';12import IKeyHandler from 'zb/interfaces/i-key-handler';13import Key from 'zb/device/input/key';14import EventPublisher from 'zb/events/event-publisher';15import Layer from 'zb/layers/layer';16import IMarkupProvider from './i-markup-provider';17import ScreenShot from './screenshot';18import UI, {PositionDiff} from './ui';19/**20 * @implements {IKeyHandler}21 */22export default class Controller {23 /**24 */25 constructor() {26 this._onChildLayerShown = this._onChildLayerShown.bind(this);27 this._onChildLayerHidden = this._onChildLayerHidden.bind(this);28 /**29 * @type {UI}30 * @protected31 */32 this._ui = null;33 /**34 * @type {number}35 * @protected36 */37 this._currentPosition = 0;38 /**39 * Default value is '77177'40 * @type {Array<Key>}41 * @protected42 */43 this._sequence = [44 Key.DIGIT_7,45 Key.DIGIT_7,46 Key.DIGIT_1,47 Key.DIGIT_7,48 Key.DIGIT_749 ];50 /**51 * @type {Array<string>}52 * @protected53 */54 this._screenshots = [];55 /**56 * @type {ScreenShot}57 * @protected58 */59 this._screenShot = null;60 /**61 * @type {Layer}62 * @protected63 */64 this._currentLayer = null;65 /**66 * @type {boolean}67 * @protected68 */69 this._isVisible = false;70 /**71 * @type {HTMLDivElement}72 * @protected73 */74 this._container = null;75 this._createUI();76 this._setViewState({77 x: 0,78 y: 0,79 opacity: 0.5,80 scale: false81 });82 }83 /**84 * @override85 */86 processKey(zbKey, event) {87 if (!this._isVisible) {88 const seq = this._sequence;89 this._currentPosition = this._currentPosition || 0;90 if (seq[this._currentPosition] !== zbKey) {91 this._currentPosition = 0;92 } else if (this._currentPosition === seq.length - 1) {93 this._currentPosition = 0;94 this.activate();95 return true;96 } else {97 this._currentPosition++;98 }99 } else {100 if (zbKey === Key.BACK) {101 this.deactivate();102 return true;103 }104 return this._ui.processKey(zbKey, event);105 }106 return false;107 }108 /**109 * Show PP UI and handle keys to perform manipulations with screenshot110 */111 activate() {112 this._isVisible = true;113 this._ui.show();114 this._screenShot.getContainer().style.display = 'block';115 // workaround for getting EVENT_AFTER_SHOW event on app start116 this._bindToLayer(app.getCurrentLayer());117 this._container.style.display = 'block';118 }119 /**120 * Hide PP UI121 */122 deactivate() {123 this._isVisible = false;124 this._ui.hide();125 this._screenShot.getContainer().style.display = 'none';126 this._container.style.display = 'none';127 }128 /**129 * @param {AbstractApplication} app130 */131 attachToApp(app) {132 this._getAppProperty(() => this._getAppBody(app), app, app.EVENT_DOM_READY)133 .then((appBody) => appBody.appendChild(this._container));134 this._getAppProperty(() => app.getLayerManager(), app, app.EVENT_DEVICE_READY)135 .then((lm) => {136 lm.on(lm.EVENT_AFTER_SHOW, (eventName, layer) =>137 this._bindToLayer(/** @type {Layer} */(layer)));138 this._bindToLayer(app.getCurrentLayer());139 });140 }141 /**142 * @param {string|Array<string>} url143 */144 setScreenShotUrl(url) {145 this._screenshots = url instanceof Array ? url : [url];146 this._renderScreenshot(this._screenshots[0]);147 }148 /**149 * @param {Array<Key>} seq150 */151 setKeySequence(seq) {152 this._sequence = seq;153 this._currentPosition = 0;154 }155 /**156 * @param {string} url157 * @protected158 */159 _renderScreenshot(url) {160 this._screenShot.setSource(url);161 this._ui.renderScreenshotValue(url);162 }163 /**164 * @protected165 */166 _createUI() {167 this._createContainer();168 this._screenShot = new ScreenShot();169 this._container.appendChild(this._screenShot.getContainer());170 this._screenShot.getContainer().style.display = 'none';171 this._ui = new UI(this._container);172 this._ui.on(this._ui.EVENT_CHANGE_OPACITY, (eventName, changeDiff) => this._setViewState({173 opacity: this._screenShot.getOpacity() + changeDiff * OPACITY_STEP174 }));175 this._ui.on(this._ui.EVENT_INVERT, () => this._setViewState({176 invert: this._screenShot.isInverted()177 }));178 this._ui.on(this._ui.EVENT_CHANGE_POSITION, (eventName, positionChangeDiff) => {179 positionChangeDiff = /** @type {PositionDiff} */ (positionChangeDiff);180 const position = this._screenShot.getPosition();181 const step = POSITION_STEP;182 if (positionChangeDiff.x) {183 position.x += step * positionChangeDiff.x;184 }185 if (positionChangeDiff.y) {186 position.y += step * positionChangeDiff.y;187 }188 this._setViewState({189 x: position.x,190 y: position.y191 });192 });193 this._ui.on(this._ui.EVENT_NEXT_SCREENSHOT, () => {194 if (this._screenshots.length > 1) {195 let nextIndex = this._screenshots.indexOf(this._screenShot.getSource()) + 1;196 if (nextIndex >= this._screenshots.length) {197 nextIndex = 0;198 }199 this._renderScreenshot(this._screenshots[nextIndex]);200 }201 });202 this._ui.on(this._ui.EVENT_TOGGLE, () => {203 const containerStyle = this._container.style;204 this._screenShot.getContainer().style.display = containerStyle.display === 'none' ? 'block' : 'none';205 });206 this._ui.on(this._ui.EVENT_TOGGLE_SCALE, () => this._setViewState({207 scale: this._screenShot.isScaled()208 }));209 }210 /**211 * @protected212 */213 _createContainer() {214 this._container = div();215 const containerStyle = this._container.style;216 containerStyle.position = 'absolute';217 containerStyle.top = '0';218 containerStyle.left = '0';219 containerStyle.width = '100%';220 containerStyle.height = '100%';221 containerStyle.zIndex = '1000';222 containerStyle.display = 'none';223 containerStyle.pointerEvents = 'none';224 }225 /**226 * @param {{227 * x: (number|undefined),228 * y: (number|undefined),229 * opacity: (number|undefined),230 * invert: (boolean|undefined),231 * scale: (boolean|undefined)232 * }} state233 * @protected234 */235 _setViewState(state) {236 if (state.x !== undefined || state.y !== undefined) {237 const position = {238 x: state.x !== undefined ? state.x : this._screenShot.getPosition().x,239 y: state.y !== undefined ? state.y : this._screenShot.getPosition().y240 };241 this._screenShot.setPosition(position.x, position.y);242 this._ui.renderPositionValue(position.x, position.y);243 }244 if (state.opacity !== undefined) {245 state.opacity = this._screenShot.setOpacity(state.opacity);246 this._ui.renderOpacityValue(state.opacity);247 }248 if (state.scale !== undefined) {249 this._screenShot.setScale(state.scale);250 this._ui.renderScaleValue(state.scale);251 }252 if (state.invert !== undefined) {253 this._screenShot.setInvert(state.invert);254 this._ui.renderInvertValue(state.invert);255 }256 }257 /**258 * @param {string} eventName259 * @param {Layer} layer260 * @protected261 */262 _onChildLayerShown(eventName, layer) {263 this._showScreenshotsFromLayer(layer);264 }265 /**266 * @protected267 */268 _onChildLayerHidden() {269 this._showScreenshotsFromLayer(this._currentLayer);270 }271 /**272 * @param {Layer} layer273 * @protected274 */275 _bindToLayer(layer) {276 if (this._currentLayer) {277 this._currentLayer.off(this._currentLayer.EVENT_CHILD_LAYER_SHOWN, this._onChildLayerShown);278 this._currentLayer.off(this._currentLayer.EVENT_CHILD_LAYER_HIDDEN, this._onChildLayerHidden);279 }280 this._currentLayer = layer;281 if (layer) {282 layer.on(layer.EVENT_CHILD_LAYER_SHOWN, this._onChildLayerShown);283 layer.on(layer.EVENT_CHILD_LAYER_HIDDEN, this._onChildLayerHidden);284 }285 this._showScreenshotsFromLayer(layer);286 }287 /**288 * @param {Layer} layer289 * @protected290 */291 _showScreenshotsFromLayer(layer) {292 const topLayer = layer ? layer.getTopChildLayer() || layer : null;293 const screenshots = this._getScreenShotsFromLayer(topLayer);294 if (screenshots && screenshots.length) {295 this.setScreenShotUrl(screenshots);296 } else {297 this.setScreenShotUrl('');298 }299 }300 /**301 * @param {Layer|IMarkupProvider} layer302 * @return {?Array<string>}303 * @protected304 */305 _getScreenShotsFromLayer(layer) {306 if (layer && typeof layer.getMarkupImage === 'function') {307 const mp = /** @type {IMarkupProvider} */ (layer);308 const screenshots = mp.getMarkupImage();309 return screenshots instanceof Array ? screenshots : [screenshots];310 }311 return null;312 }313 /**314 * @suppress {accessControls}315 * @param {AbstractApplication} app316 * @return {HTMLElement}317 * @protected318 */319 _getAppBody(app) {320 return app._body;321 }322 /**323 * @param {function(): *} getter324 * @param {EventPublisher} obj325 * @param {string} event326 * @return {Promise}327 * @protected328 */329 _getAppProperty(getter, obj, event) {330 return new Promise((resolve) => {331 const result = getter();332 if (result) {333 resolve(result);334 } else {335 obj.on(event, () => resolve(getter()));336 }337 });338 }339}340/**341 * @const {number}342 */343export const OPACITY_STEP = 0.05;344/**345 * @const {number}346 */...
screenshotcontrols.js
Source:screenshotcontrols.js
...123 {124 this._screenshot = window.views.screenshot;125 }126 this._screenshot._take_screenshot = true;127 this._screenshot.update_screenshot(event.shiftKey);128 }.bind(this);129 this._handlers['screenshot-zoom'] = function(event, target)130 {131 if (!this._screenshot)132 {133 this._screenshot = window.views.screenshot;134 }135 this._scale = parseInt(event.target.value);136 this._screenshot.zoom_center(this._scale);137 this._ruler.scale = this._scale;138 }.bind(this);139 this._handlers['screenshot-sample-size'] = function(event, target)140 {141 if (!this._screenshot)...
notifications.js
Source:notifications.js
1// vi: sts=2 sw=2 et2const Lang = imports.lang;3const Signals = imports.signals;4const St = imports.gi.St;5const Gio = imports.gi.Gio;6const Gtk = imports.gi.Gtk;7const GdkPixbuf = imports.gi.GdkPixbuf;8const Main = imports.ui.main;9const MessageTray = imports.ui.messageTray;10const Gettext = imports.gettext.domain('gnome-shell-screenshot');11const _ = Gettext.gettext;12const ExtensionUtils = imports.misc.extensionUtils;13const Local = ExtensionUtils.getCurrentExtension();14const Path = Local.imports.path.exports;15const {dump} = Local.imports.dump.exports;16const Config = Local.imports.config.exports;17const Clipboard = Local.imports.clipboard.exports;18const Thumbnail = Local.imports.thumbnail.exports;19const Convenience = Local.imports.convenience.exports;20const NotificationIcon = 'camera-photo-symbolic';21const NotificationSourceName = 'Screenshot Tool';22const ICON_SIZE = 64;23const settings = Convenience.getSettings();24const getSource = () => {25 let source = new MessageTray.Source(26 NotificationSourceName, NotificationIcon27 );28 Main.messageTray.add(source);29 return source;30}31const Notification = new Lang.Class({32 Name: "ScreenshotTool.Notification",33 Extends: MessageTray.Notification,34 _title: function () {35 return _("New Screenshot");36 },37 _banner: function ({gtkImage}) {38 let {width, height} = gtkImage.get_pixbuf();39 let banner = _("Size:") + " " + width + "x" + height + ".";40 return banner;41 },42 _init: function (source, screenshot) {43 this.parent(44 source,45 this._title(),46 this._banner(screenshot),47 { gicon: Thumbnail.getIcon(screenshot.srcFile.get_path()) }48 );49 this.connect("activated", this._onActivated.bind(this));50 // makes banner expand on hover51 this.setForFeedback(true);52 this._screenshot = screenshot;53 },54 createBanner: function() {55 let b = this.parent();56 b._iconBin.child.icon_size = ICON_SIZE;57 b.addAction(_("Copy"), this._onCopy.bind(this));58 b.addAction(_("Save"), this._onSave.bind(this));59 if (settings.get_boolean(Config.KeyEnableUploadImgur)) {60 if (settings.get_boolean(Config.KeyImgurAutoUpload)) {61 b.addAction(_("Uploading To Imgur..."), () => { /* noop */ });62 } else {63 b.addAction(_("Upload To Imgur"), this._onUpload.bind(this));64 }65 }66 return b;67 },68 _onActivated: function () {69 this._screenshot.launchOpen();70 },71 _onCopy: function () {72 this._screenshot.copyClipboard();73 },74 _onSave: function () {75 this._screenshot.launchSave();76 },77 _onUpload: function () {78 this._screenshot.imgurStartUpload();79 }80});81Signals.addSignalMethods(Notification.prototype);82const ErrorNotification = new Lang.Class({83 Name: "ScreenshotTool.ErrorNotification",84 Extends: MessageTray.Notification,85 _init: function (source, message) {86 this.parent(87 source,88 _("Error"),89 String(message),90 { secondaryGIcon: new Gio.ThemedIcon({name: 'dialog-error'}) }91 );92 }93});94Signals.addSignalMethods(ErrorNotification.prototype);95const ImgurNotification = new Lang.Class({96 Name: "ScreenshotTool.ImgurNotification",97 Extends: MessageTray.Notification,98 _init: function (source, screenshot) {99 this.parent(source, _("Imgur Upload"));100 this.setForFeedback(true);101 this.setResident(true);102 this.connect("activated", this._onActivated.bind(this));103 this._screenshot = screenshot;104 this._upload = screenshot.imgurUpload;105 this._upload.connect("progress", (obj, bytes, total) => {106 this.update(107 _("Imgur Upload"),108 '' + Math.floor(100 * (bytes / total)) + '%'109 );110 });111 this._upload.connect("error", (obj, msg) => {112 this.update(_("Imgur Upload Failed"), msg);113 });114 this._upload.connect("done", () => {115 this.update(116 _("Imgur Upload Successful"), this._upload.responseData.link117 );118 this._updateCopyButton();119 });120 },121 _updateCopyButton: function () {122 if (!this._copyButton) {123 return;124 }125 this._copyButton.visible = this._screenshot.isImgurUploadComplete();126 },127 createBanner: function() {128 let b = this.parent();129 this._copyButton = b.addAction(_("Copy Link"), this._onCopy.bind(this));130 this._updateCopyButton();131 return b;132 },133 _onActivated: function () {134 if (this._screenshot.isImgurUploadComplete()) {135 this._screenshot.imgurOpenURL();136 } else {137 this._upload.connect("done", () => {138 this._screenshot.imgurOpenURL();139 });140 }141 },142 _onCopy: function () {143 this._screenshot.imgurCopyURL();144 },145});146const notifyScreenshot = (screenshot) => {147 let source = getSource();148 let notification = new Notification(source, screenshot);149 source.notify(notification);150}151const notifyError = (message) => {152 let source = getSource();153 let notification = new ErrorNotification(source, message);154 source.notify(notification);155}156const notifyImgurUpload = (screenshot) => {157 let source = getSource();158 let notification = new ImgurNotification(source, screenshot);159 source.notify(notification);160}161var exports = {162 notifyError,163 notifyScreenshot,164 notifyImgurUpload...
screencast.js
Source:screencast.js
1import optimize from './optimize.js';2import patch from './patch.js';34/** @typedef {{ ({ x: number; y: number; width: number; height: number; }) => Buffer; }} Crop */5/** @typedef {{ stamp: Date; buffer: Buffer; width: number; height: number; format: string; crop: Crop; }} Screenshot */67export default async function* screencast(/** @type {() => AsyncGenerator<Screenshot>} */ screenshots) {8 let frame = 0;910 /** @type {Date} */11 let _stamp;1213 /** @type {Screenshot} */14 let _screenshot;1516 // Allow passing in both a generator function and a generator object17 if (typeof screenshots === 'function') {18 screenshots = screenshots();19 }2021 for await (const screenshot of screenshots) {22 // Use worker communication for crop because the crop screenshot function itself cannot be marshalled to the worker23 if (!screenshot.crop) {24 screenshot.crop = makeWorkerCrop(screenshot.buffer, screenshot.width, screenshot.height);25 }2627 const { stamp, width, height, format, buffer, crop } = screenshot;2829 // Write header and poster on initial screenshot30 if (_stamp === undefined) {31 yield `<svg width="${width}" height="${height}" xmlns="http://www.w3.org/2000/svg">\n`;32 yield `<image width="${width}" height="${height}" href="data:image/${format};base64,${(await crop()).toString('base64')}"/>\n`;33 yield `<style>\nimage[class] { visibility: hidden; }\n@keyframes _ { to { visibility: visible; } }\n</style>\n`;3435 _stamp = stamp;36 _screenshot = screenshot;37 continue;38 }3940 // Ensure size remains constant among the screenshots41 if (width !== _screenshot.width || height !== _screenshot.height) {42 throw new Error(`Screenshot size ${width}Ã${height} differs from baseline ${_screenshot.width}Ã${_screenshot.height}.`);43 }4445 // Ensure stamp remains chronological among the screenshots46 if (stamp <= _stamp) {47 throw new Error(`Screenshot stamp ${stamp} is not chronological with respect to baseline ${_stamp}.`);48 }4950 const patches = await optimize(patch(width, height, buffer, _screenshot.buffer), crop);51 if (patches.length > 0) {52 yield `<style>._${frame} { animation: _ 0ms ${~~(stamp - _stamp)}ms forwards; }</style>\n`;5354 for (const patch of patches) {55 const { x, y, width, height } = patch;56 const buffer = await crop(patch);57 yield `<image class="_${frame}" x="${x}" y="${y}" width="${width}" height="${height}" href="data:image/${format};base64,${buffer.toString('base64')}"/>\n`;58 }5960 frame++;61 }6263 _screenshot = screenshot;64 }6566 yield '</svg>\n';67}6869const crops = {};7071function makeWorkerCrop(/** @type {Buffer} */ buffer, /** @type {number} */ width, /** @type {number} */ height) {72 return function workerCrop(/** @type {{ x: number; y: number; width: number; height: number; }} */ patch) {73 const id = Math.random();74 crops[id] = defer();75 // Issue crop request76 globalThis.worker_threads.parentPort.postMessage({ crop: true, id, buffer, width, height, patch });77 return crops[id].promise;78 }79}8081void async function () {82 try {83 // Import conditionally to make runnable in the browser84 globalThis.worker_threads = await import('worker_threads');85 // Abort self-start in case `screencast` is not used in worker context86 if (worker_threads.isMainThread) {87 return;88 }8990 const status = {};91 for await (const buffer of screencast(cache(status))) {92 worker_threads.parentPort.postMessage(buffer);93 }9495 worker_threads.parentPort.postMessage(null);96 }97 catch (error) {98 // TODO: Add support for web workers to have a web browser parallel feature99 console.log('Not attempting worker check - running in browser');100 }101}()102103// TODO: Move the non-worker cache mechanism within `screencast.js` as well104async function* cache(status) {105 const messages = [];106 let done = defer();107108 globalThis.worker_threads.parentPort.addEventListener('message', event => {109 if (event.data === null) {110 done.resolve(true);111 return;112 }113114 // Handle crop response115 if (event.data.crop === true) {116 // Access the buffer.buffer property to go Uint8Array -> Buffer117 crops[event.data.id].resolve(Buffer.from(event.data.buffer));118 delete crops[event.data.id];119 return;120 }121122 messages.push(event.data);123 status.overhead = messages.length;124 done.resolve(false);125 done = defer();126 });127128 while (messages.length > 0 || !await done.promise) {129 if (messages.length > 0) {130 yield messages.shift();131 }132 }133}134135function defer() {136 let resolve;137 let reject;138 const promise = new Promise((_resolve, _reject) => {139 resolve = _resolve;140 reject = _reject;141 });142143 return { resolve, reject, promise };
...
Request_Image.js
Source:Request_Image.js
1const Request_Base = require( './Request_Base.js' );2module.exports = class Request_Image extends Request_Base {3 bodyWidth;4 bodyHeight;5 /**6 * Get scroll width and height of the rendered page and set viewport.7 * @returns {Promise<void>}8 * @private9 */10 async _initialize() {11 this.bodyWidth = await this.page.evaluate( () => document.body.scrollWidth );12 this.bodyHeight = await this.page.evaluate( () => document.body.scrollHeight );13 this.req.logger.debug( 'Page document dimensions: ' + this.bodyWidth.toString() + ', ' + this.bodyHeight.toString() );14 await this.page.setViewport( {15 width: this.bodyWidth,16 height: this.bodyHeight17 } );18 }19 async do() {20 let _screenshot = this._getScreenShotOptions( this.req, this.bodyWidth, this.bodyHeight );21 this.req.logger.debug( 'Screenshot Options', _screenshot );22 if ( ! this.req.query.block.types.includes( 'script' ) ) {23 await this._autoScroll( this.page );24 }25 let _img = await this.page.screenshot( _screenshot );26 if ( 'base64' !== _screenshot.encoding ) {27 this.res.writeHead( 200, { 'Content-Type': 'image/' + this.type } );28 this.res.end( _img, 'binary' );29 return;30 }31 this.res.writeHead( 200, { 'Content-Type': 'text/plain' } );32 this.res.end( _img, 'utf8' );33 }34 _getScreenShotOptions( req, bodyWidth, bodyHeight ) {35 let _screenshot = req.query.screenshot36 delete _screenshot.fullPage;37 delete _screenshot.path;38 _screenshot.type = this.type;39 if ( 'undefined' !== typeof _screenshot.quality ) {40 _screenshot.quality = parseInt( _screenshot.quality );41 if ( isNaN( _screenshot.quality ) ) {42 delete _screenshot.quality43 }44 }45 if ( 'undefined' !== typeof _screenshot.omitBackground ) {46 _screenshot.omitBackground = Boolean( _screenshot.omitBackground );47 }48 if ( 'base64' !== _screenshot.encoding ) {49 delete _screenshot.encoding;50 }51 _screenshot.clip.width = parseInt( this.req.query.screenshot.clip.width );52 _screenshot.clip.height = parseInt( this.req.query.screenshot.clip.height );53 _screenshot.clip.x = parseInt( this.req.query.screenshot.clip.x ) || 0;54 _screenshot.clip.y = parseInt( this.req.query.screenshot.clip.y ) || 0;55 if ( ! ( req.query.screenshot.clip.width || req.query.screenshot.clip.height || req.query.screenshot.clip.x || req.query.screenshot.clip.y ) ) {56 _screenshot.fullPage = true;57 delete _screenshot.clip;58 return _screenshot;59 }60 let _ssx = _screenshot.clip.x;61 let _ssy = _screenshot.clip.y;62 let _maxW = bodyWidth - _ssx;63 let _maxH = bodyHeight - _ssy;64 let _ssw = _screenshot.clip.width || _maxW;65 _ssw = Math.min( _ssw, _maxW );66 let _ssh = _screenshot.clip.height || _maxH;67 _ssh = Math.min( _ssh, _maxH );68 // req.debug.log( 'screenshot height calc', _ssh, _maxH, 'body height', bodyHeight, 'y offset', _ssy, 'document height' );69 this.req.logger.debug( 'Screenshot Dimension', {70 x: _ssx,71 y: _ssy,72 w: _ssw,73 h: _ssh,74 } );75 _screenshot.clip = {76 x: _ssx,77 y: _ssy,78 width: _ssw,79 height: _ssh,80 }81 return _screenshot;82 };83 /**84 * @see https://stackoverflow.com/a/5352798485 * @param page86 * @returns {Promise<void>}87 */88 async _autoScroll(page){89 await page.evaluate(async () => {90 await new Promise((resolve, reject) => {91 let totalHeight = 0;92 let distance = 100;93 let timer = setInterval(() => {94 let scrollHeight = document.body.scrollHeight;95 window.scrollBy(0, distance);96 totalHeight += distance;97 if(totalHeight >= scrollHeight){98 clearInterval(timer);99 resolve();100 }101 }, 100);102 });103 });104 }...
generate_pdf.js
Source:generate_pdf.js
1"use strict";2Object.defineProperty(exports, "__esModule", {3 value: true4});5exports.generatePdfObservable = generatePdfObservable;6var _lodash = require("lodash");7var _operators = require("rxjs/operators");8var _pdf = require("../../common/pdf");9var _tracker = require("./tracker");10/*11 * Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one12 * or more contributor license agreements. Licensed under the Elastic License13 * 2.0; you may not use this file except in compliance with the Elastic License14 * 2.0.15 */16const getTimeRange = urlScreenshots => {17 const grouped = (0, _lodash.groupBy)(urlScreenshots.map(({18 timeRange19 }) => timeRange));20 const values = Object.values(grouped);21 if (values.length === 1) {22 return values[0][0];23 }24 return null;25};26function generatePdfObservable(reporting, logger, title, options, logo) {27 const tracker = (0, _tracker.getTracker)();28 tracker.startScreenshots();29 return reporting.getScreenshots(options).pipe((0, _operators.mergeMap)(async ({30 layout,31 metrics$,32 results33 }) => {34 metrics$.subscribe(({35 cpu,36 memory37 }) => {38 tracker.setCpuUsage(cpu);39 tracker.setMemoryUsage(memory);40 });41 tracker.endScreenshots();42 tracker.startSetup();43 const pdfOutput = new _pdf.PdfMaker(layout, logo);44 if (title) {45 const timeRange = getTimeRange(results);46 title += timeRange ? ` - ${timeRange}` : '';47 pdfOutput.setTitle(title);48 }49 tracker.endSetup();50 results.forEach(r => {51 r.screenshots.forEach(screenshot => {52 var _screenshot$title, _screenshot$descripti;53 logger.debug(`Adding image to PDF. Image size: ${screenshot.data.byteLength}`); // prettier-ignore54 tracker.startAddImage();55 tracker.endAddImage();56 pdfOutput.addImage(screenshot.data, {57 title: (_screenshot$title = screenshot.title) !== null && _screenshot$title !== void 0 ? _screenshot$title : undefined,58 description: (_screenshot$descripti = screenshot.description) !== null && _screenshot$descripti !== void 0 ? _screenshot$descripti : undefined59 });60 });61 });62 let buffer = null;63 try {64 var _buffer$byteLength, _buffer;65 tracker.startCompile();66 logger.info(`Compiling PDF using "${layout.id}" layout...`);67 pdfOutput.generate();68 tracker.endCompile();69 tracker.startGetBuffer();70 logger.debug(`Generating PDF Buffer...`);71 buffer = await pdfOutput.getBuffer();72 const byteLength = (_buffer$byteLength = (_buffer = buffer) === null || _buffer === void 0 ? void 0 : _buffer.byteLength) !== null && _buffer$byteLength !== void 0 ? _buffer$byteLength : 0;73 logger.debug(`PDF buffer byte length: ${byteLength}`);74 tracker.setByteLength(byteLength);75 tracker.endGetBuffer();76 } catch (err) {77 logger.error(`Could not generate the PDF buffer!`);78 logger.error(err);79 }80 tracker.end();81 return {82 buffer,83 warnings: results.reduce((found, current) => {84 if (current.error) {85 found.push(current.error.message);86 }87 if (current.renderErrors) {88 found.push(...current.renderErrors);89 }90 return found;91 }, [])92 };93 }));...
Using AI Code Generation
1const fs = require('fs');2const { chromium } = require('playwright');3(async () => {4 const browser = await chromium.launch({ headless: false });5 const context = await browser.newContext();6 const page = await context.newPage();7 const screenshot = await page._screenshot();8 fs.writeFileSync('screenshot.png', screenshot);9 await browser.close();10})();11const fs = require('fs');12const { chromium } = require('playwright');13(async () => {14 const browser = await chromium.launch({ headless: false });15 const context = await browser.newContext();16 const page = await context.newPage();17 await page.setViewportSize({ width: 800, height: 600 });18 const screenshot = await page._screenshot({ fullPage: true });19 fs.writeFileSync('screenshot.png', screenshot);20 await browser.close();21})();
Using AI Code Generation
1const path = require('path');2const { chromium } = require('playwright');3(async () => {4 const browser = await chromium.launch({ headless: false });5 const context = await browser.newContext();6 await page._screenshot({7 path: path.join(__dirname, 'screenshot.png'),8 });9 await browser.close();10})();11{12 "scripts": {13 },14 "dependencies": {15 }16}17const path = require('path');18const { chromium } = require('playwright');19(async () => {20 const browser = await chromium.launch({ headless: false });21 const context = await browser.newContext();22 await page.screenshot({23 path: path.join(__dirname, 'screenshot.png'),24 });25 await browser.close();26})();27const path = require('path');28const puppeteer = require('puppeteer');29(async () => {30 const browser = await puppeteer.launch({ headless: false });31 const page = await browser.newPage();
Using AI Code Generation
1const { chromium } = require('playwright');2(async () => {3 const browser = await chromium.launch();4 const page = await browser.newPage();5 await page.screenshot({ path: 'example.png' });6 await browser.close();7})();8const { chromium } = require(require.resolve('playwright', { paths: [process.cwd()] }));9(async () => {10 const browser = await chromium.launch();11 const page = await browser.newPage();12 await page.screenshot({ path: 'example.png' });13 await browser.close();14})();15The require.resolve() function takes two parameters:16const utils = require(require.resolve('./utils', { paths: [process.cwd()] }));17utils.printHello();
Using AI Code Generation
1const { chromium } = require('playwright');2(async () => {3 const browser = await chromium.launch();4 const context = await browser.newContext();5 const page = await context.newPage();6 await page._screenshot({ path: 'example.png' });7 await browser.close();8})();
Using AI Code Generation
1const { _screenshot } = require('playwright/lib/server/chromium/crPage');2const { chromium } = require('playwright');3(async () => {4 const browser = await chromium.launch();5 const context = await browser.newContext();6 const page = await context.newPage();7 const screenshot = await _screenshot.call(page, {8 });9 require('fs').writeFileSync('screenshot.png', screenshot);10 await browser.close();11})();12You can also save the screenshot using the page.screenshot() method:13const { chromium } = require('playwright');14(async () => {15 const browser = await chromium.launch();16 const context = await browser.newContext();17 const page = await context.newPage();18 await page.screenshot({ path: 'screenshot.png' });19 await browser.close();20})();21You can get the browser context of a page using the page.context() method:22const { chromium } = require('playwright');23(async () => {24 const browser = await chromium.launch();25 const context = await browser.newContext();26 const page = await context.newPage();27 const browserContext = page.context();28 await browser.close();29})();30You can get the browser of a page using the page.browser() method:31const { chromium } = require('playwright');32(async () => {33 const browser = await chromium.launch();34 const context = await browser.newContext();35 const page = await context.newPage();36 const browserInstance = page.browser();37 await browser.close();38})();39You can get the frame of a page using the page.mainFrame() method:40const { chromium } = require('playwright');41(async () => {42 const browser = await chromium.launch();43 const context = await browser.newContext();44 const page = await context.newPage();
Using AI Code Generation
1const { chromium } = require('playwright');2(async () => {3 const browser = await chromium.launch();4 const page = await browser.newPage();5 const screenshot = await page._screenshot();6 console.log(screenshot);7 await browser.close();8})();9 at CDPSession.send (C:\Users\Neha\Desktop\New folder\New folder10 at Page._screenshot (C:\Users\Neha\Desktop\New folder\New folder11 at processTicksAndRejections (internal/process/task_queues.js:97:5)12 at async Object.<anonymous> (C:\Users\Neha\Desktop\New folder\New folder13 at async Promise.all (index 0)14 at async Promise.all (index 0)15 at async Page.<anonymous> (C:\Users\Neha\Desktop\New folder\New folder16 at async Promise.all (index 0)17 at async Page.<anonymous> (C:\Users\Neha\Desktop\New folder\New folder
Using AI Code Generation
1const playwright = require('playwright');2const { _screenshot } = require('playwright/lib/server/supplements/recorder/recorderSupplement.js');3(async () => {4 const browser = await playwright.chromium.launch({ headless: false });5 const context = await browser.newContext();6 const page = await context.newPage();7 const screenshot = await _screenshot(page, { clip: { x: 0, y: 0, width: 100, height: 100 } });8 console.log(screenshot);9 await browser.close();10})();11const playwright = require('playwright');12const { _screenshot } = require('playwright/lib/server/supplements/recorder/recorderSupplement.js');13(async () => {14 const browser = await playwright.chromium.launch({ headless: false });15 const context = await browser.newContext();16 const page = await context.newPage();17 const screenshot = await _screenshot(page, { clip: { x: 0, y: 0, width: 100, height: 100 } });18 console.log(screenshot);19 await browser.close();20})();21const playwright = require('playwright');22const { _screenshot } = require('playwright/lib/server/supplements/recorder/recorderSupplement.js');23(async () => {24 const browser = await playwright.chromium.launch({ headless: false });25 const context = await browser.newContext();26 const page = await context.newPage();27 const screenshot = await _screenshot(page, { clip: { x: 0, y: 0, width: 100, height: 100 } });28 console.log(screenshot);29 await browser.close();30})();31const playwright = require('playwright');32const { _screenshot } = require('playwright/lib/server/supplements/recorder/recorderSupplement.js');33(async () => {34 const browser = await playwright.chromium.launch({ headless: false });
Using AI Code Generation
1const { _screenshot } = require('playwright/lib/server/chromium/crBrowser');2(async () => {3 const browser = await chromium.launch({4 });5 const page = await browser.newPage();6 await page.screenshot({ path: 'google.png' });7 await browser.close();8})();9(async () => {10 const browser = await chromium.launch({11 });12 const page = await browser.newPage();13 const screenshot = await _screenshot.call(page, { type: 'png', fullPage:
Using AI Code Generation
1const fs = require('fs');2const { chromium } = require('playwright');3(async () => {4 const browser = await chromium.launch({5 });6 const context = await browser.newContext();7 const page = await context.newPage();8 const screenshot = await page._screenshot();9 fs.writeFileSync('screenshot.png', screenshot);10 await browser.close();11})();12const fs = require('fs');13const { chromium } = require('playwright');14(async () => {15 const browser = await chromium.launch({16 });17 const context = await browser.newContext();18 const page = await context.newPage();19 const screenshot = fs.readFileSync('screenshot.png');20 await page._screenshot({ path: 'screenshot2.png', buffer: screenshot });21 await browser.close();22})();23In the above code, we have imported fs module to write the screenshot buffer to a file
LambdaTest’s Playwright tutorial will give you a broader idea about the Playwright automation framework, its unique features, and use cases with examples to exceed your understanding of Playwright testing. This tutorial will give A to Z guidance, from installing the Playwright framework to some best practices and advanced concepts.
Get 100 minutes of automation test minutes FREE!!