@bbearai/react-native 0.9.0 → 0.9.2
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/dist/index.js +842 -422
- package/dist/index.mjs +842 -422
- package/package.json +1 -1
package/dist/index.mjs
CHANGED
|
@@ -12760,55 +12760,66 @@ var BugBearClient = class {
|
|
|
12760
12760
|
...pendingResult.data || [],
|
|
12761
12761
|
...completedResult.data || []
|
|
12762
12762
|
];
|
|
12763
|
-
const mapItem = (item) =>
|
|
12764
|
-
|
|
12765
|
-
|
|
12766
|
-
|
|
12767
|
-
|
|
12768
|
-
|
|
12769
|
-
|
|
12770
|
-
|
|
12771
|
-
|
|
12772
|
-
|
|
12773
|
-
|
|
12774
|
-
|
|
12775
|
-
|
|
12776
|
-
|
|
12777
|
-
|
|
12778
|
-
|
|
12779
|
-
|
|
12780
|
-
|
|
12781
|
-
|
|
12782
|
-
|
|
12783
|
-
|
|
12784
|
-
|
|
12785
|
-
|
|
12786
|
-
|
|
12787
|
-
|
|
12788
|
-
|
|
12789
|
-
|
|
12790
|
-
|
|
12791
|
-
|
|
12792
|
-
|
|
12793
|
-
|
|
12794
|
-
|
|
12795
|
-
|
|
12796
|
-
|
|
12797
|
-
|
|
12798
|
-
|
|
12799
|
-
|
|
12800
|
-
|
|
12801
|
-
|
|
12802
|
-
|
|
12803
|
-
|
|
12804
|
-
|
|
12805
|
-
|
|
12806
|
-
|
|
12807
|
-
|
|
12808
|
-
|
|
12809
|
-
|
|
12810
|
-
|
|
12811
|
-
|
|
12763
|
+
const mapItem = (item) => {
|
|
12764
|
+
const tc = item.test_case;
|
|
12765
|
+
return {
|
|
12766
|
+
id: item.id,
|
|
12767
|
+
status: item.status,
|
|
12768
|
+
startedAt: item.started_at,
|
|
12769
|
+
skipReason: item.skip_reason,
|
|
12770
|
+
isVerification: item.is_verification || false,
|
|
12771
|
+
originalReportId: item.original_report_id,
|
|
12772
|
+
testCase: tc ? {
|
|
12773
|
+
id: tc.id,
|
|
12774
|
+
title: tc.title,
|
|
12775
|
+
testKey: tc.test_key,
|
|
12776
|
+
description: tc.description,
|
|
12777
|
+
steps: tc.steps,
|
|
12778
|
+
expectedResult: tc.expected_result,
|
|
12779
|
+
priority: tc.priority,
|
|
12780
|
+
targetRoute: tc.target_route,
|
|
12781
|
+
track: tc.track ? {
|
|
12782
|
+
id: tc.track.id,
|
|
12783
|
+
name: tc.track.name,
|
|
12784
|
+
icon: tc.track.icon,
|
|
12785
|
+
color: tc.track.color,
|
|
12786
|
+
testTemplate: tc.track.test_template,
|
|
12787
|
+
rubricMode: tc.track.rubric_mode || "pass_fail",
|
|
12788
|
+
description: tc.track.description
|
|
12789
|
+
} : void 0,
|
|
12790
|
+
group: tc.group ? {
|
|
12791
|
+
id: tc.group.id,
|
|
12792
|
+
name: tc.group.name,
|
|
12793
|
+
description: tc.group.description,
|
|
12794
|
+
sortOrder: tc.group.sort_order
|
|
12795
|
+
} : void 0,
|
|
12796
|
+
role: tc.role ? {
|
|
12797
|
+
id: tc.role.id,
|
|
12798
|
+
name: tc.role.name,
|
|
12799
|
+
slug: tc.role.slug,
|
|
12800
|
+
color: tc.role.color,
|
|
12801
|
+
description: tc.role.description,
|
|
12802
|
+
loginHint: tc.role.login_hint
|
|
12803
|
+
} : void 0,
|
|
12804
|
+
platforms: tc.platforms || void 0
|
|
12805
|
+
} : {
|
|
12806
|
+
// Standalone verification assignment (bug reported without a test case)
|
|
12807
|
+
id: item.original_report_id || item.id,
|
|
12808
|
+
title: item.notes || "Bug Verification",
|
|
12809
|
+
testKey: "VERIFY",
|
|
12810
|
+
description: "Verify that the reported bug has been fixed",
|
|
12811
|
+
steps: [],
|
|
12812
|
+
expectedResult: "The bug should no longer be reproducible",
|
|
12813
|
+
priority: "P1",
|
|
12814
|
+
targetRoute: void 0,
|
|
12815
|
+
track: void 0,
|
|
12816
|
+
group: void 0,
|
|
12817
|
+
role: void 0,
|
|
12818
|
+
platforms: void 0
|
|
12819
|
+
}
|
|
12820
|
+
};
|
|
12821
|
+
};
|
|
12822
|
+
const mapped = allData.map(mapItem);
|
|
12812
12823
|
mapped.sort((a, b) => {
|
|
12813
12824
|
if (a.isVerification && !b.isVerification) return -1;
|
|
12814
12825
|
if (!a.isVerification && b.isVerification) return 1;
|
|
@@ -13322,7 +13333,11 @@ var BugBearClient = class {
|
|
|
13322
13333
|
verifiedByName: row.verified_by_name || void 0,
|
|
13323
13334
|
verifiedAt: row.verified_at || void 0,
|
|
13324
13335
|
originalBugId: row.original_bug_id || void 0,
|
|
13325
|
-
originalBugTitle: row.original_bug_title || void 0
|
|
13336
|
+
originalBugTitle: row.original_bug_title || void 0,
|
|
13337
|
+
resolutionNotes: row.resolution_notes || void 0,
|
|
13338
|
+
fixCommitSha: row.code_context?.fix?.commit_sha || void 0,
|
|
13339
|
+
fixCommitMessage: row.code_context?.fix?.commit_message || void 0,
|
|
13340
|
+
fixFilesChanged: row.code_context?.fix?.files_changed || void 0
|
|
13326
13341
|
}));
|
|
13327
13342
|
} catch (err) {
|
|
13328
13343
|
console.error("BugBear: Error fetching issues", err);
|
|
@@ -15147,19 +15162,19 @@ function BugBearProvider({ config, children, appVersion, enabled = true }) {
|
|
|
15147
15162
|
}
|
|
15148
15163
|
|
|
15149
15164
|
// src/BugBearButton.tsx
|
|
15150
|
-
import
|
|
15165
|
+
import React22, { useState as useState19, useRef as useRef8, useEffect as useEffect13, useMemo as useMemo16, useCallback as useCallback7 } from "react";
|
|
15151
15166
|
import {
|
|
15152
|
-
View as
|
|
15153
|
-
Text as
|
|
15167
|
+
View as View22,
|
|
15168
|
+
Text as Text20,
|
|
15154
15169
|
Image as Image4,
|
|
15155
|
-
TouchableOpacity as
|
|
15170
|
+
TouchableOpacity as TouchableOpacity19,
|
|
15156
15171
|
ScrollView as ScrollView4,
|
|
15157
|
-
StyleSheet as
|
|
15158
|
-
Dimensions as
|
|
15172
|
+
StyleSheet as StyleSheet22,
|
|
15173
|
+
Dimensions as Dimensions3,
|
|
15159
15174
|
KeyboardAvoidingView,
|
|
15160
15175
|
Platform as Platform5,
|
|
15161
|
-
PanResponder,
|
|
15162
|
-
Animated as
|
|
15176
|
+
PanResponder as PanResponder2,
|
|
15177
|
+
Animated as Animated4,
|
|
15163
15178
|
ActivityIndicator as ActivityIndicator3,
|
|
15164
15179
|
Keyboard as Keyboard4,
|
|
15165
15180
|
BackHandler
|
|
@@ -15218,6 +15233,11 @@ async function captureAppScreen() {
|
|
|
15218
15233
|
}
|
|
15219
15234
|
}
|
|
15220
15235
|
|
|
15236
|
+
// src/widget/animatedUtils.ts
|
|
15237
|
+
function getAnimatedValue(value) {
|
|
15238
|
+
return value._value;
|
|
15239
|
+
}
|
|
15240
|
+
|
|
15221
15241
|
// src/widget/screens/HomeScreen.tsx
|
|
15222
15242
|
import React3, { useEffect as useEffect3, useState as useState2, useRef as useRef3, useMemo } from "react";
|
|
15223
15243
|
import { View as View3, Text, TouchableOpacity, StyleSheet as StyleSheet3, Linking } from "react-native";
|
|
@@ -15302,7 +15322,7 @@ var s = StyleSheet2.create({
|
|
|
15302
15322
|
// src/widget/screens/HomeScreen.tsx
|
|
15303
15323
|
function HomeScreen({ nav }) {
|
|
15304
15324
|
const { assignments, unreadCount, threads, refreshAssignments, refreshThreads, issueCounts, refreshIssueCounts, dashboardUrl, isLoading, activeSession, sessionFindings, refreshSession, widgetMode, widgetColorScheme } = useBugBear();
|
|
15305
|
-
const
|
|
15325
|
+
const styles6 = useMemo(() => createStyles(), [widgetColorScheme]);
|
|
15306
15326
|
const [sessionElapsed, setSessionElapsed] = useState2(0);
|
|
15307
15327
|
const timerRef = useRef3(null);
|
|
15308
15328
|
useEffect3(() => {
|
|
@@ -15331,98 +15351,98 @@ function HomeScreen({ nav }) {
|
|
|
15331
15351
|
return /* @__PURE__ */ React3.createElement(View3, null, unreadCount > 0 ? /* @__PURE__ */ React3.createElement(
|
|
15332
15352
|
TouchableOpacity,
|
|
15333
15353
|
{
|
|
15334
|
-
style: [
|
|
15354
|
+
style: [styles6.heroBanner, styles6.heroBannerMessages],
|
|
15335
15355
|
onPress: () => nav.push({ name: "MESSAGE_LIST" }),
|
|
15336
15356
|
activeOpacity: 0.8
|
|
15337
15357
|
},
|
|
15338
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15339
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15340
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15341
|
-
) : /* @__PURE__ */ React3.createElement(View3, { style: [
|
|
15358
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.heroCount }, unreadCount),
|
|
15359
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.heroLabel }, "unread message", unreadCount !== 1 ? "s" : ""),
|
|
15360
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.heroAction }, "View Messages \u2192")
|
|
15361
|
+
) : /* @__PURE__ */ React3.createElement(View3, { style: [styles6.heroBanner, styles6.heroBannerClear] }, /* @__PURE__ */ React3.createElement(Text, { style: styles6.heroClearEmoji }, "\u{1F4AC}"), /* @__PURE__ */ React3.createElement(Text, { style: styles6.heroClearTitle }, "Help us improve"), /* @__PURE__ */ React3.createElement(Text, { style: styles6.heroClearSub }, "Report bugs, share ideas, and track your submissions")), /* @__PURE__ */ React3.createElement(View3, { style: styles6.actionGrid }, /* @__PURE__ */ React3.createElement(
|
|
15342
15362
|
TouchableOpacity,
|
|
15343
15363
|
{
|
|
15344
|
-
style:
|
|
15364
|
+
style: styles6.actionCard,
|
|
15345
15365
|
onPress: () => nav.push({ name: "REPORT", prefill: { type: "bug" } }),
|
|
15346
15366
|
activeOpacity: 0.7
|
|
15347
15367
|
},
|
|
15348
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15349
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15368
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.actionIcon }, "\u{1F41B}"),
|
|
15369
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.actionLabel }, "Report Bug")
|
|
15350
15370
|
), /* @__PURE__ */ React3.createElement(
|
|
15351
15371
|
TouchableOpacity,
|
|
15352
15372
|
{
|
|
15353
|
-
style:
|
|
15373
|
+
style: styles6.actionCard,
|
|
15354
15374
|
onPress: () => nav.push({ name: "REPORT", prefill: { type: "feedback" } }),
|
|
15355
15375
|
activeOpacity: 0.7
|
|
15356
15376
|
},
|
|
15357
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15358
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15377
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.actionIcon }, "\u{1F4A1}"),
|
|
15378
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.actionLabel }, "Share Feedback")
|
|
15359
15379
|
), /* @__PURE__ */ React3.createElement(
|
|
15360
15380
|
TouchableOpacity,
|
|
15361
15381
|
{
|
|
15362
|
-
style:
|
|
15382
|
+
style: styles6.actionCard,
|
|
15363
15383
|
onPress: () => nav.push({ name: "MESSAGE_LIST" }),
|
|
15364
15384
|
activeOpacity: 0.7
|
|
15365
15385
|
},
|
|
15366
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15367
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15368
|
-
unreadCount > 0 && /* @__PURE__ */ React3.createElement(View3, { style: [
|
|
15386
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.actionIcon }, "\u{1F4AC}"),
|
|
15387
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.actionLabel }, "Messages"),
|
|
15388
|
+
unreadCount > 0 && /* @__PURE__ */ React3.createElement(View3, { style: [styles6.actionBadge, styles6.actionBadgeMsg] }, /* @__PURE__ */ React3.createElement(Text, { style: styles6.actionBadgeText }, unreadCount))
|
|
15369
15389
|
), /* @__PURE__ */ React3.createElement(
|
|
15370
15390
|
TouchableOpacity,
|
|
15371
15391
|
{
|
|
15372
|
-
style:
|
|
15392
|
+
style: styles6.actionCard,
|
|
15373
15393
|
onPress: () => nav.push({ name: "ISSUE_LIST", category: "open" }),
|
|
15374
15394
|
activeOpacity: 0.7
|
|
15375
15395
|
},
|
|
15376
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15377
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15378
|
-
issueCounts.open > 0 && /* @__PURE__ */ React3.createElement(View3, { style: [
|
|
15379
|
-
)), /* @__PURE__ */ React3.createElement(View3, { style:
|
|
15396
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.actionIcon }, "\u{1F4CB}"),
|
|
15397
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.actionLabel }, "My Issues"),
|
|
15398
|
+
issueCounts.open > 0 && /* @__PURE__ */ React3.createElement(View3, { style: [styles6.actionBadge, styles6.actionBadgeIssue] }, /* @__PURE__ */ React3.createElement(Text, { style: styles6.actionBadgeText }, issueCounts.open))
|
|
15399
|
+
)), /* @__PURE__ */ React3.createElement(View3, { style: styles6.issueGrid }, /* @__PURE__ */ React3.createElement(
|
|
15380
15400
|
TouchableOpacity,
|
|
15381
15401
|
{
|
|
15382
|
-
style: [
|
|
15402
|
+
style: [styles6.issueCard, styles6.issueCardOpen],
|
|
15383
15403
|
onPress: () => nav.push({ name: "ISSUE_LIST", category: "open" }),
|
|
15384
15404
|
activeOpacity: 0.7
|
|
15385
15405
|
},
|
|
15386
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15387
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15406
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.issueCountOpen }, issueCounts.open),
|
|
15407
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.issueLabel }, "Open")
|
|
15388
15408
|
), /* @__PURE__ */ React3.createElement(
|
|
15389
15409
|
TouchableOpacity,
|
|
15390
15410
|
{
|
|
15391
|
-
style: [
|
|
15411
|
+
style: [styles6.issueCard, styles6.issueCardDone],
|
|
15392
15412
|
onPress: () => nav.push({ name: "ISSUE_LIST", category: "done" }),
|
|
15393
15413
|
activeOpacity: 0.7
|
|
15394
15414
|
},
|
|
15395
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15396
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15415
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.issueCountDone }, issueCounts.done),
|
|
15416
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.issueLabel }, "Done")
|
|
15397
15417
|
), /* @__PURE__ */ React3.createElement(
|
|
15398
15418
|
TouchableOpacity,
|
|
15399
15419
|
{
|
|
15400
|
-
style: [
|
|
15420
|
+
style: [styles6.issueCard, styles6.issueCardReopened],
|
|
15401
15421
|
onPress: () => nav.push({ name: "ISSUE_LIST", category: "reopened" }),
|
|
15402
15422
|
activeOpacity: 0.7
|
|
15403
15423
|
},
|
|
15404
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15405
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15424
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.issueCountReopened }, issueCounts.reopened),
|
|
15425
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.issueLabel }, "Reopened")
|
|
15406
15426
|
)), dashboardUrl && /* @__PURE__ */ React3.createElement(
|
|
15407
15427
|
TouchableOpacity,
|
|
15408
15428
|
{
|
|
15409
|
-
style:
|
|
15429
|
+
style: styles6.webAppLink,
|
|
15410
15430
|
onPress: () => Linking.openURL(dashboardUrl),
|
|
15411
15431
|
activeOpacity: 0.7
|
|
15412
15432
|
},
|
|
15413
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15414
|
-
/* @__PURE__ */ React3.createElement(View3, { style:
|
|
15415
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15433
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.webAppIcon }, "\u{1F310}"),
|
|
15434
|
+
/* @__PURE__ */ React3.createElement(View3, { style: styles6.webAppTextWrap }, /* @__PURE__ */ React3.createElement(Text, { style: styles6.webAppTitle }, "Open Web Dashboard"), /* @__PURE__ */ React3.createElement(Text, { style: styles6.webAppSub }, "View your submissions & updates")),
|
|
15435
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.webAppArrow }, "\u2192")
|
|
15416
15436
|
), /* @__PURE__ */ React3.createElement(
|
|
15417
15437
|
TouchableOpacity,
|
|
15418
15438
|
{
|
|
15419
|
-
style:
|
|
15439
|
+
style: styles6.refreshButton,
|
|
15420
15440
|
onPress: () => {
|
|
15421
15441
|
refreshThreads();
|
|
15422
15442
|
refreshIssueCounts();
|
|
15423
15443
|
}
|
|
15424
15444
|
},
|
|
15425
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15445
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.refreshText }, "\u21BB Refresh")
|
|
15426
15446
|
));
|
|
15427
15447
|
}
|
|
15428
15448
|
const formatTimer = (s2) => {
|
|
@@ -15439,130 +15459,130 @@ function HomeScreen({ nav }) {
|
|
|
15439
15459
|
return /* @__PURE__ */ React3.createElement(View3, null, pendingCount > 0 ? /* @__PURE__ */ React3.createElement(
|
|
15440
15460
|
TouchableOpacity,
|
|
15441
15461
|
{
|
|
15442
|
-
style: [
|
|
15462
|
+
style: [styles6.heroBanner, styles6.heroBannerTests],
|
|
15443
15463
|
onPress: () => nav.push({ name: "TEST_DETAIL" }),
|
|
15444
15464
|
activeOpacity: 0.8
|
|
15445
15465
|
},
|
|
15446
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15447
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15448
|
-
retestCount > 0 && /* @__PURE__ */ React3.createElement(View3, { style:
|
|
15449
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15466
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.heroCount }, pendingCount),
|
|
15467
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.heroLabel }, "test", pendingCount !== 1 ? "s" : "", " waiting"),
|
|
15468
|
+
retestCount > 0 && /* @__PURE__ */ React3.createElement(View3, { style: styles6.retestPill }, /* @__PURE__ */ React3.createElement(Text, { style: styles6.retestPillText }, "\u{1F504} ", retestCount, " retest", retestCount !== 1 ? "s" : "")),
|
|
15469
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.heroAction }, "Start Testing \u2192")
|
|
15450
15470
|
) : unreadCount > 0 ? /* @__PURE__ */ React3.createElement(
|
|
15451
15471
|
TouchableOpacity,
|
|
15452
15472
|
{
|
|
15453
|
-
style: [
|
|
15473
|
+
style: [styles6.heroBanner, styles6.heroBannerMessages],
|
|
15454
15474
|
onPress: () => nav.push({ name: "MESSAGE_LIST" }),
|
|
15455
15475
|
activeOpacity: 0.8
|
|
15456
15476
|
},
|
|
15457
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15458
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15459
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15460
|
-
) : /* @__PURE__ */ React3.createElement(View3, { style: [
|
|
15477
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.heroCount }, unreadCount),
|
|
15478
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.heroLabel }, "unread message", unreadCount !== 1 ? "s" : ""),
|
|
15479
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.heroAction }, "View Messages \u2192")
|
|
15480
|
+
) : /* @__PURE__ */ React3.createElement(View3, { style: [styles6.heroBanner, styles6.heroBannerClear] }, /* @__PURE__ */ React3.createElement(Text, { style: styles6.heroClearEmoji }, "\u2705"), /* @__PURE__ */ React3.createElement(Text, { style: styles6.heroClearTitle }, "All caught up!"), totalTests > 0 && /* @__PURE__ */ React3.createElement(Text, { style: styles6.heroClearSub }, completedCount, "/", totalTests, " tests completed")), activeSession && activeSession.status === "active" ? /* @__PURE__ */ React3.createElement(
|
|
15461
15481
|
TouchableOpacity,
|
|
15462
15482
|
{
|
|
15463
|
-
style:
|
|
15483
|
+
style: styles6.sessionCardActive,
|
|
15464
15484
|
onPress: () => nav.push({ name: "SESSION_ACTIVE" }),
|
|
15465
15485
|
activeOpacity: 0.8
|
|
15466
15486
|
},
|
|
15467
|
-
/* @__PURE__ */ React3.createElement(View3, { style:
|
|
15468
|
-
/* @__PURE__ */ React3.createElement(View3, { style:
|
|
15469
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15487
|
+
/* @__PURE__ */ React3.createElement(View3, { style: styles6.sessionDot }),
|
|
15488
|
+
/* @__PURE__ */ React3.createElement(View3, { style: styles6.sessionCardContent }, /* @__PURE__ */ React3.createElement(Text, { style: styles6.sessionCardTitle, numberOfLines: 1 }, activeSession.focusArea || "QA Session"), /* @__PURE__ */ React3.createElement(Text, { style: styles6.sessionCardMeta }, formatTimer(sessionElapsed), " \xB7 ", sessionFindings.length, " finding", sessionFindings.length !== 1 ? "s" : "")),
|
|
15489
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.sessionCardAction }, "Resume \u2192")
|
|
15470
15490
|
) : /* @__PURE__ */ React3.createElement(
|
|
15471
15491
|
TouchableOpacity,
|
|
15472
15492
|
{
|
|
15473
|
-
style:
|
|
15493
|
+
style: styles6.sessionCardInactive,
|
|
15474
15494
|
onPress: () => nav.push({ name: "SESSION_START" }),
|
|
15475
15495
|
activeOpacity: 0.7
|
|
15476
15496
|
},
|
|
15477
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15478
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15479
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15480
|
-
), /* @__PURE__ */ React3.createElement(View3, { style:
|
|
15497
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.sessionCardIcon }, "\u{1F50D}"),
|
|
15498
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.sessionCardLabel }, "Start QA Session"),
|
|
15499
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.sessionCardArrow }, "\u2192")
|
|
15500
|
+
), /* @__PURE__ */ React3.createElement(View3, { style: styles6.actionGrid }, /* @__PURE__ */ React3.createElement(
|
|
15481
15501
|
TouchableOpacity,
|
|
15482
15502
|
{
|
|
15483
|
-
style:
|
|
15503
|
+
style: styles6.actionCard,
|
|
15484
15504
|
onPress: () => nav.push({ name: "TEST_LIST" }),
|
|
15485
15505
|
activeOpacity: 0.7
|
|
15486
15506
|
},
|
|
15487
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15488
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15489
|
-
pendingCount > 0 && /* @__PURE__ */ React3.createElement(View3, { style:
|
|
15507
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.actionIcon }, "\u2705"),
|
|
15508
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.actionLabel }, "Tests"),
|
|
15509
|
+
pendingCount > 0 && /* @__PURE__ */ React3.createElement(View3, { style: styles6.actionBadge }, /* @__PURE__ */ React3.createElement(Text, { style: styles6.actionBadgeText }, pendingCount))
|
|
15490
15510
|
), /* @__PURE__ */ React3.createElement(
|
|
15491
15511
|
TouchableOpacity,
|
|
15492
15512
|
{
|
|
15493
|
-
style:
|
|
15513
|
+
style: styles6.actionCard,
|
|
15494
15514
|
onPress: () => nav.push({ name: "REPORT", prefill: { type: "bug" } }),
|
|
15495
15515
|
activeOpacity: 0.7
|
|
15496
15516
|
},
|
|
15497
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15498
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15517
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.actionIcon }, "\u{1F41B}"),
|
|
15518
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.actionLabel }, "Report Bug")
|
|
15499
15519
|
), /* @__PURE__ */ React3.createElement(
|
|
15500
15520
|
TouchableOpacity,
|
|
15501
15521
|
{
|
|
15502
|
-
style:
|
|
15522
|
+
style: styles6.actionCard,
|
|
15503
15523
|
onPress: () => nav.push({ name: "REPORT", prefill: { type: "feedback" } }),
|
|
15504
15524
|
activeOpacity: 0.7
|
|
15505
15525
|
},
|
|
15506
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15507
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15526
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.actionIcon }, "\u{1F4A1}"),
|
|
15527
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.actionLabel }, "Feedback")
|
|
15508
15528
|
), /* @__PURE__ */ React3.createElement(
|
|
15509
15529
|
TouchableOpacity,
|
|
15510
15530
|
{
|
|
15511
|
-
style:
|
|
15531
|
+
style: styles6.actionCard,
|
|
15512
15532
|
onPress: () => nav.push({ name: "MESSAGE_LIST" }),
|
|
15513
15533
|
activeOpacity: 0.7
|
|
15514
15534
|
},
|
|
15515
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15516
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15517
|
-
unreadCount > 0 && /* @__PURE__ */ React3.createElement(View3, { style: [
|
|
15518
|
-
)), /* @__PURE__ */ React3.createElement(View3, { style:
|
|
15535
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.actionIcon }, "\u{1F4AC}"),
|
|
15536
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.actionLabel }, "Messages"),
|
|
15537
|
+
unreadCount > 0 && /* @__PURE__ */ React3.createElement(View3, { style: [styles6.actionBadge, styles6.actionBadgeMsg] }, /* @__PURE__ */ React3.createElement(Text, { style: styles6.actionBadgeText }, unreadCount))
|
|
15538
|
+
)), /* @__PURE__ */ React3.createElement(View3, { style: styles6.issueGrid }, /* @__PURE__ */ React3.createElement(
|
|
15519
15539
|
TouchableOpacity,
|
|
15520
15540
|
{
|
|
15521
|
-
style: [
|
|
15541
|
+
style: [styles6.issueCard, styles6.issueCardOpen],
|
|
15522
15542
|
onPress: () => nav.push({ name: "ISSUE_LIST", category: "open" }),
|
|
15523
15543
|
activeOpacity: 0.7
|
|
15524
15544
|
},
|
|
15525
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15526
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15545
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.issueCountOpen }, issueCounts.open),
|
|
15546
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.issueLabel }, "Open")
|
|
15527
15547
|
), /* @__PURE__ */ React3.createElement(
|
|
15528
15548
|
TouchableOpacity,
|
|
15529
15549
|
{
|
|
15530
|
-
style: [
|
|
15550
|
+
style: [styles6.issueCard, styles6.issueCardDone],
|
|
15531
15551
|
onPress: () => nav.push({ name: "ISSUE_LIST", category: "done" }),
|
|
15532
15552
|
activeOpacity: 0.7
|
|
15533
15553
|
},
|
|
15534
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15535
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15554
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.issueCountDone }, issueCounts.done),
|
|
15555
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.issueLabel }, "Done")
|
|
15536
15556
|
), /* @__PURE__ */ React3.createElement(
|
|
15537
15557
|
TouchableOpacity,
|
|
15538
15558
|
{
|
|
15539
|
-
style: [
|
|
15559
|
+
style: [styles6.issueCard, styles6.issueCardReopened],
|
|
15540
15560
|
onPress: () => nav.push({ name: "ISSUE_LIST", category: "reopened" }),
|
|
15541
15561
|
activeOpacity: 0.7
|
|
15542
15562
|
},
|
|
15543
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15544
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15545
|
-
)), totalTests > 0 && /* @__PURE__ */ React3.createElement(View3, { style:
|
|
15563
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.issueCountReopened }, issueCounts.reopened),
|
|
15564
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.issueLabel }, "Reopened")
|
|
15565
|
+
)), totalTests > 0 && /* @__PURE__ */ React3.createElement(View3, { style: styles6.progressSection }, /* @__PURE__ */ React3.createElement(View3, { style: styles6.progressBar }, /* @__PURE__ */ React3.createElement(View3, { style: [styles6.progressFill, { width: `${Math.round(completedCount / totalTests * 100)}%` }] })), /* @__PURE__ */ React3.createElement(Text, { style: styles6.progressText }, completedCount, "/", totalTests, " tests completed")), dashboardUrl && /* @__PURE__ */ React3.createElement(
|
|
15546
15566
|
TouchableOpacity,
|
|
15547
15567
|
{
|
|
15548
|
-
style:
|
|
15568
|
+
style: styles6.webAppLink,
|
|
15549
15569
|
onPress: () => Linking.openURL(dashboardUrl),
|
|
15550
15570
|
activeOpacity: 0.7
|
|
15551
15571
|
},
|
|
15552
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15553
|
-
/* @__PURE__ */ React3.createElement(View3, { style:
|
|
15554
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15572
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.webAppIcon }, "\u{1F310}"),
|
|
15573
|
+
/* @__PURE__ */ React3.createElement(View3, { style: styles6.webAppTextWrap }, /* @__PURE__ */ React3.createElement(Text, { style: styles6.webAppTitle }, "Open Web Dashboard"), /* @__PURE__ */ React3.createElement(Text, { style: styles6.webAppSub }, "View analytics, history & more")),
|
|
15574
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.webAppArrow }, "\u2192")
|
|
15555
15575
|
), /* @__PURE__ */ React3.createElement(
|
|
15556
15576
|
TouchableOpacity,
|
|
15557
15577
|
{
|
|
15558
|
-
style:
|
|
15578
|
+
style: styles6.refreshButton,
|
|
15559
15579
|
onPress: () => {
|
|
15560
15580
|
refreshAssignments();
|
|
15561
15581
|
refreshThreads();
|
|
15562
15582
|
refreshIssueCounts();
|
|
15563
15583
|
}
|
|
15564
15584
|
},
|
|
15565
|
-
/* @__PURE__ */ React3.createElement(Text, { style:
|
|
15585
|
+
/* @__PURE__ */ React3.createElement(Text, { style: styles6.refreshText }, "\u21BB Refresh")
|
|
15566
15586
|
));
|
|
15567
15587
|
}
|
|
15568
15588
|
function createStyles() {
|
|
@@ -15856,11 +15876,11 @@ function createStyles() {
|
|
|
15856
15876
|
}
|
|
15857
15877
|
|
|
15858
15878
|
// src/widget/screens/TestDetailScreen.tsx
|
|
15859
|
-
import React4, { useState as useState3, useEffect as useEffect4, useCallback as useCallback2, useMemo as useMemo2 } from "react";
|
|
15860
|
-
import { View as View4, Text as Text2, TouchableOpacity as TouchableOpacity2, StyleSheet as StyleSheet4, Modal, TextInput, Keyboard } from "react-native";
|
|
15879
|
+
import React4, { useState as useState3, useEffect as useEffect4, useCallback as useCallback2, useMemo as useMemo2, useRef as useRef4 } from "react";
|
|
15880
|
+
import { View as View4, Text as Text2, TouchableOpacity as TouchableOpacity2, StyleSheet as StyleSheet4, Modal, TextInput, Keyboard, Animated as Animated2 } from "react-native";
|
|
15861
15881
|
function TestDetailScreen({ testId, nav }) {
|
|
15862
15882
|
const { client, assignments, currentAssignment, refreshAssignments, getDeviceInfo, onNavigate, widgetColorScheme } = useBugBear();
|
|
15863
|
-
const
|
|
15883
|
+
const styles6 = useMemo2(() => createStyles2(), [widgetColorScheme]);
|
|
15864
15884
|
const displayedAssignment = testId ? assignments.find((a) => a.id === testId) || currentAssignment : currentAssignment;
|
|
15865
15885
|
const [showSteps, setShowSteps] = useState3(true);
|
|
15866
15886
|
const [showDetails, setShowDetails] = useState3(false);
|
|
@@ -15871,6 +15891,20 @@ function TestDetailScreen({ testId, nav }) {
|
|
|
15871
15891
|
const [skipNotes, setSkipNotes] = useState3("");
|
|
15872
15892
|
const [skipping, setSkipping] = useState3(false);
|
|
15873
15893
|
const [isSubmitting, setIsSubmitting] = useState3(false);
|
|
15894
|
+
const [feedbackToastAssignmentId, setFeedbackToastAssignmentId] = useState3(null);
|
|
15895
|
+
const toastTimerRef = useRef4(null);
|
|
15896
|
+
const toastSlideAnim = useRef4(new Animated2.Value(80)).current;
|
|
15897
|
+
useEffect4(() => {
|
|
15898
|
+
return () => {
|
|
15899
|
+
if (toastTimerRef.current) clearTimeout(toastTimerRef.current);
|
|
15900
|
+
};
|
|
15901
|
+
}, []);
|
|
15902
|
+
useEffect4(() => {
|
|
15903
|
+
if (feedbackToastAssignmentId) {
|
|
15904
|
+
toastSlideAnim.setValue(80);
|
|
15905
|
+
Animated2.spring(toastSlideAnim, { toValue: 0, useNativeDriver: true, tension: 80, friction: 10 }).start();
|
|
15906
|
+
}
|
|
15907
|
+
}, [feedbackToastAssignmentId]);
|
|
15874
15908
|
useEffect4(() => {
|
|
15875
15909
|
setCriteriaResults({});
|
|
15876
15910
|
setShowSteps(true);
|
|
@@ -15908,13 +15942,34 @@ function TestDetailScreen({ testId, nav }) {
|
|
|
15908
15942
|
Keyboard.dismiss();
|
|
15909
15943
|
setIsSubmitting(true);
|
|
15910
15944
|
try {
|
|
15911
|
-
|
|
15945
|
+
const passedId = displayedAssignment.id;
|
|
15946
|
+
const testCaseId = displayedAssignment.testCase.id;
|
|
15947
|
+
await client.passAssignment(passedId);
|
|
15948
|
+
client.submitTestFeedback({
|
|
15949
|
+
testCaseId,
|
|
15950
|
+
assignmentId: passedId,
|
|
15951
|
+
feedback: { rating: 5 }
|
|
15952
|
+
}).catch(() => {
|
|
15953
|
+
});
|
|
15912
15954
|
await refreshAssignments();
|
|
15913
|
-
|
|
15955
|
+
setFeedbackToastAssignmentId(passedId);
|
|
15956
|
+
if (toastTimerRef.current) clearTimeout(toastTimerRef.current);
|
|
15957
|
+
toastTimerRef.current = setTimeout(() => setFeedbackToastAssignmentId(null), 4e3);
|
|
15958
|
+
const currentIdx = assignments.indexOf(displayedAssignment);
|
|
15959
|
+
const remaining = assignments.filter(
|
|
15960
|
+
(a) => (a.status === "pending" || a.status === "in_progress") && a.id !== passedId
|
|
15961
|
+
);
|
|
15962
|
+
if (remaining.length > 0) {
|
|
15963
|
+
const nextAfterCurrent = remaining.find((a) => assignments.indexOf(a) > currentIdx);
|
|
15964
|
+
const nextTest = nextAfterCurrent || remaining[0];
|
|
15965
|
+
nav.replace({ name: "TEST_DETAIL", testId: nextTest.id });
|
|
15966
|
+
} else {
|
|
15967
|
+
nav.reset();
|
|
15968
|
+
}
|
|
15914
15969
|
} finally {
|
|
15915
15970
|
setIsSubmitting(false);
|
|
15916
15971
|
}
|
|
15917
|
-
}, [client, displayedAssignment, refreshAssignments, nav, isSubmitting]);
|
|
15972
|
+
}, [client, displayedAssignment, refreshAssignments, nav, isSubmitting, assignments]);
|
|
15918
15973
|
const handleFail = useCallback2(async () => {
|
|
15919
15974
|
if (!client || !displayedAssignment || isSubmitting) return;
|
|
15920
15975
|
Keyboard.dismiss();
|
|
@@ -16003,7 +16058,7 @@ function TestDetailScreen({ testId, nav }) {
|
|
|
16003
16058
|
const steps = testCase.steps;
|
|
16004
16059
|
const info = templateInfo[template] || templateInfo.steps;
|
|
16005
16060
|
const rubricMode = testCase.track?.rubricMode || "pass_fail";
|
|
16006
|
-
return /* @__PURE__ */ React4.createElement(View4, { style:
|
|
16061
|
+
return /* @__PURE__ */ React4.createElement(View4, { style: styles6.container }, /* @__PURE__ */ React4.createElement(View4, { style: styles6.topRow }, /* @__PURE__ */ React4.createElement(View4, { style: styles6.positionInfo }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.positionText }, "Test ", currentIndex + 1, " of ", allTests.length), displayedAssignment.status === "in_progress" && assignmentElapsedTime > 0 && /* @__PURE__ */ React4.createElement(View4, { style: styles6.timerBadge }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.timerText }, formatElapsedTime(assignmentElapsedTime)))), /* @__PURE__ */ React4.createElement(TouchableOpacity2, { onPress: () => nav.push({ name: "TEST_LIST" }) }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.viewAllLink }, "View All \u2192"))), displayedAssignment.isVerification && /* @__PURE__ */ React4.createElement(View4, { style: styles6.retestBanner }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.retestIcon }, "\u{1F504}"), /* @__PURE__ */ React4.createElement(Text2, { style: styles6.retestLabel }, "Retest"), /* @__PURE__ */ React4.createElement(Text2, { style: styles6.retestSub }, "\u2014 Verify bug fix")), /* @__PURE__ */ React4.createElement(Text2, { style: styles6.testTitle }, testCase.title), testCase.key && /* @__PURE__ */ React4.createElement(Text2, { style: styles6.testKey }, testCase.key), /* @__PURE__ */ React4.createElement(TouchableOpacity2, { onPress: () => setShowSteps(!showSteps), style: styles6.sectionHeader }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.sectionHeaderText }, showSteps ? "\u25BC" : "\u25B6", " ", info.icon, " ", template === "freeform" ? "Instructions" : `${steps.length} ${template === "checklist" ? "items" : template === "rubric" ? "criteria" : "steps"}`)), showSteps && /* @__PURE__ */ React4.createElement(View4, { style: styles6.templateContent }, template === "steps" && steps.map((step, idx) => /* @__PURE__ */ React4.createElement(View4, { key: idx, style: styles6.step }, /* @__PURE__ */ React4.createElement(View4, { style: styles6.stepNumber }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.stepNumberText }, step.stepNumber)), /* @__PURE__ */ React4.createElement(View4, { style: styles6.stepBody }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.stepAction }, step.action), step.expectedResult && /* @__PURE__ */ React4.createElement(Text2, { style: styles6.stepExpected }, "\u2192 ", step.expectedResult)))), template === "checklist" && /* @__PURE__ */ React4.createElement(React4.Fragment, null, steps.map((step, idx) => /* @__PURE__ */ React4.createElement(
|
|
16007
16062
|
TouchableOpacity2,
|
|
16008
16063
|
{
|
|
16009
16064
|
key: idx,
|
|
@@ -16013,76 +16068,95 @@ function TestDetailScreen({ testId, nav }) {
|
|
|
16013
16068
|
else next[idx] = true;
|
|
16014
16069
|
return next;
|
|
16015
16070
|
}),
|
|
16016
|
-
style: [
|
|
16071
|
+
style: [styles6.checklistItem, criteriaResults[idx] === true && styles6.checklistItemChecked]
|
|
16017
16072
|
},
|
|
16018
|
-
/* @__PURE__ */ React4.createElement(View4, { style: [
|
|
16019
|
-
/* @__PURE__ */ React4.createElement(Text2, { style: [
|
|
16020
|
-
)), Object.keys(criteriaResults).length > 0 && /* @__PURE__ */ React4.createElement(TouchableOpacity2, { onPress: () => setCriteriaResults({}), style:
|
|
16073
|
+
/* @__PURE__ */ React4.createElement(View4, { style: [styles6.checkbox, criteriaResults[idx] === true && styles6.checkboxChecked] }, criteriaResults[idx] === true && /* @__PURE__ */ React4.createElement(Text2, { style: styles6.checkmark }, "\u2713")),
|
|
16074
|
+
/* @__PURE__ */ React4.createElement(Text2, { style: [styles6.checklistText, criteriaResults[idx] === true && styles6.checklistTextDone] }, step.action)
|
|
16075
|
+
)), Object.keys(criteriaResults).length > 0 && /* @__PURE__ */ React4.createElement(TouchableOpacity2, { onPress: () => setCriteriaResults({}), style: styles6.resetRow }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.resetText }, "\u21BA Reset"))), template === "rubric" && steps.map((step, idx) => /* @__PURE__ */ React4.createElement(View4, { key: idx, style: styles6.rubricItem }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.rubricTitle }, idx + 1, ". ", step.action), step.expectedResult && /* @__PURE__ */ React4.createElement(Text2, { style: styles6.rubricExpected }, step.expectedResult), rubricMode === "pass_fail" ? /* @__PURE__ */ React4.createElement(View4, { style: styles6.passFailRow }, /* @__PURE__ */ React4.createElement(
|
|
16021
16076
|
TouchableOpacity2,
|
|
16022
16077
|
{
|
|
16023
16078
|
onPress: () => setCriteriaResults((prev) => ({ ...prev, [idx]: true })),
|
|
16024
|
-
style: [
|
|
16079
|
+
style: [styles6.pfButton, criteriaResults[idx] === true && styles6.pfButtonPass]
|
|
16025
16080
|
},
|
|
16026
|
-
/* @__PURE__ */ React4.createElement(Text2, { style: [
|
|
16081
|
+
/* @__PURE__ */ React4.createElement(Text2, { style: [styles6.pfButtonText, criteriaResults[idx] === true && styles6.pfButtonTextActive] }, "\u2713 Pass")
|
|
16027
16082
|
), /* @__PURE__ */ React4.createElement(
|
|
16028
16083
|
TouchableOpacity2,
|
|
16029
16084
|
{
|
|
16030
16085
|
onPress: () => setCriteriaResults((prev) => ({ ...prev, [idx]: false })),
|
|
16031
|
-
style: [
|
|
16086
|
+
style: [styles6.pfButton, criteriaResults[idx] === false && styles6.pfButtonFail]
|
|
16032
16087
|
},
|
|
16033
|
-
/* @__PURE__ */ React4.createElement(Text2, { style: [
|
|
16034
|
-
)) : /* @__PURE__ */ React4.createElement(View4, { style:
|
|
16088
|
+
/* @__PURE__ */ React4.createElement(Text2, { style: [styles6.pfButtonText, criteriaResults[idx] === false && styles6.pfButtonTextActive] }, "\u2717 Fail")
|
|
16089
|
+
)) : /* @__PURE__ */ React4.createElement(View4, { style: styles6.ratingRow }, [1, 2, 3, 4, 5].map((n) => /* @__PURE__ */ React4.createElement(
|
|
16035
16090
|
TouchableOpacity2,
|
|
16036
16091
|
{
|
|
16037
16092
|
key: n,
|
|
16038
16093
|
onPress: () => setCriteriaResults((prev) => ({ ...prev, [idx]: n })),
|
|
16039
|
-
style: [
|
|
16094
|
+
style: [styles6.ratingBtn, criteriaResults[idx] === n && styles6.ratingBtnActive]
|
|
16040
16095
|
},
|
|
16041
|
-
/* @__PURE__ */ React4.createElement(Text2, { style: [
|
|
16042
|
-
))))), template === "freeform" && /* @__PURE__ */ React4.createElement(View4, { style:
|
|
16096
|
+
/* @__PURE__ */ React4.createElement(Text2, { style: [styles6.ratingBtnText, criteriaResults[idx] === n && styles6.ratingBtnTextActive] }, n)
|
|
16097
|
+
))))), template === "freeform" && /* @__PURE__ */ React4.createElement(View4, { style: styles6.freeformBox }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.freeformText }, "Review the area and note:"), /* @__PURE__ */ React4.createElement(Text2, { style: styles6.freeformBullet }, "\u2022 What works well"), /* @__PURE__ */ React4.createElement(Text2, { style: styles6.freeformBullet }, "\u2022 Issues or concerns"), /* @__PURE__ */ React4.createElement(Text2, { style: styles6.freeformBullet }, "\u2022 Suggestions"))), testCase.expectedResult && /* @__PURE__ */ React4.createElement(View4, { style: styles6.expectedBox }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.expectedLabel }, "\u2705 Expected Result"), /* @__PURE__ */ React4.createElement(Text2, { style: styles6.expectedText }, testCase.expectedResult)), testCase.targetRoute && onNavigate && /* @__PURE__ */ React4.createElement(
|
|
16043
16098
|
TouchableOpacity2,
|
|
16044
16099
|
{
|
|
16045
|
-
style:
|
|
16100
|
+
style: styles6.navigateButton,
|
|
16046
16101
|
onPress: () => {
|
|
16047
16102
|
Keyboard.dismiss();
|
|
16048
16103
|
onNavigate(testCase.targetRoute);
|
|
16049
16104
|
nav.closeWidget?.();
|
|
16050
16105
|
}
|
|
16051
16106
|
},
|
|
16052
|
-
/* @__PURE__ */ React4.createElement(Text2, { style:
|
|
16053
|
-
), /* @__PURE__ */ React4.createElement(TouchableOpacity2, { onPress: () => setShowDetails(!showDetails), style:
|
|
16054
|
-
|
|
16055
|
-
|
|
16056
|
-
|
|
16057
|
-
|
|
16058
|
-
|
|
16107
|
+
/* @__PURE__ */ React4.createElement(Text2, { style: styles6.navigateText }, "\u{1F9ED} Go to test location")
|
|
16108
|
+
), /* @__PURE__ */ React4.createElement(TouchableOpacity2, { onPress: () => setShowDetails(!showDetails), style: styles6.detailsToggle }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.detailsToggleText }, showDetails ? "\u25BC" : "\u25B6", " Details")), showDetails && /* @__PURE__ */ React4.createElement(View4, { style: styles6.detailsSection }, testCase.key && /* @__PURE__ */ React4.createElement(Text2, { style: styles6.detailMeta }, testCase.key, " \xB7 ", testCase.priority, " \xB7 ", info.name), testCase.track && /* @__PURE__ */ React4.createElement(Text2, { style: styles6.detailMeta }, testCase.track.icon, " ", testCase.track.name), testCase.description && /* @__PURE__ */ React4.createElement(Text2, { style: styles6.detailDesc }, testCase.description), testCase.group && /* @__PURE__ */ React4.createElement(View4, { style: styles6.folderProgress }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.folderName }, "\u{1F4C1} ", testCase.group.name))), displayedAssignment.status === "in_progress" && nav.startMiniRunner && /* @__PURE__ */ React4.createElement(
|
|
16109
|
+
TouchableOpacity2,
|
|
16110
|
+
{
|
|
16111
|
+
style: styles6.startTestBtn,
|
|
16112
|
+
onPress: () => nav.startMiniRunner(displayedAssignment.id)
|
|
16113
|
+
},
|
|
16114
|
+
/* @__PURE__ */ React4.createElement(Text2, { style: styles6.startTestText }, "\u25B6 Start Test")
|
|
16115
|
+
), displayedAssignment.status === "passed" || displayedAssignment.status === "failed" || displayedAssignment.status === "skipped" || displayedAssignment.status === "blocked" ? /* @__PURE__ */ React4.createElement(React4.Fragment, null, /* @__PURE__ */ React4.createElement(View4, { style: [
|
|
16116
|
+
styles6.completedBanner,
|
|
16117
|
+
displayedAssignment.status === "passed" && styles6.completedBannerPass,
|
|
16118
|
+
displayedAssignment.status === "failed" && styles6.completedBannerFail
|
|
16119
|
+
] }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.completedIcon }, displayedAssignment.status === "passed" ? "\u2705" : displayedAssignment.status === "failed" ? "\u274C" : displayedAssignment.status === "skipped" ? "\u23ED" : "\u{1F6AB}"), /* @__PURE__ */ React4.createElement(Text2, { style: [
|
|
16120
|
+
styles6.completedLabel,
|
|
16059
16121
|
displayedAssignment.status === "passed" && { color: colors.green },
|
|
16060
16122
|
displayedAssignment.status === "failed" && { color: colors.redLight }
|
|
16061
|
-
] }, "Marked as ", displayedAssignment.status.charAt(0).toUpperCase() + displayedAssignment.status.slice(1))), !(displayedAssignment.isVerification && (displayedAssignment.status === "passed" || displayedAssignment.status === "failed")) && /* @__PURE__ */ React4.createElement(View4, { style: [
|
|
16123
|
+
] }, "Marked as ", displayedAssignment.status.charAt(0).toUpperCase() + displayedAssignment.status.slice(1))), !(displayedAssignment.isVerification && (displayedAssignment.status === "passed" || displayedAssignment.status === "failed")) && /* @__PURE__ */ React4.createElement(View4, { style: [styles6.actionButtons, { marginTop: 4 }] }, /* @__PURE__ */ React4.createElement(
|
|
16062
16124
|
TouchableOpacity2,
|
|
16063
16125
|
{
|
|
16064
|
-
style: [
|
|
16126
|
+
style: [styles6.actionBtn, styles6.reopenBtn, isSubmitting && { opacity: 0.5 }],
|
|
16065
16127
|
onPress: handleReopen,
|
|
16066
16128
|
disabled: isSubmitting
|
|
16067
16129
|
},
|
|
16068
|
-
/* @__PURE__ */ React4.createElement(Text2, { style:
|
|
16130
|
+
/* @__PURE__ */ React4.createElement(Text2, { style: styles6.reopenBtnText }, isSubmitting ? "Reopening..." : "\u{1F504} Reopen Test")
|
|
16069
16131
|
), displayedAssignment.status === "passed" && /* @__PURE__ */ React4.createElement(
|
|
16070
16132
|
TouchableOpacity2,
|
|
16071
16133
|
{
|
|
16072
|
-
style: [
|
|
16134
|
+
style: [styles6.actionBtn, styles6.failBtn, isSubmitting && { opacity: 0.5 }],
|
|
16073
16135
|
onPress: () => handleChangeResult("failed"),
|
|
16074
16136
|
disabled: isSubmitting
|
|
16075
16137
|
},
|
|
16076
|
-
/* @__PURE__ */ React4.createElement(Text2, { style:
|
|
16138
|
+
/* @__PURE__ */ React4.createElement(Text2, { style: styles6.failBtnText }, "Change to Fail")
|
|
16077
16139
|
), displayedAssignment.status === "failed" && /* @__PURE__ */ React4.createElement(
|
|
16078
16140
|
TouchableOpacity2,
|
|
16079
16141
|
{
|
|
16080
|
-
style: [
|
|
16142
|
+
style: [styles6.actionBtn, styles6.passBtn, isSubmitting && { opacity: 0.5 }],
|
|
16081
16143
|
onPress: () => handleChangeResult("passed"),
|
|
16082
16144
|
disabled: isSubmitting
|
|
16083
16145
|
},
|
|
16084
|
-
/* @__PURE__ */ React4.createElement(Text2, { style:
|
|
16085
|
-
))) : /* @__PURE__ */ React4.createElement(View4, { style:
|
|
16146
|
+
/* @__PURE__ */ React4.createElement(Text2, { style: styles6.passBtnText }, "Change to Pass")
|
|
16147
|
+
))) : /* @__PURE__ */ React4.createElement(View4, { style: styles6.actionButtons }, /* @__PURE__ */ React4.createElement(TouchableOpacity2, { style: [styles6.actionBtn, styles6.failBtn, isSubmitting && { opacity: 0.5 }], onPress: handleFail, disabled: isSubmitting }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.failBtnText }, isSubmitting ? displayedAssignment.isVerification ? "Reporting..." : "Failing..." : displayedAssignment.isVerification ? "\u2717 Still Broken" : "Fail")), /* @__PURE__ */ React4.createElement(TouchableOpacity2, { style: [styles6.actionBtn, styles6.skipBtn, isSubmitting && { opacity: 0.5 }], onPress: () => setShowSkipModal(true), disabled: isSubmitting }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.skipBtnText }, "Skip")), /* @__PURE__ */ React4.createElement(TouchableOpacity2, { style: [styles6.actionBtn, styles6.passBtn, isSubmitting && { opacity: 0.5 }], onPress: handlePass, disabled: isSubmitting }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.passBtnText }, isSubmitting ? displayedAssignment.isVerification ? "Verifying..." : "Passing..." : displayedAssignment.isVerification ? "\u2713 Fix Verified" : "Pass"))), feedbackToastAssignmentId && /* @__PURE__ */ React4.createElement(Animated2.View, { style: [styles6.passToast, { transform: [{ translateY: toastSlideAnim }] }] }, /* @__PURE__ */ React4.createElement(View4, { style: styles6.passToastContent }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.passToastIcon }, "\u2705"), /* @__PURE__ */ React4.createElement(Text2, { style: styles6.passToastText }, "Test passed!")), /* @__PURE__ */ React4.createElement(
|
|
16148
|
+
TouchableOpacity2,
|
|
16149
|
+
{
|
|
16150
|
+
style: styles6.passToastButton,
|
|
16151
|
+
onPress: () => {
|
|
16152
|
+
if (toastTimerRef.current) clearTimeout(toastTimerRef.current);
|
|
16153
|
+
const toastId = feedbackToastAssignmentId;
|
|
16154
|
+
setFeedbackToastAssignmentId(null);
|
|
16155
|
+
nav.push({ name: "TEST_FEEDBACK", status: "passed", assignmentId: toastId });
|
|
16156
|
+
}
|
|
16157
|
+
},
|
|
16158
|
+
/* @__PURE__ */ React4.createElement(Text2, { style: styles6.passToastButtonText }, "Rate this test")
|
|
16159
|
+
)), /* @__PURE__ */ React4.createElement(Modal, { visible: showSkipModal, transparent: true, animationType: "fade" }, /* @__PURE__ */ React4.createElement(View4, { style: styles6.modalOverlay }, /* @__PURE__ */ React4.createElement(View4, { style: styles6.modalContent }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.modalTitle }, "Skip this test?"), /* @__PURE__ */ React4.createElement(Text2, { style: styles6.modalSubtitle }, "Select a reason:"), [
|
|
16086
16160
|
{ reason: "blocked", label: "\u{1F6AB} Blocked by a bug" },
|
|
16087
16161
|
{ reason: "not_ready", label: "\u{1F6A7} Feature not ready" },
|
|
16088
16162
|
{ reason: "dependency", label: "\u{1F517} Needs another test first" },
|
|
@@ -16091,32 +16165,32 @@ function TestDetailScreen({ testId, nav }) {
|
|
|
16091
16165
|
TouchableOpacity2,
|
|
16092
16166
|
{
|
|
16093
16167
|
key: reason,
|
|
16094
|
-
style: [
|
|
16168
|
+
style: [styles6.skipOption, selectedSkipReason === reason && styles6.skipOptionActive],
|
|
16095
16169
|
onPress: () => setSelectedSkipReason(reason)
|
|
16096
16170
|
},
|
|
16097
|
-
/* @__PURE__ */ React4.createElement(Text2, { style: [
|
|
16171
|
+
/* @__PURE__ */ React4.createElement(Text2, { style: [styles6.skipOptionText, selectedSkipReason === reason && styles6.skipOptionTextActive] }, label)
|
|
16098
16172
|
)), /* @__PURE__ */ React4.createElement(
|
|
16099
16173
|
TextInput,
|
|
16100
16174
|
{
|
|
16101
|
-
style:
|
|
16175
|
+
style: styles6.skipNotes,
|
|
16102
16176
|
value: skipNotes,
|
|
16103
16177
|
onChangeText: setSkipNotes,
|
|
16104
16178
|
placeholder: "Additional notes (optional)",
|
|
16105
16179
|
placeholderTextColor: colors.textMuted,
|
|
16106
16180
|
multiline: true
|
|
16107
16181
|
}
|
|
16108
|
-
), /* @__PURE__ */ React4.createElement(View4, { style:
|
|
16182
|
+
), /* @__PURE__ */ React4.createElement(View4, { style: styles6.skipActions }, /* @__PURE__ */ React4.createElement(TouchableOpacity2, { style: styles6.skipCancel, onPress: () => {
|
|
16109
16183
|
setShowSkipModal(false);
|
|
16110
16184
|
setSelectedSkipReason(null);
|
|
16111
16185
|
setSkipNotes("");
|
|
16112
|
-
} }, /* @__PURE__ */ React4.createElement(Text2, { style:
|
|
16186
|
+
} }, /* @__PURE__ */ React4.createElement(Text2, { style: styles6.skipCancelText }, "Cancel")), /* @__PURE__ */ React4.createElement(
|
|
16113
16187
|
TouchableOpacity2,
|
|
16114
16188
|
{
|
|
16115
|
-
style: [
|
|
16189
|
+
style: [styles6.skipConfirm, !selectedSkipReason && { opacity: 0.4 }],
|
|
16116
16190
|
onPress: handleSkip,
|
|
16117
16191
|
disabled: !selectedSkipReason || skipping
|
|
16118
16192
|
},
|
|
16119
|
-
/* @__PURE__ */ React4.createElement(Text2, { style:
|
|
16193
|
+
/* @__PURE__ */ React4.createElement(Text2, { style: styles6.skipConfirmText }, skipping ? "Skipping..." : "Skip Test")
|
|
16120
16194
|
))))));
|
|
16121
16195
|
}
|
|
16122
16196
|
function createStyles2() {
|
|
@@ -16219,7 +16293,17 @@ function createStyles2() {
|
|
|
16219
16293
|
skipCancel: { flex: 1, paddingVertical: 12, borderRadius: 10, alignItems: "center", backgroundColor: colors.card },
|
|
16220
16294
|
skipCancelText: { fontSize: 14, color: colors.textSecondary },
|
|
16221
16295
|
skipConfirm: { flex: 1, paddingVertical: 12, borderRadius: 10, alignItems: "center", backgroundColor: colors.yellow },
|
|
16222
|
-
skipConfirmText: { fontSize: 14, fontWeight: "600", color: colors.onBright }
|
|
16296
|
+
skipConfirmText: { fontSize: 14, fontWeight: "600", color: colors.onBright },
|
|
16297
|
+
// Start test button
|
|
16298
|
+
startTestBtn: { backgroundColor: colors.blueDark, borderRadius: 10, padding: 12, borderWidth: 1, borderColor: colors.blue, alignItems: "center", marginBottom: 8 },
|
|
16299
|
+
startTestText: { fontSize: 14, fontWeight: "600", color: colors.blueLight },
|
|
16300
|
+
// Instant pass toast
|
|
16301
|
+
passToast: { position: "absolute", bottom: 16, left: 16, right: 16, flexDirection: "row", alignItems: "center", justifyContent: "space-between", backgroundColor: colors.greenDark, borderWidth: 1, borderColor: colors.green, borderRadius: 10, paddingVertical: 10, paddingHorizontal: 14, zIndex: 1e4 },
|
|
16302
|
+
passToastContent: { flexDirection: "row", alignItems: "center", gap: 8 },
|
|
16303
|
+
passToastIcon: { fontSize: 14 },
|
|
16304
|
+
passToastText: { fontSize: 13, fontWeight: "600", color: colors.green },
|
|
16305
|
+
passToastButton: { borderWidth: 1, borderColor: colors.green, borderRadius: 8, paddingVertical: 4, paddingHorizontal: 10 },
|
|
16306
|
+
passToastButtonText: { fontSize: 12, fontWeight: "500", color: colors.green }
|
|
16223
16307
|
});
|
|
16224
16308
|
}
|
|
16225
16309
|
|
|
@@ -16228,7 +16312,7 @@ import React5, { useState as useState4, useMemo as useMemo3, useCallback as useC
|
|
|
16228
16312
|
import { View as View5, Text as Text3, TouchableOpacity as TouchableOpacity3, StyleSheet as StyleSheet5, ScrollView, TextInput as TextInput2, Platform as Platform3, Linking as Linking2 } from "react-native";
|
|
16229
16313
|
function TestListScreen({ nav }) {
|
|
16230
16314
|
const { assignments, currentAssignment, refreshAssignments, dashboardUrl, isLoading, widgetColorScheme } = useBugBear();
|
|
16231
|
-
const
|
|
16315
|
+
const styles6 = useMemo3(() => createStyles3(), [widgetColorScheme]);
|
|
16232
16316
|
const [filter, setFilter] = useState4("all");
|
|
16233
16317
|
const [roleFilter, setRoleFilter] = useState4(null);
|
|
16234
16318
|
const [trackFilter, setTrackFilter] = useState4(null);
|
|
@@ -16320,18 +16404,18 @@ function TestListScreen({ nav }) {
|
|
|
16320
16404
|
return true;
|
|
16321
16405
|
}, [platformFilter, roleFilter, trackFilter, searchQuery, filter]);
|
|
16322
16406
|
if (isLoading) return /* @__PURE__ */ React5.createElement(TestListScreenSkeleton, null);
|
|
16323
|
-
return /* @__PURE__ */ React5.createElement(View5, null, /* @__PURE__ */ React5.createElement(View5, { style:
|
|
16407
|
+
return /* @__PURE__ */ React5.createElement(View5, null, /* @__PURE__ */ React5.createElement(View5, { style: styles6.filterBar }, [
|
|
16324
16408
|
{ key: "all", label: "All", count: assignments.length },
|
|
16325
16409
|
{ key: "todo", label: "To Do", count: assignments.filter((a) => !a.isVerification && (a.status === "pending" || a.status === "in_progress" || a.status === "failed")).length },
|
|
16326
16410
|
{ key: "retest", label: "Retest", count: assignments.filter((a) => !!a.isVerification && (a.status === "pending" || a.status === "in_progress")).length },
|
|
16327
16411
|
{ key: "done", label: "Done", count: assignments.filter((a) => a.status === "passed" || a.status === "skipped" || a.status === "blocked").length }
|
|
16328
|
-
].map((f) => /* @__PURE__ */ React5.createElement(TouchableOpacity3, { key: f.key, style: [
|
|
16412
|
+
].map((f) => /* @__PURE__ */ React5.createElement(TouchableOpacity3, { key: f.key, style: [styles6.filterBtn, filter === f.key && styles6.filterBtnActive], onPress: () => setFilter(f.key) }, /* @__PURE__ */ React5.createElement(Text3, { style: [styles6.filterBtnText, filter === f.key && styles6.filterBtnTextActive] }, f.label, " (", f.count, ")")))), availableRoles.length >= 2 && /* @__PURE__ */ React5.createElement(View5, { style: styles6.roleSection }, /* @__PURE__ */ React5.createElement(ScrollView, { horizontal: true, showsHorizontalScrollIndicator: false, style: styles6.roleBar }, /* @__PURE__ */ React5.createElement(
|
|
16329
16413
|
TouchableOpacity3,
|
|
16330
16414
|
{
|
|
16331
|
-
style: [
|
|
16415
|
+
style: [styles6.roleBtn, !roleFilter && styles6.roleBtnActive],
|
|
16332
16416
|
onPress: () => setRoleFilter(null)
|
|
16333
16417
|
},
|
|
16334
|
-
/* @__PURE__ */ React5.createElement(Text3, { style: [
|
|
16418
|
+
/* @__PURE__ */ React5.createElement(Text3, { style: [styles6.roleBtnText, !roleFilter && styles6.roleBtnTextActive] }, "All Roles")
|
|
16335
16419
|
), availableRoles.map((role) => {
|
|
16336
16420
|
const isActive = roleFilter === role.id;
|
|
16337
16421
|
return /* @__PURE__ */ React5.createElement(
|
|
@@ -16339,30 +16423,30 @@ function TestListScreen({ nav }) {
|
|
|
16339
16423
|
{
|
|
16340
16424
|
key: role.id,
|
|
16341
16425
|
style: [
|
|
16342
|
-
|
|
16426
|
+
styles6.roleBtn,
|
|
16343
16427
|
isActive && { backgroundColor: role.color + "20", borderColor: role.color + "60", borderWidth: 1 }
|
|
16344
16428
|
],
|
|
16345
16429
|
onPress: () => setRoleFilter(isActive ? null : role.id)
|
|
16346
16430
|
},
|
|
16347
|
-
/* @__PURE__ */ React5.createElement(View5, { style: [
|
|
16348
|
-
/* @__PURE__ */ React5.createElement(Text3, { style: [
|
|
16431
|
+
/* @__PURE__ */ React5.createElement(View5, { style: [styles6.roleDot, { backgroundColor: role.color }] }),
|
|
16432
|
+
/* @__PURE__ */ React5.createElement(Text3, { style: [styles6.roleBtnText, isActive && { color: role.color, fontWeight: "600" }] }, role.name)
|
|
16349
16433
|
);
|
|
16350
|
-
})), selectedRole?.loginHint && /* @__PURE__ */ React5.createElement(View5, { style: [
|
|
16434
|
+
})), selectedRole?.loginHint && /* @__PURE__ */ React5.createElement(View5, { style: [styles6.loginHint, { backgroundColor: selectedRole.color + "10", borderColor: selectedRole.color + "30" }] }, /* @__PURE__ */ React5.createElement(Text3, { style: styles6.loginHintText }, "Log in as: ", selectedRole.loginHint))), /* @__PURE__ */ React5.createElement(View5, { style: styles6.searchContainer }, /* @__PURE__ */ React5.createElement(
|
|
16351
16435
|
TextInput2,
|
|
16352
16436
|
{
|
|
16353
16437
|
value: searchQuery,
|
|
16354
16438
|
onChangeText: setSearchQuery,
|
|
16355
16439
|
placeholder: "Search tests...",
|
|
16356
16440
|
placeholderTextColor: colors.textMuted,
|
|
16357
|
-
style:
|
|
16441
|
+
style: styles6.searchInput
|
|
16358
16442
|
}
|
|
16359
|
-
)), /* @__PURE__ */ React5.createElement(ScrollView, { horizontal: true, showsHorizontalScrollIndicator: false, style:
|
|
16443
|
+
)), /* @__PURE__ */ React5.createElement(ScrollView, { horizontal: true, showsHorizontalScrollIndicator: false, style: styles6.platformBar }, /* @__PURE__ */ React5.createElement(
|
|
16360
16444
|
TouchableOpacity3,
|
|
16361
16445
|
{
|
|
16362
|
-
style: [
|
|
16446
|
+
style: [styles6.platformBtn, !platformFilter && styles6.platformBtnActive],
|
|
16363
16447
|
onPress: () => setPlatformFilter(null)
|
|
16364
16448
|
},
|
|
16365
|
-
/* @__PURE__ */ React5.createElement(Text3, { style: [
|
|
16449
|
+
/* @__PURE__ */ React5.createElement(Text3, { style: [styles6.platformBtnText, !platformFilter && styles6.platformBtnTextActive] }, "All")
|
|
16366
16450
|
), [
|
|
16367
16451
|
{ key: "web", label: "Web", icon: "\u{1F310}" },
|
|
16368
16452
|
{ key: "ios", label: "iOS", icon: "\u{1F4F1}" },
|
|
@@ -16374,32 +16458,32 @@ function TestListScreen({ nav }) {
|
|
|
16374
16458
|
{
|
|
16375
16459
|
key: p.key,
|
|
16376
16460
|
style: [
|
|
16377
|
-
|
|
16461
|
+
styles6.platformBtn,
|
|
16378
16462
|
isActive && { backgroundColor: colors.blue + "20", borderColor: colors.blue + "60", borderWidth: 1 }
|
|
16379
16463
|
],
|
|
16380
16464
|
onPress: () => setPlatformFilter(isActive ? null : p.key)
|
|
16381
16465
|
},
|
|
16382
|
-
/* @__PURE__ */ React5.createElement(Text3, { style: [
|
|
16466
|
+
/* @__PURE__ */ React5.createElement(Text3, { style: [styles6.platformBtnText, isActive && { color: colors.blue, fontWeight: "600" }] }, p.icon, " ", p.label)
|
|
16383
16467
|
);
|
|
16384
|
-
})), /* @__PURE__ */ React5.createElement(View5, { style:
|
|
16468
|
+
})), /* @__PURE__ */ React5.createElement(View5, { style: styles6.trackSortRow }, availableTracks.length >= 2 && /* @__PURE__ */ React5.createElement(ScrollView, { horizontal: true, showsHorizontalScrollIndicator: false, style: { flex: 1 } }, /* @__PURE__ */ React5.createElement(
|
|
16385
16469
|
TouchableOpacity3,
|
|
16386
16470
|
{
|
|
16387
|
-
style: [
|
|
16471
|
+
style: [styles6.trackBtn, !trackFilter && styles6.trackBtnActive],
|
|
16388
16472
|
onPress: () => setTrackFilter(null)
|
|
16389
16473
|
},
|
|
16390
|
-
/* @__PURE__ */ React5.createElement(Text3, { style: [
|
|
16474
|
+
/* @__PURE__ */ React5.createElement(Text3, { style: [styles6.trackBtnText, !trackFilter && styles6.trackBtnTextActive] }, "All Tracks")
|
|
16391
16475
|
), availableTracks.map((track) => {
|
|
16392
16476
|
const isActive = trackFilter === track.id;
|
|
16393
16477
|
return /* @__PURE__ */ React5.createElement(
|
|
16394
16478
|
TouchableOpacity3,
|
|
16395
16479
|
{
|
|
16396
16480
|
key: track.id,
|
|
16397
|
-
style: [
|
|
16481
|
+
style: [styles6.trackBtn, isActive && { backgroundColor: track.color + "20", borderColor: track.color + "60", borderWidth: 1 }],
|
|
16398
16482
|
onPress: () => setTrackFilter(isActive ? null : track.id)
|
|
16399
16483
|
},
|
|
16400
|
-
/* @__PURE__ */ React5.createElement(Text3, { style: [
|
|
16484
|
+
/* @__PURE__ */ React5.createElement(Text3, { style: [styles6.trackBtnText, isActive && { color: track.color, fontWeight: "600" }] }, track.icon, " ", track.name)
|
|
16401
16485
|
);
|
|
16402
|
-
})), /* @__PURE__ */ React5.createElement(View5, { style:
|
|
16486
|
+
})), /* @__PURE__ */ React5.createElement(View5, { style: styles6.sortGroup }, [
|
|
16403
16487
|
{ key: "priority", label: "\u2195 Priority" },
|
|
16404
16488
|
{ key: "recent", label: "\u{1F550} Recent" },
|
|
16405
16489
|
{ key: "alpha", label: "A-Z" }
|
|
@@ -16407,41 +16491,41 @@ function TestListScreen({ nav }) {
|
|
|
16407
16491
|
TouchableOpacity3,
|
|
16408
16492
|
{
|
|
16409
16493
|
key: s2.key,
|
|
16410
|
-
style: [
|
|
16494
|
+
style: [styles6.sortBtn, sortMode === s2.key && styles6.sortBtnActive],
|
|
16411
16495
|
onPress: () => setSortMode(s2.key)
|
|
16412
16496
|
},
|
|
16413
|
-
/* @__PURE__ */ React5.createElement(Text3, { style: [
|
|
16497
|
+
/* @__PURE__ */ React5.createElement(Text3, { style: [styles6.sortBtnText, sortMode === s2.key && styles6.sortBtnTextActive] }, s2.label)
|
|
16414
16498
|
)))), groupedAssignments.map((folder) => {
|
|
16415
16499
|
const folderId = folder.group?.id || "ungrouped";
|
|
16416
16500
|
const isCollapsed = collapsedFolders.has(folderId);
|
|
16417
16501
|
const filtered = folder.assignments.filter(filterAssignment);
|
|
16418
16502
|
if (filtered.length === 0 && filter !== "all") return null;
|
|
16419
|
-
return /* @__PURE__ */ React5.createElement(View5, { key: folderId, style:
|
|
16503
|
+
return /* @__PURE__ */ React5.createElement(View5, { key: folderId, style: styles6.folder }, /* @__PURE__ */ React5.createElement(TouchableOpacity3, { style: styles6.folderHeader, onPress: () => toggleFolder(folderId) }, /* @__PURE__ */ React5.createElement(Text3, { style: styles6.folderToggle }, isCollapsed ? "\u25B6" : "\u25BC"), /* @__PURE__ */ React5.createElement(Text3, { style: styles6.folderName, numberOfLines: 1 }, folder.group?.name || "Ungrouped"), /* @__PURE__ */ React5.createElement(View5, { style: styles6.folderProgress }, /* @__PURE__ */ React5.createElement(View5, { style: [styles6.folderProgressFill, { width: `${folder.stats.total > 0 ? Math.round((folder.stats.passed + folder.stats.failed) / folder.stats.total * 100) : 0}%` }] })), /* @__PURE__ */ React5.createElement(Text3, { style: styles6.folderCount }, folder.stats.passed + folder.stats.failed, "/", folder.stats.total)), !isCollapsed && filtered.map((assignment) => {
|
|
16420
16504
|
const badge = getStatusBadge(assignment.status);
|
|
16421
16505
|
const isCurrent = currentAssignment?.id === assignment.id;
|
|
16422
16506
|
return /* @__PURE__ */ React5.createElement(
|
|
16423
16507
|
TouchableOpacity3,
|
|
16424
16508
|
{
|
|
16425
16509
|
key: assignment.id,
|
|
16426
|
-
style: [
|
|
16510
|
+
style: [styles6.testItem, isCurrent && styles6.testItemCurrent],
|
|
16427
16511
|
onPress: () => nav.push({ name: "TEST_DETAIL", testId: assignment.id })
|
|
16428
16512
|
},
|
|
16429
|
-
/* @__PURE__ */ React5.createElement(Text3, { style:
|
|
16430
|
-
/* @__PURE__ */ React5.createElement(View5, { style:
|
|
16431
|
-
|
|
16513
|
+
/* @__PURE__ */ React5.createElement(Text3, { style: styles6.testBadge }, badge.icon),
|
|
16514
|
+
/* @__PURE__ */ React5.createElement(View5, { style: styles6.testInfo }, /* @__PURE__ */ React5.createElement(Text3, { style: styles6.testTitle, numberOfLines: 1 }, assignment.testCase.title), /* @__PURE__ */ React5.createElement(View5, { style: styles6.testMetaRow }, assignment.isVerification && /* @__PURE__ */ React5.createElement(View5, { style: [
|
|
16515
|
+
styles6.retestTag,
|
|
16432
16516
|
assignment.status === "passed" && { backgroundColor: colors.greenDark, borderColor: colors.greenBorder }
|
|
16433
16517
|
] }, /* @__PURE__ */ React5.createElement(Text3, { style: [
|
|
16434
|
-
|
|
16518
|
+
styles6.retestTagText,
|
|
16435
16519
|
assignment.status === "passed" && { color: colors.greenLight }
|
|
16436
|
-
] }, assignment.status === "passed" ? "Verified" : "Retest")), /* @__PURE__ */ React5.createElement(Text3, { style:
|
|
16520
|
+
] }, assignment.status === "passed" ? "Verified" : "Retest")), /* @__PURE__ */ React5.createElement(Text3, { style: styles6.testMeta }, assignment.testCase.testKey, " \xB7 ", assignment.testCase.priority), assignment.testCase.role && /* @__PURE__ */ React5.createElement(View5, { style: styles6.roleBadgeRow }, /* @__PURE__ */ React5.createElement(Text3, { style: styles6.testMeta }, " \xB7 "), /* @__PURE__ */ React5.createElement(View5, { style: [styles6.roleBadgeDot, { backgroundColor: assignment.testCase.role.color }] }), /* @__PURE__ */ React5.createElement(Text3, { style: [styles6.testMeta, { color: assignment.testCase.role.color, fontWeight: "500" }] }, assignment.testCase.role.name)))),
|
|
16437
16521
|
/* @__PURE__ */ React5.createElement(View5, { style: [
|
|
16438
|
-
|
|
16522
|
+
styles6.statusPill,
|
|
16439
16523
|
{
|
|
16440
16524
|
backgroundColor: assignment.status === "passed" ? colors.greenDark : assignment.status === "failed" ? colors.redSurface : assignment.status === "in_progress" ? colors.blueSurface : colors.card,
|
|
16441
16525
|
borderColor: assignment.status === "passed" ? colors.greenBorder : assignment.status === "failed" ? colors.redDark : assignment.status === "in_progress" ? colors.blueDark : colors.border
|
|
16442
16526
|
}
|
|
16443
16527
|
] }, /* @__PURE__ */ React5.createElement(Text3, { style: [
|
|
16444
|
-
|
|
16528
|
+
styles6.statusPillText,
|
|
16445
16529
|
{
|
|
16446
16530
|
color: assignment.status === "passed" ? colors.greenMed : assignment.status === "failed" ? colors.redMed : assignment.status === "in_progress" ? colors.blueLight : colors.zincLight
|
|
16447
16531
|
}
|
|
@@ -16451,12 +16535,12 @@ function TestListScreen({ nav }) {
|
|
|
16451
16535
|
}), dashboardUrl && /* @__PURE__ */ React5.createElement(
|
|
16452
16536
|
TouchableOpacity3,
|
|
16453
16537
|
{
|
|
16454
|
-
style:
|
|
16538
|
+
style: styles6.dashboardLink,
|
|
16455
16539
|
onPress: () => Linking2.openURL(`${dashboardUrl}/test-cases`),
|
|
16456
16540
|
activeOpacity: 0.7
|
|
16457
16541
|
},
|
|
16458
|
-
/* @__PURE__ */ React5.createElement(Text3, { style:
|
|
16459
|
-
), /* @__PURE__ */ React5.createElement(TouchableOpacity3, { style:
|
|
16542
|
+
/* @__PURE__ */ React5.createElement(Text3, { style: styles6.dashboardLinkText }, "\u{1F310}", " Manage on Dashboard ", "\u2192")
|
|
16543
|
+
), /* @__PURE__ */ React5.createElement(TouchableOpacity3, { style: styles6.refreshBtn, onPress: refreshAssignments }, /* @__PURE__ */ React5.createElement(Text3, { style: styles6.refreshText }, "\u21BB", " Refresh")));
|
|
16460
16544
|
}
|
|
16461
16545
|
function createStyles3() {
|
|
16462
16546
|
return StyleSheet5.create({
|
|
@@ -16776,7 +16860,7 @@ var styles2 = StyleSheet7.create({
|
|
|
16776
16860
|
// src/widget/screens/TestFeedbackScreen.tsx
|
|
16777
16861
|
function TestFeedbackScreen({ status, assignmentId, nav }) {
|
|
16778
16862
|
const { client, assignments, refreshAssignments, uploadImage, widgetColorScheme } = useBugBear();
|
|
16779
|
-
const
|
|
16863
|
+
const styles6 = useMemo4(() => createStyles4(), [widgetColorScheme]);
|
|
16780
16864
|
const images = useImageAttachments(uploadImage, 3, "screenshots");
|
|
16781
16865
|
const [rating, setRating] = useState6(5);
|
|
16782
16866
|
const [note, setNote] = useState6("");
|
|
@@ -16836,7 +16920,7 @@ function TestFeedbackScreen({ status, assignmentId, nav }) {
|
|
|
16836
16920
|
}
|
|
16837
16921
|
}
|
|
16838
16922
|
};
|
|
16839
|
-
return /* @__PURE__ */ React8.createElement(View8, { style:
|
|
16923
|
+
return /* @__PURE__ */ React8.createElement(View8, { style: styles6.container }, /* @__PURE__ */ React8.createElement(Text6, { style: styles6.header }, status === "passed" ? "\u2705 Test Passed!" : "\u274C Test Failed"), /* @__PURE__ */ React8.createElement(Text6, { style: styles6.subheader }, "Rate this test case"), /* @__PURE__ */ React8.createElement(View8, { style: styles6.starRow }, [1, 2, 3, 4, 5].map((n) => /* @__PURE__ */ React8.createElement(TouchableOpacity6, { key: n, onPress: () => setRating(n), style: styles6.starButton }, /* @__PURE__ */ React8.createElement(Text6, { style: [styles6.star, n <= rating && styles6.starActive] }, n <= rating ? "\u2605" : "\u2606")))), showFlags && /* @__PURE__ */ React8.createElement(View8, { style: styles6.flagsSection }, /* @__PURE__ */ React8.createElement(Text6, { style: styles6.flagsLabel }, "What could be improved?"), [
|
|
16840
16924
|
{ key: "isOutdated", label: "Test is outdated" },
|
|
16841
16925
|
{ key: "needsMoreDetail", label: "Needs more detail" },
|
|
16842
16926
|
{ key: "stepsUnclear", label: "Steps are unclear" },
|
|
@@ -16845,15 +16929,15 @@ function TestFeedbackScreen({ status, assignmentId, nav }) {
|
|
|
16845
16929
|
TouchableOpacity6,
|
|
16846
16930
|
{
|
|
16847
16931
|
key,
|
|
16848
|
-
style: [
|
|
16932
|
+
style: [styles6.flagItem, flags[key] && styles6.flagItemActive],
|
|
16849
16933
|
onPress: () => setFlags((prev) => ({ ...prev, [key]: !prev[key] }))
|
|
16850
16934
|
},
|
|
16851
|
-
/* @__PURE__ */ React8.createElement(View8, { style: [
|
|
16852
|
-
/* @__PURE__ */ React8.createElement(Text6, { style: [
|
|
16935
|
+
/* @__PURE__ */ React8.createElement(View8, { style: [styles6.flagCheck, flags[key] && styles6.flagCheckActive] }, flags[key] && /* @__PURE__ */ React8.createElement(Text6, { style: styles6.flagCheckmark }, "\u2713")),
|
|
16936
|
+
/* @__PURE__ */ React8.createElement(Text6, { style: [styles6.flagText, flags[key] && styles6.flagTextActive] }, label)
|
|
16853
16937
|
))), /* @__PURE__ */ React8.createElement(
|
|
16854
16938
|
TextInput3,
|
|
16855
16939
|
{
|
|
16856
|
-
style:
|
|
16940
|
+
style: styles6.noteInput,
|
|
16857
16941
|
value: note,
|
|
16858
16942
|
onChangeText: setNote,
|
|
16859
16943
|
placeholder: "Add a note (optional)",
|
|
@@ -16870,7 +16954,7 @@ function TestFeedbackScreen({ status, assignmentId, nav }) {
|
|
|
16870
16954
|
onRemove: images.removeImage,
|
|
16871
16955
|
label: "Screenshots (optional)"
|
|
16872
16956
|
}
|
|
16873
|
-
), /* @__PURE__ */ React8.createElement(View8, { style:
|
|
16957
|
+
), /* @__PURE__ */ React8.createElement(View8, { style: styles6.actions }, /* @__PURE__ */ React8.createElement(TouchableOpacity6, { style: styles6.skipButton, onPress: handleSkip }, /* @__PURE__ */ React8.createElement(Text6, { style: styles6.skipText }, "Skip")), /* @__PURE__ */ React8.createElement(TouchableOpacity6, { style: [shared.primaryButton, { flex: 2, opacity: submitting || images.isUploading ? 0.5 : 1 }], onPress: handleSubmit, disabled: submitting || images.isUploading }, /* @__PURE__ */ React8.createElement(Text6, { style: shared.primaryButtonText }, images.isUploading ? "Uploading..." : submitting ? "Submitting..." : "Submit"))));
|
|
16874
16958
|
}
|
|
16875
16959
|
function createStyles4() {
|
|
16876
16960
|
return StyleSheet8.create({
|
|
@@ -16898,7 +16982,7 @@ function createStyles4() {
|
|
|
16898
16982
|
}
|
|
16899
16983
|
|
|
16900
16984
|
// src/widget/screens/ReportScreen.tsx
|
|
16901
|
-
import React10, { useState as useState8, useRef as
|
|
16985
|
+
import React10, { useState as useState8, useRef as useRef5, useEffect as useEffect6, useMemo as useMemo5 } from "react";
|
|
16902
16986
|
import { View as View10, Text as Text8, TouchableOpacity as TouchableOpacity8, TextInput as TextInput4, StyleSheet as StyleSheet10 } from "react-native";
|
|
16903
16987
|
|
|
16904
16988
|
// src/widget/CategoryPicker.tsx
|
|
@@ -17059,7 +17143,7 @@ var styles3 = StyleSheet9.create({
|
|
|
17059
17143
|
// src/widget/screens/ReportScreen.tsx
|
|
17060
17144
|
function ReportScreen({ nav, prefill, autoCaptureUri, onAutoCaptureConsumed }) {
|
|
17061
17145
|
const { client, getDeviceInfo, uploadImage, refreshAssignments, widgetColorScheme } = useBugBear();
|
|
17062
|
-
const
|
|
17146
|
+
const styles6 = useMemo5(() => createStyles5(), [widgetColorScheme]);
|
|
17063
17147
|
const [reportType, setReportType] = useState8(prefill?.type || "bug");
|
|
17064
17148
|
const [severity, setSeverity] = useState8("medium");
|
|
17065
17149
|
const [category, setCategory] = useState8(null);
|
|
@@ -17069,9 +17153,9 @@ function ReportScreen({ nav, prefill, autoCaptureUri, onAutoCaptureConsumed }) {
|
|
|
17069
17153
|
const [affectedScreen, setAffectedScreen] = useState8("");
|
|
17070
17154
|
const [submitting, setSubmitting] = useState8(false);
|
|
17071
17155
|
const [error, setError] = useState8(null);
|
|
17072
|
-
const submittingRef =
|
|
17156
|
+
const submittingRef = useRef5(false);
|
|
17073
17157
|
const images = useImageAttachments(uploadImage, 5, "screenshots");
|
|
17074
|
-
const hasConsumedCapture =
|
|
17158
|
+
const hasConsumedCapture = useRef5(false);
|
|
17075
17159
|
useEffect6(() => {
|
|
17076
17160
|
if (autoCaptureUri && !hasConsumedCapture.current) {
|
|
17077
17161
|
hasConsumedCapture.current = true;
|
|
@@ -17165,7 +17249,7 @@ function ReportScreen({ nav, prefill, autoCaptureUri, onAutoCaptureConsumed }) {
|
|
|
17165
17249
|
submittingRef.current = false;
|
|
17166
17250
|
}
|
|
17167
17251
|
};
|
|
17168
|
-
return /* @__PURE__ */ React10.createElement(View10, null, isRetestFailure ? /* @__PURE__ */ React10.createElement(React10.Fragment, null, /* @__PURE__ */ React10.createElement(View10, { style:
|
|
17252
|
+
return /* @__PURE__ */ React10.createElement(View10, null, isRetestFailure ? /* @__PURE__ */ React10.createElement(React10.Fragment, null, /* @__PURE__ */ React10.createElement(View10, { style: styles6.retestBanner }, /* @__PURE__ */ React10.createElement(Text8, { style: styles6.retestIcon }, "\u{1F504}"), /* @__PURE__ */ React10.createElement(View10, null, /* @__PURE__ */ React10.createElement(Text8, { style: styles6.retestTitle }, "Bug Still Present"), /* @__PURE__ */ React10.createElement(Text8, { style: styles6.retestSubtitle }, "The fix did not resolve this issue"))), /* @__PURE__ */ React10.createElement(View10, { style: styles6.section }, /* @__PURE__ */ React10.createElement(Text8, { style: shared.label }, "Severity"), /* @__PURE__ */ React10.createElement(View10, { style: styles6.severityRow }, [
|
|
17169
17253
|
{ sev: "critical", color: colors.red },
|
|
17170
17254
|
{ sev: "high", color: colors.orange },
|
|
17171
17255
|
{ sev: "medium", color: colors.yellow },
|
|
@@ -17174,14 +17258,14 @@ function ReportScreen({ nav, prefill, autoCaptureUri, onAutoCaptureConsumed }) {
|
|
|
17174
17258
|
TouchableOpacity8,
|
|
17175
17259
|
{
|
|
17176
17260
|
key: sev,
|
|
17177
|
-
style: [
|
|
17261
|
+
style: [styles6.sevButton, severity === sev && { backgroundColor: `${color}30`, borderColor: color }],
|
|
17178
17262
|
onPress: () => setSeverity(sev)
|
|
17179
17263
|
},
|
|
17180
|
-
/* @__PURE__ */ React10.createElement(Text8, { style: [
|
|
17181
|
-
)))), /* @__PURE__ */ React10.createElement(View10, { style:
|
|
17264
|
+
/* @__PURE__ */ React10.createElement(Text8, { style: [styles6.sevText, severity === sev && { color }] }, sev)
|
|
17265
|
+
)))), /* @__PURE__ */ React10.createElement(View10, { style: styles6.section }, /* @__PURE__ */ React10.createElement(Text8, { style: shared.label }, "Category (optional)"), /* @__PURE__ */ React10.createElement(CategoryPicker, { value: category, onChange: setCategory, optional: true })), /* @__PURE__ */ React10.createElement(View10, { style: styles6.section }, /* @__PURE__ */ React10.createElement(Text8, { style: shared.label }, "What went wrong?"), /* @__PURE__ */ React10.createElement(
|
|
17182
17266
|
TextInput4,
|
|
17183
17267
|
{
|
|
17184
|
-
style:
|
|
17268
|
+
style: styles6.descInput,
|
|
17185
17269
|
value: description,
|
|
17186
17270
|
onChangeText: setDescription,
|
|
17187
17271
|
placeholder: "Describe what you observed. What still doesn't work?",
|
|
@@ -17234,15 +17318,15 @@ function ReportScreen({ nav, prefill, autoCaptureUri, onAutoCaptureConsumed }) {
|
|
|
17234
17318
|
onRemove: images.removeImage,
|
|
17235
17319
|
label: "Attachments (optional)"
|
|
17236
17320
|
}
|
|
17237
|
-
), error && /* @__PURE__ */ React10.createElement(View10, { style:
|
|
17321
|
+
), error && /* @__PURE__ */ React10.createElement(View10, { style: styles6.errorBanner }, /* @__PURE__ */ React10.createElement(Text8, { style: styles6.errorText }, error)), /* @__PURE__ */ React10.createElement(
|
|
17238
17322
|
TouchableOpacity8,
|
|
17239
17323
|
{
|
|
17240
|
-
style: [shared.primaryButton,
|
|
17324
|
+
style: [shared.primaryButton, styles6.retestSubmitButton, (!description.trim() || submitting || images.isUploading) && shared.primaryButtonDisabled, { marginTop: 20 }],
|
|
17241
17325
|
onPress: handleSubmit,
|
|
17242
17326
|
disabled: !description.trim() || submitting || images.isUploading
|
|
17243
17327
|
},
|
|
17244
17328
|
/* @__PURE__ */ React10.createElement(Text8, { style: shared.primaryButtonText }, images.isUploading ? "Uploading images..." : submitting ? "Submitting..." : error ? "Retry" : "Submit Failed Retest")
|
|
17245
|
-
)) : /* @__PURE__ */ React10.createElement(React10.Fragment, null, /* @__PURE__ */ React10.createElement(Text8, { style: shared.label }, "What are you reporting?"), /* @__PURE__ */ React10.createElement(View10, { style:
|
|
17329
|
+
)) : /* @__PURE__ */ React10.createElement(React10.Fragment, null, /* @__PURE__ */ React10.createElement(Text8, { style: shared.label }, "What are you reporting?"), /* @__PURE__ */ React10.createElement(View10, { style: styles6.typeRow }, [
|
|
17246
17330
|
{ type: "bug", label: "Bug", icon: "\u{1F41B}" },
|
|
17247
17331
|
{ type: "feedback", label: "Feedback", icon: "\u{1F4A1}" },
|
|
17248
17332
|
{ type: "suggestion", label: "Idea", icon: "\u2728" }
|
|
@@ -17250,12 +17334,12 @@ function ReportScreen({ nav, prefill, autoCaptureUri, onAutoCaptureConsumed }) {
|
|
|
17250
17334
|
TouchableOpacity8,
|
|
17251
17335
|
{
|
|
17252
17336
|
key: type,
|
|
17253
|
-
style: [
|
|
17337
|
+
style: [styles6.typeCard, reportType === type && styles6.typeCardActive],
|
|
17254
17338
|
onPress: () => setReportType(type)
|
|
17255
17339
|
},
|
|
17256
|
-
/* @__PURE__ */ React10.createElement(Text8, { style:
|
|
17257
|
-
/* @__PURE__ */ React10.createElement(Text8, { style: [
|
|
17258
|
-
))), isBugType && /* @__PURE__ */ React10.createElement(View10, { style:
|
|
17340
|
+
/* @__PURE__ */ React10.createElement(Text8, { style: styles6.typeIcon }, icon),
|
|
17341
|
+
/* @__PURE__ */ React10.createElement(Text8, { style: [styles6.typeLabel, reportType === type && styles6.typeLabelActive] }, label)
|
|
17342
|
+
))), isBugType && /* @__PURE__ */ React10.createElement(View10, { style: styles6.section }, /* @__PURE__ */ React10.createElement(Text8, { style: shared.label }, "Severity"), /* @__PURE__ */ React10.createElement(View10, { style: styles6.severityRow }, [
|
|
17259
17343
|
{ sev: "critical", color: colors.red },
|
|
17260
17344
|
{ sev: "high", color: colors.orange },
|
|
17261
17345
|
{ sev: "medium", color: colors.yellow },
|
|
@@ -17264,14 +17348,14 @@ function ReportScreen({ nav, prefill, autoCaptureUri, onAutoCaptureConsumed }) {
|
|
|
17264
17348
|
TouchableOpacity8,
|
|
17265
17349
|
{
|
|
17266
17350
|
key: sev,
|
|
17267
|
-
style: [
|
|
17351
|
+
style: [styles6.sevButton, severity === sev && { backgroundColor: `${color}30`, borderColor: color }],
|
|
17268
17352
|
onPress: () => setSeverity(sev)
|
|
17269
17353
|
},
|
|
17270
|
-
/* @__PURE__ */ React10.createElement(Text8, { style: [
|
|
17271
|
-
)))), isBugType && /* @__PURE__ */ React10.createElement(View10, { style:
|
|
17354
|
+
/* @__PURE__ */ React10.createElement(Text8, { style: [styles6.sevText, severity === sev && { color }] }, sev)
|
|
17355
|
+
)))), isBugType && /* @__PURE__ */ React10.createElement(View10, { style: styles6.section }, /* @__PURE__ */ React10.createElement(Text8, { style: shared.label }, "Category (optional)"), /* @__PURE__ */ React10.createElement(CategoryPicker, { value: category, onChange: setCategory, optional: true })), /* @__PURE__ */ React10.createElement(View10, { style: styles6.section }, /* @__PURE__ */ React10.createElement(Text8, { style: shared.label }, "What happened?"), /* @__PURE__ */ React10.createElement(
|
|
17272
17356
|
TextInput4,
|
|
17273
17357
|
{
|
|
17274
|
-
style:
|
|
17358
|
+
style: styles6.descInput,
|
|
17275
17359
|
value: description,
|
|
17276
17360
|
onChangeText: setDescription,
|
|
17277
17361
|
placeholder: "Describe the issue...",
|
|
@@ -17314,16 +17398,16 @@ function ReportScreen({ nav, prefill, autoCaptureUri, onAutoCaptureConsumed }) {
|
|
|
17314
17398
|
issue.title
|
|
17315
17399
|
),
|
|
17316
17400
|
/* @__PURE__ */ React10.createElement(Text8, { style: { fontSize: 11, color: colors.textMuted } }, issue.status)
|
|
17317
|
-
)))), isBugType && /* @__PURE__ */ React10.createElement(View10, { style:
|
|
17401
|
+
)))), isBugType && /* @__PURE__ */ React10.createElement(View10, { style: styles6.section }, /* @__PURE__ */ React10.createElement(Text8, { style: shared.label }, "Which screen?"), /* @__PURE__ */ React10.createElement(
|
|
17318
17402
|
TextInput4,
|
|
17319
17403
|
{
|
|
17320
|
-
style:
|
|
17404
|
+
style: styles6.screenInput,
|
|
17321
17405
|
value: affectedScreen,
|
|
17322
17406
|
onChangeText: setAffectedScreen,
|
|
17323
17407
|
placeholder: "e.g. Reservations, Settings...",
|
|
17324
17408
|
placeholderTextColor: colors.textMuted
|
|
17325
17409
|
}
|
|
17326
|
-
), /* @__PURE__ */ React10.createElement(Text8, { style:
|
|
17410
|
+
), /* @__PURE__ */ React10.createElement(Text8, { style: styles6.screenHint }, "Which screen or area was the bug on? (optional)")), /* @__PURE__ */ React10.createElement(
|
|
17327
17411
|
ImagePickerButtons,
|
|
17328
17412
|
{
|
|
17329
17413
|
images: images.images,
|
|
@@ -17333,7 +17417,7 @@ function ReportScreen({ nav, prefill, autoCaptureUri, onAutoCaptureConsumed }) {
|
|
|
17333
17417
|
onRemove: images.removeImage,
|
|
17334
17418
|
label: "Screenshots (optional)"
|
|
17335
17419
|
}
|
|
17336
|
-
), error && /* @__PURE__ */ React10.createElement(View10, { style:
|
|
17420
|
+
), error && /* @__PURE__ */ React10.createElement(View10, { style: styles6.errorBanner }, /* @__PURE__ */ React10.createElement(Text8, { style: styles6.errorText }, error)), /* @__PURE__ */ React10.createElement(
|
|
17337
17421
|
TouchableOpacity8,
|
|
17338
17422
|
{
|
|
17339
17423
|
style: [shared.primaryButton, (!description.trim() || submitting || images.isUploading) && shared.primaryButtonDisabled, { marginTop: 20 }],
|
|
@@ -17373,12 +17457,12 @@ import React11, { useEffect as useEffect7, useMemo as useMemo6 } from "react";
|
|
|
17373
17457
|
import { View as View11, Text as Text9, StyleSheet as StyleSheet11 } from "react-native";
|
|
17374
17458
|
function ReportSuccessScreen({ nav }) {
|
|
17375
17459
|
const { widgetColorScheme } = useBugBear();
|
|
17376
|
-
const
|
|
17460
|
+
const styles6 = useMemo6(() => createStyles6(), [widgetColorScheme]);
|
|
17377
17461
|
useEffect7(() => {
|
|
17378
17462
|
const timer = setTimeout(() => nav.reset(), 2e3);
|
|
17379
17463
|
return () => clearTimeout(timer);
|
|
17380
17464
|
}, [nav]);
|
|
17381
|
-
return /* @__PURE__ */ React11.createElement(View11, { style:
|
|
17465
|
+
return /* @__PURE__ */ React11.createElement(View11, { style: styles6.container }, /* @__PURE__ */ React11.createElement(Text9, { style: styles6.emoji }, "\u{1F389}"), /* @__PURE__ */ React11.createElement(Text9, { style: styles6.title }, "Report submitted!"), /* @__PURE__ */ React11.createElement(Text9, { style: styles6.subtitle }, "Thank you for your feedback"));
|
|
17382
17466
|
}
|
|
17383
17467
|
function createStyles6() {
|
|
17384
17468
|
return StyleSheet11.create({
|
|
@@ -17394,7 +17478,7 @@ import React12, { useMemo as useMemo7, useState as useState9 } from "react";
|
|
|
17394
17478
|
import { View as View12, Text as Text10, TouchableOpacity as TouchableOpacity9, ScrollView as ScrollView3, StyleSheet as StyleSheet12, Linking as Linking3 } from "react-native";
|
|
17395
17479
|
function MessageListScreen({ nav }) {
|
|
17396
17480
|
const { threads, unreadCount, refreshThreads, dashboardUrl, isLoading, widgetColorScheme } = useBugBear();
|
|
17397
|
-
const
|
|
17481
|
+
const styles6 = useMemo7(() => createStyles7(), [widgetColorScheme]);
|
|
17398
17482
|
const [activeFilter, setActiveFilter] = useState9("all");
|
|
17399
17483
|
const filteredThreads = threads.filter((thread) => {
|
|
17400
17484
|
if (activeFilter === "all") return true;
|
|
@@ -17412,10 +17496,10 @@ function MessageListScreen({ nav }) {
|
|
|
17412
17496
|
return /* @__PURE__ */ React12.createElement(View12, null, /* @__PURE__ */ React12.createElement(
|
|
17413
17497
|
TouchableOpacity9,
|
|
17414
17498
|
{
|
|
17415
|
-
style:
|
|
17499
|
+
style: styles6.newMsgButton,
|
|
17416
17500
|
onPress: () => nav.push({ name: "COMPOSE_MESSAGE" })
|
|
17417
17501
|
},
|
|
17418
|
-
/* @__PURE__ */ React12.createElement(Text10, { style:
|
|
17502
|
+
/* @__PURE__ */ React12.createElement(Text10, { style: styles6.newMsgText }, "\u2709\uFE0F New Message")
|
|
17419
17503
|
), /* @__PURE__ */ React12.createElement(
|
|
17420
17504
|
ScrollView3,
|
|
17421
17505
|
{
|
|
@@ -17460,20 +17544,20 @@ function MessageListScreen({ nav }) {
|
|
|
17460
17544
|
TouchableOpacity9,
|
|
17461
17545
|
{
|
|
17462
17546
|
key: thread.id,
|
|
17463
|
-
style: [
|
|
17547
|
+
style: [styles6.threadItem, thread.unreadCount > 0 && styles6.threadItemUnread],
|
|
17464
17548
|
onPress: () => nav.push({ name: "THREAD_DETAIL", thread })
|
|
17465
17549
|
},
|
|
17466
|
-
/* @__PURE__ */ React12.createElement(View12, { style:
|
|
17467
|
-
/* @__PURE__ */ React12.createElement(View12, { style:
|
|
17550
|
+
/* @__PURE__ */ React12.createElement(View12, { style: styles6.threadLeft }, /* @__PURE__ */ React12.createElement(Text10, { style: styles6.threadIcon }, getThreadTypeIcon(thread.threadType)), /* @__PURE__ */ React12.createElement(View12, { style: styles6.threadInfo }, /* @__PURE__ */ React12.createElement(View12, { style: styles6.threadTitleRow }, thread.isPinned && /* @__PURE__ */ React12.createElement(Text10, { style: styles6.pinIcon }, "\u{1F4CC}"), /* @__PURE__ */ React12.createElement(Text10, { style: styles6.threadSubject, numberOfLines: 1 }, thread.subject || "No subject")), thread.threadType === "report" && thread.reporterName && /* @__PURE__ */ React12.createElement(Text10, { style: { fontSize: 11, color: colors.textMuted } }, "Reported by: ", thread.reporterName), thread.lastMessage && /* @__PURE__ */ React12.createElement(Text10, { style: styles6.threadPreview, numberOfLines: 1 }, thread.lastMessage.senderName, ": ", thread.lastMessage.content))),
|
|
17551
|
+
/* @__PURE__ */ React12.createElement(View12, { style: styles6.threadRight }, /* @__PURE__ */ React12.createElement(Text10, { style: styles6.threadTime }, formatRelativeTime(thread.lastMessageAt)), thread.unreadCount > 0 && /* @__PURE__ */ React12.createElement(View12, { style: styles6.unreadBadge }, /* @__PURE__ */ React12.createElement(Text10, { style: styles6.unreadText }, thread.unreadCount)), thread.priority !== "normal" && /* @__PURE__ */ React12.createElement(View12, { style: [styles6.priorityDot, { backgroundColor: getPriorityColor(thread.priority) }] }))
|
|
17468
17552
|
))), dashboardUrl && /* @__PURE__ */ React12.createElement(
|
|
17469
17553
|
TouchableOpacity9,
|
|
17470
17554
|
{
|
|
17471
|
-
style:
|
|
17555
|
+
style: styles6.dashboardLink,
|
|
17472
17556
|
onPress: () => Linking3.openURL(`${dashboardUrl}/discussions`),
|
|
17473
17557
|
activeOpacity: 0.7
|
|
17474
17558
|
},
|
|
17475
|
-
/* @__PURE__ */ React12.createElement(Text10, { style:
|
|
17476
|
-
), /* @__PURE__ */ React12.createElement(View12, { style:
|
|
17559
|
+
/* @__PURE__ */ React12.createElement(Text10, { style: styles6.dashboardLinkText }, "\u{1F310}", " View on Dashboard ", "\u2192")
|
|
17560
|
+
), /* @__PURE__ */ React12.createElement(View12, { style: styles6.footer }, /* @__PURE__ */ React12.createElement(Text10, { style: styles6.footerText }, filteredThreads.length, " thread", filteredThreads.length !== 1 ? "s" : "", " \xB7 ", unreadCount, " unread"), /* @__PURE__ */ React12.createElement(TouchableOpacity9, { onPress: refreshThreads }, /* @__PURE__ */ React12.createElement(Text10, { style: styles6.refreshText }, "\u21BB Refresh"))));
|
|
17477
17561
|
}
|
|
17478
17562
|
function createStyles7() {
|
|
17479
17563
|
return StyleSheet12.create({
|
|
@@ -17506,7 +17590,7 @@ import React13, { useState as useState10, useEffect as useEffect8, useMemo as us
|
|
|
17506
17590
|
import { View as View13, Text as Text11, TouchableOpacity as TouchableOpacity10, TextInput as TextInput5, StyleSheet as StyleSheet13, Image as Image2 } from "react-native";
|
|
17507
17591
|
function ThreadDetailScreen({ thread, nav }) {
|
|
17508
17592
|
const { getThreadMessages, sendMessage, markAsRead, uploadImage, widgetColorScheme } = useBugBear();
|
|
17509
|
-
const
|
|
17593
|
+
const styles6 = useMemo8(() => createStyles8(), [widgetColorScheme]);
|
|
17510
17594
|
const [messages, setMessages] = useState10([]);
|
|
17511
17595
|
const [loading, setLoading] = useState10(true);
|
|
17512
17596
|
const [replyText, setReplyText] = useState10("");
|
|
@@ -17558,20 +17642,20 @@ function ThreadDetailScreen({ thread, nav }) {
|
|
|
17558
17642
|
}
|
|
17559
17643
|
setSending(false);
|
|
17560
17644
|
};
|
|
17561
|
-
return /* @__PURE__ */ React13.createElement(View13, { style:
|
|
17645
|
+
return /* @__PURE__ */ React13.createElement(View13, { style: styles6.container }, /* @__PURE__ */ React13.createElement(View13, { style: styles6.header }, /* @__PURE__ */ React13.createElement(Text11, { style: styles6.headerIcon }, getThreadTypeIcon(thread.threadType)), /* @__PURE__ */ React13.createElement(Text11, { style: styles6.headerSubject, numberOfLines: 2 }, thread.subject || "No subject")), loading ? /* @__PURE__ */ React13.createElement(View13, { style: styles6.loadingContainer }, /* @__PURE__ */ React13.createElement(Text11, { style: styles6.loadingText }, "Loading messages...")) : /* @__PURE__ */ React13.createElement(View13, { style: styles6.messagesContainer }, messages.map((msg) => /* @__PURE__ */ React13.createElement(
|
|
17562
17646
|
View13,
|
|
17563
17647
|
{
|
|
17564
17648
|
key: msg.id,
|
|
17565
|
-
style: [
|
|
17649
|
+
style: [styles6.bubble, msg.senderType === "tester" ? styles6.bubbleTester : styles6.bubbleAdmin]
|
|
17566
17650
|
},
|
|
17567
|
-
/* @__PURE__ */ React13.createElement(Text11, { style: [
|
|
17568
|
-
/* @__PURE__ */ React13.createElement(Text11, { style: [
|
|
17569
|
-
msg.attachments && msg.attachments.length > 0 && /* @__PURE__ */ React13.createElement(View13, { style:
|
|
17570
|
-
/* @__PURE__ */ React13.createElement(Text11, { style: [
|
|
17571
|
-
))), sendError && /* @__PURE__ */ React13.createElement(View13, { style:
|
|
17651
|
+
/* @__PURE__ */ React13.createElement(Text11, { style: [styles6.sender, msg.senderType === "tester" && styles6.senderTester] }, msg.senderType === "tester" ? "You" : msg.senderName),
|
|
17652
|
+
/* @__PURE__ */ React13.createElement(Text11, { style: [styles6.content, msg.senderType === "tester" && styles6.contentTester] }, msg.content),
|
|
17653
|
+
msg.attachments && msg.attachments.length > 0 && /* @__PURE__ */ React13.createElement(View13, { style: styles6.attachments }, msg.attachments.filter((a) => a.type === "image").map((att, idx) => /* @__PURE__ */ React13.createElement(Image2, { key: idx, source: { uri: att.url }, style: styles6.attachmentImage, resizeMode: "cover" }))),
|
|
17654
|
+
/* @__PURE__ */ React13.createElement(Text11, { style: [styles6.time, msg.senderType === "tester" && styles6.timeTester] }, formatMessageTime(msg.createdAt))
|
|
17655
|
+
))), sendError && /* @__PURE__ */ React13.createElement(View13, { style: styles6.errorBar }, /* @__PURE__ */ React13.createElement(Text11, { style: styles6.errorText }, "Failed to send. Tap Send to retry.")), replyImages.images.length > 0 && /* @__PURE__ */ React13.createElement(View13, { style: styles6.replyPreview }, /* @__PURE__ */ React13.createElement(ImagePreviewStrip, { images: replyImages.images, onRemove: replyImages.removeImage })), /* @__PURE__ */ React13.createElement(View13, { style: styles6.composer }, IMAGE_PICKER_AVAILABLE && /* @__PURE__ */ React13.createElement(TouchableOpacity10, { style: styles6.attachBtn, onPress: replyImages.pickFromGallery, disabled: replyImages.images.length >= 3 }, /* @__PURE__ */ React13.createElement(Text11, { style: styles6.attachBtnText }, "\u{1F4CE}")), /* @__PURE__ */ React13.createElement(
|
|
17572
17656
|
TextInput5,
|
|
17573
17657
|
{
|
|
17574
|
-
style:
|
|
17658
|
+
style: styles6.replyInput,
|
|
17575
17659
|
value: replyText,
|
|
17576
17660
|
onChangeText: setReplyText,
|
|
17577
17661
|
placeholder: "Type a reply...",
|
|
@@ -17582,11 +17666,11 @@ function ThreadDetailScreen({ thread, nav }) {
|
|
|
17582
17666
|
), /* @__PURE__ */ React13.createElement(
|
|
17583
17667
|
TouchableOpacity10,
|
|
17584
17668
|
{
|
|
17585
|
-
style: [
|
|
17669
|
+
style: [styles6.sendBtn, (!replyText.trim() && replyImages.images.length === 0 || sending || replyImages.isUploading) && styles6.sendBtnDisabled],
|
|
17586
17670
|
onPress: handleSend,
|
|
17587
17671
|
disabled: !replyText.trim() && replyImages.images.length === 0 || sending || replyImages.isUploading
|
|
17588
17672
|
},
|
|
17589
|
-
/* @__PURE__ */ React13.createElement(Text11, { style:
|
|
17673
|
+
/* @__PURE__ */ React13.createElement(Text11, { style: styles6.sendBtnText }, sending ? "..." : "Send")
|
|
17590
17674
|
)));
|
|
17591
17675
|
}
|
|
17592
17676
|
function createStyles8() {
|
|
@@ -17627,7 +17711,7 @@ import React14, { useState as useState11, useMemo as useMemo9 } from "react";
|
|
|
17627
17711
|
import { View as View14, Text as Text12, TextInput as TextInput6, TouchableOpacity as TouchableOpacity11, StyleSheet as StyleSheet14 } from "react-native";
|
|
17628
17712
|
function ComposeMessageScreen({ nav }) {
|
|
17629
17713
|
const { createThread, uploadImage, widgetColorScheme } = useBugBear();
|
|
17630
|
-
const
|
|
17714
|
+
const styles6 = useMemo9(() => createStyles9(), [widgetColorScheme]);
|
|
17631
17715
|
const [subject, setSubject] = useState11("");
|
|
17632
17716
|
const [message, setMessage] = useState11("");
|
|
17633
17717
|
const [sending, setSending] = useState11(false);
|
|
@@ -17646,10 +17730,10 @@ function ComposeMessageScreen({ nav }) {
|
|
|
17646
17730
|
nav.pop();
|
|
17647
17731
|
}
|
|
17648
17732
|
};
|
|
17649
|
-
return /* @__PURE__ */ React14.createElement(View14, null, /* @__PURE__ */ React14.createElement(View14, { style:
|
|
17733
|
+
return /* @__PURE__ */ React14.createElement(View14, null, /* @__PURE__ */ React14.createElement(View14, { style: styles6.header }, /* @__PURE__ */ React14.createElement(Text12, { style: styles6.title }, "New Message"), /* @__PURE__ */ React14.createElement(Text12, { style: styles6.subtitle }, "Send a message to the QA team")), /* @__PURE__ */ React14.createElement(View14, { style: styles6.form }, /* @__PURE__ */ React14.createElement(Text12, { style: shared.label }, "Subject"), /* @__PURE__ */ React14.createElement(
|
|
17650
17734
|
TextInput6,
|
|
17651
17735
|
{
|
|
17652
|
-
style:
|
|
17736
|
+
style: styles6.subjectInput,
|
|
17653
17737
|
value: subject,
|
|
17654
17738
|
onChangeText: setSubject,
|
|
17655
17739
|
placeholder: "What's this about?",
|
|
@@ -17659,7 +17743,7 @@ function ComposeMessageScreen({ nav }) {
|
|
|
17659
17743
|
), /* @__PURE__ */ React14.createElement(Text12, { style: [shared.label, { marginTop: 16 }] }, "Message"), /* @__PURE__ */ React14.createElement(
|
|
17660
17744
|
TextInput6,
|
|
17661
17745
|
{
|
|
17662
|
-
style:
|
|
17746
|
+
style: styles6.messageInput,
|
|
17663
17747
|
value: message,
|
|
17664
17748
|
onChangeText: setMessage,
|
|
17665
17749
|
placeholder: "Write your message...",
|
|
@@ -17704,7 +17788,7 @@ import React15, { useState as useState12, useEffect as useEffect9, useMemo as us
|
|
|
17704
17788
|
import { View as View15, Text as Text13, TouchableOpacity as TouchableOpacity12, TextInput as TextInput7, StyleSheet as StyleSheet15 } from "react-native";
|
|
17705
17789
|
function ProfileScreen({ nav }) {
|
|
17706
17790
|
const { testerInfo, assignments, updateTesterProfile, refreshTesterInfo, widgetColorScheme } = useBugBear();
|
|
17707
|
-
const
|
|
17791
|
+
const styles6 = useMemo10(() => createStyles10(), [widgetColorScheme]);
|
|
17708
17792
|
const [editing, setEditing] = useState12(false);
|
|
17709
17793
|
const [name, setName] = useState12(testerInfo?.name || "");
|
|
17710
17794
|
const [additionalEmails, setAdditionalEmails] = useState12(testerInfo?.additionalEmails || []);
|
|
@@ -17755,13 +17839,13 @@ function ProfileScreen({ nav }) {
|
|
|
17755
17839
|
return /* @__PURE__ */ React15.createElement(View15, { style: shared.emptyState }, /* @__PURE__ */ React15.createElement(Text13, { style: shared.emptyEmoji }, "\u{1F464}"), /* @__PURE__ */ React15.createElement(Text13, { style: shared.emptyTitle }, "No profile found"));
|
|
17756
17840
|
}
|
|
17757
17841
|
if (editing) {
|
|
17758
|
-
return /* @__PURE__ */ React15.createElement(View15, null, /* @__PURE__ */ React15.createElement(View15, { style:
|
|
17842
|
+
return /* @__PURE__ */ React15.createElement(View15, null, /* @__PURE__ */ React15.createElement(View15, { style: styles6.editHeader }, /* @__PURE__ */ React15.createElement(Text13, { style: styles6.editTitle }, "Edit Profile"), /* @__PURE__ */ React15.createElement(TouchableOpacity12, { onPress: () => {
|
|
17759
17843
|
setEditing(false);
|
|
17760
17844
|
setNewEmailInput("");
|
|
17761
|
-
} }, /* @__PURE__ */ React15.createElement(Text13, { style:
|
|
17845
|
+
} }, /* @__PURE__ */ React15.createElement(Text13, { style: styles6.cancelText }, "Cancel"))), /* @__PURE__ */ React15.createElement(View15, { style: styles6.field }, /* @__PURE__ */ React15.createElement(Text13, { style: shared.label }, "Name"), /* @__PURE__ */ React15.createElement(TextInput7, { style: styles6.input, value: name, onChangeText: setName, placeholder: "Your name", placeholderTextColor: colors.textMuted })), /* @__PURE__ */ React15.createElement(View15, { style: styles6.field }, /* @__PURE__ */ React15.createElement(Text13, { style: shared.label }, "Primary Email"), /* @__PURE__ */ React15.createElement(Text13, { style: styles6.emailFixed }, testerInfo.email)), /* @__PURE__ */ React15.createElement(View15, { style: styles6.field }, /* @__PURE__ */ React15.createElement(Text13, { style: shared.label }, "Additional Emails"), additionalEmails.map((email) => /* @__PURE__ */ React15.createElement(View15, { key: email, style: styles6.emailRow }, /* @__PURE__ */ React15.createElement(Text13, { style: styles6.emailText }, email), /* @__PURE__ */ React15.createElement(TouchableOpacity12, { onPress: () => setAdditionalEmails(additionalEmails.filter((e) => e !== email)) }, /* @__PURE__ */ React15.createElement(Text13, { style: styles6.removeEmail }, "\u2715")))), /* @__PURE__ */ React15.createElement(View15, { style: styles6.addEmailRow }, /* @__PURE__ */ React15.createElement(
|
|
17762
17846
|
TextInput7,
|
|
17763
17847
|
{
|
|
17764
|
-
style: [
|
|
17848
|
+
style: [styles6.input, { flex: 1, marginRight: 8 }],
|
|
17765
17849
|
value: newEmailInput,
|
|
17766
17850
|
onChangeText: setNewEmailInput,
|
|
17767
17851
|
placeholder: "Add email",
|
|
@@ -17769,17 +17853,17 @@ function ProfileScreen({ nav }) {
|
|
|
17769
17853
|
keyboardType: "email-address",
|
|
17770
17854
|
autoCapitalize: "none"
|
|
17771
17855
|
}
|
|
17772
|
-
), /* @__PURE__ */ React15.createElement(TouchableOpacity12, { style:
|
|
17856
|
+
), /* @__PURE__ */ React15.createElement(TouchableOpacity12, { style: styles6.addButton, onPress: handleAddEmail }, /* @__PURE__ */ React15.createElement(Text13, { style: styles6.addButtonText }, "Add")))), /* @__PURE__ */ React15.createElement(View15, { style: styles6.field }, /* @__PURE__ */ React15.createElement(Text13, { style: shared.label }, "Testing Platforms"), /* @__PURE__ */ React15.createElement(View15, { style: styles6.platformRow }, [{ key: "ios", label: "\u{1F4F1} iOS" }, { key: "android", label: "\u{1F916} Android" }, { key: "web", label: "\u{1F310} Web" }].map(({ key, label }) => /* @__PURE__ */ React15.createElement(
|
|
17773
17857
|
TouchableOpacity12,
|
|
17774
17858
|
{
|
|
17775
17859
|
key,
|
|
17776
|
-
style: [
|
|
17860
|
+
style: [styles6.platformBtn, platforms.includes(key) && styles6.platformBtnActive],
|
|
17777
17861
|
onPress: () => setPlatforms((prev) => prev.includes(key) ? prev.filter((p) => p !== key) : [...prev, key])
|
|
17778
17862
|
},
|
|
17779
|
-
/* @__PURE__ */ React15.createElement(Text13, { style: [
|
|
17863
|
+
/* @__PURE__ */ React15.createElement(Text13, { style: [styles6.platformText, platforms.includes(key) && styles6.platformTextActive] }, label)
|
|
17780
17864
|
)))), /* @__PURE__ */ React15.createElement(TouchableOpacity12, { style: [shared.primaryButton, { marginTop: 20 }], onPress: handleSave, disabled: saving }, /* @__PURE__ */ React15.createElement(Text13, { style: shared.primaryButtonText }, saving ? "Saving..." : "Save Profile")));
|
|
17781
17865
|
}
|
|
17782
|
-
return /* @__PURE__ */ React15.createElement(View15, null, /* @__PURE__ */ React15.createElement(View15, { style:
|
|
17866
|
+
return /* @__PURE__ */ React15.createElement(View15, null, /* @__PURE__ */ React15.createElement(View15, { style: styles6.profileCard }, /* @__PURE__ */ React15.createElement(View15, { style: styles6.avatar }, /* @__PURE__ */ React15.createElement(Text13, { style: styles6.avatarText }, testerInfo.name.charAt(0).toUpperCase())), /* @__PURE__ */ React15.createElement(Text13, { style: styles6.profileName }, testerInfo.name), /* @__PURE__ */ React15.createElement(Text13, { style: styles6.profileEmail }, testerInfo.email)), /* @__PURE__ */ React15.createElement(View15, { style: styles6.statsRow }, /* @__PURE__ */ React15.createElement(View15, { style: styles6.statItem }, /* @__PURE__ */ React15.createElement(Text13, { style: styles6.statNumber }, completedCount), /* @__PURE__ */ React15.createElement(Text13, { style: styles6.statLabel }, "Completed")), /* @__PURE__ */ React15.createElement(View15, { style: styles6.statDivider }), /* @__PURE__ */ React15.createElement(View15, { style: styles6.statItem }, /* @__PURE__ */ React15.createElement(Text13, { style: styles6.statNumber }, assignments.length), /* @__PURE__ */ React15.createElement(Text13, { style: styles6.statLabel }, "Total Assigned"))), /* @__PURE__ */ React15.createElement(TouchableOpacity12, { onPress: () => setShowDetails(!showDetails), style: styles6.detailsToggle }, /* @__PURE__ */ React15.createElement(Text13, { style: styles6.detailsToggleText }, showDetails ? "\u25BC" : "\u25B6", " Details")), showDetails && /* @__PURE__ */ React15.createElement(View15, { style: styles6.detailsSection }, additionalEmails.length > 0 && /* @__PURE__ */ React15.createElement(View15, { style: styles6.detailBlock }, /* @__PURE__ */ React15.createElement(Text13, { style: styles6.detailLabel }, "Additional Emails"), additionalEmails.map((e) => /* @__PURE__ */ React15.createElement(Text13, { key: e, style: styles6.detailValue }, e))), platforms.length > 0 && /* @__PURE__ */ React15.createElement(View15, { style: styles6.detailBlock }, /* @__PURE__ */ React15.createElement(Text13, { style: styles6.detailLabel }, "Platforms"), /* @__PURE__ */ React15.createElement(View15, { style: styles6.platformTags }, platforms.map((p) => /* @__PURE__ */ React15.createElement(View15, { key: p, style: styles6.platformTag }, /* @__PURE__ */ React15.createElement(Text13, { style: styles6.platformTagText }, p === "ios" ? "\u{1F4F1} iOS" : p === "android" ? "\u{1F916} Android" : "\u{1F310} Web")))))), /* @__PURE__ */ React15.createElement(
|
|
17783
17867
|
TouchableOpacity12,
|
|
17784
17868
|
{
|
|
17785
17869
|
style: [shared.primaryButton, { marginTop: 20 }],
|
|
@@ -17837,7 +17921,7 @@ var CATEGORIES = ["open", "done", "reopened"];
|
|
|
17837
17921
|
var SEVERITY_ORDER2 = { critical: 0, high: 1, medium: 2, low: 3 };
|
|
17838
17922
|
function IssueListScreen({ nav, category }) {
|
|
17839
17923
|
const { client, widgetColorScheme } = useBugBear();
|
|
17840
|
-
const
|
|
17924
|
+
const styles6 = useMemo11(() => createStyles11(), [widgetColorScheme]);
|
|
17841
17925
|
const CATEGORY_CONFIG = useMemo11(() => ({
|
|
17842
17926
|
open: { label: "Open", accent: colors.orange, emptyIcon: "\u2705", emptyText: "No open issues" },
|
|
17843
17927
|
done: { label: "Done", accent: colors.green, emptyIcon: "\u{1F389}", emptyText: "No completed issues yet" },
|
|
@@ -17907,7 +17991,7 @@ function IssueListScreen({ nav, category }) {
|
|
|
17907
17991
|
const searchFilteredIssues = debouncedQuery ? sortedIssues.filter(
|
|
17908
17992
|
(issue) => (issue.title || "").toLowerCase().includes(debouncedQuery.toLowerCase()) || (issue.description || "").toLowerCase().includes(debouncedQuery.toLowerCase())
|
|
17909
17993
|
) : sortedIssues;
|
|
17910
|
-
return /* @__PURE__ */ React16.createElement(View16, null, /* @__PURE__ */ React16.createElement(View16, { style:
|
|
17994
|
+
return /* @__PURE__ */ React16.createElement(View16, null, /* @__PURE__ */ React16.createElement(View16, { style: styles6.tabBar }, CATEGORIES.map((cat) => {
|
|
17911
17995
|
const catConfig = CATEGORY_CONFIG[cat];
|
|
17912
17996
|
const isActive = activeCategory === cat;
|
|
17913
17997
|
const count = counts?.[cat];
|
|
@@ -17916,27 +18000,30 @@ function IssueListScreen({ nav, category }) {
|
|
|
17916
18000
|
{
|
|
17917
18001
|
key: cat,
|
|
17918
18002
|
style: [
|
|
17919
|
-
|
|
18003
|
+
styles6.tab,
|
|
17920
18004
|
{ borderBottomColor: isActive ? catConfig.accent : "transparent" }
|
|
17921
18005
|
],
|
|
17922
|
-
onPress: () =>
|
|
18006
|
+
onPress: () => {
|
|
18007
|
+
setActiveCategory(cat);
|
|
18008
|
+
nav.replace({ name: "ISSUE_LIST", category: cat });
|
|
18009
|
+
},
|
|
17923
18010
|
activeOpacity: 0.7
|
|
17924
18011
|
},
|
|
17925
18012
|
/* @__PURE__ */ React16.createElement(Text14, { style: [
|
|
17926
|
-
|
|
18013
|
+
styles6.tabLabel,
|
|
17927
18014
|
isActive && { fontWeight: "600", color: colors.textPrimary }
|
|
17928
18015
|
] }, catConfig.label),
|
|
17929
18016
|
count !== void 0 && /* @__PURE__ */ React16.createElement(View16, { style: [
|
|
17930
|
-
|
|
18017
|
+
styles6.countBadge,
|
|
17931
18018
|
{
|
|
17932
18019
|
backgroundColor: isActive ? catConfig.accent + "18" : colors.card
|
|
17933
18020
|
}
|
|
17934
18021
|
] }, /* @__PURE__ */ React16.createElement(Text14, { style: [
|
|
17935
|
-
|
|
18022
|
+
styles6.countText,
|
|
17936
18023
|
{ color: isActive ? catConfig.accent : colors.textDim }
|
|
17937
18024
|
] }, count))
|
|
17938
18025
|
);
|
|
17939
|
-
})), /* @__PURE__ */ React16.createElement(View16, { style:
|
|
18026
|
+
})), /* @__PURE__ */ React16.createElement(View16, { style: styles6.sortRow }, [
|
|
17940
18027
|
{ key: "severity", label: "Severity" },
|
|
17941
18028
|
{ key: "recent", label: "Recent" }
|
|
17942
18029
|
].map((s2) => /* @__PURE__ */ React16.createElement(
|
|
@@ -17944,14 +18031,14 @@ function IssueListScreen({ nav, category }) {
|
|
|
17944
18031
|
{
|
|
17945
18032
|
key: s2.key,
|
|
17946
18033
|
style: [
|
|
17947
|
-
|
|
17948
|
-
sortMode === s2.key &&
|
|
18034
|
+
styles6.sortBtn,
|
|
18035
|
+
sortMode === s2.key && styles6.sortBtnActive
|
|
17949
18036
|
],
|
|
17950
18037
|
onPress: () => setSortMode(s2.key)
|
|
17951
18038
|
},
|
|
17952
18039
|
/* @__PURE__ */ React16.createElement(Text14, { style: [
|
|
17953
|
-
|
|
17954
|
-
sortMode === s2.key &&
|
|
18040
|
+
styles6.sortBtnText,
|
|
18041
|
+
sortMode === s2.key && styles6.sortBtnTextActive
|
|
17955
18042
|
] }, s2.label)
|
|
17956
18043
|
))), /* @__PURE__ */ React16.createElement(View16, { style: { paddingHorizontal: 16, paddingBottom: 12 } }, /* @__PURE__ */ React16.createElement(
|
|
17957
18044
|
TextInput8,
|
|
@@ -17971,18 +18058,18 @@ function IssueListScreen({ nav, category }) {
|
|
|
17971
18058
|
fontSize: 13
|
|
17972
18059
|
}
|
|
17973
18060
|
}
|
|
17974
|
-
)), loading ? /* @__PURE__ */ React16.createElement(IssueListScreenSkeleton, null) : searchFilteredIssues.length === 0 ? /* @__PURE__ */ React16.createElement(View16, { style:
|
|
18061
|
+
)), loading ? /* @__PURE__ */ React16.createElement(IssueListScreenSkeleton, null) : searchFilteredIssues.length === 0 ? /* @__PURE__ */ React16.createElement(View16, { style: styles6.emptyContainer }, /* @__PURE__ */ React16.createElement(Text14, { style: styles6.emptyIcon }, debouncedQuery ? "\u{1F50D}" : config.emptyIcon), /* @__PURE__ */ React16.createElement(Text14, { style: styles6.emptyText }, debouncedQuery ? "No matching issues" : config.emptyText)) : searchFilteredIssues.map((issue) => /* @__PURE__ */ React16.createElement(
|
|
17975
18062
|
TouchableOpacity13,
|
|
17976
18063
|
{
|
|
17977
18064
|
key: issue.id,
|
|
17978
|
-
style:
|
|
18065
|
+
style: styles6.issueCard,
|
|
17979
18066
|
onPress: () => nav.push({ name: "ISSUE_DETAIL", issue }),
|
|
17980
18067
|
activeOpacity: 0.7
|
|
17981
18068
|
},
|
|
17982
|
-
/* @__PURE__ */ React16.createElement(View16, { style:
|
|
17983
|
-
/* @__PURE__ */ React16.createElement(View16, { style:
|
|
17984
|
-
activeCategory === "done" && issue.verifiedByName && /* @__PURE__ */ React16.createElement(View16, { style:
|
|
17985
|
-
activeCategory === "reopened" && issue.originalBugTitle && /* @__PURE__ */ React16.createElement(View16, { style:
|
|
18069
|
+
/* @__PURE__ */ React16.createElement(View16, { style: styles6.topRow }, issue.severity && /* @__PURE__ */ React16.createElement(View16, { style: [styles6.severityDot, { backgroundColor: SEVERITY_COLORS[issue.severity] || colors.textDim }] }), /* @__PURE__ */ React16.createElement(Text14, { style: styles6.issueTitle, numberOfLines: 1 }, issue.title)),
|
|
18070
|
+
/* @__PURE__ */ React16.createElement(View16, { style: styles6.bottomRow }, issue.route && /* @__PURE__ */ React16.createElement(Text14, { style: styles6.routeText, numberOfLines: 1 }, issue.route), /* @__PURE__ */ React16.createElement(Text14, { style: styles6.timeText }, formatRelativeTime(issue.updatedAt))),
|
|
18071
|
+
activeCategory === "done" && issue.verifiedByName && /* @__PURE__ */ React16.createElement(View16, { style: styles6.verifiedBadge }, /* @__PURE__ */ React16.createElement(Text14, { style: styles6.verifiedBadgeText }, "\u2714", " Verified by ", issue.verifiedByName)),
|
|
18072
|
+
activeCategory === "reopened" && issue.originalBugTitle && /* @__PURE__ */ React16.createElement(View16, { style: styles6.reopenedBadge }, /* @__PURE__ */ React16.createElement(Text14, { style: styles6.reopenedBadgeText, numberOfLines: 1 }, "\u{1F504}", " Retest of: ", issue.originalBugTitle))
|
|
17986
18073
|
)));
|
|
17987
18074
|
}
|
|
17988
18075
|
function createStyles11() {
|
|
@@ -18141,7 +18228,7 @@ import { View as View17, Text as Text15, Image as Image3, StyleSheet as StyleShe
|
|
|
18141
18228
|
var DONE_STATUSES = ["verified", "resolved", "closed", "reviewed"];
|
|
18142
18229
|
function IssueDetailScreen({ nav, issue }) {
|
|
18143
18230
|
const { dashboardUrl, widgetColorScheme, reopenReport } = useBugBear();
|
|
18144
|
-
const
|
|
18231
|
+
const styles6 = useMemo12(() => createStyles12(), [widgetColorScheme]);
|
|
18145
18232
|
const [showReopenForm, setShowReopenForm] = useState14(false);
|
|
18146
18233
|
const [reopenReason, setReopenReason] = useState14("");
|
|
18147
18234
|
const [isSubmitting, setIsSubmitting] = useState14(false);
|
|
@@ -18183,44 +18270,44 @@ function IssueDetailScreen({ nav, issue }) {
|
|
|
18183
18270
|
setReopenError(result.error || "Failed to reopen");
|
|
18184
18271
|
}
|
|
18185
18272
|
}, [reopenReason, reopenReport, issue.id]);
|
|
18186
|
-
return /* @__PURE__ */ React17.createElement(View17, null, /* @__PURE__ */ React17.createElement(View17, { style:
|
|
18273
|
+
return /* @__PURE__ */ React17.createElement(View17, null, /* @__PURE__ */ React17.createElement(View17, { style: styles6.badgeRow }, /* @__PURE__ */ React17.createElement(View17, { style: [styles6.badge, { backgroundColor: wasReopened ? colors.yellowDark : statusConfig.bg }] }, /* @__PURE__ */ React17.createElement(Text15, { style: [styles6.badgeText, { color: wasReopened ? colors.yellowLight : statusConfig.color }] }, wasReopened ? "Reopened" : statusConfig.label)), severityConfig && /* @__PURE__ */ React17.createElement(View17, { style: [styles6.badge, { backgroundColor: severityConfig.bg }] }, /* @__PURE__ */ React17.createElement(Text15, { style: [styles6.badgeText, { color: severityConfig.color }] }, severityConfig.label))), /* @__PURE__ */ React17.createElement(Text15, { style: styles6.title }, issue.title), issue.route && /* @__PURE__ */ React17.createElement(Text15, { style: styles6.route }, issue.route), issue.description && /* @__PURE__ */ React17.createElement(View17, { style: styles6.descriptionCard }, /* @__PURE__ */ React17.createElement(Text15, { style: styles6.descriptionText }, issue.description)), wasReopened && /* @__PURE__ */ React17.createElement(View17, { style: styles6.reopenedCard }, /* @__PURE__ */ React17.createElement(View17, { style: styles6.reopenedRow }, /* @__PURE__ */ React17.createElement(Text15, { style: styles6.reopenedIcon }, "\u{1F504}"), /* @__PURE__ */ React17.createElement(Text15, { style: styles6.reopenedText }, "Issue reopened \u2014 your team has been notified"))), issue.verifiedByName && !wasReopened && /* @__PURE__ */ React17.createElement(View17, { style: styles6.verifiedCard }, /* @__PURE__ */ React17.createElement(View17, { style: styles6.verifiedHeader }, /* @__PURE__ */ React17.createElement(Text15, { style: styles6.verifiedIcon }, "\u2705"), /* @__PURE__ */ React17.createElement(Text15, { style: styles6.verifiedTitle }, "Retesting Proof")), /* @__PURE__ */ React17.createElement(Text15, { style: styles6.verifiedBody }, "Verified by ", issue.verifiedByName, issue.verifiedAt && ` on ${new Date(issue.verifiedAt).toLocaleDateString(void 0, { month: "short", day: "numeric", year: "numeric" })}`)), issue.originalBugTitle && /* @__PURE__ */ React17.createElement(View17, { style: styles6.originalBugCard }, /* @__PURE__ */ React17.createElement(View17, { style: styles6.originalBugHeader }, /* @__PURE__ */ React17.createElement(Text15, { style: styles6.originalBugIcon }, "\u{1F504}"), /* @__PURE__ */ React17.createElement(Text15, { style: styles6.originalBugTitleText }, "Original Bug")), /* @__PURE__ */ React17.createElement(Text15, { style: styles6.originalBugBody }, "Retest of: ", issue.originalBugTitle)), isDone && !wasReopened && !showReopenForm && /* @__PURE__ */ React17.createElement(
|
|
18187
18274
|
TouchableOpacity14,
|
|
18188
18275
|
{
|
|
18189
|
-
style:
|
|
18276
|
+
style: styles6.reopenButton,
|
|
18190
18277
|
onPress: () => setShowReopenForm(true),
|
|
18191
18278
|
activeOpacity: 0.7
|
|
18192
18279
|
},
|
|
18193
|
-
/* @__PURE__ */ React17.createElement(Text15, { style:
|
|
18194
|
-
), showReopenForm && !wasReopened && /* @__PURE__ */ React17.createElement(View17, { style:
|
|
18280
|
+
/* @__PURE__ */ React17.createElement(Text15, { style: styles6.reopenButtonText }, "\u{1F504}", " Not Fixed \u2014 Reopen Issue")
|
|
18281
|
+
), showReopenForm && !wasReopened && /* @__PURE__ */ React17.createElement(View17, { style: styles6.reopenForm }, /* @__PURE__ */ React17.createElement(Text15, { style: styles6.reopenFormTitle }, "Why isn't this fixed?"), /* @__PURE__ */ React17.createElement(
|
|
18195
18282
|
TextInput9,
|
|
18196
18283
|
{
|
|
18197
18284
|
value: reopenReason,
|
|
18198
18285
|
onChangeText: setReopenReason,
|
|
18199
18286
|
placeholder: "Describe what you're still seeing...",
|
|
18200
18287
|
placeholderTextColor: colors.textMuted,
|
|
18201
|
-
style:
|
|
18288
|
+
style: styles6.reopenInput,
|
|
18202
18289
|
multiline: true,
|
|
18203
18290
|
autoFocus: true
|
|
18204
18291
|
}
|
|
18205
|
-
), reopenError && /* @__PURE__ */ React17.createElement(Text15, { style:
|
|
18292
|
+
), reopenError && /* @__PURE__ */ React17.createElement(Text15, { style: styles6.reopenErrorText }, reopenError), /* @__PURE__ */ React17.createElement(View17, { style: styles6.reopenActions }, /* @__PURE__ */ React17.createElement(
|
|
18206
18293
|
TouchableOpacity14,
|
|
18207
18294
|
{
|
|
18208
18295
|
style: [
|
|
18209
|
-
|
|
18210
|
-
(!reopenReason.trim() || isSubmitting) &&
|
|
18296
|
+
styles6.reopenSubmitButton,
|
|
18297
|
+
(!reopenReason.trim() || isSubmitting) && styles6.reopenSubmitDisabled
|
|
18211
18298
|
],
|
|
18212
18299
|
onPress: handleReopen,
|
|
18213
18300
|
disabled: isSubmitting || !reopenReason.trim(),
|
|
18214
18301
|
activeOpacity: 0.7
|
|
18215
18302
|
},
|
|
18216
18303
|
isSubmitting ? /* @__PURE__ */ React17.createElement(ActivityIndicator2, { size: "small", color: "#fff" }) : /* @__PURE__ */ React17.createElement(Text15, { style: [
|
|
18217
|
-
|
|
18218
|
-
!reopenReason.trim() &&
|
|
18304
|
+
styles6.reopenSubmitText,
|
|
18305
|
+
!reopenReason.trim() && styles6.reopenSubmitTextDisabled
|
|
18219
18306
|
] }, "Reopen Issue")
|
|
18220
18307
|
), /* @__PURE__ */ React17.createElement(
|
|
18221
18308
|
TouchableOpacity14,
|
|
18222
18309
|
{
|
|
18223
|
-
style:
|
|
18310
|
+
style: styles6.reopenCancelButton,
|
|
18224
18311
|
onPress: () => {
|
|
18225
18312
|
setShowReopenForm(false);
|
|
18226
18313
|
setReopenReason("");
|
|
@@ -18229,15 +18316,22 @@ function IssueDetailScreen({ nav, issue }) {
|
|
|
18229
18316
|
disabled: isSubmitting,
|
|
18230
18317
|
activeOpacity: 0.7
|
|
18231
18318
|
},
|
|
18232
|
-
/* @__PURE__ */ React17.createElement(Text15, { style:
|
|
18233
|
-
))), issue.
|
|
18319
|
+
/* @__PURE__ */ React17.createElement(Text15, { style: styles6.reopenCancelText }, "Cancel")
|
|
18320
|
+
))), issue.status === "ready_to_test" && (issue.fixCommitSha || issue.resolutionNotes) && /* @__PURE__ */ React17.createElement(View17, { style: {
|
|
18321
|
+
backgroundColor: "rgba(59, 130, 246, 0.1)",
|
|
18322
|
+
borderWidth: 1,
|
|
18323
|
+
borderColor: "rgba(96, 165, 250, 0.2)",
|
|
18324
|
+
borderRadius: 8,
|
|
18325
|
+
padding: 12,
|
|
18326
|
+
marginBottom: 12
|
|
18327
|
+
} }, /* @__PURE__ */ React17.createElement(View17, { style: { flexDirection: "row", alignItems: "center", gap: 6, marginBottom: 8 } }, /* @__PURE__ */ React17.createElement(Text15, { style: { fontSize: 13 } }, "\u{1F527}"), /* @__PURE__ */ React17.createElement(Text15, { style: { fontSize: 12, fontWeight: "600", color: "#60a5fa" } }, "Fix Details")), issue.resolutionNotes ? /* @__PURE__ */ React17.createElement(Text15, { style: { fontSize: 12, color: colors.textSecondary, marginBottom: 6, lineHeight: 17 } }, issue.resolutionNotes) : null, issue.fixCommitSha ? /* @__PURE__ */ React17.createElement(Text15, { style: { fontSize: 11, color: colors.textDim, fontFamily: "monospace" } }, "Commit: ", issue.fixCommitSha.slice(0, 7), issue.fixCommitMessage && ` \u2014 ${issue.fixCommitMessage}`) : null, issue.fixFilesChanged && issue.fixFilesChanged.length > 0 ? /* @__PURE__ */ React17.createElement(Text15, { style: { fontSize: 11, color: colors.textDim, marginTop: 4 } }, issue.fixFilesChanged.length, " file", issue.fixFilesChanged.length > 1 ? "s" : "", " changed") : null), issue.screenshotUrls && issue.screenshotUrls.length > 0 && /* @__PURE__ */ React17.createElement(View17, { style: styles6.screenshotSection }, /* @__PURE__ */ React17.createElement(Text15, { style: styles6.screenshotLabel }, "Screenshots (", issue.screenshotUrls.length, ")"), /* @__PURE__ */ React17.createElement(View17, { style: styles6.screenshotRow }, issue.screenshotUrls.map((url, i) => /* @__PURE__ */ React17.createElement(TouchableOpacity14, { key: i, onPress: () => Linking4.openURL(url), activeOpacity: 0.7 }, /* @__PURE__ */ React17.createElement(Image3, { source: { uri: url }, style: styles6.screenshotThumb }))))), /* @__PURE__ */ React17.createElement(View17, { style: styles6.metaSection }, issue.reporterName && /* @__PURE__ */ React17.createElement(Text15, { style: styles6.metaText }, "Reported by ", issue.reporterName), /* @__PURE__ */ React17.createElement(Text15, { style: styles6.metaTextSmall }, "Created ", formatRelativeTime(issue.createdAt), " ", "\xB7", " Updated ", formatRelativeTime(issue.updatedAt))), dashboardUrl && /* @__PURE__ */ React17.createElement(
|
|
18234
18328
|
TouchableOpacity14,
|
|
18235
18329
|
{
|
|
18236
|
-
style:
|
|
18330
|
+
style: styles6.dashboardLink,
|
|
18237
18331
|
onPress: () => Linking4.openURL(`${dashboardUrl}/reports`),
|
|
18238
18332
|
activeOpacity: 0.7
|
|
18239
18333
|
},
|
|
18240
|
-
/* @__PURE__ */ React17.createElement(Text15, { style:
|
|
18334
|
+
/* @__PURE__ */ React17.createElement(Text15, { style: styles6.dashboardLinkText }, "\u{1F310}", " View on Dashboard ", "\u2192")
|
|
18241
18335
|
));
|
|
18242
18336
|
}
|
|
18243
18337
|
function createStyles12() {
|
|
@@ -18494,7 +18588,7 @@ import React18, { useState as useState15, useMemo as useMemo13 } from "react";
|
|
|
18494
18588
|
import { View as View18, Text as Text16, TextInput as TextInput10, TouchableOpacity as TouchableOpacity15, StyleSheet as StyleSheet18, Keyboard as Keyboard2 } from "react-native";
|
|
18495
18589
|
function SessionStartScreen({ nav }) {
|
|
18496
18590
|
const { startSession, assignments, widgetColorScheme } = useBugBear();
|
|
18497
|
-
const
|
|
18591
|
+
const styles6 = useMemo13(() => createStyles13(), [widgetColorScheme]);
|
|
18498
18592
|
const [focusArea, setFocusArea] = useState15("");
|
|
18499
18593
|
const [isStarting, setIsStarting] = useState15(false);
|
|
18500
18594
|
const [error, setError] = useState15(null);
|
|
@@ -18521,35 +18615,35 @@ function SessionStartScreen({ nav }) {
|
|
|
18521
18615
|
setIsStarting(false);
|
|
18522
18616
|
}
|
|
18523
18617
|
};
|
|
18524
|
-
return /* @__PURE__ */ React18.createElement(View18, null, /* @__PURE__ */ React18.createElement(View18, { style:
|
|
18618
|
+
return /* @__PURE__ */ React18.createElement(View18, null, /* @__PURE__ */ React18.createElement(View18, { style: styles6.header }, /* @__PURE__ */ React18.createElement(Text16, { style: styles6.headerIcon }, "\u{1F50D}"), /* @__PURE__ */ React18.createElement(Text16, { style: styles6.headerDesc }, "Start an exploratory QA session. Log findings as you go \u2014 bugs, concerns, suggestions, or questions.")), /* @__PURE__ */ React18.createElement(View18, { style: styles6.inputSection }, /* @__PURE__ */ React18.createElement(Text16, { style: styles6.label }, "What are you testing?"), /* @__PURE__ */ React18.createElement(
|
|
18525
18619
|
TextInput10,
|
|
18526
18620
|
{
|
|
18527
18621
|
value: focusArea,
|
|
18528
18622
|
onChangeText: setFocusArea,
|
|
18529
18623
|
placeholder: "e.g. Checkout flow, Settings page...",
|
|
18530
18624
|
placeholderTextColor: colors.textMuted,
|
|
18531
|
-
style:
|
|
18625
|
+
style: styles6.input,
|
|
18532
18626
|
returnKeyType: "done",
|
|
18533
18627
|
onSubmitEditing: handleStart
|
|
18534
18628
|
}
|
|
18535
|
-
)), trackNames.length > 0 && /* @__PURE__ */ React18.createElement(View18, { style:
|
|
18629
|
+
)), trackNames.length > 0 && /* @__PURE__ */ React18.createElement(View18, { style: styles6.chipsSection }, /* @__PURE__ */ React18.createElement(Text16, { style: styles6.chipsLabel }, "Quick pick:"), /* @__PURE__ */ React18.createElement(View18, { style: styles6.chipsRow }, trackNames.map((name) => /* @__PURE__ */ React18.createElement(
|
|
18536
18630
|
TouchableOpacity15,
|
|
18537
18631
|
{
|
|
18538
18632
|
key: name,
|
|
18539
|
-
style: [
|
|
18633
|
+
style: [styles6.chip, focusArea === name && styles6.chipActive],
|
|
18540
18634
|
onPress: () => setFocusArea(name),
|
|
18541
18635
|
activeOpacity: 0.7
|
|
18542
18636
|
},
|
|
18543
|
-
/* @__PURE__ */ React18.createElement(Text16, { style: [
|
|
18544
|
-
)))), error && /* @__PURE__ */ React18.createElement(View18, { style:
|
|
18637
|
+
/* @__PURE__ */ React18.createElement(Text16, { style: [styles6.chipText, focusArea === name && styles6.chipTextActive] }, name)
|
|
18638
|
+
)))), error && /* @__PURE__ */ React18.createElement(View18, { style: styles6.errorBox }, /* @__PURE__ */ React18.createElement(Text16, { style: styles6.errorText }, error)), /* @__PURE__ */ React18.createElement(
|
|
18545
18639
|
TouchableOpacity15,
|
|
18546
18640
|
{
|
|
18547
|
-
style: [
|
|
18641
|
+
style: [styles6.startBtn, isStarting && styles6.startBtnDisabled],
|
|
18548
18642
|
onPress: handleStart,
|
|
18549
18643
|
disabled: isStarting,
|
|
18550
18644
|
activeOpacity: 0.8
|
|
18551
18645
|
},
|
|
18552
|
-
/* @__PURE__ */ React18.createElement(Text16, { style:
|
|
18646
|
+
/* @__PURE__ */ React18.createElement(Text16, { style: styles6.startBtnText }, isStarting ? "Starting..." : "\u25B6 Start Session")
|
|
18553
18647
|
));
|
|
18554
18648
|
}
|
|
18555
18649
|
function createStyles13() {
|
|
@@ -18654,11 +18748,11 @@ function createStyles13() {
|
|
|
18654
18748
|
}
|
|
18655
18749
|
|
|
18656
18750
|
// src/widget/screens/SessionActiveScreen.tsx
|
|
18657
|
-
import React19, { useState as useState16, useEffect as useEffect11, useRef as
|
|
18751
|
+
import React19, { useState as useState16, useEffect as useEffect11, useRef as useRef6, useMemo as useMemo14 } from "react";
|
|
18658
18752
|
import { View as View19, Text as Text17, TouchableOpacity as TouchableOpacity16, StyleSheet as StyleSheet19 } from "react-native";
|
|
18659
18753
|
function SessionActiveScreen({ nav }) {
|
|
18660
18754
|
const { activeSession, sessionFindings, endSession, refreshSession, widgetColorScheme } = useBugBear();
|
|
18661
|
-
const
|
|
18755
|
+
const styles6 = useMemo14(() => createStyles14(), [widgetColorScheme]);
|
|
18662
18756
|
const FINDING_TYPE_CONFIG = useMemo14(() => ({
|
|
18663
18757
|
bug: { icon: "\u{1F41B}", label: "Bug", color: colors.red },
|
|
18664
18758
|
concern: { icon: "\u26A0\uFE0F", label: "Concern", color: colors.amber },
|
|
@@ -18667,7 +18761,7 @@ function SessionActiveScreen({ nav }) {
|
|
|
18667
18761
|
}), [widgetColorScheme]);
|
|
18668
18762
|
const [isEnding, setIsEnding] = useState16(false);
|
|
18669
18763
|
const [elapsed, setElapsed] = useState16(0);
|
|
18670
|
-
const timerRef =
|
|
18764
|
+
const timerRef = useRef6(null);
|
|
18671
18765
|
useEffect11(() => {
|
|
18672
18766
|
refreshSession();
|
|
18673
18767
|
}, []);
|
|
@@ -18700,30 +18794,30 @@ function SessionActiveScreen({ nav }) {
|
|
|
18700
18794
|
}
|
|
18701
18795
|
};
|
|
18702
18796
|
if (!activeSession) {
|
|
18703
|
-
return /* @__PURE__ */ React19.createElement(View19, { style:
|
|
18797
|
+
return /* @__PURE__ */ React19.createElement(View19, { style: styles6.emptyContainer }, /* @__PURE__ */ React19.createElement(Text17, { style: styles6.emptyText }, "No active session"), /* @__PURE__ */ React19.createElement(TouchableOpacity16, { onPress: () => nav.replace({ name: "SESSION_START" }) }, /* @__PURE__ */ React19.createElement(Text17, { style: styles6.emptyLink }, "Start a new session")));
|
|
18704
18798
|
}
|
|
18705
18799
|
const renderFinding = (finding) => {
|
|
18706
18800
|
const config = FINDING_TYPE_CONFIG[finding.type] || FINDING_TYPE_CONFIG.bug;
|
|
18707
|
-
return /* @__PURE__ */ React19.createElement(View19, { key: finding.id, style:
|
|
18801
|
+
return /* @__PURE__ */ React19.createElement(View19, { key: finding.id, style: styles6.findingRow }, /* @__PURE__ */ React19.createElement(Text17, { style: styles6.findingIcon }, config.icon), /* @__PURE__ */ React19.createElement(View19, { style: styles6.findingContent }, /* @__PURE__ */ React19.createElement(Text17, { style: styles6.findingTitle, numberOfLines: 1 }, finding.title), /* @__PURE__ */ React19.createElement(View19, { style: styles6.findingMeta }, /* @__PURE__ */ React19.createElement(Text17, { style: [styles6.findingType, { color: config.color }] }, config.label), /* @__PURE__ */ React19.createElement(Text17, { style: styles6.findingSeverity }, finding.severity), finding.convertedToBugId && /* @__PURE__ */ React19.createElement(Text17, { style: styles6.findingConverted }, "\u2192 Bug filed"))));
|
|
18708
18802
|
};
|
|
18709
|
-
return /* @__PURE__ */ React19.createElement(View19, null, /* @__PURE__ */ React19.createElement(View19, { style:
|
|
18803
|
+
return /* @__PURE__ */ React19.createElement(View19, null, /* @__PURE__ */ React19.createElement(View19, { style: styles6.timerCard }, /* @__PURE__ */ React19.createElement(View19, { style: styles6.recordingRow }, /* @__PURE__ */ React19.createElement(View19, { style: styles6.recordingDot }), /* @__PURE__ */ React19.createElement(Text17, { style: styles6.recordingLabel }, "Recording")), /* @__PURE__ */ React19.createElement(Text17, { style: styles6.timerText }, formatTimer(elapsed)), activeSession.focusArea ? /* @__PURE__ */ React19.createElement(Text17, { style: styles6.focusArea }, activeSession.focusArea) : null), /* @__PURE__ */ React19.createElement(View19, { style: styles6.actionRow }, /* @__PURE__ */ React19.createElement(
|
|
18710
18804
|
TouchableOpacity16,
|
|
18711
18805
|
{
|
|
18712
|
-
style:
|
|
18806
|
+
style: styles6.addFindingBtn,
|
|
18713
18807
|
onPress: () => nav.push({ name: "SESSION_FINDING" }),
|
|
18714
18808
|
activeOpacity: 0.8
|
|
18715
18809
|
},
|
|
18716
|
-
/* @__PURE__ */ React19.createElement(Text17, { style:
|
|
18810
|
+
/* @__PURE__ */ React19.createElement(Text17, { style: styles6.addFindingText }, "+ Add Finding")
|
|
18717
18811
|
), /* @__PURE__ */ React19.createElement(
|
|
18718
18812
|
TouchableOpacity16,
|
|
18719
18813
|
{
|
|
18720
|
-
style: [
|
|
18814
|
+
style: [styles6.endBtn, isEnding && styles6.endBtnDisabled],
|
|
18721
18815
|
onPress: handleEnd,
|
|
18722
18816
|
disabled: isEnding,
|
|
18723
18817
|
activeOpacity: 0.8
|
|
18724
18818
|
},
|
|
18725
|
-
/* @__PURE__ */ React19.createElement(Text17, { style:
|
|
18726
|
-
)), /* @__PURE__ */ React19.createElement(Text17, { style:
|
|
18819
|
+
/* @__PURE__ */ React19.createElement(Text17, { style: styles6.endBtnText }, isEnding ? "..." : "End")
|
|
18820
|
+
)), /* @__PURE__ */ React19.createElement(Text17, { style: styles6.sectionTitle }, "Findings (", sessionFindings.length, ")"), sessionFindings.length === 0 ? /* @__PURE__ */ React19.createElement(View19, { style: styles6.emptyFindings }, /* @__PURE__ */ React19.createElement(Text17, { style: styles6.emptyFindingsIcon }, "\u{1F4CB}"), /* @__PURE__ */ React19.createElement(Text17, { style: styles6.emptyFindingsText }, 'No findings yet. Tap "Add Finding" to log something.')) : /* @__PURE__ */ React19.createElement(View19, { style: styles6.findingsList }, sessionFindings.map(renderFinding)));
|
|
18727
18821
|
}
|
|
18728
18822
|
function createStyles14() {
|
|
18729
18823
|
return StyleSheet19.create({
|
|
@@ -18901,7 +18995,7 @@ var FINDING_TYPES = [
|
|
|
18901
18995
|
];
|
|
18902
18996
|
function SessionFindingScreen({ nav }) {
|
|
18903
18997
|
const { addFinding, widgetColorScheme } = useBugBear();
|
|
18904
|
-
const
|
|
18998
|
+
const styles6 = useMemo15(() => createStyles15(), [widgetColorScheme]);
|
|
18905
18999
|
const SEVERITIES = useMemo15(() => [
|
|
18906
19000
|
{ value: "critical", label: "Critical", color: colors.red },
|
|
18907
19001
|
{ value: "high", label: "High", color: colors.orange },
|
|
@@ -18933,46 +19027,46 @@ function SessionFindingScreen({ nav }) {
|
|
|
18933
19027
|
}
|
|
18934
19028
|
};
|
|
18935
19029
|
const canSubmit = title.trim().length > 0 && !isSubmitting;
|
|
18936
|
-
return /* @__PURE__ */ React20.createElement(View20, null, /* @__PURE__ */ React20.createElement(View20, { style:
|
|
19030
|
+
return /* @__PURE__ */ React20.createElement(View20, null, /* @__PURE__ */ React20.createElement(View20, { style: styles6.section }, /* @__PURE__ */ React20.createElement(Text18, { style: styles6.sectionLabel }, "Type"), /* @__PURE__ */ React20.createElement(View20, { style: styles6.typeRow }, FINDING_TYPES.map((ft) => /* @__PURE__ */ React20.createElement(
|
|
18937
19031
|
TouchableOpacity17,
|
|
18938
19032
|
{
|
|
18939
19033
|
key: ft.value,
|
|
18940
|
-
style: [
|
|
19034
|
+
style: [styles6.typePill, type === ft.value && styles6.typePillActive],
|
|
18941
19035
|
onPress: () => setType(ft.value),
|
|
18942
19036
|
activeOpacity: 0.7
|
|
18943
19037
|
},
|
|
18944
|
-
/* @__PURE__ */ React20.createElement(Text18, { style:
|
|
18945
|
-
/* @__PURE__ */ React20.createElement(Text18, { style: [
|
|
18946
|
-
)))), /* @__PURE__ */ React20.createElement(View20, { style:
|
|
19038
|
+
/* @__PURE__ */ React20.createElement(Text18, { style: styles6.typePillIcon }, ft.icon),
|
|
19039
|
+
/* @__PURE__ */ React20.createElement(Text18, { style: [styles6.typePillLabel, type === ft.value && styles6.typePillLabelActive] }, ft.label)
|
|
19040
|
+
)))), /* @__PURE__ */ React20.createElement(View20, { style: styles6.section }, /* @__PURE__ */ React20.createElement(Text18, { style: styles6.sectionLabel }, "Severity"), /* @__PURE__ */ React20.createElement(View20, { style: styles6.severityRow }, SEVERITIES.map((s2) => /* @__PURE__ */ React20.createElement(
|
|
18947
19041
|
TouchableOpacity17,
|
|
18948
19042
|
{
|
|
18949
19043
|
key: s2.value,
|
|
18950
19044
|
style: [
|
|
18951
|
-
|
|
19045
|
+
styles6.severityPill,
|
|
18952
19046
|
severity === s2.value && { backgroundColor: `${s2.color}20`, borderColor: s2.color }
|
|
18953
19047
|
],
|
|
18954
19048
|
onPress: () => setSeverity(s2.value),
|
|
18955
19049
|
activeOpacity: 0.7
|
|
18956
19050
|
},
|
|
18957
|
-
/* @__PURE__ */ React20.createElement(Text18, { style: [
|
|
18958
|
-
)))), /* @__PURE__ */ React20.createElement(View20, { style:
|
|
19051
|
+
/* @__PURE__ */ React20.createElement(Text18, { style: [styles6.severityText, severity === s2.value && { color: s2.color }] }, s2.label)
|
|
19052
|
+
)))), /* @__PURE__ */ React20.createElement(View20, { style: styles6.inputSection }, /* @__PURE__ */ React20.createElement(
|
|
18959
19053
|
TextInput11,
|
|
18960
19054
|
{
|
|
18961
19055
|
value: title,
|
|
18962
19056
|
onChangeText: setTitle,
|
|
18963
19057
|
placeholder: "What did you find?",
|
|
18964
19058
|
placeholderTextColor: colors.textMuted,
|
|
18965
|
-
style:
|
|
19059
|
+
style: styles6.titleInput,
|
|
18966
19060
|
returnKeyType: "next"
|
|
18967
19061
|
}
|
|
18968
|
-
)), /* @__PURE__ */ React20.createElement(View20, { style:
|
|
19062
|
+
)), /* @__PURE__ */ React20.createElement(View20, { style: styles6.inputSection }, /* @__PURE__ */ React20.createElement(
|
|
18969
19063
|
TextInput11,
|
|
18970
19064
|
{
|
|
18971
19065
|
value: description,
|
|
18972
19066
|
onChangeText: setDescription,
|
|
18973
19067
|
placeholder: "Details (optional)",
|
|
18974
19068
|
placeholderTextColor: colors.textMuted,
|
|
18975
|
-
style:
|
|
19069
|
+
style: styles6.descInput,
|
|
18976
19070
|
multiline: true,
|
|
18977
19071
|
numberOfLines: 3,
|
|
18978
19072
|
textAlignVertical: "top"
|
|
@@ -18980,12 +19074,12 @@ function SessionFindingScreen({ nav }) {
|
|
|
18980
19074
|
)), /* @__PURE__ */ React20.createElement(
|
|
18981
19075
|
TouchableOpacity17,
|
|
18982
19076
|
{
|
|
18983
|
-
style: [
|
|
19077
|
+
style: [styles6.submitBtn, !canSubmit && styles6.submitBtnDisabled],
|
|
18984
19078
|
onPress: handleSubmit,
|
|
18985
19079
|
disabled: !canSubmit,
|
|
18986
19080
|
activeOpacity: 0.8
|
|
18987
19081
|
},
|
|
18988
|
-
/* @__PURE__ */ React20.createElement(Text18, { style: [
|
|
19082
|
+
/* @__PURE__ */ React20.createElement(Text18, { style: [styles6.submitBtnText, !canSubmit && styles6.submitBtnTextDisabled] }, isSubmitting ? "Saving..." : "Save Finding")
|
|
18989
19083
|
));
|
|
18990
19084
|
}
|
|
18991
19085
|
function createStyles15() {
|
|
@@ -19097,9 +19191,278 @@ function createStyles15() {
|
|
|
19097
19191
|
});
|
|
19098
19192
|
}
|
|
19099
19193
|
|
|
19100
|
-
// src/
|
|
19194
|
+
// src/widget/MiniTestRunner.tsx
|
|
19195
|
+
import React21, { useState as useState18, useEffect as useEffect12, useCallback as useCallback6, useRef as useRef7 } from "react";
|
|
19196
|
+
import { View as View21, Text as Text19, TouchableOpacity as TouchableOpacity18, StyleSheet as StyleSheet21, Animated as Animated3, PanResponder, Dimensions as Dimensions2 } from "react-native";
|
|
19101
19197
|
var screenWidth = Dimensions2.get("window").width;
|
|
19102
19198
|
var screenHeight = Dimensions2.get("window").height;
|
|
19199
|
+
var RUNNER_WIDTH = 280;
|
|
19200
|
+
function MiniTestRunner({ assignmentId, onExpand, onComplete, onAdvance, onNavigateToReport }) {
|
|
19201
|
+
const { client, assignments, refreshAssignments } = useBugBear();
|
|
19202
|
+
const assignment = assignments.find((a) => a.id === assignmentId);
|
|
19203
|
+
const [currentStepIndex, setCurrentStepIndex] = useState18(0);
|
|
19204
|
+
const [isSubmitting, setIsSubmitting] = useState18(false);
|
|
19205
|
+
const [elapsedTime, setElapsedTime] = useState18(0);
|
|
19206
|
+
const mountAnim = useRef7(new Animated3.Value(0)).current;
|
|
19207
|
+
useEffect12(() => {
|
|
19208
|
+
Animated3.spring(mountAnim, { toValue: 1, useNativeDriver: true, tension: 80, friction: 10 }).start();
|
|
19209
|
+
}, []);
|
|
19210
|
+
useEffect12(() => {
|
|
19211
|
+
setCurrentStepIndex(0);
|
|
19212
|
+
}, [assignmentId]);
|
|
19213
|
+
const pan = useRef7(new Animated3.ValueXY({
|
|
19214
|
+
x: screenWidth - RUNNER_WIDTH - 16,
|
|
19215
|
+
y: screenHeight - 220
|
|
19216
|
+
})).current;
|
|
19217
|
+
const panResponder = useRef7(
|
|
19218
|
+
PanResponder.create({
|
|
19219
|
+
onStartShouldSetPanResponder: () => true,
|
|
19220
|
+
onMoveShouldSetPanResponder: (_, gs) => Math.abs(gs.dx) > 5 || Math.abs(gs.dy) > 5,
|
|
19221
|
+
onPanResponderGrant: () => {
|
|
19222
|
+
pan.setOffset({
|
|
19223
|
+
x: getAnimatedValue(pan.x),
|
|
19224
|
+
y: getAnimatedValue(pan.y)
|
|
19225
|
+
});
|
|
19226
|
+
pan.setValue({ x: 0, y: 0 });
|
|
19227
|
+
},
|
|
19228
|
+
onPanResponderMove: Animated3.event(
|
|
19229
|
+
[null, { dx: pan.x, dy: pan.y }],
|
|
19230
|
+
{ useNativeDriver: false }
|
|
19231
|
+
),
|
|
19232
|
+
onPanResponderRelease: () => {
|
|
19233
|
+
pan.flattenOffset();
|
|
19234
|
+
const currentX = getAnimatedValue(pan.x);
|
|
19235
|
+
const currentY = getAnimatedValue(pan.y);
|
|
19236
|
+
const snapX = currentX < screenWidth / 2 ? 16 : screenWidth - RUNNER_WIDTH - 16;
|
|
19237
|
+
const snapY = Math.max(80, Math.min(currentY, screenHeight - 200));
|
|
19238
|
+
Animated3.spring(pan, {
|
|
19239
|
+
toValue: { x: snapX, y: snapY },
|
|
19240
|
+
useNativeDriver: false,
|
|
19241
|
+
friction: 7,
|
|
19242
|
+
tension: 40
|
|
19243
|
+
}).start();
|
|
19244
|
+
}
|
|
19245
|
+
})
|
|
19246
|
+
).current;
|
|
19247
|
+
useEffect12(() => {
|
|
19248
|
+
if (!assignment?.startedAt) return;
|
|
19249
|
+
const startTime = new Date(assignment.startedAt).getTime();
|
|
19250
|
+
setElapsedTime(Math.floor((Date.now() - startTime) / 1e3));
|
|
19251
|
+
const interval = setInterval(() => {
|
|
19252
|
+
setElapsedTime(Math.floor((Date.now() - startTime) / 1e3));
|
|
19253
|
+
}, 1e3);
|
|
19254
|
+
return () => clearInterval(interval);
|
|
19255
|
+
}, [assignment?.startedAt]);
|
|
19256
|
+
const handlePass = useCallback6(async () => {
|
|
19257
|
+
if (!client || !assignment || isSubmitting) return;
|
|
19258
|
+
setIsSubmitting(true);
|
|
19259
|
+
try {
|
|
19260
|
+
const passedId = assignment.id;
|
|
19261
|
+
await client.passAssignment(passedId);
|
|
19262
|
+
client.submitTestFeedback({
|
|
19263
|
+
testCaseId: assignment.testCase.id,
|
|
19264
|
+
assignmentId: passedId,
|
|
19265
|
+
feedback: { rating: 5 }
|
|
19266
|
+
}).catch(() => {
|
|
19267
|
+
});
|
|
19268
|
+
await refreshAssignments();
|
|
19269
|
+
const remaining = assignments.filter(
|
|
19270
|
+
(a) => (a.status === "pending" || a.status === "in_progress") && a.id !== passedId
|
|
19271
|
+
);
|
|
19272
|
+
if (remaining.length > 0) {
|
|
19273
|
+
onAdvance(remaining[0].id);
|
|
19274
|
+
} else {
|
|
19275
|
+
onComplete();
|
|
19276
|
+
}
|
|
19277
|
+
} finally {
|
|
19278
|
+
setIsSubmitting(false);
|
|
19279
|
+
}
|
|
19280
|
+
}, [client, assignment, isSubmitting, refreshAssignments, assignments, onAdvance, onComplete]);
|
|
19281
|
+
const handleFail = useCallback6(async () => {
|
|
19282
|
+
if (!client || !assignment || isSubmitting) return;
|
|
19283
|
+
setIsSubmitting(true);
|
|
19284
|
+
try {
|
|
19285
|
+
await client.failAssignment(assignment.id);
|
|
19286
|
+
await refreshAssignments();
|
|
19287
|
+
onNavigateToReport(assignment.id, assignment.testCase.id);
|
|
19288
|
+
} finally {
|
|
19289
|
+
setIsSubmitting(false);
|
|
19290
|
+
}
|
|
19291
|
+
}, [client, assignment, isSubmitting, refreshAssignments, onNavigateToReport]);
|
|
19292
|
+
if (!assignment) return null;
|
|
19293
|
+
const testCase = assignment.testCase;
|
|
19294
|
+
const steps = testCase.steps;
|
|
19295
|
+
const totalSteps = steps.length;
|
|
19296
|
+
const currentStep = steps[currentStepIndex];
|
|
19297
|
+
return /* @__PURE__ */ React21.createElement(
|
|
19298
|
+
Animated3.View,
|
|
19299
|
+
{
|
|
19300
|
+
style: [
|
|
19301
|
+
styles4.container,
|
|
19302
|
+
{ transform: pan.getTranslateTransform() },
|
|
19303
|
+
{ opacity: mountAnim, transform: [...pan.getTranslateTransform(), { scale: mountAnim.interpolate({ inputRange: [0, 1], outputRange: [0.8, 1] }) }] }
|
|
19304
|
+
],
|
|
19305
|
+
...panResponder.panHandlers
|
|
19306
|
+
},
|
|
19307
|
+
/* @__PURE__ */ React21.createElement(View21, { style: styles4.header }, /* @__PURE__ */ React21.createElement(View21, { style: styles4.headerLeft }, /* @__PURE__ */ React21.createElement(Text19, { style: styles4.stepCounter }, "Step ", currentStepIndex + 1, " of ", totalSteps), elapsedTime > 0 && /* @__PURE__ */ React21.createElement(Text19, { style: styles4.timer }, formatElapsedTime(elapsedTime))), /* @__PURE__ */ React21.createElement(TouchableOpacity18, { onPress: onExpand, style: styles4.expandButton }, /* @__PURE__ */ React21.createElement(Text19, { style: styles4.expandText }, "\u2197 Expand"))),
|
|
19308
|
+
/* @__PURE__ */ React21.createElement(View21, { style: styles4.stepContent }, /* @__PURE__ */ React21.createElement(Text19, { style: styles4.stepAction, numberOfLines: 3 }, currentStep?.action || testCase.title), currentStep?.expectedResult && /* @__PURE__ */ React21.createElement(Text19, { style: styles4.stepExpected, numberOfLines: 1 }, "\u2192 ", currentStep.expectedResult)),
|
|
19309
|
+
totalSteps > 1 && /* @__PURE__ */ React21.createElement(View21, { style: styles4.stepNav }, /* @__PURE__ */ React21.createElement(
|
|
19310
|
+
TouchableOpacity18,
|
|
19311
|
+
{
|
|
19312
|
+
disabled: currentStepIndex === 0,
|
|
19313
|
+
onPress: () => setCurrentStepIndex((i) => i - 1)
|
|
19314
|
+
},
|
|
19315
|
+
/* @__PURE__ */ React21.createElement(Text19, { style: [styles4.stepNavText, currentStepIndex === 0 && styles4.stepNavDisabled] }, "\u25C0 Prev")
|
|
19316
|
+
), /* @__PURE__ */ React21.createElement(
|
|
19317
|
+
TouchableOpacity18,
|
|
19318
|
+
{
|
|
19319
|
+
disabled: currentStepIndex >= totalSteps - 1,
|
|
19320
|
+
onPress: () => setCurrentStepIndex((i) => i + 1)
|
|
19321
|
+
},
|
|
19322
|
+
/* @__PURE__ */ React21.createElement(Text19, { style: [styles4.stepNavText, currentStepIndex >= totalSteps - 1 && styles4.stepNavDisabled] }, "Next \u25B6")
|
|
19323
|
+
)),
|
|
19324
|
+
/* @__PURE__ */ React21.createElement(View21, { style: styles4.actions }, /* @__PURE__ */ React21.createElement(
|
|
19325
|
+
TouchableOpacity18,
|
|
19326
|
+
{
|
|
19327
|
+
style: [styles4.failBtn, isSubmitting && { opacity: 0.5 }],
|
|
19328
|
+
onPress: handleFail,
|
|
19329
|
+
disabled: isSubmitting
|
|
19330
|
+
},
|
|
19331
|
+
/* @__PURE__ */ React21.createElement(Text19, { style: styles4.failText }, "Fail")
|
|
19332
|
+
), /* @__PURE__ */ React21.createElement(
|
|
19333
|
+
TouchableOpacity18,
|
|
19334
|
+
{
|
|
19335
|
+
style: [styles4.passBtn, isSubmitting && { opacity: 0.5 }],
|
|
19336
|
+
onPress: handlePass,
|
|
19337
|
+
disabled: isSubmitting
|
|
19338
|
+
},
|
|
19339
|
+
/* @__PURE__ */ React21.createElement(Text19, { style: styles4.passText }, isSubmitting ? "Passing..." : "\u2713 Pass")
|
|
19340
|
+
))
|
|
19341
|
+
);
|
|
19342
|
+
}
|
|
19343
|
+
var styles4 = StyleSheet21.create({
|
|
19344
|
+
container: {
|
|
19345
|
+
position: "absolute",
|
|
19346
|
+
width: RUNNER_WIDTH,
|
|
19347
|
+
zIndex: 9999,
|
|
19348
|
+
backgroundColor: colors.bg,
|
|
19349
|
+
borderRadius: 12,
|
|
19350
|
+
borderWidth: 1,
|
|
19351
|
+
borderColor: colors.border,
|
|
19352
|
+
shadowColor: "#000",
|
|
19353
|
+
shadowOffset: { width: 0, height: 8 },
|
|
19354
|
+
shadowOpacity: 0.4,
|
|
19355
|
+
shadowRadius: 16,
|
|
19356
|
+
elevation: 20,
|
|
19357
|
+
overflow: "hidden"
|
|
19358
|
+
},
|
|
19359
|
+
header: {
|
|
19360
|
+
backgroundColor: colors.bgDarker,
|
|
19361
|
+
paddingVertical: 6,
|
|
19362
|
+
paddingHorizontal: 12,
|
|
19363
|
+
flexDirection: "row",
|
|
19364
|
+
alignItems: "center",
|
|
19365
|
+
justifyContent: "space-between",
|
|
19366
|
+
borderBottomWidth: 1,
|
|
19367
|
+
borderBottomColor: colors.border
|
|
19368
|
+
},
|
|
19369
|
+
headerLeft: {
|
|
19370
|
+
flexDirection: "row",
|
|
19371
|
+
alignItems: "center",
|
|
19372
|
+
gap: 6
|
|
19373
|
+
},
|
|
19374
|
+
stepCounter: {
|
|
19375
|
+
fontSize: 11,
|
|
19376
|
+
color: colors.textMuted
|
|
19377
|
+
},
|
|
19378
|
+
timer: {
|
|
19379
|
+
fontSize: 10,
|
|
19380
|
+
color: colors.green,
|
|
19381
|
+
fontWeight: "600",
|
|
19382
|
+
fontVariant: ["tabular-nums"]
|
|
19383
|
+
},
|
|
19384
|
+
expandButton: {
|
|
19385
|
+
paddingVertical: 2,
|
|
19386
|
+
paddingHorizontal: 4
|
|
19387
|
+
},
|
|
19388
|
+
expandText: {
|
|
19389
|
+
fontSize: 12,
|
|
19390
|
+
color: colors.blue,
|
|
19391
|
+
fontWeight: "500"
|
|
19392
|
+
},
|
|
19393
|
+
stepContent: {
|
|
19394
|
+
paddingVertical: 8,
|
|
19395
|
+
paddingHorizontal: 12
|
|
19396
|
+
},
|
|
19397
|
+
stepAction: {
|
|
19398
|
+
fontSize: 13,
|
|
19399
|
+
color: colors.textPrimary,
|
|
19400
|
+
lineHeight: 18
|
|
19401
|
+
},
|
|
19402
|
+
stepExpected: {
|
|
19403
|
+
fontSize: 11,
|
|
19404
|
+
color: colors.textMuted,
|
|
19405
|
+
fontStyle: "italic",
|
|
19406
|
+
marginTop: 2
|
|
19407
|
+
},
|
|
19408
|
+
stepNav: {
|
|
19409
|
+
flexDirection: "row",
|
|
19410
|
+
justifyContent: "center",
|
|
19411
|
+
gap: 16,
|
|
19412
|
+
paddingBottom: 6,
|
|
19413
|
+
paddingHorizontal: 12
|
|
19414
|
+
},
|
|
19415
|
+
stepNavText: {
|
|
19416
|
+
fontSize: 12,
|
|
19417
|
+
color: colors.blue,
|
|
19418
|
+
paddingVertical: 2,
|
|
19419
|
+
paddingHorizontal: 6
|
|
19420
|
+
},
|
|
19421
|
+
stepNavDisabled: {
|
|
19422
|
+
color: colors.textDim
|
|
19423
|
+
},
|
|
19424
|
+
actions: {
|
|
19425
|
+
flexDirection: "row",
|
|
19426
|
+
gap: 6,
|
|
19427
|
+
paddingVertical: 6,
|
|
19428
|
+
paddingHorizontal: 10,
|
|
19429
|
+
paddingBottom: 10,
|
|
19430
|
+
borderTopWidth: 1,
|
|
19431
|
+
borderTopColor: colors.border
|
|
19432
|
+
},
|
|
19433
|
+
failBtn: {
|
|
19434
|
+
flex: 1,
|
|
19435
|
+
paddingVertical: 8,
|
|
19436
|
+
borderRadius: 8,
|
|
19437
|
+
backgroundColor: colors.redDark,
|
|
19438
|
+
borderWidth: 1,
|
|
19439
|
+
borderColor: colors.red,
|
|
19440
|
+
alignItems: "center"
|
|
19441
|
+
},
|
|
19442
|
+
failText: {
|
|
19443
|
+
fontSize: 12,
|
|
19444
|
+
fontWeight: "600",
|
|
19445
|
+
color: colors.redLight
|
|
19446
|
+
},
|
|
19447
|
+
passBtn: {
|
|
19448
|
+
flex: 2,
|
|
19449
|
+
paddingVertical: 8,
|
|
19450
|
+
borderRadius: 8,
|
|
19451
|
+
backgroundColor: colors.greenDark,
|
|
19452
|
+
borderWidth: 1,
|
|
19453
|
+
borderColor: colors.green,
|
|
19454
|
+
alignItems: "center"
|
|
19455
|
+
},
|
|
19456
|
+
passText: {
|
|
19457
|
+
fontSize: 12,
|
|
19458
|
+
fontWeight: "600",
|
|
19459
|
+
color: colors.greenLight
|
|
19460
|
+
}
|
|
19461
|
+
});
|
|
19462
|
+
|
|
19463
|
+
// src/BugBearButton.tsx
|
|
19464
|
+
var screenWidth2 = Dimensions3.get("window").width;
|
|
19465
|
+
var screenHeight2 = Dimensions3.get("window").height;
|
|
19103
19466
|
function BugBearButton({
|
|
19104
19467
|
position = "bottom-right",
|
|
19105
19468
|
buttonStyle,
|
|
@@ -19111,16 +19474,18 @@ function BugBearButton({
|
|
|
19111
19474
|
}) {
|
|
19112
19475
|
const { shouldShowWidget, testerInfo, isLoading, unreadCount, assignments, widgetMode, widgetColorScheme } = useBugBear();
|
|
19113
19476
|
const { currentScreen, canGoBack, push, pop, replace, reset } = useNavigation();
|
|
19114
|
-
const [
|
|
19115
|
-
const
|
|
19116
|
-
const
|
|
19117
|
-
const
|
|
19477
|
+
const [viewMode, setViewMode] = useState19("closed");
|
|
19478
|
+
const [miniRunnerAssignmentId, setMiniRunnerAssignmentId] = useState19(null);
|
|
19479
|
+
const panelAnim = useRef8(new Animated4.Value(0)).current;
|
|
19480
|
+
const styles6 = useMemo16(() => createStyles16(), [widgetColorScheme]);
|
|
19481
|
+
const panelVisible = viewMode === "panel";
|
|
19482
|
+
const screenCaptureRef = useRef8(null);
|
|
19118
19483
|
const openPanel = () => {
|
|
19119
19484
|
captureAppScreen().then((uri) => {
|
|
19120
19485
|
screenCaptureRef.current = uri;
|
|
19121
19486
|
});
|
|
19122
|
-
|
|
19123
|
-
|
|
19487
|
+
setViewMode("panel");
|
|
19488
|
+
Animated4.spring(panelAnim, {
|
|
19124
19489
|
toValue: 1,
|
|
19125
19490
|
useNativeDriver: true,
|
|
19126
19491
|
friction: 8,
|
|
@@ -19129,12 +19494,12 @@ function BugBearButton({
|
|
|
19129
19494
|
};
|
|
19130
19495
|
const closePanel = () => {
|
|
19131
19496
|
Keyboard4.dismiss();
|
|
19132
|
-
|
|
19497
|
+
Animated4.timing(panelAnim, {
|
|
19133
19498
|
toValue: 0,
|
|
19134
19499
|
duration: 250,
|
|
19135
19500
|
useNativeDriver: true
|
|
19136
19501
|
}).start(() => {
|
|
19137
|
-
|
|
19502
|
+
setViewMode("closed");
|
|
19138
19503
|
});
|
|
19139
19504
|
};
|
|
19140
19505
|
const getInitialPosition = () => {
|
|
@@ -19143,22 +19508,22 @@ function BugBearButton({
|
|
|
19143
19508
|
if (initialX !== void 0 && initialY !== void 0) {
|
|
19144
19509
|
return { x: initialX, y: initialY };
|
|
19145
19510
|
}
|
|
19146
|
-
const x = position === "bottom-right" ?
|
|
19147
|
-
const y =
|
|
19511
|
+
const x = position === "bottom-right" ? screenWidth2 - buttonSize - margin : margin;
|
|
19512
|
+
const y = screenHeight2 - 160;
|
|
19148
19513
|
return { x, y };
|
|
19149
19514
|
};
|
|
19150
19515
|
const initialPos = getInitialPosition();
|
|
19151
|
-
const pan =
|
|
19152
|
-
const isDragging =
|
|
19153
|
-
const panResponder =
|
|
19154
|
-
|
|
19516
|
+
const pan = useRef8(new Animated4.ValueXY(initialPos)).current;
|
|
19517
|
+
const isDragging = useRef8(false);
|
|
19518
|
+
const panResponder = useRef8(
|
|
19519
|
+
PanResponder2.create({
|
|
19155
19520
|
onStartShouldSetPanResponder: () => draggable,
|
|
19156
19521
|
onMoveShouldSetPanResponder: (_, gs) => draggable && (Math.abs(gs.dx) > 5 || Math.abs(gs.dy) > 5),
|
|
19157
19522
|
onPanResponderGrant: () => {
|
|
19158
19523
|
isDragging.current = false;
|
|
19159
19524
|
pan.setOffset({
|
|
19160
|
-
x: pan.x
|
|
19161
|
-
y: pan.y
|
|
19525
|
+
x: getAnimatedValue(pan.x),
|
|
19526
|
+
y: getAnimatedValue(pan.y)
|
|
19162
19527
|
});
|
|
19163
19528
|
pan.setValue({ x: 0, y: 0 });
|
|
19164
19529
|
},
|
|
@@ -19166,20 +19531,20 @@ function BugBearButton({
|
|
|
19166
19531
|
if (Math.abs(gs.dx) > 5 || Math.abs(gs.dy) > 5) {
|
|
19167
19532
|
isDragging.current = true;
|
|
19168
19533
|
}
|
|
19169
|
-
|
|
19534
|
+
Animated4.event(
|
|
19170
19535
|
[null, { dx: pan.x, dy: pan.y }],
|
|
19171
19536
|
{ useNativeDriver: false }
|
|
19172
19537
|
)(_, gs);
|
|
19173
19538
|
},
|
|
19174
19539
|
onPanResponderRelease: (_, gs) => {
|
|
19175
19540
|
pan.flattenOffset();
|
|
19176
|
-
const currentX = pan.x
|
|
19177
|
-
const currentY = pan.y
|
|
19541
|
+
const currentX = getAnimatedValue(pan.x);
|
|
19542
|
+
const currentY = getAnimatedValue(pan.y);
|
|
19178
19543
|
const buttonSize = 56;
|
|
19179
19544
|
const margin = 16;
|
|
19180
|
-
const snapX = currentX <
|
|
19181
|
-
const snapY = Math.max(minY, Math.min(currentY,
|
|
19182
|
-
|
|
19545
|
+
const snapX = currentX < screenWidth2 / 2 ? margin : screenWidth2 - buttonSize - margin;
|
|
19546
|
+
const snapY = Math.max(minY, Math.min(currentY, screenHeight2 - maxYOffset));
|
|
19547
|
+
Animated4.spring(pan, {
|
|
19183
19548
|
toValue: { x: snapX, y: snapY },
|
|
19184
19549
|
useNativeDriver: false,
|
|
19185
19550
|
friction: 7,
|
|
@@ -19194,7 +19559,7 @@ function BugBearButton({
|
|
|
19194
19559
|
).current;
|
|
19195
19560
|
const pendingTests = widgetMode === "qa" ? assignments.filter((a) => a.status === "pending" || a.status === "in_progress").length : 0;
|
|
19196
19561
|
const badgeCount = pendingTests + unreadCount;
|
|
19197
|
-
|
|
19562
|
+
useEffect13(() => {
|
|
19198
19563
|
if (!panelVisible || Platform5.OS !== "android") return;
|
|
19199
19564
|
const handler = BackHandler.addEventListener("hardwareBackPress", () => {
|
|
19200
19565
|
if (canGoBack) {
|
|
@@ -19207,6 +19572,51 @@ function BugBearButton({
|
|
|
19207
19572
|
});
|
|
19208
19573
|
return () => handler.remove();
|
|
19209
19574
|
}, [panelVisible, canGoBack]);
|
|
19575
|
+
const startMiniRunner = useCallback7((assignId) => {
|
|
19576
|
+
Keyboard4.dismiss();
|
|
19577
|
+
Animated4.timing(panelAnim, {
|
|
19578
|
+
toValue: 0,
|
|
19579
|
+
duration: 200,
|
|
19580
|
+
useNativeDriver: true
|
|
19581
|
+
}).start(() => {
|
|
19582
|
+
setMiniRunnerAssignmentId(assignId);
|
|
19583
|
+
setViewMode("mini-runner");
|
|
19584
|
+
});
|
|
19585
|
+
}, [panelAnim]);
|
|
19586
|
+
const expandFromMiniRunner = useCallback7(() => {
|
|
19587
|
+
setViewMode("panel");
|
|
19588
|
+
if (miniRunnerAssignmentId) {
|
|
19589
|
+
replace({ name: "TEST_DETAIL", testId: miniRunnerAssignmentId });
|
|
19590
|
+
}
|
|
19591
|
+
setMiniRunnerAssignmentId(null);
|
|
19592
|
+
Animated4.spring(panelAnim, {
|
|
19593
|
+
toValue: 1,
|
|
19594
|
+
useNativeDriver: true,
|
|
19595
|
+
friction: 8,
|
|
19596
|
+
tension: 65
|
|
19597
|
+
}).start();
|
|
19598
|
+
}, [miniRunnerAssignmentId, replace, panelAnim]);
|
|
19599
|
+
const handleMiniRunnerAdvance = useCallback7((nextId) => {
|
|
19600
|
+
setMiniRunnerAssignmentId(nextId);
|
|
19601
|
+
}, []);
|
|
19602
|
+
const handleMiniRunnerComplete = useCallback7(() => {
|
|
19603
|
+
setMiniRunnerAssignmentId(null);
|
|
19604
|
+
setViewMode("closed");
|
|
19605
|
+
}, []);
|
|
19606
|
+
const handleMiniRunnerReport = useCallback7((assignId, testCaseId) => {
|
|
19607
|
+
setMiniRunnerAssignmentId(null);
|
|
19608
|
+
setViewMode("panel");
|
|
19609
|
+
replace({
|
|
19610
|
+
name: "REPORT",
|
|
19611
|
+
prefill: { type: "test_fail", assignmentId: assignId, testCaseId }
|
|
19612
|
+
});
|
|
19613
|
+
Animated4.spring(panelAnim, {
|
|
19614
|
+
toValue: 1,
|
|
19615
|
+
useNativeDriver: true,
|
|
19616
|
+
friction: 8,
|
|
19617
|
+
tension: 65
|
|
19618
|
+
}).start();
|
|
19619
|
+
}, [replace, panelAnim]);
|
|
19210
19620
|
if (!shouldShowWidget) return null;
|
|
19211
19621
|
const getHeaderTitle = () => {
|
|
19212
19622
|
switch (currentScreen.name) {
|
|
@@ -19265,24 +19675,25 @@ function BugBearButton({
|
|
|
19265
19675
|
reset();
|
|
19266
19676
|
},
|
|
19267
19677
|
canGoBack,
|
|
19268
|
-
closeWidget: handleClose
|
|
19678
|
+
closeWidget: handleClose,
|
|
19679
|
+
startMiniRunner
|
|
19269
19680
|
};
|
|
19270
19681
|
const QA_ONLY_SCREENS = ["TEST_DETAIL", "TEST_LIST", "TEST_FEEDBACK", "SESSION_START", "SESSION_ACTIVE", "SESSION_FINDING"];
|
|
19271
19682
|
const renderScreen = () => {
|
|
19272
19683
|
if (widgetMode === "feedback" && QA_ONLY_SCREENS.includes(currentScreen.name)) {
|
|
19273
|
-
return /* @__PURE__ */
|
|
19684
|
+
return /* @__PURE__ */ React22.createElement(HomeScreen, { nav });
|
|
19274
19685
|
}
|
|
19275
19686
|
switch (currentScreen.name) {
|
|
19276
19687
|
case "HOME":
|
|
19277
|
-
return /* @__PURE__ */
|
|
19688
|
+
return /* @__PURE__ */ React22.createElement(HomeScreen, { nav });
|
|
19278
19689
|
case "TEST_DETAIL":
|
|
19279
|
-
return /* @__PURE__ */
|
|
19690
|
+
return /* @__PURE__ */ React22.createElement(TestDetailScreen, { testId: currentScreen.testId, nav });
|
|
19280
19691
|
case "TEST_LIST":
|
|
19281
|
-
return /* @__PURE__ */
|
|
19692
|
+
return /* @__PURE__ */ React22.createElement(TestListScreen, { nav });
|
|
19282
19693
|
case "TEST_FEEDBACK":
|
|
19283
|
-
return /* @__PURE__ */
|
|
19694
|
+
return /* @__PURE__ */ React22.createElement(TestFeedbackScreen, { status: currentScreen.status, assignmentId: currentScreen.assignmentId, nav });
|
|
19284
19695
|
case "REPORT":
|
|
19285
|
-
return /* @__PURE__ */
|
|
19696
|
+
return /* @__PURE__ */ React22.createElement(
|
|
19286
19697
|
ReportScreen,
|
|
19287
19698
|
{
|
|
19288
19699
|
nav,
|
|
@@ -19294,84 +19705,93 @@ function BugBearButton({
|
|
|
19294
19705
|
}
|
|
19295
19706
|
);
|
|
19296
19707
|
case "REPORT_SUCCESS":
|
|
19297
|
-
return /* @__PURE__ */
|
|
19708
|
+
return /* @__PURE__ */ React22.createElement(ReportSuccessScreen, { nav });
|
|
19298
19709
|
case "MESSAGE_LIST":
|
|
19299
|
-
return /* @__PURE__ */
|
|
19710
|
+
return /* @__PURE__ */ React22.createElement(MessageListScreen, { nav });
|
|
19300
19711
|
case "THREAD_DETAIL":
|
|
19301
|
-
return /* @__PURE__ */
|
|
19712
|
+
return /* @__PURE__ */ React22.createElement(ThreadDetailScreen, { thread: currentScreen.thread, nav });
|
|
19302
19713
|
case "COMPOSE_MESSAGE":
|
|
19303
|
-
return /* @__PURE__ */
|
|
19714
|
+
return /* @__PURE__ */ React22.createElement(ComposeMessageScreen, { nav });
|
|
19304
19715
|
case "ISSUE_LIST":
|
|
19305
|
-
return /* @__PURE__ */
|
|
19716
|
+
return /* @__PURE__ */ React22.createElement(IssueListScreen, { nav, category: currentScreen.category });
|
|
19306
19717
|
case "ISSUE_DETAIL":
|
|
19307
|
-
return /* @__PURE__ */
|
|
19718
|
+
return /* @__PURE__ */ React22.createElement(IssueDetailScreen, { nav, issue: currentScreen.issue });
|
|
19308
19719
|
case "PROFILE":
|
|
19309
|
-
return /* @__PURE__ */
|
|
19720
|
+
return /* @__PURE__ */ React22.createElement(ProfileScreen, { nav });
|
|
19310
19721
|
case "SESSION_START":
|
|
19311
|
-
return /* @__PURE__ */
|
|
19722
|
+
return /* @__PURE__ */ React22.createElement(SessionStartScreen, { nav });
|
|
19312
19723
|
case "SESSION_ACTIVE":
|
|
19313
|
-
return /* @__PURE__ */
|
|
19724
|
+
return /* @__PURE__ */ React22.createElement(SessionActiveScreen, { nav });
|
|
19314
19725
|
case "SESSION_FINDING":
|
|
19315
|
-
return /* @__PURE__ */
|
|
19726
|
+
return /* @__PURE__ */ React22.createElement(SessionFindingScreen, { nav });
|
|
19316
19727
|
default:
|
|
19317
|
-
return /* @__PURE__ */
|
|
19728
|
+
return /* @__PURE__ */ React22.createElement(HomeScreen, { nav });
|
|
19318
19729
|
}
|
|
19319
19730
|
};
|
|
19320
|
-
return /* @__PURE__ */
|
|
19321
|
-
|
|
19731
|
+
return /* @__PURE__ */ React22.createElement(React22.Fragment, null, viewMode === "mini-runner" && miniRunnerAssignmentId && /* @__PURE__ */ React22.createElement(
|
|
19732
|
+
MiniTestRunner,
|
|
19322
19733
|
{
|
|
19323
|
-
|
|
19734
|
+
assignmentId: miniRunnerAssignmentId,
|
|
19735
|
+
onExpand: expandFromMiniRunner,
|
|
19736
|
+
onAdvance: handleMiniRunnerAdvance,
|
|
19737
|
+
onComplete: handleMiniRunnerComplete,
|
|
19738
|
+
onNavigateToReport: handleMiniRunnerReport
|
|
19739
|
+
}
|
|
19740
|
+
), viewMode === "closed" && /* @__PURE__ */ React22.createElement(
|
|
19741
|
+
Animated4.View,
|
|
19742
|
+
{
|
|
19743
|
+
style: [styles6.fabContainer, { transform: pan.getTranslateTransform() }, buttonStyle],
|
|
19324
19744
|
...panResponder.panHandlers
|
|
19325
19745
|
},
|
|
19326
|
-
/* @__PURE__ */
|
|
19327
|
-
|
|
19746
|
+
/* @__PURE__ */ React22.createElement(
|
|
19747
|
+
TouchableOpacity19,
|
|
19328
19748
|
{
|
|
19329
|
-
style:
|
|
19749
|
+
style: styles6.fab,
|
|
19330
19750
|
onPress: openPanel,
|
|
19331
19751
|
activeOpacity: draggable ? 1 : 0.7
|
|
19332
19752
|
},
|
|
19333
|
-
/* @__PURE__ */
|
|
19334
|
-
badgeCount > 0 && /* @__PURE__ */
|
|
19753
|
+
/* @__PURE__ */ React22.createElement(Image4, { source: { uri: BUGBEAR_LOGO_BASE64 }, style: styles6.fabIcon }),
|
|
19754
|
+
badgeCount > 0 && /* @__PURE__ */ React22.createElement(View22, { style: styles6.badge }, /* @__PURE__ */ React22.createElement(Text20, { style: styles6.badgeText }, badgeCount > 9 ? "9+" : badgeCount))
|
|
19335
19755
|
)
|
|
19336
|
-
),
|
|
19756
|
+
), viewMode === "panel" && /* @__PURE__ */ React22.createElement(View22, { style: styles6.panelWrapper, pointerEvents: "box-none" }, /* @__PURE__ */ React22.createElement(
|
|
19337
19757
|
KeyboardAvoidingView,
|
|
19338
19758
|
{
|
|
19339
19759
|
behavior: Platform5.OS === "ios" ? "padding" : "height",
|
|
19340
|
-
style:
|
|
19760
|
+
style: styles6.panelKeyboardAvoid,
|
|
19341
19761
|
pointerEvents: "box-none"
|
|
19342
19762
|
},
|
|
19343
|
-
/* @__PURE__ */
|
|
19344
|
-
|
|
19763
|
+
/* @__PURE__ */ React22.createElement(
|
|
19764
|
+
Animated4.View,
|
|
19345
19765
|
{
|
|
19346
19766
|
style: [
|
|
19347
|
-
|
|
19767
|
+
styles6.panelContainer,
|
|
19348
19768
|
{
|
|
19349
19769
|
transform: [{
|
|
19350
19770
|
translateY: panelAnim.interpolate({
|
|
19351
19771
|
inputRange: [0, 1],
|
|
19352
|
-
outputRange: [
|
|
19772
|
+
outputRange: [screenHeight2, 0]
|
|
19353
19773
|
})
|
|
19354
19774
|
}]
|
|
19355
19775
|
}
|
|
19356
19776
|
]
|
|
19357
19777
|
},
|
|
19358
|
-
/* @__PURE__ */
|
|
19359
|
-
/* @__PURE__ */
|
|
19360
|
-
/* @__PURE__ */
|
|
19778
|
+
/* @__PURE__ */ React22.createElement(View22, { style: styles6.panelHandle }, /* @__PURE__ */ React22.createElement(View22, { style: styles6.panelHandleBar })),
|
|
19779
|
+
/* @__PURE__ */ React22.createElement(View22, { style: styles6.header }, /* @__PURE__ */ React22.createElement(View22, { style: styles6.headerLeft }, canGoBack ? /* @__PURE__ */ React22.createElement(TouchableOpacity19, { onPress: () => nav.pop(), style: styles6.backButton }, /* @__PURE__ */ React22.createElement(Text20, { style: styles6.backText }, "\u2190 Back")) : /* @__PURE__ */ React22.createElement(View22, { style: styles6.headerTitleRow }, /* @__PURE__ */ React22.createElement(Text20, { style: styles6.headerTitle }, "BugBear"), testerInfo && /* @__PURE__ */ React22.createElement(TouchableOpacity19, { onPress: () => push({ name: "PROFILE" }) }, /* @__PURE__ */ React22.createElement(Text20, { style: styles6.headerName }, testerInfo.name, " \u270E")))), getHeaderTitle() ? /* @__PURE__ */ React22.createElement(Text20, { style: styles6.headerScreenTitle, numberOfLines: 1 }, getHeaderTitle()) : null, /* @__PURE__ */ React22.createElement(View22, { style: styles6.headerActions }, currentScreen.name !== "HOME" && /* @__PURE__ */ React22.createElement(TouchableOpacity19, { onPress: () => nav.reset(), style: styles6.homeButton }, /* @__PURE__ */ React22.createElement(Text20, { style: styles6.homeIcon }, "\u2302")), /* @__PURE__ */ React22.createElement(TouchableOpacity19, { onPress: handleClose, style: styles6.closeButton }, /* @__PURE__ */ React22.createElement(Text20, { style: styles6.closeText }, "\u2715")))),
|
|
19780
|
+
/* @__PURE__ */ React22.createElement(
|
|
19361
19781
|
ScrollView4,
|
|
19362
19782
|
{
|
|
19363
|
-
style:
|
|
19364
|
-
contentContainerStyle:
|
|
19783
|
+
style: styles6.content,
|
|
19784
|
+
contentContainerStyle: styles6.contentContainer,
|
|
19365
19785
|
keyboardShouldPersistTaps: "handled",
|
|
19366
19786
|
showsVerticalScrollIndicator: false
|
|
19367
19787
|
},
|
|
19368
|
-
isLoading ? /* @__PURE__ */
|
|
19788
|
+
isLoading ? /* @__PURE__ */ React22.createElement(View22, { style: styles6.loadingContainer }, /* @__PURE__ */ React22.createElement(ActivityIndicator3, { size: "large", color: colors.blue }), /* @__PURE__ */ React22.createElement(Text20, { style: styles6.loadingText }, "Loading...")) : renderScreen()
|
|
19369
19789
|
)
|
|
19370
19790
|
)
|
|
19371
19791
|
)));
|
|
19372
19792
|
}
|
|
19373
19793
|
function createStyles16() {
|
|
19374
|
-
return
|
|
19794
|
+
return StyleSheet22.create({
|
|
19375
19795
|
// FAB
|
|
19376
19796
|
fabContainer: {
|
|
19377
19797
|
position: "absolute",
|
|
@@ -19546,8 +19966,8 @@ function createStyles16() {
|
|
|
19546
19966
|
}
|
|
19547
19967
|
|
|
19548
19968
|
// src/BugBearErrorBoundary.tsx
|
|
19549
|
-
import
|
|
19550
|
-
import { View as
|
|
19969
|
+
import React23, { Component } from "react";
|
|
19970
|
+
import { View as View23, Text as Text21, TouchableOpacity as TouchableOpacity20, StyleSheet as StyleSheet23 } from "react-native";
|
|
19551
19971
|
var BugBearErrorBoundary = class extends Component {
|
|
19552
19972
|
constructor(props) {
|
|
19553
19973
|
super(props);
|
|
@@ -19592,7 +20012,7 @@ var BugBearErrorBoundary = class extends Component {
|
|
|
19592
20012
|
if (fallback) {
|
|
19593
20013
|
return fallback;
|
|
19594
20014
|
}
|
|
19595
|
-
return /* @__PURE__ */
|
|
20015
|
+
return /* @__PURE__ */ React23.createElement(View23, { style: styles5.container }, /* @__PURE__ */ React23.createElement(Text21, { style: styles5.title }, "Something went wrong"), /* @__PURE__ */ React23.createElement(Text21, { style: styles5.message }, error.message), /* @__PURE__ */ React23.createElement(TouchableOpacity20, { style: styles5.button, onPress: this.reset }, /* @__PURE__ */ React23.createElement(Text21, { style: styles5.buttonText }, "Try Again")), /* @__PURE__ */ React23.createElement(Text21, { style: styles5.caption }, "The error has been captured by BugBear"));
|
|
19596
20016
|
}
|
|
19597
20017
|
return children;
|
|
19598
20018
|
}
|
|
@@ -19603,7 +20023,7 @@ function useErrorContext() {
|
|
|
19603
20023
|
getEnhancedContext: () => contextCapture.getEnhancedContext()
|
|
19604
20024
|
};
|
|
19605
20025
|
}
|
|
19606
|
-
var
|
|
20026
|
+
var styles5 = StyleSheet23.create({
|
|
19607
20027
|
container: {
|
|
19608
20028
|
padding: 20,
|
|
19609
20029
|
margin: 20,
|