glitchgrab 1.40.0 → 1.41.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -1
- package/dist/index.js +262 -36
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +262 -36
- package/dist/index.mjs.map +1 -1
- package/package.json +2 -2
package/dist/index.mjs
CHANGED
|
@@ -1259,6 +1259,7 @@ function AssistSheet({
|
|
|
1259
1259
|
assist,
|
|
1260
1260
|
theme: t2,
|
|
1261
1261
|
screenshots,
|
|
1262
|
+
pageShot = null,
|
|
1262
1263
|
onAddImages,
|
|
1263
1264
|
attachmentCount,
|
|
1264
1265
|
context,
|
|
@@ -1304,6 +1305,34 @@ function AssistSheet({
|
|
|
1304
1305
|
const inputRef = useRef2(null);
|
|
1305
1306
|
const draftRef = useRef2(null);
|
|
1306
1307
|
const seededRef = useRef2(false);
|
|
1308
|
+
const eventsRef = useRef2([]);
|
|
1309
|
+
const aiDraftRef = useRef2(null);
|
|
1310
|
+
function logEvent(type, detail) {
|
|
1311
|
+
eventsRef.current.push({ type, at: Date.now(), ...detail ? { detail } : {} });
|
|
1312
|
+
}
|
|
1313
|
+
function takeEvents() {
|
|
1314
|
+
if (eventsRef.current.length === 0) return void 0;
|
|
1315
|
+
const events = eventsRef.current;
|
|
1316
|
+
eventsRef.current = [];
|
|
1317
|
+
return events;
|
|
1318
|
+
}
|
|
1319
|
+
function flushEvents() {
|
|
1320
|
+
if (!conversationId) return;
|
|
1321
|
+
const events = takeEvents();
|
|
1322
|
+
if (!events) return;
|
|
1323
|
+
try {
|
|
1324
|
+
void Promise.resolve(
|
|
1325
|
+
assist({ messages: [], conversationId, events, screenshots: [], context: null })
|
|
1326
|
+
).catch(() => {
|
|
1327
|
+
});
|
|
1328
|
+
} catch (e) {
|
|
1329
|
+
}
|
|
1330
|
+
}
|
|
1331
|
+
function leave(type, detail) {
|
|
1332
|
+
logEvent(type, detail);
|
|
1333
|
+
flushEvents();
|
|
1334
|
+
onClose();
|
|
1335
|
+
}
|
|
1307
1336
|
useEffect2(() => {
|
|
1308
1337
|
const el = scrollRef.current;
|
|
1309
1338
|
if (el) el.scrollTop = el.scrollHeight;
|
|
@@ -1312,27 +1341,45 @@ function AssistSheet({
|
|
|
1312
1341
|
var _a;
|
|
1313
1342
|
if (phase === "draft") (_a = draftRef.current) == null ? void 0 : _a.focus();
|
|
1314
1343
|
}, [phase]);
|
|
1344
|
+
function degradeKeepingEvents(events, message) {
|
|
1345
|
+
if (events) eventsRef.current = [...events, ...eventsRef.current];
|
|
1346
|
+
flushEvents();
|
|
1347
|
+
onDegrade(message);
|
|
1348
|
+
}
|
|
1315
1349
|
async function runTurn(history2) {
|
|
1316
1350
|
var _a, _b, _c, _d, _e;
|
|
1317
1351
|
setBusy(true);
|
|
1318
1352
|
let result;
|
|
1353
|
+
const events = takeEvents();
|
|
1319
1354
|
try {
|
|
1320
1355
|
const sent = screenshots.slice(-MAX_ASSIST_IMAGES);
|
|
1321
1356
|
result = await assist({
|
|
1322
|
-
|
|
1357
|
+
// `kind` only on drafts, so an older server sees the exact shape it
|
|
1358
|
+
// always did — it just learns the draft text now instead of a
|
|
1359
|
+
// placeholder line.
|
|
1360
|
+
messages: history2.map(
|
|
1361
|
+
(m) => m.kind ? { role: m.role, content: m.content, kind: m.kind } : m
|
|
1362
|
+
),
|
|
1323
1363
|
conversationId,
|
|
1324
1364
|
screenshots: sent,
|
|
1325
1365
|
screenshot: (_a = sent[sent.length - 1]) != null ? _a : null,
|
|
1326
|
-
context
|
|
1366
|
+
context: {
|
|
1367
|
+
...context != null ? context : {},
|
|
1368
|
+
imageSources: sent.map((shot) => pageShot && shot === pageShot ? "page" : "attached")
|
|
1369
|
+
},
|
|
1370
|
+
events
|
|
1327
1371
|
});
|
|
1328
1372
|
} catch (e) {
|
|
1329
|
-
|
|
1373
|
+
degradeKeepingEvents(
|
|
1374
|
+
events,
|
|
1375
|
+
"The assistant is unavailable \u2014 write your report below and send it as normal."
|
|
1376
|
+
);
|
|
1330
1377
|
return;
|
|
1331
1378
|
} finally {
|
|
1332
1379
|
setBusy(false);
|
|
1333
1380
|
}
|
|
1334
1381
|
if (result.degraded) {
|
|
1335
|
-
|
|
1382
|
+
degradeKeepingEvents(events, result.degraded);
|
|
1336
1383
|
return;
|
|
1337
1384
|
}
|
|
1338
1385
|
if (result.conversationId) {
|
|
@@ -1349,7 +1396,9 @@ function AssistSheet({
|
|
|
1349
1396
|
}
|
|
1350
1397
|
if (result.report) {
|
|
1351
1398
|
onDescriptionChange(result.report);
|
|
1352
|
-
|
|
1399
|
+
aiDraftRef.current = result.report;
|
|
1400
|
+
logEvent("draft_shown");
|
|
1401
|
+
setMessages([...history2, { role: "assistant", content: result.report, kind: "report" }]);
|
|
1353
1402
|
setOptions([]);
|
|
1354
1403
|
setPhase("draft");
|
|
1355
1404
|
return;
|
|
@@ -1384,6 +1433,36 @@ function AssistSheet({
|
|
|
1384
1433
|
onPickType(tile);
|
|
1385
1434
|
setPhase(tile === "RATING" ? "rating" : "chat");
|
|
1386
1435
|
}
|
|
1436
|
+
function keepChatting() {
|
|
1437
|
+
const current = description.trim();
|
|
1438
|
+
logEvent(
|
|
1439
|
+
"keep_chatting",
|
|
1440
|
+
aiDraftRef.current && current !== aiDraftRef.current.trim() ? "after editing" : void 0
|
|
1441
|
+
);
|
|
1442
|
+
setMessages((prev) => {
|
|
1443
|
+
const next = [...prev];
|
|
1444
|
+
for (let i = next.length - 1; i >= 0; i--) {
|
|
1445
|
+
if (next[i].kind === "report") {
|
|
1446
|
+
if (current) next[i] = { ...next[i], content: current };
|
|
1447
|
+
break;
|
|
1448
|
+
}
|
|
1449
|
+
}
|
|
1450
|
+
return next;
|
|
1451
|
+
});
|
|
1452
|
+
setPhase("chat");
|
|
1453
|
+
requestAnimationFrame(() => {
|
|
1454
|
+
var _a;
|
|
1455
|
+
return (_a = inputRef.current) == null ? void 0 : _a.focus();
|
|
1456
|
+
});
|
|
1457
|
+
}
|
|
1458
|
+
function sendDraft() {
|
|
1459
|
+
const edited = aiDraftRef.current !== null && description.trim() !== aiDraftRef.current.trim();
|
|
1460
|
+
logEvent("draft_sent", edited ? "edited" : "as drafted");
|
|
1461
|
+
flushEvents();
|
|
1462
|
+
onSend();
|
|
1463
|
+
}
|
|
1464
|
+
const lastMessage = messages[messages.length - 1];
|
|
1465
|
+
const correcting = phase === "chat" && (lastMessage == null ? void 0 : lastMessage.kind) === "report";
|
|
1387
1466
|
const empty = phase === "chat" && messages.length === 0 && !busy;
|
|
1388
1467
|
const initials = (reporterName != null ? reporterName : "").split(/\s+/).filter(Boolean).slice(0, 2).map((w) => {
|
|
1389
1468
|
var _a, _b;
|
|
@@ -1429,7 +1508,7 @@ function AssistSheet({
|
|
|
1429
1508
|
animation: "gg-sheet-fade .18s ease",
|
|
1430
1509
|
fontFamily: '-apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif'
|
|
1431
1510
|
},
|
|
1432
|
-
onClick:
|
|
1511
|
+
onClick: () => leave("closed"),
|
|
1433
1512
|
onPointerDown: (e) => e.stopPropagation(),
|
|
1434
1513
|
children: /* @__PURE__ */ jsxs2(
|
|
1435
1514
|
"div",
|
|
@@ -1509,7 +1588,7 @@ function AssistSheet({
|
|
|
1509
1588
|
{
|
|
1510
1589
|
type: "button",
|
|
1511
1590
|
"data-gg-write-myself": "",
|
|
1512
|
-
onClick:
|
|
1591
|
+
onClick: () => leave("write_myself", `header, ${phase}`),
|
|
1513
1592
|
"aria-label": "Write it myself instead",
|
|
1514
1593
|
style: {
|
|
1515
1594
|
flexShrink: 0,
|
|
@@ -1765,7 +1844,10 @@ function AssistSheet({
|
|
|
1765
1844
|
{
|
|
1766
1845
|
type: "button",
|
|
1767
1846
|
"data-gg-chip": "",
|
|
1768
|
-
onClick: () =>
|
|
1847
|
+
onClick: () => {
|
|
1848
|
+
logEvent("starter_tap", s);
|
|
1849
|
+
send(s);
|
|
1850
|
+
},
|
|
1769
1851
|
style: {
|
|
1770
1852
|
border: `1px solid ${t2.inputBorder}`,
|
|
1771
1853
|
background: "transparent",
|
|
@@ -1785,6 +1867,60 @@ function AssistSheet({
|
|
|
1785
1867
|
] }),
|
|
1786
1868
|
messages.map((m, i) => {
|
|
1787
1869
|
const mine = m.role === "user";
|
|
1870
|
+
if (m.kind === "report") {
|
|
1871
|
+
const live = phase === "draft" && i === messages.length - 1;
|
|
1872
|
+
return /* @__PURE__ */ jsxs2("div", { style: { display: "flex", gap: "8px", minWidth: 0 }, children: [
|
|
1873
|
+
/* @__PURE__ */ jsx2(Avatar, { who: "assistant", theme: t2 }),
|
|
1874
|
+
/* @__PURE__ */ jsx2(
|
|
1875
|
+
"div",
|
|
1876
|
+
{
|
|
1877
|
+
"data-gg-draft-bubble": "",
|
|
1878
|
+
style: {
|
|
1879
|
+
maxWidth: "82%",
|
|
1880
|
+
minWidth: 0,
|
|
1881
|
+
padding: "9px 12px",
|
|
1882
|
+
borderRadius: "12px 12px 12px 4px",
|
|
1883
|
+
fontSize: "13px",
|
|
1884
|
+
lineHeight: 1.55,
|
|
1885
|
+
backgroundColor: t2.bgSecondary,
|
|
1886
|
+
color: t2.text,
|
|
1887
|
+
border: live ? "none" : `1px solid ${t2.accent}66`
|
|
1888
|
+
},
|
|
1889
|
+
children: live ? "Here's your report \u2014 have a read." : /* @__PURE__ */ jsxs2(Fragment, { children: [
|
|
1890
|
+
/* @__PURE__ */ jsx2(
|
|
1891
|
+
"span",
|
|
1892
|
+
{
|
|
1893
|
+
style: {
|
|
1894
|
+
display: "block",
|
|
1895
|
+
fontSize: "10px",
|
|
1896
|
+
fontWeight: 700,
|
|
1897
|
+
letterSpacing: ".06em",
|
|
1898
|
+
textTransform: "uppercase",
|
|
1899
|
+
color: t2.accent,
|
|
1900
|
+
marginBottom: "4px"
|
|
1901
|
+
},
|
|
1902
|
+
children: "Draft so far"
|
|
1903
|
+
}
|
|
1904
|
+
),
|
|
1905
|
+
/* @__PURE__ */ jsx2(
|
|
1906
|
+
"span",
|
|
1907
|
+
{
|
|
1908
|
+
style: {
|
|
1909
|
+
display: "block",
|
|
1910
|
+
whiteSpace: "pre-wrap",
|
|
1911
|
+
wordBreak: "break-word",
|
|
1912
|
+
maxHeight: "160px",
|
|
1913
|
+
overflowY: "auto",
|
|
1914
|
+
color: t2.textMuted
|
|
1915
|
+
},
|
|
1916
|
+
children: m.content
|
|
1917
|
+
}
|
|
1918
|
+
)
|
|
1919
|
+
] })
|
|
1920
|
+
}
|
|
1921
|
+
)
|
|
1922
|
+
] }, i);
|
|
1923
|
+
}
|
|
1788
1924
|
return /* @__PURE__ */ jsxs2(
|
|
1789
1925
|
"div",
|
|
1790
1926
|
{
|
|
@@ -1839,7 +1975,10 @@ function AssistSheet({
|
|
|
1839
1975
|
type: "button",
|
|
1840
1976
|
"data-gg-chip": "",
|
|
1841
1977
|
"data-gg-option": "",
|
|
1842
|
-
onClick: () =>
|
|
1978
|
+
onClick: () => {
|
|
1979
|
+
logEvent("option_tap", option);
|
|
1980
|
+
send(option);
|
|
1981
|
+
},
|
|
1843
1982
|
style: {
|
|
1844
1983
|
border: `1px solid ${t2.inputBorder}`,
|
|
1845
1984
|
background: "transparent",
|
|
@@ -2041,7 +2180,7 @@ function AssistSheet({
|
|
|
2041
2180
|
"button",
|
|
2042
2181
|
{
|
|
2043
2182
|
type: "button",
|
|
2044
|
-
onClick:
|
|
2183
|
+
onClick: keepChatting,
|
|
2045
2184
|
style: {
|
|
2046
2185
|
alignSelf: "flex-start",
|
|
2047
2186
|
border: "none",
|
|
@@ -2176,7 +2315,7 @@ function AssistSheet({
|
|
|
2176
2315
|
{
|
|
2177
2316
|
type: "button",
|
|
2178
2317
|
"data-gg-sheet-send": "",
|
|
2179
|
-
onClick:
|
|
2318
|
+
onClick: sendDraft,
|
|
2180
2319
|
disabled: isSubmitting || !description.trim(),
|
|
2181
2320
|
style: {
|
|
2182
2321
|
width: "100%",
|
|
@@ -2254,7 +2393,10 @@ function AssistSheet({
|
|
|
2254
2393
|
onChange: (e) => {
|
|
2255
2394
|
var _a;
|
|
2256
2395
|
const files = Array.from((_a = e.target.files) != null ? _a : []);
|
|
2257
|
-
if (files.length)
|
|
2396
|
+
if (files.length) {
|
|
2397
|
+
logEvent("image_added", String(files.length));
|
|
2398
|
+
onAddImages(files);
|
|
2399
|
+
}
|
|
2258
2400
|
e.target.value = "";
|
|
2259
2401
|
},
|
|
2260
2402
|
style: { display: "none" }
|
|
@@ -2284,7 +2426,7 @@ function AssistSheet({
|
|
|
2284
2426
|
send(input);
|
|
2285
2427
|
}
|
|
2286
2428
|
},
|
|
2287
|
-
placeholder: "Type your answer\u2026",
|
|
2429
|
+
placeholder: correcting ? "What should change in the draft?" : "Type your answer\u2026",
|
|
2288
2430
|
rows: 1,
|
|
2289
2431
|
disabled: busy,
|
|
2290
2432
|
autoFocus: true,
|
|
@@ -2344,7 +2486,7 @@ function AssistSheet({
|
|
|
2344
2486
|
{
|
|
2345
2487
|
type: "button",
|
|
2346
2488
|
"data-gg-write-myself": "",
|
|
2347
|
-
onClick:
|
|
2489
|
+
onClick: () => leave("write_myself", "footer"),
|
|
2348
2490
|
style: {
|
|
2349
2491
|
display: "block",
|
|
2350
2492
|
margin: "8px auto 0",
|
|
@@ -2416,6 +2558,107 @@ var ATTACHMENT_ACCEPT = [
|
|
|
2416
2558
|
".xlsx",
|
|
2417
2559
|
".zip"
|
|
2418
2560
|
].join(",");
|
|
2561
|
+
var MAX_SCALE = 2;
|
|
2562
|
+
var FRAME_TIMEOUT_MS = 3e3;
|
|
2563
|
+
function canCaptureTabPixels() {
|
|
2564
|
+
var _a;
|
|
2565
|
+
try {
|
|
2566
|
+
return typeof navigator !== "undefined" && typeof ((_a = navigator.mediaDevices) == null ? void 0 : _a.getDisplayMedia) === "function" && typeof globalThis.CaptureController !== "undefined";
|
|
2567
|
+
} catch (e) {
|
|
2568
|
+
return false;
|
|
2569
|
+
}
|
|
2570
|
+
}
|
|
2571
|
+
var HAVE_CURRENT_DATA = 2;
|
|
2572
|
+
function waitForFrame(video) {
|
|
2573
|
+
if (video.readyState >= HAVE_CURRENT_DATA && video.videoWidth > 0) {
|
|
2574
|
+
return Promise.resolve(true);
|
|
2575
|
+
}
|
|
2576
|
+
return new Promise((resolve) => {
|
|
2577
|
+
const timer = setTimeout(() => resolve(false), FRAME_TIMEOUT_MS);
|
|
2578
|
+
const done = () => {
|
|
2579
|
+
clearTimeout(timer);
|
|
2580
|
+
resolve(true);
|
|
2581
|
+
};
|
|
2582
|
+
if (typeof video.requestVideoFrameCallback === "function") {
|
|
2583
|
+
video.requestVideoFrameCallback(done);
|
|
2584
|
+
} else if (video.readyState >= 2) {
|
|
2585
|
+
done();
|
|
2586
|
+
} else {
|
|
2587
|
+
video.addEventListener("loadeddata", done, { once: true });
|
|
2588
|
+
}
|
|
2589
|
+
});
|
|
2590
|
+
}
|
|
2591
|
+
async function grabFrame(stream) {
|
|
2592
|
+
const video = document.createElement("video");
|
|
2593
|
+
video.muted = true;
|
|
2594
|
+
video.playsInline = true;
|
|
2595
|
+
video.srcObject = stream;
|
|
2596
|
+
try {
|
|
2597
|
+
await video.play();
|
|
2598
|
+
if (!await waitForFrame(video)) return null;
|
|
2599
|
+
if (!video.videoWidth || !video.videoHeight) return null;
|
|
2600
|
+
const maxWidth = Math.max(1, window.innerWidth) * MAX_SCALE;
|
|
2601
|
+
const factor = Math.min(1, maxWidth / video.videoWidth);
|
|
2602
|
+
const canvas = document.createElement("canvas");
|
|
2603
|
+
canvas.width = Math.round(video.videoWidth * factor);
|
|
2604
|
+
canvas.height = Math.round(video.videoHeight * factor);
|
|
2605
|
+
const ctx = canvas.getContext("2d");
|
|
2606
|
+
if (!ctx) return null;
|
|
2607
|
+
ctx.drawImage(video, 0, 0, canvas.width, canvas.height);
|
|
2608
|
+
return canvas;
|
|
2609
|
+
} finally {
|
|
2610
|
+
video.srcObject = null;
|
|
2611
|
+
}
|
|
2612
|
+
}
|
|
2613
|
+
async function captureViaTabPixels() {
|
|
2614
|
+
var _a, _b;
|
|
2615
|
+
if (!canCaptureTabPixels()) return null;
|
|
2616
|
+
let stream = null;
|
|
2617
|
+
try {
|
|
2618
|
+
const options = {
|
|
2619
|
+
video: { displaySurface: "browser" },
|
|
2620
|
+
audio: false,
|
|
2621
|
+
preferCurrentTab: true,
|
|
2622
|
+
selfBrowserSurface: "include",
|
|
2623
|
+
surfaceSwitching: "exclude",
|
|
2624
|
+
monitorTypeSurfaces: "exclude"
|
|
2625
|
+
};
|
|
2626
|
+
stream = await navigator.mediaDevices.getDisplayMedia(options);
|
|
2627
|
+
const surface = (_b = (_a = stream.getVideoTracks()[0]) == null ? void 0 : _a.getSettings()) == null ? void 0 : _b.displaySurface;
|
|
2628
|
+
if (surface && surface !== "browser") return null;
|
|
2629
|
+
const canvas = await grabFrame(stream);
|
|
2630
|
+
return canvas ? encodeScreenshot(canvas) : null;
|
|
2631
|
+
} catch (e) {
|
|
2632
|
+
return null;
|
|
2633
|
+
} finally {
|
|
2634
|
+
stream == null ? void 0 : stream.getTracks().forEach((track) => track.stop());
|
|
2635
|
+
}
|
|
2636
|
+
}
|
|
2637
|
+
async function captureViaHtml2Canvas() {
|
|
2638
|
+
try {
|
|
2639
|
+
const { default: html2canvas } = await import("html2canvas-pro");
|
|
2640
|
+
const scale = Math.min(Math.max(window.devicePixelRatio || 1, 1), MAX_SCALE);
|
|
2641
|
+
const canvas = await html2canvas(document.body, {
|
|
2642
|
+
scale,
|
|
2643
|
+
logging: false,
|
|
2644
|
+
useCORS: true,
|
|
2645
|
+
allowTaint: true,
|
|
2646
|
+
x: window.scrollX,
|
|
2647
|
+
y: window.scrollY,
|
|
2648
|
+
width: window.innerWidth,
|
|
2649
|
+
height: window.innerHeight,
|
|
2650
|
+
windowWidth: window.innerWidth,
|
|
2651
|
+
windowHeight: window.innerHeight
|
|
2652
|
+
});
|
|
2653
|
+
return encodeScreenshot(canvas);
|
|
2654
|
+
} catch (e) {
|
|
2655
|
+
return null;
|
|
2656
|
+
}
|
|
2657
|
+
}
|
|
2658
|
+
async function captureDefaultScreenshot() {
|
|
2659
|
+
var _a;
|
|
2660
|
+
return (_a = await captureViaTabPixels()) != null ? _a : await captureViaHtml2Canvas();
|
|
2661
|
+
}
|
|
2419
2662
|
var SEVERITY_REQUIRED = "Pick how bad it is before sending.";
|
|
2420
2663
|
function useIsDark() {
|
|
2421
2664
|
if (typeof window === "undefined") return true;
|
|
@@ -2690,27 +2933,6 @@ function isLowQualityText(text) {
|
|
|
2690
2933
|
}
|
|
2691
2934
|
return null;
|
|
2692
2935
|
}
|
|
2693
|
-
async function captureViaHtml2Canvas() {
|
|
2694
|
-
try {
|
|
2695
|
-
const { default: html2canvas } = await import("html2canvas-pro");
|
|
2696
|
-
const scale = Math.min(Math.max(window.devicePixelRatio || 1, 1), 2);
|
|
2697
|
-
const canvas = await html2canvas(document.body, {
|
|
2698
|
-
scale,
|
|
2699
|
-
logging: false,
|
|
2700
|
-
useCORS: true,
|
|
2701
|
-
allowTaint: true,
|
|
2702
|
-
x: window.scrollX,
|
|
2703
|
-
y: window.scrollY,
|
|
2704
|
-
width: window.innerWidth,
|
|
2705
|
-
height: window.innerHeight,
|
|
2706
|
-
windowWidth: window.innerWidth,
|
|
2707
|
-
windowHeight: window.innerHeight
|
|
2708
|
-
});
|
|
2709
|
-
return encodeScreenshot(canvas);
|
|
2710
|
-
} catch (e) {
|
|
2711
|
-
return null;
|
|
2712
|
-
}
|
|
2713
|
-
}
|
|
2714
2936
|
var MIC_MESSAGES = {
|
|
2715
2937
|
blocked: "Microphone is blocked for this site. Allow it in your browser's site settings, then reload this page. You can type your report instead.",
|
|
2716
2938
|
notFound: "No microphone found. Connect one and try again, or type your report instead.",
|
|
@@ -2748,7 +2970,7 @@ function ReportDialog({
|
|
|
2748
2970
|
transcribeAudio: transcribeAudio2,
|
|
2749
2971
|
types,
|
|
2750
2972
|
showSeverity = true,
|
|
2751
|
-
captureScreenshot =
|
|
2973
|
+
captureScreenshot = captureDefaultScreenshot,
|
|
2752
2974
|
reporter,
|
|
2753
2975
|
onClose,
|
|
2754
2976
|
headerSlot
|
|
@@ -2778,6 +3000,7 @@ function ReportDialog({
|
|
|
2778
3000
|
const [isSubmitting, setIsSubmitting] = useState3(false);
|
|
2779
3001
|
const [submitted, setSubmitted] = useState3(false);
|
|
2780
3002
|
const [screenshots, setScreenshots] = useState3([]);
|
|
3003
|
+
const [pageShot, setPageShot] = useState3(null);
|
|
2781
3004
|
const [attachments, setAttachments] = useState3([]);
|
|
2782
3005
|
const [previewIndex, setPreviewIndex] = useState3(null);
|
|
2783
3006
|
const [annotatingIndex, setAnnotatingIndex] = useState3(null);
|
|
@@ -2943,6 +3166,7 @@ function ReportDialog({
|
|
|
2943
3166
|
setStep(2);
|
|
2944
3167
|
}
|
|
2945
3168
|
const shot = await captureScreenshot();
|
|
3169
|
+
setPageShot(shot != null ? shot : null);
|
|
2946
3170
|
if (shot) setScreenshots([shot]);
|
|
2947
3171
|
if (assist && !assistUsed) setAssistOpen(true);
|
|
2948
3172
|
setIsOpen(true);
|
|
@@ -5140,6 +5364,7 @@ function ReportDialog({
|
|
|
5140
5364
|
imageSrc: screenshots[annotatingIndex],
|
|
5141
5365
|
onCancel: () => setAnnotatingIndex(null),
|
|
5142
5366
|
onSave: (dataUrl) => {
|
|
5367
|
+
if (screenshots[annotatingIndex] === pageShot) setPageShot(dataUrl);
|
|
5143
5368
|
setScreenshots(
|
|
5144
5369
|
(prev) => prev.map((s, i) => i === annotatingIndex ? dataUrl : s)
|
|
5145
5370
|
);
|
|
@@ -5165,6 +5390,7 @@ function ReportDialog({
|
|
|
5165
5390
|
accentText: t2.accentText
|
|
5166
5391
|
},
|
|
5167
5392
|
screenshots,
|
|
5393
|
+
pageShot,
|
|
5168
5394
|
onAddImages: addFiles,
|
|
5169
5395
|
attachmentCount: screenshots.length + attachments.length,
|
|
5170
5396
|
context: { ...assistContext != null ? assistContext : {}, reportType },
|