[electron] Include bindings in macOS build (#5937)
This commit is contained in:
parent
b4772cc542
commit
ee7f2e1c8c
2
.github/workflows/package-and-publish.yml
vendored
2
.github/workflows/package-and-publish.yml
vendored
@ -41,7 +41,7 @@ jobs:
|
||||
|
||||
- name: Install dependencies
|
||||
if: steps.npm-cache.outputs.cache-hit != 'true'
|
||||
run: npm ci
|
||||
run: npm ci --include=dev # Hack: install `electron-drag-click` as a dev dependency, so build happens only on macOS
|
||||
|
||||
- name: Import MacOS signing certificate
|
||||
env:
|
||||
|
||||
@ -43,7 +43,7 @@ Electron allows building a native application that can be installed on Windows,
|
||||
|
||||
#### NPM scripts
|
||||
|
||||
- `npm run dev:electron`
|
||||
- `npm run electron:dev`
|
||||
|
||||
Run Electron in development mode, concurrently starts 3 processes with watch for changes: main (main Electron process), renderer (FE code) and Webpack for Electron (compiles main Electron process from TypeScript).
|
||||
|
||||
|
||||
1055
package-lock.json
generated
1055
package-lock.json
generated
File diff suppressed because it is too large
Load Diff
26
package.json
26
package.json
@ -12,10 +12,10 @@
|
||||
"build:mocked": "cross-env APP_ENV=test APP_MOCKED_CLIENT=1 npm run build:dev",
|
||||
"build:production": "webpack && bash ./deploy/copy_to_dist.sh",
|
||||
"web:release:production": "npm i && npm run build:production && git add -A && git commit -a -m '[Build]' --no-verify && git push",
|
||||
"electron:dev": "npm run electron:webpack && IS_PACKAGED_ELECTRON=true concurrently -n main,renderer,electron \"npm run electron:webpack -- --watch\" \"npm run dev\" \"electronmon dist/electron.cjs\"",
|
||||
"electron:dev": "npm run electron:webpack && IS_PACKAGED_ELECTRON=true concurrently --ks SIGKILL -n main,renderer,electron \"npm run electron:webpack -- --watch\" \"npm run dev\" \"electronmon dist/electron.cjs\"",
|
||||
"electron:webpack": "cross-env APP_ENV=$ENV webpack --config ./webpack-electron.config.ts",
|
||||
"electron:build": "IS_PACKAGED_ELECTRON=true npm run build:$ENV && electron-builder install-app-deps && electron-rebuild && ENV=$ENV npm run electron:webpack",
|
||||
"electron:package": "npm run electron:build && npx rimraf dist-electron && electron-builder build --win --mac --linux --config src/electron/config.yml",
|
||||
"electron:build": "IS_PACKAGED_ELECTRON=true npm run build:$ENV && electron-builder install-app-deps && ENV=$ENV npm run electron:webpack",
|
||||
"electron:package": "npm run electron:build && npx rimraf dist-electron && electron-builder build --win --mac --linux --config src/electron/config.js",
|
||||
"electron:package:staging": "ENV=staging npm run electron:package -- -p never",
|
||||
"electron:release:production": "ENV=production npm run electron:package -- -p always",
|
||||
"telegraph:update_changelog": "node ./dev/telegraphChangelog.js",
|
||||
@ -51,8 +51,7 @@
|
||||
"@babel/preset-react": "^7.27.1",
|
||||
"@babel/preset-typescript": "^7.27.1",
|
||||
"@babel/register": "^7.27.1",
|
||||
"@electron/rebuild": "^4.0.1",
|
||||
"@eslint/js": "^9.26.0",
|
||||
"@eslint/js": "^9.27.0",
|
||||
"@glen/jest-raw-loader": "^2.0.0",
|
||||
"@playwright/test": "^1.52.0",
|
||||
"@statoscope/cli": "5.29.0",
|
||||
@ -66,8 +65,8 @@
|
||||
"@types/dom-view-transitions": "^1.0.6",
|
||||
"@types/hast": "^3.0.4",
|
||||
"@types/jest": "^29.5.14",
|
||||
"@types/node": "^22.15.17",
|
||||
"@types/react": "^19.1.4",
|
||||
"@types/node": "^22.15.21",
|
||||
"@types/react": "^19.1.5",
|
||||
"@types/react-dom": "^19.1.5",
|
||||
"@types/webpack": "^5.28.5",
|
||||
"@typescript-eslint/eslint-plugin": "^8.32.1",
|
||||
@ -76,21 +75,22 @@
|
||||
"autoprefixer": "^10.4.21",
|
||||
"babel-loader": "^10.0.0",
|
||||
"babel-plugin-transform-import-meta": "^2.3.2",
|
||||
"bindings": "git+https://github.com/zubiden/node-bindings#6b9b0711a12e9df9cbf59a3271c25bf34c306907",
|
||||
"bindings": "git+https://github.com/zubiden/node-bindings#1f689378b1cd26f99d3b7156fe40a520365d1272",
|
||||
"browserlist": "^1.0.1",
|
||||
"buffer": "^6.0.3",
|
||||
"concurrently": "^9.1.2",
|
||||
"copy-webpack-plugin": "^13.0.0",
|
||||
"cross-env": "^7.0.3",
|
||||
"css-loader": "^7.1.2",
|
||||
"dotenv": "^16.5.0",
|
||||
"electron": "^36.2.0",
|
||||
"electron": "^36.2.1",
|
||||
"electron-builder": "^26.0.12",
|
||||
"electron-conf": "^1.3.0",
|
||||
"electron-context-menu": "^4.0.5",
|
||||
"electron-context-menu": "^4.1.0",
|
||||
"electron-drag-click": "git+https://github.com/zubiden/electron-drag-click#cf6918ddb648e13ebcf6cf1e7aa008258edc06ad",
|
||||
"electron-updater": "^6.6.2",
|
||||
"electronmon": "^2.0.3",
|
||||
"eslint": "^9.26.0",
|
||||
"eslint": "^9.27.0",
|
||||
"eslint-plugin-import": "^2.31.0",
|
||||
"eslint-plugin-jest": "^28.11.0",
|
||||
"eslint-plugin-jsx-a11y": "^6.10.2",
|
||||
@ -113,7 +113,7 @@
|
||||
"postcss-loader": "^8.1.1",
|
||||
"postcss-modules": "^6.0.1",
|
||||
"react": "^19.1.0",
|
||||
"sass": "^1.88.0",
|
||||
"sass": "^1.89.0",
|
||||
"sass-loader": "^16.0.5",
|
||||
"script-loader": "^0.7.2",
|
||||
"serve": "^14.2.4",
|
||||
@ -148,7 +148,7 @@
|
||||
},
|
||||
"optionalDependencies": {
|
||||
"dmg-license": "^1.0.11",
|
||||
"fsevents": "2.3.3"
|
||||
"fsevents": "^2.3.3"
|
||||
},
|
||||
"overrides": {
|
||||
"bindings": "$bindings"
|
||||
|
||||
@ -20,6 +20,9 @@ export const IS_TEST = process.env.APP_ENV === 'test';
|
||||
export const IS_PERF = process.env.APP_ENV === 'perf';
|
||||
export const IS_BETA = process.env.APP_ENV === 'staging';
|
||||
export const IS_PACKAGED_ELECTRON = process.env.IS_PACKAGED_ELECTRON;
|
||||
|
||||
export const ELECTRON_WINDOW_DRAG_EVENT_START = 'tt-electron-window-drag-start';
|
||||
export const ELECTRON_WINDOW_DRAG_EVENT_END = 'tt-electron-window-drag-end';
|
||||
export const PAID_MESSAGES_PURPOSE = 'paid_messages';
|
||||
|
||||
export const DEBUG = process.env.APP_ENV !== 'production';
|
||||
|
||||
86
src/electron/config.js
Normal file
86
src/electron/config.js
Normal file
@ -0,0 +1,86 @@
|
||||
const config = {
|
||||
productName: 'Telegram A',
|
||||
artifactName: '${productName}-${arch}.${ext}',
|
||||
appId: 'org.telegram.TelegramA',
|
||||
extraMetadata: {
|
||||
main: './dist/electron.cjs',
|
||||
productName: 'Telegram A',
|
||||
},
|
||||
asarUnpack: [
|
||||
'build/Release/electron_drag_click.node',
|
||||
],
|
||||
files: [
|
||||
'dist',
|
||||
'package.json',
|
||||
'public/icon-electron-windows.ico',
|
||||
'build/Release/electron_drag_click.node',
|
||||
'!dist/**/build-stats.json',
|
||||
'!dist/**/statoscope-report.html',
|
||||
'!dist/**/reference.json',
|
||||
'!dist/img-apple-*',
|
||||
'!dist/get',
|
||||
'!node_modules',
|
||||
],
|
||||
directories: {
|
||||
buildResources: './public',
|
||||
output: './dist-electron',
|
||||
},
|
||||
protocols: [
|
||||
{
|
||||
name: 'Tg',
|
||||
schemes: ['tg'],
|
||||
},
|
||||
],
|
||||
publish: {
|
||||
provider: 'github',
|
||||
owner: 'Ajaxy',
|
||||
repo: 'telegram-tt',
|
||||
releaseType: 'draft',
|
||||
},
|
||||
win: {
|
||||
target: {
|
||||
target: 'nsis',
|
||||
arch: ['x64'],
|
||||
},
|
||||
icon: 'public/icon-electron-windows.ico',
|
||||
},
|
||||
nsis: {
|
||||
oneClick: false,
|
||||
createDesktopShortcut: true,
|
||||
createStartMenuShortcut: true,
|
||||
},
|
||||
mac: {
|
||||
target: {
|
||||
target: 'default',
|
||||
arch: ['x64', 'arm64'],
|
||||
},
|
||||
entitlements: 'public/electron-entitlements.mac.plist',
|
||||
icon: 'public/icon-electron-macos.icns',
|
||||
},
|
||||
dmg: {
|
||||
background: 'public/background-electron-dmg.tiff',
|
||||
iconSize: 100,
|
||||
contents: [
|
||||
{
|
||||
x: 138,
|
||||
y: 225,
|
||||
type: 'file',
|
||||
},
|
||||
{
|
||||
x: 402,
|
||||
y: 225,
|
||||
type: 'link',
|
||||
path: '/Applications',
|
||||
},
|
||||
],
|
||||
},
|
||||
linux: {
|
||||
category: 'Chat;Network;InstantMessaging;',
|
||||
target: {
|
||||
target: 'AppImage',
|
||||
arch: ['x64'],
|
||||
},
|
||||
},
|
||||
};
|
||||
|
||||
export default config;
|
||||
@ -1,63 +0,0 @@
|
||||
productName: Telegram A
|
||||
artifactName: ${productName}-${arch}.${ext}
|
||||
appId: org.telegram.TelegramA
|
||||
extraMetadata:
|
||||
main: ./dist/electron.cjs
|
||||
productName: Telegram A
|
||||
files:
|
||||
- "dist"
|
||||
- "package.json"
|
||||
- "public/icon-electron-windows.ico"
|
||||
- "!dist/**/build-stats.json"
|
||||
- "!dist/**/statoscope-report.html"
|
||||
- "!dist/**/reference.json"
|
||||
- "!dist/img-apple-*"
|
||||
- "!dist/get"
|
||||
- "!node_modules"
|
||||
directories:
|
||||
buildResources: ./public
|
||||
output: ./dist-electron
|
||||
protocols:
|
||||
- name: Tg
|
||||
schemes:
|
||||
- tg
|
||||
publish:
|
||||
provider: github
|
||||
owner: Ajaxy
|
||||
repo: telegram-tt
|
||||
releaseType: draft
|
||||
win:
|
||||
target:
|
||||
target: nsis
|
||||
arch:
|
||||
- x64
|
||||
icon: public/icon-electron-windows.ico
|
||||
nsis:
|
||||
oneClick: false
|
||||
createDesktopShortcut: true
|
||||
createStartMenuShortcut: true
|
||||
mac:
|
||||
target:
|
||||
target: default
|
||||
arch:
|
||||
- x64
|
||||
- arm64
|
||||
entitlements: public/electron-entitlements.mac.plist
|
||||
icon: public/icon-electron-macos.icns
|
||||
dmg:
|
||||
background: public/background-electron-dmg.tiff
|
||||
iconSize: 100
|
||||
contents:
|
||||
- x: 138
|
||||
y: 225
|
||||
type: file
|
||||
- x: 402
|
||||
y: 225
|
||||
type: link
|
||||
path: "/Applications"
|
||||
linux:
|
||||
category: Community
|
||||
target:
|
||||
target: AppImage
|
||||
arch:
|
||||
- x64
|
||||
@ -8,7 +8,9 @@ import { IS_MAC_OS, IS_PRODUCTION, IS_WINDOWS } from './utils';
|
||||
import { createWindow, setupCloseHandlers, setupElectronActionHandlers } from './window';
|
||||
|
||||
initDeeplink();
|
||||
electronDragClick();
|
||||
if (IS_MAC_OS) {
|
||||
electronDragClick();
|
||||
}
|
||||
|
||||
contextMenu({
|
||||
showLearnSpelling: false,
|
||||
|
||||
@ -66,7 +66,7 @@ export function createWindow(url?: string) {
|
||||
},
|
||||
...(IS_MAC_OS && {
|
||||
titleBarStyle: 'hidden',
|
||||
windowButtonPosition: WINDOW_BUTTONS_POSITION.standard,
|
||||
trafficLightPosition: WINDOW_BUTTONS_POSITION.standard,
|
||||
}),
|
||||
});
|
||||
|
||||
|
||||
@ -1,6 +1,7 @@
|
||||
import type { ElementRef } from '../lib/teact/teact';
|
||||
import { useEffect, useRef } from '../lib/teact/teact';
|
||||
|
||||
import { ELECTRON_WINDOW_DRAG_EVENT_END, ELECTRON_WINDOW_DRAG_EVENT_START } from '../config';
|
||||
import { IS_ELECTRON, IS_MAC_OS } from '../util/browser/windowEnvironment';
|
||||
|
||||
const DRAG_DISTANCE_THRESHOLD = 5;
|
||||
@ -17,31 +18,34 @@ const useElectronDrag = (ref: ElementRef<HTMLDivElement>) => {
|
||||
if (!element || !(IS_ELECTRON && IS_MAC_OS)) return undefined;
|
||||
|
||||
const handleClick = (event: MouseEvent) => {
|
||||
distance.current = 0;
|
||||
|
||||
if (isDragging.current) {
|
||||
event.preventDefault();
|
||||
event.stopPropagation();
|
||||
isDragging.current = false;
|
||||
document.body.dispatchEvent(new CustomEvent(ELECTRON_WINDOW_DRAG_EVENT_END));
|
||||
}
|
||||
};
|
||||
|
||||
const handleMousedown = (event: MouseEvent) => {
|
||||
if (isDragging.current) {
|
||||
event.preventDefault();
|
||||
event.stopPropagation();
|
||||
}
|
||||
const handleMouseDown = (event: MouseEvent) => {
|
||||
distance.current = 0;
|
||||
isDragging.current = false;
|
||||
x.current = window.screenX;
|
||||
y.current = window.screenY;
|
||||
};
|
||||
|
||||
const handleDrag = (event: MouseEvent) => {
|
||||
if (event.buttons === 1) {
|
||||
distance.current += Math.sqrt((x.current - window.screenX) ** 2 + (y.current - window.screenY) ** 2);
|
||||
const deltaX = x.current - window.screenX;
|
||||
const deltaY = y.current - window.screenY;
|
||||
const deltaDistance = Math.sqrt(deltaX ** 2 + deltaY ** 2);
|
||||
distance.current += deltaDistance;
|
||||
|
||||
x.current = window.screenX;
|
||||
y.current = window.screenY;
|
||||
|
||||
if (!isDragging.current && distance.current > DRAG_DISTANCE_THRESHOLD) {
|
||||
isDragging.current = true;
|
||||
document.body.dispatchEvent(new CustomEvent(ELECTRON_WINDOW_DRAG_EVENT_START));
|
||||
}
|
||||
}
|
||||
};
|
||||
@ -53,13 +57,13 @@ const useElectronDrag = (ref: ElementRef<HTMLDivElement>) => {
|
||||
};
|
||||
|
||||
element.addEventListener('click', handleClick);
|
||||
element.addEventListener('mousedown', handleMousedown);
|
||||
element.addEventListener('mousedown', handleMouseDown);
|
||||
element.addEventListener('mousemove', handleDrag);
|
||||
element.addEventListener('dblclick', handleDoubleClick);
|
||||
|
||||
return () => {
|
||||
element.removeEventListener('click', handleClick);
|
||||
element.removeEventListener('mouseup', handleMousedown);
|
||||
element.removeEventListener('mousedown', handleMouseDown);
|
||||
element.removeEventListener('mousemove', handleDrag);
|
||||
element.removeEventListener('dblclick', handleDoubleClick);
|
||||
};
|
||||
|
||||
@ -1,4 +1,7 @@
|
||||
import { useCallback, useRef, useUnmountCleanup } from '../lib/teact/teact';
|
||||
import { useEffect, useRef, useUnmountCleanup } from '../lib/teact/teact';
|
||||
|
||||
import { ELECTRON_WINDOW_DRAG_EVENT_START } from '../config';
|
||||
import useLastCallback from './useLastCallback';
|
||||
|
||||
const DEFAULT_THRESHOLD = 250;
|
||||
|
||||
@ -14,7 +17,7 @@ function useLongPress({
|
||||
const isPressed = useRef(false);
|
||||
const timerId = useRef<number | undefined>(undefined);
|
||||
|
||||
const start = useCallback((e: React.MouseEvent | React.TouchEvent) => {
|
||||
const start = useLastCallback((e: React.MouseEvent | React.TouchEvent) => {
|
||||
const canProcessEvent = ('button' in e && e.button === 0) || ('touches' in e && e.touches.length > 0);
|
||||
if (isPressed.current || !canProcessEvent) {
|
||||
return;
|
||||
@ -25,9 +28,9 @@ function useLongPress({
|
||||
onStart?.();
|
||||
isLongPressActive.current = true;
|
||||
}, threshold);
|
||||
}, [onStart, threshold]);
|
||||
});
|
||||
|
||||
const cancel = useCallback((e: React.MouseEvent | React.TouchEvent) => {
|
||||
const end = useLastCallback((e: React.MouseEvent | React.TouchEvent) => {
|
||||
if (!isPressed.current) return;
|
||||
|
||||
if (isLongPressActive.current) {
|
||||
@ -36,21 +39,33 @@ function useLongPress({
|
||||
onClick?.(e);
|
||||
}
|
||||
|
||||
cancel();
|
||||
});
|
||||
|
||||
const cancel = useLastCallback(() => {
|
||||
isLongPressActive.current = false;
|
||||
isPressed.current = false;
|
||||
window.clearTimeout(timerId.current);
|
||||
}, [onEnd, onClick]);
|
||||
});
|
||||
|
||||
useUnmountCleanup(() => {
|
||||
window.clearTimeout(timerId.current);
|
||||
});
|
||||
|
||||
useEffect(() => {
|
||||
document.body.addEventListener(ELECTRON_WINDOW_DRAG_EVENT_START, cancel);
|
||||
|
||||
return () => {
|
||||
document.body.removeEventListener(ELECTRON_WINDOW_DRAG_EVENT_START, cancel);
|
||||
};
|
||||
}, []);
|
||||
|
||||
return {
|
||||
onMouseDown: start,
|
||||
onMouseUp: cancel,
|
||||
onMouseLeave: cancel,
|
||||
onMouseUp: end,
|
||||
onMouseLeave: end,
|
||||
onTouchStart: start,
|
||||
onTouchEnd: cancel,
|
||||
onTouchEnd: end,
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
@ -1,3 +1,4 @@
|
||||
import CopyWebpackPlugin from 'copy-webpack-plugin';
|
||||
import path from 'path';
|
||||
import { EnvironmentPlugin } from 'webpack';
|
||||
|
||||
@ -36,6 +37,14 @@ export default {
|
||||
BASE_URL,
|
||||
IS_PREVIEW: false,
|
||||
}),
|
||||
new CopyWebpackPlugin({
|
||||
patterns: [
|
||||
{
|
||||
from: path.resolve(__dirname, 'node_modules/electron-drag-click/build/Release/electron_drag_click.node'),
|
||||
to: path.resolve(__dirname, 'build/Release/electron_drag_click.node'),
|
||||
},
|
||||
],
|
||||
}),
|
||||
],
|
||||
|
||||
module: {
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user