mirror of
https://github.com/finos/SymphonyElectron.git
synced 2024-11-21 16:38:41 -06:00
bugfix/rtc-revert (#1377)
* Revert "SDA-3616 - Upgrade ffi-napi and ref-napi (#1364)" This reverts commit2fcd7cee60
. * Revert "Initial implementation (#1363)" This reverts commit08198aa86b
. * Revert "Initial implementation (#1362)" This reverts commit41f0ca4e7e
.
This commit is contained in:
parent
23f9fadbfa
commit
e11097d258
89
package-lock.json
generated
89
package-lock.json
generated
@ -27536,9 +27536,9 @@
|
||||
}
|
||||
},
|
||||
"@types/ffi-napi": {
|
||||
"version": "4.0.3",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/@types/ffi-napi/-/ffi-napi-4.0.3.tgz",
|
||||
"integrity": "sha1-LwFjaBmOTG+7CmlQG2fNi+ycw7c=",
|
||||
"version": "2.4.1",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/@types/ffi-napi/-/ffi-napi-2.4.1.tgz",
|
||||
"integrity": "sha1-4o7DOZjkFgWxeSlE44eY3uhhIiE=",
|
||||
"dev": true,
|
||||
"requires": {
|
||||
"@types/node": "*",
|
||||
@ -27709,18 +27709,18 @@
|
||||
}
|
||||
},
|
||||
"@types/ref-napi": {
|
||||
"version": "3.0.4",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/@types/ref-napi/-/ref-napi-3.0.4.tgz",
|
||||
"integrity": "sha1-1+3AY7JEyFdnhnzhFn7C1wUXKKE=",
|
||||
"version": "1.4.0",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/@types/ref-napi/-/ref-napi-1.4.0.tgz",
|
||||
"integrity": "sha1-hg/a55MZme88pPI/U3IAU6lh4UM=",
|
||||
"dev": true,
|
||||
"requires": {
|
||||
"@types/node": "*"
|
||||
}
|
||||
},
|
||||
"@types/ref-struct-di": {
|
||||
"version": "1.1.6",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/@types/ref-struct-di/-/ref-struct-di-1.1.6.tgz",
|
||||
"integrity": "sha1-l3V1OyS6W/JI3WbXnU/bfOvvbpU=",
|
||||
"version": "1.1.0",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/@types/ref-struct-di/-/ref-struct-di-1.1.0.tgz",
|
||||
"integrity": "sha1-TnogyLLyWm5LPLSg1hWDW2GrjYQ=",
|
||||
"dev": true,
|
||||
"requires": {
|
||||
"@types/ref-napi": "*"
|
||||
@ -29315,7 +29315,6 @@
|
||||
"version": "1.5.0",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/bindings/-/bindings-1.5.0.tgz",
|
||||
"integrity": "sha1-EDU8npRTNLwFEabZCzj7x8nFBN8=",
|
||||
"optional": true,
|
||||
"requires": {
|
||||
"file-uri-to-path": "1.0.0"
|
||||
}
|
||||
@ -33391,16 +33390,34 @@
|
||||
}
|
||||
},
|
||||
"ffi-napi": {
|
||||
"version": "4.0.3",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/ffi-napi/-/ffi-napi-4.0.3.tgz",
|
||||
"integrity": "sha1-J6jUKo6pOEVxVIlcWXYfvxoQ9EE=",
|
||||
"version": "3.0.0",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/ffi-napi/-/ffi-napi-3.0.0.tgz",
|
||||
"integrity": "sha1-uF6ODvlDRkbzQhUDPCXOctOOYdY=",
|
||||
"requires": {
|
||||
"debug": "^4.1.1",
|
||||
"get-uv-event-loop-napi-h": "^1.0.5",
|
||||
"node-addon-api": "^3.0.0",
|
||||
"node-addon-api": "^2.0.0",
|
||||
"node-gyp-build": "^4.2.1",
|
||||
"ref-napi": "^2.0.1 || ^3.0.2",
|
||||
"ref-napi": "^2.0.1",
|
||||
"ref-struct-di": "^1.1.0"
|
||||
},
|
||||
"dependencies": {
|
||||
"node-addon-api": {
|
||||
"version": "2.0.2",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/node-addon-api/-/node-addon-api-2.0.2.tgz",
|
||||
"integrity": "sha1-Qyz6gpYs5JSxMunXKhWyn3H/XTI="
|
||||
},
|
||||
"ref-napi": {
|
||||
"version": "2.1.2",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/ref-napi/-/ref-napi-2.1.2.tgz",
|
||||
"integrity": "sha1-WYYGnXsOqD4f70gjmivXUxjONBs=",
|
||||
"requires": {
|
||||
"debug": "^4.1.1",
|
||||
"get-symbol-from-current-process-h": "^1.0.2",
|
||||
"node-addon-api": "^2.0.0",
|
||||
"node-gyp-build": "^4.2.1"
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"figures": {
|
||||
@ -33429,8 +33446,7 @@
|
||||
"file-uri-to-path": {
|
||||
"version": "1.0.0",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/file-uri-to-path/-/file-uri-to-path-1.0.0.tgz",
|
||||
"integrity": "sha1-VTp7hEb/b2hDWcRF8eN6BdrMM90=",
|
||||
"optional": true
|
||||
"integrity": "sha1-VTp7hEb/b2hDWcRF8eN6BdrMM90="
|
||||
},
|
||||
"file-url": {
|
||||
"version": "1.1.0",
|
||||
@ -38615,9 +38631,9 @@
|
||||
}
|
||||
},
|
||||
"node-addon-api": {
|
||||
"version": "3.2.1",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/node-addon-api/-/node-addon-api-3.2.1.tgz",
|
||||
"integrity": "sha1-gTJeCiEXeJwBKNq2Xn448HzroWE="
|
||||
"version": "4.3.0",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/node-addon-api/-/node-addon-api-4.3.0.tgz",
|
||||
"integrity": "sha1-UqGgtHUZPgko6Y4EJqDRJUeCt38="
|
||||
},
|
||||
"node-api-version": {
|
||||
"version": "0.1.4",
|
||||
@ -40700,14 +40716,33 @@
|
||||
}
|
||||
},
|
||||
"ref-napi": {
|
||||
"version": "3.0.3",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/ref-napi/-/ref-napi-3.0.3.tgz",
|
||||
"integrity": "sha1-4lm/wruvs+Fp6M2bpJA33QA5ayI=",
|
||||
"version": "1.4.3",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/ref-napi/-/ref-napi-1.4.3.tgz",
|
||||
"integrity": "sha1-yUlaRnChhlWz1FRyKEzB/awD4xQ=",
|
||||
"requires": {
|
||||
"debug": "^4.1.1",
|
||||
"get-symbol-from-current-process-h": "^1.0.2",
|
||||
"node-addon-api": "^3.0.0",
|
||||
"node-gyp-build": "^4.2.1"
|
||||
"bindings": "^1.3.0",
|
||||
"debug": "^3.1.0",
|
||||
"node-addon-api": "^2.0.0"
|
||||
},
|
||||
"dependencies": {
|
||||
"debug": {
|
||||
"version": "3.2.7",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/debug/-/debug-3.2.7.tgz",
|
||||
"integrity": "sha1-clgLfpFF+zm2Z2+cXl+xALk0F5o=",
|
||||
"requires": {
|
||||
"ms": "^2.1.1"
|
||||
}
|
||||
},
|
||||
"ms": {
|
||||
"version": "2.1.3",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/ms/-/ms-2.1.3.tgz",
|
||||
"integrity": "sha1-V0yBOM4dK1hh8LRFedut1gxmFbI="
|
||||
},
|
||||
"node-addon-api": {
|
||||
"version": "2.0.2",
|
||||
"resolved": "https://repo.symphony.com/artifactory/api/npm/npm-virtual-dev/node-addon-api/-/node-addon-api-2.0.2.tgz",
|
||||
"integrity": "sha1-Qyz6gpYs5JSxMunXKhWyn3H/XTI="
|
||||
}
|
||||
}
|
||||
},
|
||||
"ref-struct-di": {
|
||||
|
@ -113,13 +113,13 @@
|
||||
"devDependencies": {
|
||||
"@types/cheerio": "^0.22.22",
|
||||
"@types/enzyme": "^3.10.7",
|
||||
"@types/ffi-napi": "4.0.3",
|
||||
"@types/ffi-napi": "2.4.1",
|
||||
"@types/fs-extra": "^8.1.1",
|
||||
"@types/jest": "23.3.12",
|
||||
"@types/node": "^12.12.43",
|
||||
"@types/react": "16.8.3",
|
||||
"@types/react-dom": "16.0.9",
|
||||
"@types/ref-napi": "3.0.4",
|
||||
"@types/ref-napi": "1.4.0",
|
||||
"@types/rimraf": "^3.0.0",
|
||||
"ava": "2.4.0",
|
||||
"browserify": "16.5.1",
|
||||
@ -164,12 +164,12 @@
|
||||
"electron-fetch": "1.4.0",
|
||||
"electron-log": "4.0.7",
|
||||
"electron-spellchecker": "git+https://github.com/finos/electron-spellchecker.git#v2.3.6",
|
||||
"ffi-napi": "4.0.3",
|
||||
"ffi-napi": "3.0.0",
|
||||
"filesize": "6.1.0",
|
||||
"lazy-brush": "^1.0.1",
|
||||
"react": "16.13.0",
|
||||
"react-dom": "16.13.0",
|
||||
"ref-napi": "3.0.3",
|
||||
"ref-napi": "1.4.3",
|
||||
"rimraf": "^3.0.2",
|
||||
"save-svg-as-png": "^1.4.17",
|
||||
"shell-path": "2.1.0"
|
||||
|
@ -1,159 +0,0 @@
|
||||
import { getContentWindowHandle } from '../src/app/hwnd-handler';
|
||||
|
||||
jest.mock('../src/common/env', () => {
|
||||
return {
|
||||
isWindowsOS: true,
|
||||
isLinux: false,
|
||||
isMac: false,
|
||||
};
|
||||
});
|
||||
|
||||
const mockFindWindowExA = jest.fn();
|
||||
const mockGetWindowRect = jest.fn();
|
||||
|
||||
jest.mock('ffi-napi', () => {
|
||||
return {
|
||||
Library: jest.fn(() => {
|
||||
return {
|
||||
FindWindowExA: mockFindWindowExA,
|
||||
GetWindowRect: mockGetWindowRect,
|
||||
};
|
||||
}),
|
||||
};
|
||||
});
|
||||
|
||||
function writeRect(
|
||||
buffer: Buffer,
|
||||
left: number,
|
||||
top: number,
|
||||
right: number,
|
||||
bottom: number,
|
||||
) {
|
||||
buffer.writeInt32LE(left, 0);
|
||||
buffer.writeInt32LE(top, 4);
|
||||
buffer.writeInt32LE(right, 8);
|
||||
buffer.writeInt32LE(bottom, 12);
|
||||
}
|
||||
|
||||
describe('hwnd handler', () => {
|
||||
beforeEach(() => {
|
||||
jest.clearAllMocks().resetModules();
|
||||
|
||||
mockGetWindowRect.mockImplementation((_hwnd: bigint, _rect: Buffer) => {
|
||||
return 0;
|
||||
});
|
||||
mockFindWindowExA.mockImplementation(() => {
|
||||
return 0;
|
||||
});
|
||||
});
|
||||
|
||||
it('not using windows', () => {
|
||||
jest.mock('../src/common/env', () => {
|
||||
return {
|
||||
isWindowsOS: false,
|
||||
isLinux: true,
|
||||
isMac: false,
|
||||
};
|
||||
});
|
||||
const { getContentWindowHandle } = require('../src/app/hwnd-handler');
|
||||
const parent = Buffer.from('hwnd', 'utf8');
|
||||
const hwnd = getContentWindowHandle(parent);
|
||||
expect(hwnd).toBe(parent);
|
||||
});
|
||||
|
||||
it('unexpected buffer size', () => {
|
||||
const parent = Buffer.from('hwnd', 'utf8');
|
||||
const hwnd = getContentWindowHandle(parent);
|
||||
expect(hwnd).toBe(parent);
|
||||
});
|
||||
|
||||
it('no rect found for parent window', () => {
|
||||
const parent = Buffer.from('validhwnd', 'utf8');
|
||||
const hwnd = getContentWindowHandle(parent);
|
||||
expect(hwnd).toBe(parent);
|
||||
});
|
||||
|
||||
it('no child window found', () => {
|
||||
mockGetWindowRect.mockImplementationOnce((_hwnd, rect) => {
|
||||
writeRect(rect, 10, 10, 100, 100);
|
||||
return 1;
|
||||
});
|
||||
|
||||
const parent = Buffer.from('validhwnd', 'utf8');
|
||||
const hwnd = getContentWindowHandle(parent);
|
||||
|
||||
expect(mockGetWindowRect).toBeCalledTimes(1);
|
||||
expect(mockFindWindowExA).toBeCalledTimes(1);
|
||||
expect(hwnd).toBe(parent);
|
||||
});
|
||||
|
||||
it('matching child window found', () => {
|
||||
mockGetWindowRect.mockImplementationOnce((_hwnd, rect) => {
|
||||
writeRect(rect, 10, 10, 100, 100);
|
||||
return 1;
|
||||
});
|
||||
mockGetWindowRect.mockImplementationOnce((_hwnd, rect) => {
|
||||
writeRect(rect, 10, 20, 100, 100);
|
||||
return 1;
|
||||
});
|
||||
mockFindWindowExA.mockImplementationOnce(() => {
|
||||
return 4711;
|
||||
});
|
||||
|
||||
const parent = Buffer.from('validhwnd', 'utf8');
|
||||
const hwnd = getContentWindowHandle(parent);
|
||||
|
||||
expect(mockGetWindowRect).toBeCalledTimes(2);
|
||||
expect(mockFindWindowExA).toBeCalledTimes(1);
|
||||
expect(hwnd.readInt32LE(0)).toBe(4711);
|
||||
});
|
||||
|
||||
it('matching child window found second', () => {
|
||||
mockGetWindowRect.mockImplementationOnce((_hwnd, rect) => {
|
||||
writeRect(rect, 10, 10, 100, 100);
|
||||
return 1;
|
||||
});
|
||||
mockGetWindowRect.mockImplementationOnce((_hwnd, rect) => {
|
||||
writeRect(rect, 100, 10, 100, 100);
|
||||
return 1;
|
||||
});
|
||||
mockGetWindowRect.mockImplementationOnce((_hwnd, rect) => {
|
||||
writeRect(rect, 10, 20, 100, 100);
|
||||
return 1;
|
||||
});
|
||||
mockFindWindowExA.mockImplementationOnce(() => {
|
||||
return 4711;
|
||||
});
|
||||
mockFindWindowExA.mockImplementationOnce(() => {
|
||||
return 42;
|
||||
});
|
||||
|
||||
const parent = Buffer.from('validhwnd', 'utf8');
|
||||
const hwnd = getContentWindowHandle(parent);
|
||||
|
||||
expect(mockGetWindowRect).toBeCalledTimes(3);
|
||||
expect(mockFindWindowExA).toBeCalledTimes(2);
|
||||
expect(hwnd.readInt32LE(0)).toBe(42);
|
||||
});
|
||||
|
||||
it('no matching child window found', () => {
|
||||
mockGetWindowRect.mockImplementationOnce((_hwnd, rect) => {
|
||||
writeRect(rect, 10, 10, 100, 100);
|
||||
return 1;
|
||||
});
|
||||
mockGetWindowRect.mockImplementationOnce((_hwnd, rect) => {
|
||||
writeRect(rect, 10, 10, 100, 100);
|
||||
return 1;
|
||||
});
|
||||
mockFindWindowExA.mockImplementationOnce(() => {
|
||||
return 4711;
|
||||
});
|
||||
|
||||
const parent = Buffer.from('validhwnd', 'utf8');
|
||||
const hwnd = getContentWindowHandle(parent);
|
||||
|
||||
expect(mockGetWindowRect).toBeCalledTimes(2);
|
||||
expect(mockFindWindowExA).toBeCalledTimes(2);
|
||||
expect(hwnd).toBe(parent);
|
||||
});
|
||||
});
|
@ -58,7 +58,6 @@ jest.mock('../src/app/window-handler', () => {
|
||||
jest.mock('../src/app/window-utils', () => {
|
||||
return {
|
||||
downloadManagerAction: jest.fn(),
|
||||
getWindowByName: jest.fn(),
|
||||
isValidWindow: jest.fn(() => true),
|
||||
sanitize: jest.fn(),
|
||||
setDataUrl: jest.fn(),
|
||||
@ -472,35 +471,17 @@ describe('main api handler', () => {
|
||||
});
|
||||
|
||||
it('should call `getNativeWindowHandle` correctly', () => {
|
||||
const windows = {
|
||||
main: {
|
||||
getNativeWindowHandle: jest.fn(),
|
||||
},
|
||||
popout1: {
|
||||
getNativeWindowHandle: jest.fn(),
|
||||
},
|
||||
popout2: {
|
||||
getNativeWindowHandle: jest.fn(),
|
||||
},
|
||||
const fromWebContentsMocked = {
|
||||
getNativeWindowHandle: jest.fn(),
|
||||
};
|
||||
jest
|
||||
.spyOn(utils, 'getWindowByName')
|
||||
.mockImplementation((windowName: string) => {
|
||||
return windows[windowName];
|
||||
});
|
||||
|
||||
ipcMain.send(apiName.symphonyApi, {
|
||||
cmd: apiCmds.getNativeWindowHandle,
|
||||
windowName: 'main',
|
||||
jest.spyOn(BrowserWindow, 'fromWebContents').mockImplementation(() => {
|
||||
return fromWebContentsMocked;
|
||||
});
|
||||
expect(windows['main'].getNativeWindowHandle).toBeCalledTimes(1);
|
||||
|
||||
ipcMain.send(apiName.symphonyApi, {
|
||||
const value = {
|
||||
cmd: apiCmds.getNativeWindowHandle,
|
||||
windowName: 'popout1',
|
||||
});
|
||||
expect(windows['popout1'].getNativeWindowHandle).toBeCalledTimes(1);
|
||||
expect(windows['popout2'].getNativeWindowHandle).toBeCalledTimes(0);
|
||||
};
|
||||
ipcMain.send(apiName.symphonyApi, value);
|
||||
expect(fromWebContentsMocked.getNativeWindowHandle).toBeCalledTimes(1);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
@ -1,70 +0,0 @@
|
||||
import { Library } from 'ffi-napi';
|
||||
import { isWindowsOS } from '../common/env';
|
||||
|
||||
/**
|
||||
* Translate the nativeWindowHandle of an Electron BrowserWindow to the handle
|
||||
* of the window where the main content is hosted. On Windows, Chrome uses a separate
|
||||
* window handle for the title bar and the main content has a different window handle
|
||||
* that is positioned below the title bar.
|
||||
* @returns translated window handle, or original handle if no applicable translation found
|
||||
*/
|
||||
export const getContentWindowHandle = (nativeWindowHandle: Buffer): Buffer => {
|
||||
if (!isWindowsOS) {
|
||||
return nativeWindowHandle;
|
||||
}
|
||||
if (nativeWindowHandle.byteLength < 8) {
|
||||
return nativeWindowHandle;
|
||||
}
|
||||
|
||||
const user32 = Library('user32.dll', {
|
||||
FindWindowExA: ['int', ['int', 'int', 'string', 'string']],
|
||||
GetWindowRect: ['int', ['int', 'pointer']],
|
||||
});
|
||||
|
||||
const getWindowRect = (hwnd: bigint) => {
|
||||
const rect = Buffer.alloc(16);
|
||||
|
||||
const ret = user32.GetWindowRect(hwnd.toString(), rect);
|
||||
if (ret) {
|
||||
return {
|
||||
left: rect.readInt32LE(0),
|
||||
top: rect.readInt32LE(4),
|
||||
right: rect.readInt32LE(8),
|
||||
bottom: rect.readInt32LE(12),
|
||||
};
|
||||
} else {
|
||||
return undefined;
|
||||
}
|
||||
};
|
||||
|
||||
const parentHwnd = nativeWindowHandle.readBigUInt64LE();
|
||||
const parentRect = getWindowRect(parentHwnd);
|
||||
if (!parentRect) {
|
||||
return nativeWindowHandle;
|
||||
}
|
||||
|
||||
let child = user32.FindWindowExA(
|
||||
parentHwnd.toString(),
|
||||
0,
|
||||
'Chrome_RenderWidgetHostHWND',
|
||||
null,
|
||||
);
|
||||
while (child !== 0) {
|
||||
const rect = getWindowRect(child);
|
||||
|
||||
// The candidate child window is located at the same x position as the parent window, but
|
||||
// has a higher y position (due to the window title frame at the top).
|
||||
if (rect && parentRect.left === rect.left && parentRect.top < rect.top) {
|
||||
const ret = Buffer.alloc(8);
|
||||
ret.writeBigUInt64LE(BigInt(child));
|
||||
return ret;
|
||||
}
|
||||
child = user32.FindWindowExA(
|
||||
parentHwnd.toString(),
|
||||
child,
|
||||
'Chrome_RenderWidgetHostHWND',
|
||||
null,
|
||||
);
|
||||
}
|
||||
return nativeWindowHandle;
|
||||
};
|
@ -21,7 +21,6 @@ import appStateHandler from './app-state-handler';
|
||||
import { getCitrixMediaRedirectionStatus } from './citrix-handler';
|
||||
import { CloudConfigDataTypes, config, ICloudConfig } from './config-handler';
|
||||
import { downloadHandler } from './download-handler';
|
||||
import { getContentWindowHandle } from './hwnd-handler';
|
||||
import { mainEvents } from './main-event-handler';
|
||||
import { memoryMonitor } from './memory-monitor';
|
||||
import notificationHelper from './notifications/notification-helper';
|
||||
@ -32,7 +31,6 @@ import { activate, handleKeyPress } from './window-actions';
|
||||
import { ICustomBrowserWindow, windowHandler } from './window-handler';
|
||||
import {
|
||||
downloadManagerAction,
|
||||
getWindowByName,
|
||||
isValidView,
|
||||
isValidWindow,
|
||||
sanitize,
|
||||
@ -425,10 +423,11 @@ ipcMain.handle(
|
||||
}
|
||||
break;
|
||||
case apiCmds.getNativeWindowHandle:
|
||||
const browserWin = getWindowByName(arg.windowName);
|
||||
const browserWin = BrowserWindow.fromWebContents(
|
||||
event.sender,
|
||||
) as ICustomBrowserWindow;
|
||||
if (browserWin && windowExists(browserWin)) {
|
||||
const windowHandle = browserWin.getNativeWindowHandle();
|
||||
return getContentWindowHandle(windowHandle);
|
||||
return browserWin.getNativeWindowHandle();
|
||||
}
|
||||
break;
|
||||
case apiCmds.getCitrixMediaRedirectionStatus:
|
||||
|
@ -279,10 +279,7 @@
|
||||
|
||||
<hr />
|
||||
<p>Native Window Handle:</p>
|
||||
<button id="get-window-handle">
|
||||
Get window handle (optionally enter a window name)
|
||||
</button>
|
||||
<input type="text" id="text-window-handle-name" />
|
||||
<button id="get-window-handle">Get window handle</button>
|
||||
<input type="text" id="text-window-handle" />
|
||||
<hr />
|
||||
<br />
|
||||
@ -1203,15 +1200,12 @@
|
||||
.join('');
|
||||
document.getElementById('text-window-handle').value = handleStr;
|
||||
};
|
||||
const windowName = document.getElementById('text-window-handle-name')
|
||||
.value;
|
||||
if (window.ssf) {
|
||||
window.ssf.getNativeWindowHandle(windowName).then(resultCallback);
|
||||
window.ssf.getNativeWindowHandle().then(resultCallback);
|
||||
} else if (window.manaSSF) {
|
||||
window.manaSSF.getNativeWindowHandle(windowName).then(resultCallback);
|
||||
window.manaSSF.getNativeWindowHandle().then(resultCallback);
|
||||
} else {
|
||||
postRequest(apiCmds.getNativeWindowHandle, null, {
|
||||
windowName,
|
||||
successCallback: resultCallback,
|
||||
});
|
||||
}
|
||||
|
@ -737,18 +737,12 @@ export class SSFApi {
|
||||
}
|
||||
|
||||
/**
|
||||
* Get native window handle of the window, by default where the renderer is displayed,
|
||||
* or optionally another window identified by its name.
|
||||
* @param windowName optional window name, defaults to current renderer window
|
||||
* Get native window handle of the window where the renderer is displayed
|
||||
* @returns the platform-specific handle of the window.
|
||||
*/
|
||||
public getNativeWindowHandle(windowName?: string): Promise<Buffer> {
|
||||
if (!windowName) {
|
||||
windowName = window.name || 'main';
|
||||
}
|
||||
public getNativeWindowHandle(): Promise<Buffer> {
|
||||
return ipcRenderer.invoke(apiName.symphonyApi, {
|
||||
cmd: apiCmds.getNativeWindowHandle,
|
||||
windowName,
|
||||
});
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user