Skip to content

Commit

Permalink
update: resize using CDP setWindowBounds (#8169)
Browse files Browse the repository at this point in the history
<!--
Thank you for your contribution.

Before making a PR, please read our contributing guidelines at

https://github.com/DevExpress/testcafe/blob/master/CONTRIBUTING.md#code-contribution

We recommend creating a *draft* PR, so that you can mark it as 'ready
for review' when you are done.
-->

## Purpose
_Describe the problem you want to address or the feature you want to
implement._

## Approach
_Describe how your changes address the issue or implement the desired
functionality in as much detail as possible._

## References
closes #8157

## Pre-Merge TODO
- [x] Write tests for your proposed changes
- [x] Make sure that existing tests do not fail

---------

Co-authored-by: Bayheck <adil.rakhaliyev@devexpress.com>
  • Loading branch information
Bayheck and Bayheck authored Apr 29, 2024
1 parent 886a267 commit 5d5bf6f
Show file tree
Hide file tree
Showing 9 changed files with 101 additions and 6 deletions.
8 changes: 8 additions & 0 deletions src/browser/provider/built-in/dedicated/base.js
Original file line number Diff line number Diff line change
Expand Up @@ -105,6 +105,14 @@ export default {
await this.resizeWindow(browserId, maximumSize.width, maximumSize.height, maximumSize.width, maximumSize.height);
},

async maximizeWindowNativeAutomation (browserId) {
await this.maximizeWindowNativeAutomation(browserId);
},

async resizeWindowNativeAutomation (browserId, width, height, currentWidth, currentHeight) {
await this.resizeBounds(browserId, width, height, currentWidth, currentHeight);
},

async closeBrowserChildWindow (browserId, windowId) {
const runtimeInfo = this.openedBrowsers[browserId];
const browserClient = this._getBrowserProtocolClient(runtimeInfo);
Expand Down
49 changes: 49 additions & 0 deletions src/browser/provider/built-in/dedicated/chrome/cdp-client/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -232,6 +232,55 @@ export class BrowserClient {
}
}

public async maximizeWindowNativeAutomation (): Promise<void> {
const target = await getFirstTab(this._port);
const client = await this.getActiveClient();

if (client) {
const windowParams = await client.Browser.getWindowForTarget({ targetId: target.id });

await client.Browser.setWindowBounds({ windowId: windowParams.windowId, bounds: { windowState: 'maximized' } });
}
}

public async resizeBounds (newDimensions: Size): Promise<void> {
const { viewportSize, config } = this._runtimeInfo;

let nonClientWidth = 0;
let nonClientHeight = 0;

if (viewportSize.outerWidth && viewportSize.outerHeight) {
nonClientWidth = viewportSize.outerWidth - viewportSize.width;
nonClientHeight = viewportSize.outerHeight - viewportSize.height;
}

const target = await getFirstTab(this._port);
const client = await this.getActiveClient();

if (client) {
await this._setDeviceMetricsOverride(client, newDimensions.width, newDimensions.height, 1, config.mobile);

const windowParams = await client.Browser.getWindowForTarget({ targetId: target.id });

if (windowParams.bounds.windowState !== 'normal') {
await client.Browser.setWindowBounds({
windowId: windowParams.windowId,
bounds: {
windowState: 'normal',
},
});
}

await client.Browser.setWindowBounds({
windowId: windowParams.windowId,
bounds: {
width: newDimensions.width + nonClientWidth,
height: newDimensions.height + nonClientHeight,
},
});
}
}

public isHeadlessTab (): boolean {
return !!this._parentTarget && this._config.headless;
}
Expand Down
12 changes: 12 additions & 0 deletions src/browser/provider/built-in/dedicated/chrome/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -144,6 +144,18 @@ export default {
await runtimeInfo.browserClient.resizeWindow({ width, height });
},

async maximizeWindowNativeAutomation (browserId) {
const { browserClient } = this.openedBrowsers[browserId];

await browserClient.maximizeWindowNativeAutomation();
},

async resizeBounds (browserId, width, height, currentWidth, currentHeight) {
const { browserClient } = this.openedBrowsers[browserId];

await browserClient.resizeBounds({ width, height, currentWidth, currentHeight });
},

async startCapturingVideo (browserId) {
const { browserClient } = this.openedBrowsers[browserId];

Expand Down
2 changes: 2 additions & 0 deletions src/browser/provider/built-in/dedicated/chrome/interfaces.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@ import { BrowserClient } from './cdp-client';
export interface Size {
width: number;
height: number;
outerWidth?: number;
outerHeight?: number;
}

export interface Config {
Expand Down
11 changes: 9 additions & 2 deletions src/browser/provider/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -355,11 +355,15 @@ export default class BrowserProvider {
return await this.plugin.isValidBrowserName(browserName);
}

public async resizeWindow (browserId: string, width: number, height: number, currentWidth: number, currentHeight: number): Promise<void> {
public async resizeWindow (browserId: string, width: number, height: number, currentWidth: number, currentHeight: number, isNativeAutomation: boolean): Promise<void> {
const canUseDefaultWindowActions = await this.canUseDefaultWindowActions(browserId);
const customActionsInfo = await this.hasCustomActionForBrowser(browserId);
const hasCustomResizeWindow = customActionsInfo.hasResizeWindow;

if (canUseDefaultWindowActions && !hasCustomResizeWindow && isNativeAutomation) {
await this.plugin.resizeWindowNativeAutomation(browserId, width, height, currentWidth, currentHeight);
return;
}

if (canUseDefaultWindowActions && !hasCustomResizeWindow) {
await this._resizeLocalBrowserWindow(browserId, width, height, currentWidth, currentHeight);
Expand All @@ -381,11 +385,14 @@ export default class BrowserProvider {
return await this.plugin.canResizeWindowToDimensions(browserId, width, height);
}

public async maximizeWindow (browserId: string): Promise<void> {
public async maximizeWindow (browserId: string, isNativeAutomation: boolean): Promise<void> {
const canUseDefaultWindowActions = await this.canUseDefaultWindowActions(browserId);
const customActionsInfo = await this.hasCustomActionForBrowser(browserId);
const hasCustomMaximizeWindow = customActionsInfo.hasMaximizeWindow;

if (canUseDefaultWindowActions && !hasCustomMaximizeWindow && isNativeAutomation)
return await this.plugin.maximizeWindowNativeAutomation(browserId);

if (canUseDefaultWindowActions && !hasCustomMaximizeWindow)
return await this._maximizeLocalBrowserWindow(browserId);

Expand Down
7 changes: 4 additions & 3 deletions src/test-run/browser-manipulation-queue.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,12 +5,13 @@ import WARNING_MESSAGE from '../notifications/warning-message';
import { WindowDimensionsOverflowError } from '../errors/test-run/';

export default class BrowserManipulationQueue {
constructor (browserConnection, screenshotCapturer, warningLog) {
constructor (browserConnection, screenshotCapturer, warningLog, isNativeAutomation) {
this.commands = [];
this.browserId = browserConnection.id;
this.browserProvider = browserConnection.provider;
this.screenshotCapturer = screenshotCapturer;
this.warningLog = warningLog;
this.isNativeAutomation = isNativeAutomation;
}

async _resizeWindow (width, height, currentWidth, currentHeight) {
Expand All @@ -20,7 +21,7 @@ export default class BrowserManipulationQueue {
throw new WindowDimensionsOverflowError();

try {
return await this.browserProvider.resizeWindow(this.browserId, width, height, currentWidth, currentHeight);
return await this.browserProvider.resizeWindow(this.browserId, width, height, currentWidth, currentHeight, this.isNativeAutomation);
}
catch (err) {
this.warningLog.addWarning(WARNING_MESSAGE.resizeError, err.message);
Expand All @@ -40,7 +41,7 @@ export default class BrowserManipulationQueue {

async _maximizeWindow () {
try {
return await this.browserProvider.maximizeWindow(this.browserId);
return await this.browserProvider.maximizeWindow(this.browserId, this.isNativeAutomation);
}
catch (err) {
this.warningLog.addWarning(WARNING_MESSAGE.maximizeError, err.message);
Expand Down
2 changes: 1 addition & 1 deletion src/test-run/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -338,7 +338,7 @@ export default class TestRun extends AsyncEventEmitter {
this.disableDebugBreakpoints = false;
this.debugReporterPluginHost = new ReporterPluginHost({ noColors: false });

this.browserManipulationQueue = new BrowserManipulationQueue(browserConnection, screenshotCapturer, this.warningLog);
this.browserManipulationQueue = new BrowserManipulationQueue(browserConnection, screenshotCapturer, this.warningLog, nativeAutomation);

this.debugLog = new TestRunDebugLog(this.browserConnection.userAgent);

Expand Down
4 changes: 4 additions & 0 deletions test/functional/fixtures/api/es-next/resize-window/test.js
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,10 @@ describe('[API] Resize window actions', function () {
errorInEachBrowserContains(errs, '> 76 | await t.resizeWindow(500, 500);', 0);
});
});

it('Should resize the window after maximizeWindow', function () {
return runTests('./testcafe-fixtures/resize-window-test.js', 'Resize the window after maximizeWindow', { only: 'chrome' });
});
});

describe('t.resizeWindowToFitDevice', function () {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -88,3 +88,15 @@ test('Too big size', async t => {

await t.resizeWindow(hugeWidth, hugeHeight);
});

test('Resize the window after maximizeWindow', async t => {
await t.maximizeWindow();

expect(await getWindowWidth()).to.be.at.least(640);
expect(await getWindowHeight()).to.be.at.least(480);

await t.resizeWindow(640, 480);

expect(await getWindowWidth()).equals(640);
expect(await getWindowHeight()).equals(480);
});

0 comments on commit 5d5bf6f

Please sign in to comment.