mirror of
https://github.com/puppeteer/puppeteer
synced 2024-06-14 14:02:48 +00:00
feat(ElementHandle): implement ElementHandle.contentFrame() (#2094)
This patch adds ElementHandle.contentFrame() method that allows to get a reference to the Frame owned by the iframe. Fixes #433.
This commit is contained in:
parent
e2b96df4d7
commit
223b59254c
@ -187,6 +187,7 @@
|
||||
* [elementHandle.asElement()](#elementhandleaselement)
|
||||
* [elementHandle.boundingBox()](#elementhandleboundingbox)
|
||||
* [elementHandle.click([options])](#elementhandleclickoptions)
|
||||
* [elementHandle.contentFrame()](#elementhandlecontentframe)
|
||||
* [elementHandle.dispose()](#elementhandledispose)
|
||||
* [elementHandle.executionContext()](#elementhandleexecutioncontext)
|
||||
* [elementHandle.focus()](#elementhandlefocus)
|
||||
@ -2187,6 +2188,9 @@ This method returns the bounding box of the element (relative to the main frame)
|
||||
This method scrolls element into view if needed, and then uses [page.mouse](#pagemouse) to click in the center of the element.
|
||||
If the element is detached from DOM, the method throws an error.
|
||||
|
||||
#### elementHandle.contentFrame()
|
||||
- returns: <[Promise]<?[Frame]>> Resolves to the content frame for element handles referencing iframe nodes, or null otherwise
|
||||
|
||||
#### elementHandle.dispose()
|
||||
- returns: <[Promise]> Promise which resolves when the element handle is successfully disposed.
|
||||
|
||||
|
@ -23,12 +23,14 @@ class ElementHandle extends JSHandle {
|
||||
* @param {!Puppeteer.CDPSession} client
|
||||
* @param {!Object} remoteObject
|
||||
* @param {!Puppeteer.Page} page
|
||||
* @param {!Puppeteer.FrameManager} frameManager
|
||||
*/
|
||||
constructor(context, client, remoteObject, page) {
|
||||
constructor(context, client, remoteObject, page, frameManager) {
|
||||
super(context, client, remoteObject);
|
||||
this._client = client;
|
||||
this._remoteObject = remoteObject;
|
||||
this._page = page;
|
||||
this._frameManager = frameManager;
|
||||
this._disposed = false;
|
||||
}
|
||||
|
||||
@ -40,6 +42,18 @@ class ElementHandle extends JSHandle {
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return {!Promise<?Puppeteer.Frame>}
|
||||
*/
|
||||
async contentFrame() {
|
||||
const nodeInfo = await this._client.send('DOM.describeNode', {
|
||||
objectId: this._remoteObject.objectId
|
||||
});
|
||||
if (typeof nodeInfo.node.frameId !== 'string')
|
||||
return null;
|
||||
return this._frameManager.frame(nodeInfo.node.frameId);
|
||||
}
|
||||
|
||||
async _scrollIntoViewIfNeeded() {
|
||||
const error = await this.executionContext().evaluate(element => {
|
||||
if (!element.isConnected)
|
||||
|
@ -196,7 +196,7 @@ class FrameManager extends EventEmitter {
|
||||
const context = this._contextIdToContext.get(contextId);
|
||||
console.assert(context, 'INTERNAL ERROR: missing context with id = ' + contextId);
|
||||
if (remoteObject.subtype === 'node')
|
||||
return new ElementHandle(context, this._client, remoteObject, this._page);
|
||||
return new ElementHandle(context, this._client, remoteObject, this._page, this);
|
||||
return new JSHandle(context, this._client, remoteObject);
|
||||
}
|
||||
|
||||
|
10
test/test.js
10
test/test.js
@ -2039,6 +2039,16 @@ describe('Page', function() {
|
||||
});
|
||||
});
|
||||
|
||||
describe('ElementHandle.contentFrame', function() {
|
||||
it('should work', async({page,server}) => {
|
||||
await page.goto(server.EMPTY_PAGE);
|
||||
await FrameUtils.attachFrame(page, 'frame1', server.EMPTY_PAGE);
|
||||
const elementHandle = await page.$('#frame1');
|
||||
const frame = await elementHandle.contentFrame();
|
||||
expect(frame).toBe(page.frames()[1]);
|
||||
});
|
||||
});
|
||||
|
||||
describe('ElementHandle.click', function() {
|
||||
it('should work', async({page, server}) => {
|
||||
await page.goto(server.PREFIX + '/input/button.html');
|
||||
|
Loading…
Reference in New Issue
Block a user