@buoy-gg/highlight-updates 7.0.36 → 7.0.38

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.
Files changed (104) hide show
  1. package/README.md +28 -6
  2. package/lib/commonjs/highlight-updates/HighlightUpdatesOverlay.js +1 -281
  3. package/lib/commonjs/highlight-updates/components/HighlightFilterView.js +1 -1474
  4. package/lib/commonjs/highlight-updates/components/HighlightUpdatesModal.js +1 -641
  5. package/lib/commonjs/highlight-updates/components/IdentifierBadge.js +1 -273
  6. package/lib/commonjs/highlight-updates/components/IsolatedRenderList.js +1 -188
  7. package/lib/commonjs/highlight-updates/components/ModalHeaderContent.js +1 -293
  8. package/lib/commonjs/highlight-updates/components/RenderCauseBadge.js +1 -508
  9. package/lib/commonjs/highlight-updates/components/RenderDetailView.js +1 -846
  10. package/lib/commonjs/highlight-updates/components/RenderHistoryViewer.js +1 -915
  11. package/lib/commonjs/highlight-updates/components/RenderListItem.js +1 -235
  12. package/lib/commonjs/highlight-updates/components/RendersCopySettingsView.js +1 -466
  13. package/lib/commonjs/highlight-updates/components/StatsDisplay.js +1 -73
  14. package/lib/commonjs/highlight-updates/types/copySettings.js +1 -107
  15. package/lib/commonjs/highlight-updates/utils/CommitProfiler.js +1 -446
  16. package/lib/commonjs/highlight-updates/utils/HighlightUpdatesController.js +1 -1920
  17. package/lib/commonjs/highlight-updates/utils/PerformanceLogger.js +1 -359
  18. package/lib/commonjs/highlight-updates/utils/ProfilerInterceptor.js +1 -371
  19. package/lib/commonjs/highlight-updates/utils/RenderCauseDetector.js +1 -1840
  20. package/lib/commonjs/highlight-updates/utils/RenderTracker.js +1 -952
  21. package/lib/commonjs/highlight-updates/utils/ViewTypeMapper.js +1 -264
  22. package/lib/commonjs/highlight-updates/utils/copySettingsStorage.js +1 -32
  23. package/lib/commonjs/highlight-updates/utils/devtoolsComponentNames.js +1 -188
  24. package/lib/commonjs/highlight-updates/utils/namedComposite.js +1 -41
  25. package/lib/commonjs/highlight-updates/utils/ownStateChanged.js +1 -103
  26. package/lib/commonjs/highlight-updates/utils/rawEventEmitter.js +1 -50
  27. package/lib/commonjs/highlight-updates/utils/renderExportFormatter.js +1 -58
  28. package/lib/commonjs/highlight-updates/utils/rendersExportFormatter.js +1 -485
  29. package/lib/commonjs/highlight-updates/utils/screenElements.js +1 -1248
  30. package/lib/commonjs/highlight-updates/utils/tapMatch.js +1 -83
  31. package/lib/commonjs/highlight-updates/utils/testIDs.js +1 -68
  32. package/lib/commonjs/highlight-updates/utils/touchCapture.js +1 -277
  33. package/lib/commonjs/index.js +1 -429
  34. package/lib/commonjs/preset.js +1 -278
  35. package/lib/commonjs/sync/highlightUpdatesSyncAdapter.js +1 -235
  36. package/lib/module/highlight-updates/HighlightUpdatesOverlay.js +1 -274
  37. package/lib/module/highlight-updates/components/HighlightFilterView.js +1 -1468
  38. package/lib/module/highlight-updates/components/HighlightUpdatesModal.js +1 -634
  39. package/lib/module/highlight-updates/components/IdentifierBadge.js +1 -265
  40. package/lib/module/highlight-updates/components/IsolatedRenderList.js +1 -183
  41. package/lib/module/highlight-updates/components/ModalHeaderContent.js +1 -288
  42. package/lib/module/highlight-updates/components/RenderCauseBadge.js +1 -499
  43. package/lib/module/highlight-updates/components/RenderDetailView.js +1 -840
  44. package/lib/module/highlight-updates/components/RenderHistoryViewer.js +1 -908
  45. package/lib/module/highlight-updates/components/RenderListItem.js +1 -230
  46. package/lib/module/highlight-updates/components/RendersCopySettingsView.js +1 -462
  47. package/lib/module/highlight-updates/components/StatsDisplay.js +1 -70
  48. package/lib/module/highlight-updates/types/copySettings.js +1 -102
  49. package/lib/module/highlight-updates/utils/CommitProfiler.js +1 -442
  50. package/lib/module/highlight-updates/utils/HighlightUpdatesController.js +1 -1916
  51. package/lib/module/highlight-updates/utils/PerformanceLogger.js +1 -353
  52. package/lib/module/highlight-updates/utils/ProfilerInterceptor.js +1 -358
  53. package/lib/module/highlight-updates/utils/RenderCauseDetector.js +1 -1830
  54. package/lib/module/highlight-updates/utils/RenderTracker.js +1 -949
  55. package/lib/module/highlight-updates/utils/ViewTypeMapper.js +1 -255
  56. package/lib/module/highlight-updates/utils/copySettingsStorage.js +1 -26
  57. package/lib/module/highlight-updates/utils/devtoolsComponentNames.js +1 -178
  58. package/lib/module/highlight-updates/utils/namedComposite.js +1 -36
  59. package/lib/module/highlight-updates/utils/ownStateChanged.js +1 -98
  60. package/lib/module/highlight-updates/utils/rawEventEmitter.js +1 -46
  61. package/lib/module/highlight-updates/utils/renderExportFormatter.js +1 -54
  62. package/lib/module/highlight-updates/utils/rendersExportFormatter.js +1 -478
  63. package/lib/module/highlight-updates/utils/screenElements.js +1 -1242
  64. package/lib/module/highlight-updates/utils/tapMatch.js +1 -76
  65. package/lib/module/highlight-updates/utils/testIDs.js +1 -60
  66. package/lib/module/highlight-updates/utils/touchCapture.js +1 -270
  67. package/lib/module/index.js +1 -130
  68. package/lib/module/preset.js +1 -272
  69. package/lib/module/sync/highlightUpdatesSyncAdapter.js +1 -230
  70. package/package.json +8 -8
  71. package/lib/typescript/highlight-updates/HighlightUpdatesOverlay.d.ts.map +0 -1
  72. package/lib/typescript/highlight-updates/components/HighlightFilterView.d.ts.map +0 -1
  73. package/lib/typescript/highlight-updates/components/HighlightUpdatesModal.d.ts.map +0 -1
  74. package/lib/typescript/highlight-updates/components/IdentifierBadge.d.ts.map +0 -1
  75. package/lib/typescript/highlight-updates/components/IsolatedRenderList.d.ts.map +0 -1
  76. package/lib/typescript/highlight-updates/components/ModalHeaderContent.d.ts.map +0 -1
  77. package/lib/typescript/highlight-updates/components/RenderCauseBadge.d.ts.map +0 -1
  78. package/lib/typescript/highlight-updates/components/RenderDetailView.d.ts.map +0 -1
  79. package/lib/typescript/highlight-updates/components/RenderHistoryViewer.d.ts.map +0 -1
  80. package/lib/typescript/highlight-updates/components/RenderListItem.d.ts.map +0 -1
  81. package/lib/typescript/highlight-updates/components/RendersCopySettingsView.d.ts.map +0 -1
  82. package/lib/typescript/highlight-updates/components/StatsDisplay.d.ts.map +0 -1
  83. package/lib/typescript/highlight-updates/types/copySettings.d.ts.map +0 -1
  84. package/lib/typescript/highlight-updates/utils/CommitProfiler.d.ts.map +0 -1
  85. package/lib/typescript/highlight-updates/utils/HighlightUpdatesController.d.ts.map +0 -1
  86. package/lib/typescript/highlight-updates/utils/PerformanceLogger.d.ts.map +0 -1
  87. package/lib/typescript/highlight-updates/utils/ProfilerInterceptor.d.ts.map +0 -1
  88. package/lib/typescript/highlight-updates/utils/RenderCauseDetector.d.ts.map +0 -1
  89. package/lib/typescript/highlight-updates/utils/RenderTracker.d.ts.map +0 -1
  90. package/lib/typescript/highlight-updates/utils/ViewTypeMapper.d.ts.map +0 -1
  91. package/lib/typescript/highlight-updates/utils/copySettingsStorage.d.ts.map +0 -1
  92. package/lib/typescript/highlight-updates/utils/devtoolsComponentNames.d.ts.map +0 -1
  93. package/lib/typescript/highlight-updates/utils/namedComposite.d.ts.map +0 -1
  94. package/lib/typescript/highlight-updates/utils/ownStateChanged.d.ts.map +0 -1
  95. package/lib/typescript/highlight-updates/utils/rawEventEmitter.d.ts.map +0 -1
  96. package/lib/typescript/highlight-updates/utils/renderExportFormatter.d.ts.map +0 -1
  97. package/lib/typescript/highlight-updates/utils/rendersExportFormatter.d.ts.map +0 -1
  98. package/lib/typescript/highlight-updates/utils/screenElements.d.ts.map +0 -1
  99. package/lib/typescript/highlight-updates/utils/tapMatch.d.ts.map +0 -1
  100. package/lib/typescript/highlight-updates/utils/testIDs.d.ts.map +0 -1
  101. package/lib/typescript/highlight-updates/utils/touchCapture.d.ts.map +0 -1
  102. package/lib/typescript/index.d.ts.map +0 -1
  103. package/lib/typescript/preset.d.ts.map +0 -1
  104. package/lib/typescript/sync/highlightUpdatesSyncAdapter.d.ts.map +0 -1
@@ -1,846 +1 @@
1
- "use strict";
2
-
3
- Object.defineProperty(exports, "__esModule", {
4
- value: true
5
- });
6
- exports.RenderDetailView = RenderDetailView;
7
- exports.default = void 0;
8
- var _react = _interopRequireWildcard(require("react"));
9
- var _reactNative = require("react-native");
10
- var _sharedUi = require("@buoy-gg/shared-ui");
11
- var _dataViewer = require("@buoy-gg/shared-ui/dataViewer");
12
- var _RenderCauseBadge = require("./RenderCauseBadge");
13
- var _rendersExportFormatter = require("../utils/rendersExportFormatter");
14
- var _jsxRuntime = require("react/jsx-runtime");
15
- function _interopRequireWildcard(e, t) { if ("function" == typeof WeakMap) var r = new WeakMap(), n = new WeakMap(); return (_interopRequireWildcard = function (e, t) { if (!t && e && e.__esModule) return e; var o, i, f = { __proto__: null, default: e }; if (null === e || "object" != typeof e && "function" != typeof e) return f; if (o = t ? n : r) { if (o.has(e)) return o.get(e); o.set(e, f); } for (const t in e) "default" !== t && {}.hasOwnProperty.call(e, t) && ((i = (o = Object.defineProperty) && Object.getOwnPropertyDescriptor(e, t)) && (i.get || i.set) ? o(f, t, i) : f[t] = e[t]); return f; })(e, t); }
16
- /**
17
- * RenderDetailView
18
- *
19
- * Minimal, glanceable view for render details.
20
- * Design principle: Dev should understand WHY in 3 seconds.
21
- *
22
- * Layout:
23
- * - Header: Component name + native type
24
- * - Answer Card: Cause badges + hook change (THE answer)
25
- * - History Row: Compact inline navigation
26
- */
27
-
28
- // Free tier limit for render history events
29
- function RenderDetailView({
30
- render,
31
- disableInternalFooter = false,
32
- selectedEventIndex: externalIndex,
33
- onEventIndexChange: externalOnChange,
34
- onAddFilter,
35
- isPro = false
36
- }) {
37
- // Internal state for event index when not controlled externally
38
- const [internalIndex, setInternalIndex] = (0, _react.useState)(0);
39
-
40
- // Use external or internal state
41
- const selectedEventIndex = externalIndex ?? internalIndex;
42
- const onEventIndexChange = externalOnChange ?? setInternalIndex;
43
-
44
- // Get events sorted by timestamp (oldest first)
45
- const events = (0, _react.useMemo)(() => {
46
- if (!render.renderHistory || render.renderHistory.length === 0) {
47
- return [];
48
- }
49
- return [...render.renderHistory].sort((a, b) => a.timestamp - b.timestamp);
50
- }, [render.renderHistory]);
51
- const totalEvents = events.length;
52
- const currentEvent = events[selectedEventIndex];
53
-
54
- // `isPro` stays a prop so callers can force the unlimited view; the tier cap
55
- // applies otherwise. useLimit() already returns Infinity for Pro, so the two
56
- // agree — this only preserves the prop contract for cross-package callers.
57
- const tierLimit = (0, _sharedUi.useLimit)("highlightUpdates.detailEvents");
58
- const eventLimit = isPro ? Infinity : tierLimit;
59
- const hiddenEventCount = (0, _react.useMemo)(() => Math.max(0, totalEvents - eventLimit), [eventLimit, totalEvents]);
60
-
61
- // Use current event's cause if available, otherwise fall back to lastRenderCause
62
- const displayCause = currentEvent?.cause || render.lastRenderCause;
63
-
64
- // Navigation handlers
65
- const goToPrevious = (0, _react.useCallback)(() => {
66
- if (selectedEventIndex > 0) {
67
- onEventIndexChange(selectedEventIndex - 1);
68
- }
69
- }, [selectedEventIndex, onEventIndexChange]);
70
- const goToNext = (0, _react.useCallback)(() => {
71
- // Infinity - 1 is Infinity, so an unlimited tier just gets totalEvents - 1.
72
- const maxIndex = Math.min(eventLimit - 1, totalEvents - 1);
73
- if (selectedEventIndex < maxIndex) {
74
- onEventIndexChange(selectedEventIndex + 1);
75
- }
76
- }, [selectedEventIndex, totalEvents, onEventIndexChange, eventLimit]);
77
-
78
- // Memoize copy data
79
- const copyData = (0, _react.useMemo)(() => (0, _rendersExportFormatter.generateSingleComponentExport)(render), [render]);
80
-
81
- // Get component name (prefer componentName, fall back to displayName)
82
- const componentName = render.componentName || render.displayName;
83
- const nativeType = render.viewType;
84
-
85
- // Calculate render stats
86
- const renderDuration = render.lastRenderTime - render.firstRenderTime;
87
- const rendersPerSec = renderDuration > 0 ? (render.renderCount / (renderDuration / 1000)).toFixed(1) : render.renderCount.toString();
88
-
89
- // Determine if we should show footer (either history or filters)
90
- const showHistoryFooter = !disableInternalFooter && totalEvents > 1;
91
- return /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
92
- style: styles.container,
93
- children: [/*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
94
- style: styles.header,
95
- children: [/*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
96
- style: styles.headerLeft,
97
- children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
98
- testID: "buoy-highlight-detail-name",
99
- style: styles.componentName,
100
- numberOfLines: 1,
101
- children: componentName
102
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.View, {
103
- style: styles.nativeTypeBadge,
104
- children: /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
105
- testID: "buoy-highlight-detail-type",
106
- style: styles.nativeTypeText,
107
- children: nativeType
108
- })
109
- })]
110
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_sharedUi.CopyButton, {
111
- value: copyData,
112
- size: 14,
113
- testID: "buoy-highlight-detail-copy"
114
- })]
115
- }), /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.ScrollView, {
116
- testID: "buoy-highlight-detail-scroll",
117
- style: styles.scrollView,
118
- contentContainerStyle: [styles.scrollContent, showHistoryFooter && {
119
- paddingBottom: 100
120
- }],
121
- showsVerticalScrollIndicator: false,
122
- children: [displayCause && /*#__PURE__*/(0, _jsxRuntime.jsx)(AnswerCard, {
123
- cause: displayCause,
124
- renderNumber: currentEvent?.renderNumber
125
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(DetailsSection, {
126
- render: render,
127
- rendersPerSec: rendersPerSec
128
- }), hiddenEventCount > 0 && /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
129
- testID: "buoy-highlight-detail-locked",
130
- style: styles.lockedBanner,
131
- children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(_sharedUi.Lock, {
132
- size: 14,
133
- color: _sharedUi.night.color.warning
134
- }), /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.Text, {
135
- testID: "buoy-highlight-detail-locked-text",
136
- style: styles.lockedBannerText,
137
- children: [hiddenEventCount, " ", hiddenEventCount === 1 ? 'event' : 'events', " hidden"]
138
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
139
- style: styles.lockedBannerSubtext,
140
- children: "Upgrade to Pro"
141
- })]
142
- }), onAddFilter && /*#__PURE__*/(0, _jsxRuntime.jsx)(QuickActionsSection, {
143
- render: render,
144
- onAddFilter: onAddFilter
145
- })]
146
- }), showHistoryFooter && /*#__PURE__*/(0, _jsxRuntime.jsx)(_sharedUi.EventStepperFooter, {
147
- currentIndex: selectedEventIndex,
148
- totalItems: totalEvents,
149
- onPrevious: goToPrevious,
150
- onNext: goToNext,
151
- itemLabel: "Render",
152
- subtitle: currentEvent?.timestamp ? (0, _sharedUi.formatRelativeTime)(new Date(currentEvent.timestamp)) : undefined,
153
- applySafeAreaInset: false,
154
- absolute: true
155
- })]
156
- });
157
- }
158
-
159
- /**
160
- * AnswerCard - The hero section showing WHY the component rendered
161
- * Design: Single badge + what changed below it
162
- */
163
- function AnswerCard({
164
- cause,
165
- renderNumber
166
- }) {
167
- // Use component cause if available, otherwise native cause
168
- const displayCauseType = cause.componentCause || cause.type;
169
- const config = cause.componentCause ? _RenderCauseBadge.COMPONENT_CAUSE_CONFIG[cause.componentCause] : _RenderCauseBadge.CAUSE_CONFIG[cause.type];
170
- const hasHookChanges = cause.hookChanges && cause.hookChanges.length > 0;
171
- const hasChangedKeys = cause.changedKeys && cause.changedKeys.length > 0;
172
-
173
- // Get contextual label based on cause type
174
- const getLabel = () => {
175
- if (cause.type === "mount") return "First render";
176
- if (displayCauseType === "parent") return "Triggered by";
177
- return "Changed:";
178
- };
179
- return /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
180
- testID: "buoy-highlight-detail-cause",
181
- style: styles.answerCard,
182
- children: [/*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
183
- style: styles.causeBadgeRow,
184
- children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
185
- testID: "buoy-highlight-detail-cause-label",
186
- style: styles.causeLabel,
187
- children: getLabel()
188
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.View, {
189
- style: [styles.causeBadgeLarge, {
190
- backgroundColor: config.color + "20"
191
- }],
192
- children: /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
193
- testID: "buoy-highlight-detail-cause-badge",
194
- style: [styles.causeBadgeLargeText, {
195
- color: config.color
196
- }],
197
- children: config.label.toUpperCase()
198
- })
199
- })]
200
- }), hasHookChanges && /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.View, {
201
- style: styles.hookChangesContainer,
202
- children: cause.hookChanges.map((hook, index) => {
203
- const hookKey = `${hook.type}[${hook.index}]`;
204
- const oldValue = {
205
- [hookKey]: hook.previousValue
206
- };
207
- const newValue = {
208
- [hookKey]: hook.currentValue
209
- };
210
- return /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.View, {
211
- style: styles.hookDiffContainer,
212
- children: /*#__PURE__*/(0, _jsxRuntime.jsx)(_dataViewer.TreeDiffViewer, {
213
- oldValue: oldValue,
214
- newValue: newValue,
215
- theme: "dark",
216
- showUnchanged: false
217
- })
218
- }, index);
219
- })
220
- }), !hasHookChanges && hasChangedKeys && /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.View, {
221
- style: styles.propsChangesContainer,
222
- children: cause.changedKeys.filter(k => !k.includes("(ref only)")).slice(0, 5).map((key, index) => /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.View, {
223
- style: styles.propChangeChip,
224
- children: /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
225
- testID: `buoy-highlight-detail-changed-${index}`,
226
- style: styles.propChangeText,
227
- children: key
228
- })
229
- }, index))
230
- })]
231
- });
232
- }
233
-
234
- /**
235
- * DetailsSection - Component identifiers, measurements, and stats
236
- * Helps devs find the component in their codebase
237
- */
238
- function DetailsSection({
239
- render,
240
- rendersPerSec
241
- }) {
242
- const hasIdentifiers = render.testID || render.nativeID || render.accessibilityLabel;
243
- const hasMeasurements = render.measurements;
244
- return /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
245
- style: styles.detailsSection,
246
- children: [hasIdentifiers && /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
247
- testID: "buoy-highlight-detail-identifiers",
248
- style: styles.detailsCard,
249
- children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
250
- style: styles.detailsCardTitle,
251
- children: "Identifiers"
252
- }), render.testID && /*#__PURE__*/(0, _jsxRuntime.jsx)(DetailRow, {
253
- label: "testID",
254
- value: render.testID
255
- }), render.nativeID && /*#__PURE__*/(0, _jsxRuntime.jsx)(DetailRow, {
256
- label: "nativeID",
257
- value: render.nativeID
258
- }), render.accessibilityLabel && /*#__PURE__*/(0, _jsxRuntime.jsx)(DetailRow, {
259
- label: "a11y",
260
- value: render.accessibilityLabel
261
- })]
262
- }), /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
263
- testID: "buoy-highlight-detail-stats",
264
- style: styles.statsRow,
265
- children: [/*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
266
- testID: "buoy-highlight-detail-stat-renders",
267
- style: styles.statItem,
268
- children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
269
- testID: "buoy-highlight-detail-stat-renders-value",
270
- style: [styles.statValue, {
271
- color: render.color
272
- }],
273
- children: render.renderCount
274
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
275
- style: styles.statLabel,
276
- children: "renders"
277
- })]
278
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.View, {
279
- style: styles.statDivider
280
- }), /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
281
- testID: "buoy-highlight-detail-stat-rate",
282
- style: styles.statItem,
283
- children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
284
- testID: "buoy-highlight-detail-stat-rate-value",
285
- style: styles.statValue,
286
- children: rendersPerSec
287
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
288
- style: styles.statLabel,
289
- children: "/sec"
290
- })]
291
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.View, {
292
- style: styles.statDivider
293
- }), /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
294
- testID: "buoy-highlight-detail-stat-tag",
295
- style: styles.statItem,
296
- children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
297
- testID: "buoy-highlight-detail-stat-tag-value",
298
- style: styles.statValue,
299
- children: render.nativeTag
300
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
301
- style: styles.statLabel,
302
- children: "tag"
303
- })]
304
- })]
305
- }), hasMeasurements && /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
306
- testID: "buoy-highlight-detail-measure",
307
- style: styles.measurementsRow,
308
- children: [/*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
309
- style: styles.measurementItem,
310
- children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
311
- style: styles.measurementLabel,
312
- children: "x"
313
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
314
- testID: "buoy-highlight-detail-measure-x",
315
- style: styles.measurementValue,
316
- children: Math.round(render.measurements.x)
317
- })]
318
- }), /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
319
- style: styles.measurementItem,
320
- children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
321
- style: styles.measurementLabel,
322
- children: "y"
323
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
324
- testID: "buoy-highlight-detail-measure-y",
325
- style: styles.measurementValue,
326
- children: Math.round(render.measurements.y)
327
- })]
328
- }), /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
329
- style: styles.measurementItem,
330
- children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
331
- style: styles.measurementLabel,
332
- children: "w"
333
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
334
- testID: "buoy-highlight-detail-measure-w",
335
- style: styles.measurementValue,
336
- children: Math.round(render.measurements.width)
337
- })]
338
- }), /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
339
- style: styles.measurementItem,
340
- children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
341
- style: styles.measurementLabel,
342
- children: "h"
343
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
344
- testID: "buoy-highlight-detail-measure-h",
345
- style: styles.measurementValue,
346
- children: Math.round(render.measurements.height)
347
- })]
348
- })]
349
- })]
350
- });
351
- }
352
-
353
- /**
354
- * DetailRow - Single row for identifier display
355
- */
356
- function DetailRow({
357
- label,
358
- value
359
- }) {
360
- const handle = `buoy-highlight-detail-id-${label.toLowerCase()}`;
361
- return /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
362
- testID: handle,
363
- style: styles.detailRow,
364
- children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
365
- style: styles.detailLabel,
366
- children: label
367
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
368
- testID: `${handle}-value`,
369
- style: styles.detailValue,
370
- numberOfLines: 1,
371
- children: value
372
- })]
373
- });
374
- }
375
-
376
- /**
377
- * QuickActionsSection - Quick filter actions for the component
378
- * Users select a filter option, then use action buttons to include/exclude
379
- */
380
- function QuickActionsSection({
381
- render,
382
- onAddFilter
383
- }) {
384
- const [selectedIndex, setSelectedIndex] = (0, _react.useState)(null);
385
-
386
- // Build list of available filter options (most specific to most general)
387
- const filterOptions = (0, _react.useMemo)(() => {
388
- const options = [];
389
-
390
- // Most specific first
391
- if (render.nativeID) {
392
- options.push({
393
- type: "nativeID",
394
- value: render.nativeID,
395
- label: "nativeID"
396
- });
397
- }
398
- if (render.testID) {
399
- options.push({
400
- type: "testID",
401
- value: render.testID,
402
- label: "testID"
403
- });
404
- }
405
- if (render.accessibilityLabel) {
406
- options.push({
407
- type: "accessibilityLabel",
408
- value: render.accessibilityLabel,
409
- label: "a11y"
410
- });
411
- }
412
- if (render.componentName) {
413
- options.push({
414
- type: "component",
415
- value: render.componentName,
416
- label: "component"
417
- });
418
- }
419
- // Most general last (always available)
420
- options.push({
421
- type: "viewType",
422
- value: render.viewType,
423
- label: "viewType"
424
- });
425
- return options;
426
- }, [render]);
427
- const selectedOption = selectedIndex !== null ? filterOptions[selectedIndex] : null;
428
- const handleSelectOption = (0, _react.useCallback)(index => {
429
- setSelectedIndex(prev => prev === index ? null : index);
430
- }, []);
431
- const handleInclude = (0, _react.useCallback)(() => {
432
- if (selectedOption) {
433
- onAddFilter({
434
- type: selectedOption.type,
435
- value: selectedOption.value
436
- }, "include");
437
- setSelectedIndex(null);
438
- }
439
- }, [selectedOption, onAddFilter]);
440
- const handleExclude = (0, _react.useCallback)(() => {
441
- if (selectedOption) {
442
- onAddFilter({
443
- type: selectedOption.type,
444
- value: selectedOption.value
445
- }, "exclude");
446
- setSelectedIndex(null);
447
- }
448
- }, [selectedOption, onAddFilter]);
449
- return /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
450
- testID: "buoy-highlight-quick",
451
- style: styles.quickActionsSection,
452
- children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
453
- style: styles.quickActionsTitle,
454
- children: "Quick Filters"
455
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.View, {
456
- style: styles.filterOptionsList,
457
- children: filterOptions.map((option, index) => /*#__PURE__*/(0, _jsxRuntime.jsx)(FilterOptionCard, {
458
- testID: `buoy-highlight-quick-${option.type.toLowerCase()}`,
459
- label: option.label,
460
- value: option.value,
461
- isSelected: selectedIndex === index,
462
- onSelect: () => handleSelectOption(index)
463
- }, option.type))
464
- }), /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.View, {
465
- style: styles.filterActionButtons,
466
- children: [/*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.TouchableOpacity, {
467
- testID: "buoy-highlight-quick-include",
468
- accessibilityRole: "button",
469
- accessibilityLabel: "Only show this",
470
- style: [styles.filterActionButton, styles.filterActionButtonInclude, !selectedOption && styles.filterActionButtonDisabled],
471
- onPress: handleInclude,
472
- disabled: !selectedOption,
473
- activeOpacity: 0.7,
474
- children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(_sharedUi.PlusIcon, {
475
- size: 14,
476
- color: selectedOption ? _sharedUi.night.color.accent : _sharedUi.night.color.textTertiary
477
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
478
- style: [styles.filterActionButtonText, {
479
- color: selectedOption ? _sharedUi.night.color.accent : _sharedUi.night.color.textTertiary
480
- }],
481
- children: "Only Show This"
482
- })]
483
- }), /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.TouchableOpacity, {
484
- testID: "buoy-highlight-quick-exclude",
485
- accessibilityRole: "button",
486
- accessibilityLabel: "Hide this",
487
- style: [styles.filterActionButton, styles.filterActionButtonExclude, !selectedOption && styles.filterActionButtonDisabled],
488
- onPress: handleExclude,
489
- disabled: !selectedOption,
490
- activeOpacity: 0.7,
491
- children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(_sharedUi.MinusIcon, {
492
- size: 14,
493
- color: selectedOption ? _sharedUi.night.color.danger : _sharedUi.night.color.textTertiary
494
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
495
- style: [styles.filterActionButtonText, {
496
- color: selectedOption ? _sharedUi.night.color.danger : _sharedUi.night.color.textTertiary
497
- }],
498
- children: "Hide This"
499
- })]
500
- })]
501
- })]
502
- });
503
- }
504
-
505
- /**
506
- * FilterOptionCard - A selectable filter option card
507
- */
508
- function FilterOptionCard({
509
- testID,
510
- label,
511
- value,
512
- isSelected,
513
- onSelect
514
- }) {
515
- return /*#__PURE__*/(0, _jsxRuntime.jsxs)(_reactNative.TouchableOpacity, {
516
- testID: testID,
517
- accessibilityRole: "button",
518
- accessibilityLabel: `${label}, ${value}`,
519
- style: [styles.filterOptionCard, isSelected && styles.filterOptionCardSelected],
520
- onPress: onSelect,
521
- activeOpacity: 0.7,
522
- children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
523
- style: [styles.filterOptionLabel, isSelected && styles.filterOptionLabelSelected],
524
- children: label
525
- }), /*#__PURE__*/(0, _jsxRuntime.jsx)(_reactNative.Text, {
526
- testID: testID ? `${testID}-value` : undefined,
527
- style: [styles.filterOptionValue, isSelected && styles.filterOptionValueSelected],
528
- numberOfLines: 1,
529
- children: value
530
- })]
531
- });
532
- }
533
- const styles = _reactNative.StyleSheet.create({
534
- container: {
535
- flex: 1,
536
- // Transparent so JsModal's ToolBackground shows through (the modal paints opaque base beneath it).
537
- backgroundColor: "transparent"
538
- },
539
- // Header
540
- header: {
541
- flexDirection: "row",
542
- alignItems: "center",
543
- justifyContent: "center",
544
- gap: 12,
545
- padding: 16,
546
- paddingBottom: 0
547
- },
548
- // ScrollView
549
- scrollView: {
550
- flex: 1
551
- },
552
- scrollContent: {
553
- padding: 16,
554
- paddingTop: 12,
555
- paddingBottom: 80,
556
- gap: 12
557
- },
558
- headerLeft: {
559
- flex: 1,
560
- flexDirection: "row",
561
- alignItems: "center",
562
- justifyContent: "center",
563
- gap: 10
564
- },
565
- componentName: {
566
- fontSize: 18,
567
- fontWeight: "700",
568
- color: _sharedUi.night.color.text,
569
- flexShrink: 1
570
- },
571
- nativeTypeBadge: {
572
- // Inset display chip — the night track color.
573
- backgroundColor: _sharedUi.night.color.bg,
574
- paddingVertical: 3,
575
- paddingHorizontal: 8,
576
- borderRadius: 4
577
- },
578
- nativeTypeText: {
579
- fontSize: 11,
580
- fontWeight: "600",
581
- color: _sharedUi.night.color.textTertiary,
582
- fontFamily: _sharedUi.monoFont
583
- },
584
- // Answer Card
585
- answerCard: {
586
- backgroundColor: _sharedUi.night.color.surface,
587
- borderRadius: 8,
588
- borderWidth: 1,
589
- borderColor: _sharedUi.night.color.border,
590
- padding: 12,
591
- gap: 6
592
- },
593
- causeBadgeRow: {
594
- flexDirection: "row",
595
- alignItems: "center",
596
- gap: 8
597
- },
598
- causeBadgeLarge: {
599
- paddingVertical: 4,
600
- paddingHorizontal: 10,
601
- borderRadius: 4
602
- },
603
- causeBadgeLargeText: {
604
- fontSize: 11,
605
- fontWeight: "700",
606
- letterSpacing: 0.5
607
- },
608
- causeLabel: {
609
- fontSize: 12,
610
- color: _sharedUi.night.color.textSecondary,
611
- fontWeight: "500"
612
- },
613
- hookChangesContainer: {
614
- gap: 6
615
- },
616
- hookDiffContainer: {
617
- // Inset code box — the night track color.
618
- backgroundColor: _sharedUi.night.color.bg,
619
- borderRadius: 6,
620
- overflow: "hidden"
621
- },
622
- propsChangesContainer: {
623
- flexDirection: "row",
624
- flexWrap: "wrap",
625
- gap: 4
626
- },
627
- propChangeChip: {
628
- // Inset display chip — the night track color.
629
- backgroundColor: _sharedUi.night.color.bg,
630
- paddingVertical: 2,
631
- paddingHorizontal: 6,
632
- borderRadius: 4
633
- },
634
- propChangeText: {
635
- fontSize: 11,
636
- color: _sharedUi.night.color.text,
637
- fontFamily: _sharedUi.monoFont
638
- },
639
- // Details Section
640
- detailsSection: {
641
- gap: 10
642
- },
643
- detailsCard: {
644
- backgroundColor: _sharedUi.night.color.surface,
645
- borderRadius: 8,
646
- borderWidth: 1,
647
- borderColor: _sharedUi.night.color.border,
648
- padding: 12,
649
- gap: 6
650
- },
651
- detailsCardTitle: {
652
- fontSize: 10,
653
- fontWeight: "600",
654
- color: _sharedUi.night.color.textTertiary,
655
- letterSpacing: 0.5,
656
- textTransform: "uppercase",
657
- marginBottom: 4
658
- },
659
- detailRow: {
660
- flexDirection: "row",
661
- alignItems: "center",
662
- gap: 8
663
- },
664
- detailLabel: {
665
- fontSize: 11,
666
- fontWeight: "600",
667
- color: _sharedUi.night.color.textSecondary,
668
- minWidth: 55
669
- },
670
- detailValue: {
671
- fontSize: 12,
672
- color: _sharedUi.night.color.text,
673
- fontFamily: _sharedUi.monoFont,
674
- flex: 1
675
- },
676
- // Stats Row
677
- statsRow: {
678
- flexDirection: "row",
679
- alignItems: "center",
680
- justifyContent: "center",
681
- backgroundColor: _sharedUi.night.color.surface,
682
- borderRadius: 8,
683
- borderWidth: 1,
684
- borderColor: _sharedUi.night.color.border,
685
- paddingVertical: 10,
686
- paddingHorizontal: 16
687
- },
688
- statItem: {
689
- flex: 1,
690
- alignItems: "center"
691
- },
692
- statValue: {
693
- fontSize: 16,
694
- fontWeight: "700",
695
- color: _sharedUi.night.color.text,
696
- fontFamily: _sharedUi.monoFont
697
- },
698
- statLabel: {
699
- fontSize: 10,
700
- color: _sharedUi.night.color.textTertiary,
701
- marginTop: 2
702
- },
703
- statDivider: {
704
- width: 1,
705
- height: 24,
706
- backgroundColor: _sharedUi.night.color.border,
707
- marginHorizontal: 12
708
- },
709
- // Measurements Row
710
- measurementsRow: {
711
- flexDirection: "row",
712
- alignItems: "center",
713
- justifyContent: "space-around",
714
- backgroundColor: _sharedUi.night.color.surface,
715
- borderRadius: 8,
716
- borderWidth: 1,
717
- borderColor: _sharedUi.night.color.border,
718
- paddingVertical: 8,
719
- paddingHorizontal: 12
720
- },
721
- measurementItem: {
722
- flexDirection: "row",
723
- alignItems: "baseline",
724
- gap: 4
725
- },
726
- measurementLabel: {
727
- fontSize: 10,
728
- fontWeight: "600",
729
- color: _sharedUi.night.color.textTertiary,
730
- textTransform: "uppercase"
731
- },
732
- measurementValue: {
733
- fontSize: 12,
734
- fontWeight: "600",
735
- color: _sharedUi.night.color.text,
736
- fontFamily: _sharedUi.monoFont
737
- },
738
- // Quick Actions Section
739
- quickActionsSection: {
740
- backgroundColor: _sharedUi.night.color.surface,
741
- borderRadius: 8,
742
- borderWidth: 1,
743
- borderColor: _sharedUi.night.color.border,
744
- padding: 12,
745
- gap: 10
746
- },
747
- quickActionsTitle: {
748
- fontSize: 10,
749
- fontWeight: "600",
750
- color: _sharedUi.night.color.textTertiary,
751
- letterSpacing: 0.5,
752
- textTransform: "uppercase",
753
- marginBottom: 2
754
- },
755
- filterOptionsList: {
756
- gap: 6
757
- },
758
- filterOptionCard: {
759
- flexDirection: "row",
760
- alignItems: "center",
761
- backgroundColor: _sharedUi.night.color.surfaceElevated,
762
- borderRadius: 6,
763
- paddingVertical: 10,
764
- paddingHorizontal: 12,
765
- borderWidth: 1,
766
- borderColor: "transparent",
767
- gap: 10
768
- },
769
- filterOptionCardSelected: {
770
- borderColor: _sharedUi.night.color.accentBorderStrong,
771
- backgroundColor: _sharedUi.night.color.accentSoft
772
- },
773
- filterOptionLabel: {
774
- fontSize: 10,
775
- fontWeight: "600",
776
- color: _sharedUi.night.color.textTertiary,
777
- minWidth: 70
778
- },
779
- filterOptionLabelSelected: {
780
- color: _sharedUi.night.color.accent
781
- },
782
- filterOptionValue: {
783
- fontSize: 12,
784
- color: _sharedUi.night.color.text,
785
- fontFamily: _sharedUi.monoFont,
786
- flex: 1
787
- },
788
- filterOptionValueSelected: {
789
- color: _sharedUi.night.color.text
790
- },
791
- filterActionButtons: {
792
- flexDirection: "row",
793
- gap: 8,
794
- marginTop: 12
795
- },
796
- filterActionButton: {
797
- flexDirection: "row",
798
- alignItems: "center",
799
- justifyContent: "center",
800
- gap: 4,
801
- paddingVertical: 8,
802
- paddingHorizontal: 10,
803
- borderRadius: 6,
804
- borderWidth: 1
805
- },
806
- filterActionButtonInclude: {
807
- backgroundColor: _sharedUi.night.color.accentSoft,
808
- borderColor: _sharedUi.night.color.accentBorderStrong
809
- },
810
- filterActionButtonExclude: {
811
- backgroundColor: _sharedUi.night.color.dangerSoft,
812
- borderColor: _sharedUi.night.color.danger + "40"
813
- },
814
- filterActionButtonDisabled: {
815
- backgroundColor: _sharedUi.night.color.surfaceElevated,
816
- borderColor: _sharedUi.night.color.border,
817
- opacity: 0.5
818
- },
819
- filterActionButtonText: {
820
- fontSize: 11,
821
- fontWeight: "600"
822
- },
823
- // Locked Banner
824
- lockedBanner: {
825
- flexDirection: "row",
826
- alignItems: "center",
827
- justifyContent: "center",
828
- backgroundColor: _sharedUi.night.color.surface,
829
- borderRadius: 8,
830
- borderWidth: 1,
831
- borderColor: _sharedUi.night.color.warning + "40",
832
- paddingVertical: 12,
833
- paddingHorizontal: 16,
834
- gap: 8
835
- },
836
- lockedBannerText: {
837
- color: _sharedUi.night.color.warning,
838
- fontSize: 13,
839
- fontWeight: "600"
840
- },
841
- lockedBannerSubtext: {
842
- color: _sharedUi.night.color.textTertiary,
843
- fontSize: 12
844
- }
845
- });
846
- var _default = exports.default = RenderDetailView;
1
+ "use strict";Object.defineProperty(exports,"__esModule",{value:!0}),exports.RenderDetailView=RenderDetailView,exports.default=void 0;var _react=_interopRequireWildcard(require("react")),_reactNative=require("react-native"),_sharedUi=require("@buoy-gg/shared-ui"),_dataViewer=require("@buoy-gg/shared-ui/dataViewer"),_RenderCauseBadge=require("./RenderCauseBadge"),_rendersExportFormatter=require("../utils/rendersExportFormatter"),_jsxRuntime=require("react/jsx-runtime");function _interopRequireWildcard(e,t){if("function"==typeof WeakMap)var i=new WeakMap,r=new WeakMap;return(_interopRequireWildcard=function(e,t){if(!t&&e&&e.__esModule)return e;var s,a,n={__proto__:null,default:e};if(null===e||"object"!=typeof e&&"function"!=typeof e)return n;if(s=t?r:i){if(s.has(e))return s.get(e);s.set(e,n)}for(const t in e)"default"!==t&&{}.hasOwnProperty.call(e,t)&&((a=(s=Object.defineProperty)&&Object.getOwnPropertyDescriptor(e,t))&&(a.get||a.set)?s(n,t,a):n[t]=e[t]);return n})(e,t)}function RenderDetailView({render:e,disableInternalFooter:t=!1,selectedEventIndex:i,onEventIndexChange:r,onAddFilter:s,isPro:a=!1}){const[n,l]=(0,_react.useState)(0),o=i??n,c=r??l,d=(0,_react.useMemo)(()=>e.renderHistory&&0!==e.renderHistory.length?[...e.renderHistory].sort((e,t)=>e.timestamp-t.timestamp):[],[e.renderHistory]),u=d.length,h=d[o],g=(0,_sharedUi.useLimit)("highlightUpdates.detailEvents"),x=a?1/0:g,y=(0,_react.useMemo)(()=>Math.max(0,u-x),[x,u]),_=h?.cause||e.lastRenderCause,m=(0,_react.useCallback)(()=>{o>0&&c(o-1)},[o,c]),p=(0,_react.useCallback)(()=>{const e=Math.min(x-1,u-1);o<e&&c(o+1)},[o,u,c,x]),b=(0,_react.useMemo)(()=>(0,_rendersExportFormatter.generateSingleComponentExport)(e),[e]),j=e.componentName||e.displayName,f=e.viewType,v=e.lastRenderTime-e.firstRenderTime,R=v>0?(e.renderCount/(v/1e3)).toFixed(1):e.renderCount.toString(),C=!t&&u>1;return(0,_jsxRuntime.jsxs)(_reactNative.View,{style:styles.container,children:[(0,_jsxRuntime.jsxs)(_reactNative.View,{style:styles.header,children:[(0,_jsxRuntime.jsxs)(_reactNative.View,{style:styles.headerLeft,children:[(0,_jsxRuntime.jsx)(_reactNative.Text,{testID:"buoy-highlight-detail-name",style:styles.componentName,numberOfLines:1,children:j}),(0,_jsxRuntime.jsx)(_reactNative.View,{style:styles.nativeTypeBadge,children:(0,_jsxRuntime.jsx)(_reactNative.Text,{testID:"buoy-highlight-detail-type",style:styles.nativeTypeText,children:f})})]}),(0,_jsxRuntime.jsx)(_sharedUi.CopyButton,{value:b,size:14,testID:"buoy-highlight-detail-copy"})]}),(0,_jsxRuntime.jsxs)(_reactNative.ScrollView,{testID:"buoy-highlight-detail-scroll",style:styles.scrollView,contentContainerStyle:[styles.scrollContent,C&&{paddingBottom:100}],showsVerticalScrollIndicator:!1,children:[_&&(0,_jsxRuntime.jsx)(AnswerCard,{cause:_,renderNumber:h?.renderNumber}),(0,_jsxRuntime.jsx)(DetailsSection,{render:e,rendersPerSec:R}),y>0&&(0,_jsxRuntime.jsxs)(_reactNative.View,{testID:"buoy-highlight-detail-locked",style:styles.lockedBanner,children:[(0,_jsxRuntime.jsx)(_sharedUi.Lock,{size:14,color:_sharedUi.night.color.warning}),(0,_jsxRuntime.jsxs)(_reactNative.Text,{testID:"buoy-highlight-detail-locked-text",style:styles.lockedBannerText,children:[y," ",1===y?"event":"events"," hidden"]}),(0,_jsxRuntime.jsx)(_reactNative.Text,{style:styles.lockedBannerSubtext,children:"Upgrade to Pro"})]}),s&&(0,_jsxRuntime.jsx)(QuickActionsSection,{render:e,onAddFilter:s})]}),C&&(0,_jsxRuntime.jsx)(_sharedUi.EventStepperFooter,{currentIndex:o,totalItems:u,onPrevious:m,onNext:p,itemLabel:"Render",subtitle:h?.timestamp?(0,_sharedUi.formatRelativeTime)(new Date(h.timestamp)):void 0,applySafeAreaInset:!1,absolute:!0})]})}function AnswerCard({cause:e,renderNumber:t}){const i=e.componentCause||e.type,r=e.componentCause?_RenderCauseBadge.COMPONENT_CAUSE_CONFIG[e.componentCause]:_RenderCauseBadge.CAUSE_CONFIG[e.type],s=e.hookChanges&&e.hookChanges.length>0,a=e.changedKeys&&e.changedKeys.length>0;return(0,_jsxRuntime.jsxs)(_reactNative.View,{testID:"buoy-highlight-detail-cause",style:styles.answerCard,children:[(0,_jsxRuntime.jsxs)(_reactNative.View,{style:styles.causeBadgeRow,children:[(0,_jsxRuntime.jsx)(_reactNative.Text,{testID:"buoy-highlight-detail-cause-label",style:styles.causeLabel,children:"mount"===e.type?"First render":"parent"===i?"Triggered by":"Changed:"}),(0,_jsxRuntime.jsx)(_reactNative.View,{style:[styles.causeBadgeLarge,{backgroundColor:r.color+"20"}],children:(0,_jsxRuntime.jsx)(_reactNative.Text,{testID:"buoy-highlight-detail-cause-badge",style:[styles.causeBadgeLargeText,{color:r.color}],children:r.label.toUpperCase()})})]}),s&&(0,_jsxRuntime.jsx)(_reactNative.View,{style:styles.hookChangesContainer,children:e.hookChanges.map((e,t)=>{const i=`${e.type}[${e.index}]`,r={[i]:e.previousValue},s={[i]:e.currentValue};return(0,_jsxRuntime.jsx)(_reactNative.View,{style:styles.hookDiffContainer,children:(0,_jsxRuntime.jsx)(_dataViewer.TreeDiffViewer,{oldValue:r,newValue:s,theme:"dark",showUnchanged:!1})},t)})}),!s&&a&&(0,_jsxRuntime.jsx)(_reactNative.View,{style:styles.propsChangesContainer,children:e.changedKeys.filter(e=>!e.includes("(ref only)")).slice(0,5).map((e,t)=>(0,_jsxRuntime.jsx)(_reactNative.View,{style:styles.propChangeChip,children:(0,_jsxRuntime.jsx)(_reactNative.Text,{testID:`buoy-highlight-detail-changed-${t}`,style:styles.propChangeText,children:e})},t))})]})}function DetailsSection({render:e,rendersPerSec:t}){const i=e.testID||e.nativeID||e.accessibilityLabel,r=e.measurements;return(0,_jsxRuntime.jsxs)(_reactNative.View,{style:styles.detailsSection,children:[i&&(0,_jsxRuntime.jsxs)(_reactNative.View,{testID:"buoy-highlight-detail-identifiers",style:styles.detailsCard,children:[(0,_jsxRuntime.jsx)(_reactNative.Text,{style:styles.detailsCardTitle,children:"Identifiers"}),e.testID&&(0,_jsxRuntime.jsx)(DetailRow,{label:"testID",value:e.testID}),e.nativeID&&(0,_jsxRuntime.jsx)(DetailRow,{label:"nativeID",value:e.nativeID}),e.accessibilityLabel&&(0,_jsxRuntime.jsx)(DetailRow,{label:"a11y",value:e.accessibilityLabel})]}),(0,_jsxRuntime.jsxs)(_reactNative.View,{testID:"buoy-highlight-detail-stats",style:styles.statsRow,children:[(0,_jsxRuntime.jsxs)(_reactNative.View,{testID:"buoy-highlight-detail-stat-renders",style:styles.statItem,children:[(0,_jsxRuntime.jsx)(_reactNative.Text,{testID:"buoy-highlight-detail-stat-renders-value",style:[styles.statValue,{color:e.color}],children:e.renderCount}),(0,_jsxRuntime.jsx)(_reactNative.Text,{style:styles.statLabel,children:"renders"})]}),(0,_jsxRuntime.jsx)(_reactNative.View,{style:styles.statDivider}),(0,_jsxRuntime.jsxs)(_reactNative.View,{testID:"buoy-highlight-detail-stat-rate",style:styles.statItem,children:[(0,_jsxRuntime.jsx)(_reactNative.Text,{testID:"buoy-highlight-detail-stat-rate-value",style:styles.statValue,children:t}),(0,_jsxRuntime.jsx)(_reactNative.Text,{style:styles.statLabel,children:"/sec"})]}),(0,_jsxRuntime.jsx)(_reactNative.View,{style:styles.statDivider}),(0,_jsxRuntime.jsxs)(_reactNative.View,{testID:"buoy-highlight-detail-stat-tag",style:styles.statItem,children:[(0,_jsxRuntime.jsx)(_reactNative.Text,{testID:"buoy-highlight-detail-stat-tag-value",style:styles.statValue,children:e.nativeTag}),(0,_jsxRuntime.jsx)(_reactNative.Text,{style:styles.statLabel,children:"tag"})]})]}),r&&(0,_jsxRuntime.jsxs)(_reactNative.View,{testID:"buoy-highlight-detail-measure",style:styles.measurementsRow,children:[(0,_jsxRuntime.jsxs)(_reactNative.View,{style:styles.measurementItem,children:[(0,_jsxRuntime.jsx)(_reactNative.Text,{style:styles.measurementLabel,children:"x"}),(0,_jsxRuntime.jsx)(_reactNative.Text,{testID:"buoy-highlight-detail-measure-x",style:styles.measurementValue,children:Math.round(e.measurements.x)})]}),(0,_jsxRuntime.jsxs)(_reactNative.View,{style:styles.measurementItem,children:[(0,_jsxRuntime.jsx)(_reactNative.Text,{style:styles.measurementLabel,children:"y"}),(0,_jsxRuntime.jsx)(_reactNative.Text,{testID:"buoy-highlight-detail-measure-y",style:styles.measurementValue,children:Math.round(e.measurements.y)})]}),(0,_jsxRuntime.jsxs)(_reactNative.View,{style:styles.measurementItem,children:[(0,_jsxRuntime.jsx)(_reactNative.Text,{style:styles.measurementLabel,children:"w"}),(0,_jsxRuntime.jsx)(_reactNative.Text,{testID:"buoy-highlight-detail-measure-w",style:styles.measurementValue,children:Math.round(e.measurements.width)})]}),(0,_jsxRuntime.jsxs)(_reactNative.View,{style:styles.measurementItem,children:[(0,_jsxRuntime.jsx)(_reactNative.Text,{style:styles.measurementLabel,children:"h"}),(0,_jsxRuntime.jsx)(_reactNative.Text,{testID:"buoy-highlight-detail-measure-h",style:styles.measurementValue,children:Math.round(e.measurements.height)})]})]})]})}function DetailRow({label:e,value:t}){const i=`buoy-highlight-detail-id-${e.toLowerCase()}`;return(0,_jsxRuntime.jsxs)(_reactNative.View,{testID:i,style:styles.detailRow,children:[(0,_jsxRuntime.jsx)(_reactNative.Text,{style:styles.detailLabel,children:e}),(0,_jsxRuntime.jsx)(_reactNative.Text,{testID:`${i}-value`,style:styles.detailValue,numberOfLines:1,children:t})]})}function QuickActionsSection({render:e,onAddFilter:t}){const[i,r]=(0,_react.useState)(null),s=(0,_react.useMemo)(()=>{const t=[];return e.nativeID&&t.push({type:"nativeID",value:e.nativeID,label:"nativeID"}),e.testID&&t.push({type:"testID",value:e.testID,label:"testID"}),e.accessibilityLabel&&t.push({type:"accessibilityLabel",value:e.accessibilityLabel,label:"a11y"}),e.componentName&&t.push({type:"component",value:e.componentName,label:"component"}),t.push({type:"viewType",value:e.viewType,label:"viewType"}),t},[e]),a=null!==i?s[i]:null,n=(0,_react.useCallback)(e=>{r(t=>t===e?null:e)},[]),l=(0,_react.useCallback)(()=>{a&&(t({type:a.type,value:a.value},"include"),r(null))},[a,t]),o=(0,_react.useCallback)(()=>{a&&(t({type:a.type,value:a.value},"exclude"),r(null))},[a,t]);return(0,_jsxRuntime.jsxs)(_reactNative.View,{testID:"buoy-highlight-quick",style:styles.quickActionsSection,children:[(0,_jsxRuntime.jsx)(_reactNative.Text,{style:styles.quickActionsTitle,children:"Quick Filters"}),(0,_jsxRuntime.jsx)(_reactNative.View,{style:styles.filterOptionsList,children:s.map((e,t)=>(0,_jsxRuntime.jsx)(FilterOptionCard,{testID:`buoy-highlight-quick-${e.type.toLowerCase()}`,label:e.label,value:e.value,isSelected:i===t,onSelect:()=>n(t)},e.type))}),(0,_jsxRuntime.jsxs)(_reactNative.View,{style:styles.filterActionButtons,children:[(0,_jsxRuntime.jsxs)(_reactNative.TouchableOpacity,{testID:"buoy-highlight-quick-include",accessibilityRole:"button",accessibilityLabel:"Only show this",style:[styles.filterActionButton,styles.filterActionButtonInclude,!a&&styles.filterActionButtonDisabled],onPress:l,disabled:!a,activeOpacity:.7,children:[(0,_jsxRuntime.jsx)(_sharedUi.PlusIcon,{size:14,color:a?_sharedUi.night.color.accent:_sharedUi.night.color.textTertiary}),(0,_jsxRuntime.jsx)(_reactNative.Text,{style:[styles.filterActionButtonText,{color:a?_sharedUi.night.color.accent:_sharedUi.night.color.textTertiary}],children:"Only Show This"})]}),(0,_jsxRuntime.jsxs)(_reactNative.TouchableOpacity,{testID:"buoy-highlight-quick-exclude",accessibilityRole:"button",accessibilityLabel:"Hide this",style:[styles.filterActionButton,styles.filterActionButtonExclude,!a&&styles.filterActionButtonDisabled],onPress:o,disabled:!a,activeOpacity:.7,children:[(0,_jsxRuntime.jsx)(_sharedUi.MinusIcon,{size:14,color:a?_sharedUi.night.color.danger:_sharedUi.night.color.textTertiary}),(0,_jsxRuntime.jsx)(_reactNative.Text,{style:[styles.filterActionButtonText,{color:a?_sharedUi.night.color.danger:_sharedUi.night.color.textTertiary}],children:"Hide This"})]})]})]})}function FilterOptionCard({testID:e,label:t,value:i,isSelected:r,onSelect:s}){return(0,_jsxRuntime.jsxs)(_reactNative.TouchableOpacity,{testID:e,accessibilityRole:"button",accessibilityLabel:`${t}, ${i}`,style:[styles.filterOptionCard,r&&styles.filterOptionCardSelected],onPress:s,activeOpacity:.7,children:[(0,_jsxRuntime.jsx)(_reactNative.Text,{style:[styles.filterOptionLabel,r&&styles.filterOptionLabelSelected],children:t}),(0,_jsxRuntime.jsx)(_reactNative.Text,{testID:e?`${e}-value`:void 0,style:[styles.filterOptionValue,r&&styles.filterOptionValueSelected],numberOfLines:1,children:i})]})}const styles=_reactNative.StyleSheet.create({container:{flex:1,backgroundColor:"transparent"},header:{flexDirection:"row",alignItems:"center",justifyContent:"center",gap:12,padding:16,paddingBottom:0},scrollView:{flex:1},scrollContent:{padding:16,paddingTop:12,paddingBottom:80,gap:12},headerLeft:{flex:1,flexDirection:"row",alignItems:"center",justifyContent:"center",gap:10},componentName:{fontSize:18,fontWeight:"700",color:_sharedUi.night.color.text,flexShrink:1},nativeTypeBadge:{backgroundColor:_sharedUi.night.color.bg,paddingVertical:3,paddingHorizontal:8,borderRadius:4},nativeTypeText:{fontSize:11,fontWeight:"600",color:_sharedUi.night.color.textTertiary,fontFamily:_sharedUi.monoFont},answerCard:{backgroundColor:_sharedUi.night.color.surface,borderRadius:8,borderWidth:1,borderColor:_sharedUi.night.color.border,padding:12,gap:6},causeBadgeRow:{flexDirection:"row",alignItems:"center",gap:8},causeBadgeLarge:{paddingVertical:4,paddingHorizontal:10,borderRadius:4},causeBadgeLargeText:{fontSize:11,fontWeight:"700",letterSpacing:.5},causeLabel:{fontSize:12,color:_sharedUi.night.color.textSecondary,fontWeight:"500"},hookChangesContainer:{gap:6},hookDiffContainer:{backgroundColor:_sharedUi.night.color.bg,borderRadius:6,overflow:"hidden"},propsChangesContainer:{flexDirection:"row",flexWrap:"wrap",gap:4},propChangeChip:{backgroundColor:_sharedUi.night.color.bg,paddingVertical:2,paddingHorizontal:6,borderRadius:4},propChangeText:{fontSize:11,color:_sharedUi.night.color.text,fontFamily:_sharedUi.monoFont},detailsSection:{gap:10},detailsCard:{backgroundColor:_sharedUi.night.color.surface,borderRadius:8,borderWidth:1,borderColor:_sharedUi.night.color.border,padding:12,gap:6},detailsCardTitle:{fontSize:10,fontWeight:"600",color:_sharedUi.night.color.textTertiary,letterSpacing:.5,textTransform:"uppercase",marginBottom:4},detailRow:{flexDirection:"row",alignItems:"center",gap:8},detailLabel:{fontSize:11,fontWeight:"600",color:_sharedUi.night.color.textSecondary,minWidth:55},detailValue:{fontSize:12,color:_sharedUi.night.color.text,fontFamily:_sharedUi.monoFont,flex:1},statsRow:{flexDirection:"row",alignItems:"center",justifyContent:"center",backgroundColor:_sharedUi.night.color.surface,borderRadius:8,borderWidth:1,borderColor:_sharedUi.night.color.border,paddingVertical:10,paddingHorizontal:16},statItem:{flex:1,alignItems:"center"},statValue:{fontSize:16,fontWeight:"700",color:_sharedUi.night.color.text,fontFamily:_sharedUi.monoFont},statLabel:{fontSize:10,color:_sharedUi.night.color.textTertiary,marginTop:2},statDivider:{width:1,height:24,backgroundColor:_sharedUi.night.color.border,marginHorizontal:12},measurementsRow:{flexDirection:"row",alignItems:"center",justifyContent:"space-around",backgroundColor:_sharedUi.night.color.surface,borderRadius:8,borderWidth:1,borderColor:_sharedUi.night.color.border,paddingVertical:8,paddingHorizontal:12},measurementItem:{flexDirection:"row",alignItems:"baseline",gap:4},measurementLabel:{fontSize:10,fontWeight:"600",color:_sharedUi.night.color.textTertiary,textTransform:"uppercase"},measurementValue:{fontSize:12,fontWeight:"600",color:_sharedUi.night.color.text,fontFamily:_sharedUi.monoFont},quickActionsSection:{backgroundColor:_sharedUi.night.color.surface,borderRadius:8,borderWidth:1,borderColor:_sharedUi.night.color.border,padding:12,gap:10},quickActionsTitle:{fontSize:10,fontWeight:"600",color:_sharedUi.night.color.textTertiary,letterSpacing:.5,textTransform:"uppercase",marginBottom:2},filterOptionsList:{gap:6},filterOptionCard:{flexDirection:"row",alignItems:"center",backgroundColor:_sharedUi.night.color.surfaceElevated,borderRadius:6,paddingVertical:10,paddingHorizontal:12,borderWidth:1,borderColor:"transparent",gap:10},filterOptionCardSelected:{borderColor:_sharedUi.night.color.accentBorderStrong,backgroundColor:_sharedUi.night.color.accentSoft},filterOptionLabel:{fontSize:10,fontWeight:"600",color:_sharedUi.night.color.textTertiary,minWidth:70},filterOptionLabelSelected:{color:_sharedUi.night.color.accent},filterOptionValue:{fontSize:12,color:_sharedUi.night.color.text,fontFamily:_sharedUi.monoFont,flex:1},filterOptionValueSelected:{color:_sharedUi.night.color.text},filterActionButtons:{flexDirection:"row",gap:8,marginTop:12},filterActionButton:{flexDirection:"row",alignItems:"center",justifyContent:"center",gap:4,paddingVertical:8,paddingHorizontal:10,borderRadius:6,borderWidth:1},filterActionButtonInclude:{backgroundColor:_sharedUi.night.color.accentSoft,borderColor:_sharedUi.night.color.accentBorderStrong},filterActionButtonExclude:{backgroundColor:_sharedUi.night.color.dangerSoft,borderColor:_sharedUi.night.color.danger+"40"},filterActionButtonDisabled:{backgroundColor:_sharedUi.night.color.surfaceElevated,borderColor:_sharedUi.night.color.border,opacity:.5},filterActionButtonText:{fontSize:11,fontWeight:"600"},lockedBanner:{flexDirection:"row",alignItems:"center",justifyContent:"center",backgroundColor:_sharedUi.night.color.surface,borderRadius:8,borderWidth:1,borderColor:_sharedUi.night.color.warning+"40",paddingVertical:12,paddingHorizontal:16,gap:8},lockedBannerText:{color:_sharedUi.night.color.warning,fontSize:13,fontWeight:"600"},lockedBannerSubtext:{color:_sharedUi.night.color.textTertiary,fontSize:12}});var _default=exports.default=RenderDetailView;