Skip to content

Commit aa3b445

Browse files
committed
Select frame
1 parent 5fa252b commit aa3b445

File tree

4 files changed

+125
-21
lines changed

4 files changed

+125
-21
lines changed

src/App.tsx

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,11 @@ export default function App() {
1616
render={(props) => {
1717
const { search } = props.location;
1818
const so = qs.parse(search.slice(search.lastIndexOf('?') + 1));
19-
return so.page === 'screen' ? <Screen /> : <Main />;
19+
return so.page === 'screen' ? (
20+
<Screen select={so.select?.toString() || 'frame'} />
21+
) : (
22+
<Main />
23+
);
2024
}}
2125
/>
2226
</Switch>

src/components/printer/Main.tsx

Lines changed: 68 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,77 @@
1-
import React from 'react';
1+
import React, { useState } from 'react';
22
import { ipcRenderer } from 'electron';
33

4+
interface Coord {
5+
select: string;
6+
x0: number;
7+
y0: number;
8+
x1: number;
9+
y1: number;
10+
}
11+
412
const Main = () => {
5-
const handleScreenSelect = async () => {
6-
await ipcRenderer.invoke('open-screen');
13+
const [frameCoord, setFrameCoord] = useState<Coord>();
14+
const [nextCoord, setNextCoord] = useState<Coord>();
15+
16+
const handleCloseScreen = (c: Coord) => {
17+
if (c.select === 'frame') {
18+
setFrameCoord({ ...c });
19+
} else if (c.select === 'next') {
20+
setNextCoord({ ...c });
21+
}
722
};
823

24+
const handleOpenScreen = (select: string) => {
25+
if (select === 'frame') {
26+
setFrameCoord(undefined);
27+
} else {
28+
setNextCoord(undefined);
29+
}
30+
31+
ipcRenderer.invoke('open-screen', { select });
32+
};
33+
34+
ipcRenderer.on('close-screen', (_, c: Coord) => {
35+
handleCloseScreen(c);
36+
});
37+
938
return (
10-
<section className="flex flex-1">
11-
<button type="button" onClick={handleScreenSelect}>
12-
Open
13-
</button>
39+
<section className="flex flex-col items-start justify-center p-8 space-y-8">
40+
<section className="flex items-center justify-start">
41+
<button
42+
type="button"
43+
onClick={() => handleOpenScreen('frame')}
44+
className="btn"
45+
>
46+
Select screenshot frame...
47+
</button>
48+
{frameCoord ? (
49+
<p>
50+
Frame: ({frameCoord.x0}, {frameCoord.y0}) and ({frameCoord.x1},{' '}
51+
{frameCoord.y1})
52+
</p>
53+
) : (
54+
<p />
55+
)}
56+
</section>
57+
58+
<section className="flex items-center justify-start">
59+
<button
60+
type="button"
61+
onClick={() => handleOpenScreen('next')}
62+
className="btn"
63+
>
64+
Select next button...
65+
</button>
66+
{nextCoord ? (
67+
<p>
68+
Next button: ({(nextCoord.x0 + nextCoord.x1) / 2},{' '}
69+
{(nextCoord.y0 + nextCoord.y1) / 2})
70+
</p>
71+
) : (
72+
<p />
73+
)}
74+
</section>
1475
</section>
1576
);
1677
};

src/components/printer/Screen.tsx

Lines changed: 38 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,26 +1,43 @@
1-
import React, { MouseEvent, useRef, useState } from 'react';
1+
import { ipcRenderer } from 'electron';
2+
import React, { MouseEvent, useRef, useState, useEffect } from 'react';
23

3-
const Screen = () => {
4+
const Screen = ({ select }: { select: string }) => {
45
const parentRef = useRef<HTMLDivElement>(null);
56
const canvasRef = useRef<HTMLCanvasElement>(null);
67

78
const [mouse, setMouse] = useState({
9+
select,
810
startX: 0,
911
startY: 0,
12+
x0: 0,
13+
y0: 0,
14+
x1: 0,
15+
y1: 0,
1016
});
1117
const [draging, setDraging] = useState(false);
1218

13-
const handleMouseDown = (ev: MouseEvent) => {
14-
setMouse({
15-
startX: ev.pageX - (canvasRef.current?.getBoundingClientRect().left || 0),
16-
startY: ev.pageY - (canvasRef.current?.getBoundingClientRect().top || 0),
17-
});
19+
const closeScreen = () => {
20+
ipcRenderer.invoke('close-screen', { ...mouse });
21+
};
22+
23+
const setCanvasSize = () => {
1824
const ctx = canvasRef.current;
1925
if (ctx) {
2026
ctx.width = window.innerWidth || 1000;
2127
ctx.height = window.innerHeight || 1000;
2228
}
29+
};
2330

31+
const handleMouseDown = (ev: MouseEvent) => {
32+
setMouse({
33+
...mouse,
34+
startX: ev.pageX - (canvasRef.current?.getBoundingClientRect().left || 0),
35+
startY: ev.pageY - (canvasRef.current?.getBoundingClientRect().top || 0),
36+
x0: ev.screenX,
37+
y0: ev.screenY,
38+
});
39+
40+
setCanvasSize();
2441
setDraging(true);
2542
};
2643

@@ -41,21 +58,33 @@ const Screen = () => {
4158
(canvasRef.current?.getBoundingClientRect().top || 0) -
4259
mouse.startY;
4360

61+
setMouse({
62+
...mouse,
63+
x1: ev.screenX,
64+
y1: ev.screenY,
65+
});
66+
4467
ctx.clearRect(
4568
0,
4669
0,
4770
parentRef.current?.clientWidth || 1000,
4871
parentRef.current?.clientHeight || 1000
4972
);
50-
ctx.fillStyle = 'red';
73+
ctx.fillStyle = 'rgba(0, 0, 0, 0.5)';
5174
ctx.fillRect(mouse.startX, mouse.startY, width, height);
5275
}
5376
};
5477

5578
const handleMouseUp = () => {
5679
setDraging(false);
80+
closeScreen();
5781
};
5882

83+
useEffect(() => {
84+
window.onblur = closeScreen;
85+
window.onresize = setCanvasSize;
86+
}, []);
87+
5988
return (
6089
<div
6190
style={{ cursor: draging ? 'crosshair' : 'default' }}
@@ -64,6 +93,7 @@ const Screen = () => {
6493
>
6594
<canvas
6695
ref={canvasRef}
96+
className="bg-gray-50 opacity-20"
6797
onMouseDown={handleMouseDown}
6898
onMouseMove={handleMouseMove}
6999
onMouseUp={handleMouseUp}

src/main.dev.ts

Lines changed: 14 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -177,21 +177,25 @@ ipcMain.handle(
177177
}
178178
);
179179

180-
const createScreenWindow = () => {
180+
const createScreenWindow = (select: string) => {
181181
if (screenWindow == null) {
182182
screenWindow = new BrowserWindow({
183183
frame: false,
184184
transparent: true,
185185
webPreferences: {
186186
nodeIntegration: true,
187+
contextIsolation: false,
187188
},
189+
parent: mainWindow || undefined,
188190
});
189191
}
190-
screenWindow.loadURL(`file://${__dirname}/index.html?page=screen`);
192+
screenWindow.loadURL(
193+
`file://${__dirname}/index.html?page=screen&select=${select}`
194+
);
191195

192196
screenWindow.webContents.on('did-finish-load', () => {
193-
screenWindow?.show();
194197
screenWindow?.maximize();
198+
screenWindow?.show();
195199
});
196200

197201
screenWindow.webContents.on('before-input-event', (event, ipnut) => {
@@ -207,14 +211,19 @@ const createScreenWindow = () => {
207211
screenWindow.webContents.openDevTools({ mode: 'undocked' });
208212
};
209213

210-
ipcMain.handle('open-screen', async () => {
211-
createScreenWindow();
214+
ipcMain.handle('open-screen', async (_, { select }) => {
215+
createScreenWindow(select);
212216
});
213217

214218
ipcMain.handle('get-store', (_event, { key }) => {
215219
return store.get(key);
216220
});
217221

222+
ipcMain.handle('close-screen', (_, coord) => {
223+
mainWindow?.webContents.send('close-screen', coord);
224+
screenWindow?.close();
225+
});
226+
218227
/**
219228
* Add event listeners...
220229
*/

0 commit comments

Comments
 (0)