@platform-blocks/ui 0.6.0 → 0.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +0 -24
- package/lib/cjs/index.js +476 -720
- package/lib/cjs/index.js.map +1 -1
- package/lib/components/Accordion/types.d.ts +5 -5
- package/lib/components/AutoComplete/types.d.ts +3 -3
- package/lib/components/Avatar/types.d.ts +3 -3
- package/lib/components/Badge/types.d.ts +3 -3
- package/lib/components/Block/types.d.ts +2 -2
- package/lib/components/Blockquote/types.d.ts +2 -2
- package/lib/components/Breadcrumbs/types.d.ts +4 -4
- package/lib/components/Calendar/types.d.ts +2 -2
- package/lib/components/Carousel/types.d.ts +3 -3
- package/lib/components/Chip/types.d.ts +3 -3
- package/lib/components/CodeBlock/types.d.ts +4 -4
- package/lib/components/ColorPicker/types.d.ts +4 -4
- package/lib/components/CopyButton/types.d.ts +2 -2
- package/lib/components/DatePicker/types.d.ts +2 -2
- package/lib/components/Dialog/Dialog.d.ts +1 -1
- package/lib/components/Dialog/types.d.ts +23 -2
- package/lib/components/Divider/types.d.ts +2 -2
- package/lib/components/Grid/types.d.ts +3 -3
- package/lib/components/HoverCard/types.d.ts +3 -3
- package/lib/components/Image/Image.d.ts +1 -1
- package/lib/components/Image/types.d.ts +6 -6
- package/lib/components/Indicator/types.d.ts +2 -2
- package/lib/components/Input/styles.d.ts +1 -12
- package/lib/components/Knob/components/SurfaceLayers.d.ts +2 -2
- package/lib/components/Knob/components/ThumbLayer.d.ts +1 -1
- package/lib/components/Knob/components/TickLayers.d.ts +2 -2
- package/lib/components/Knob/types.d.ts +11 -11
- package/lib/components/Layout/Layout.d.ts +1 -0
- package/lib/components/ListGroup/types.d.ts +4 -4
- package/lib/components/Loader/types.d.ts +2 -2
- package/lib/components/Masonry/types.d.ts +4 -4
- package/lib/components/Menu/types.d.ts +2 -2
- package/lib/components/Navigation/types.d.ts +2 -2
- package/lib/components/Notice/types.d.ts +2 -2
- package/lib/components/Pagination/types.d.ts +6 -6
- package/lib/components/Popover/types.d.ts +5 -5
- package/lib/components/Progress/types.d.ts +3 -3
- package/lib/components/QRCode/types.d.ts +2 -2
- package/lib/components/Rating/types.d.ts +2 -2
- package/lib/components/Ring/types.d.ts +7 -7
- package/lib/components/SegmentedControl/types.d.ts +4 -4
- package/lib/components/Select/Select.types.d.ts +1 -1
- package/lib/components/Skeleton/types.d.ts +4 -4
- package/lib/components/Slider/types.d.ts +7 -7
- package/lib/components/Spotlight/types.d.ts +6 -6
- package/lib/components/Table/Table.d.ts +4 -4
- package/lib/components/Tabs/types.d.ts +5 -5
- package/lib/components/TextArea/types.d.ts +2 -2
- package/lib/components/Timeline/types.d.ts +20 -0
- package/lib/components/Toast/types.d.ts +2 -2
- package/lib/components/Tooltip/types.d.ts +2 -2
- package/lib/components/Video/NativeVideoPlayer.d.ts +2 -2
- package/lib/components/Video/VideoControls.d.ts +2 -2
- package/lib/components/Video/YouTubePlayer.d.ts +2 -2
- package/lib/components/Video/types.d.ts +6 -6
- package/lib/components/Waveform/WaveformSkeleton.d.ts +2 -2
- package/lib/components/Waveform/types.d.ts +2 -2
- package/lib/components/index.d.ts +0 -2
- package/lib/components/types.d.ts +0 -1
- package/lib/core/utils/layout.d.ts +13 -16
- package/lib/core/utils/positioning-enhanced.d.ts +2 -0
- package/lib/esm/index.js +478 -720
- package/lib/esm/index.js.map +1 -1
- package/lib/index.d.ts +0 -4
- package/package.json +67 -57
- package/lib/components/Lottie/Lottie.d.ts +0 -30
- package/lib/components/Lottie/index.d.ts +0 -2
- package/lib/components/RichTextEditor/RichTextEditor.d.ts +0 -3
- package/lib/components/RichTextEditor/index.d.ts +0 -2
- package/lib/components/RichTextEditor/styles.d.ts +0 -61
- package/lib/components/RichTextEditor/types.d.ts +0 -150
package/lib/cjs/index.js
CHANGED
|
@@ -726,16 +726,16 @@ const DARK_THEME = {
|
|
|
726
726
|
'#F2F2F7'
|
|
727
727
|
],
|
|
728
728
|
highlight: [
|
|
729
|
-
'#
|
|
730
|
-
'#
|
|
731
|
-
'#
|
|
732
|
-
'#
|
|
733
|
-
'#
|
|
734
|
-
'#
|
|
735
|
-
'#
|
|
736
|
-
'#
|
|
737
|
-
'#
|
|
738
|
-
'#
|
|
729
|
+
'#1E3A5F', // Deep blue
|
|
730
|
+
'#1E4976', //
|
|
731
|
+
'#1D5A8F', //
|
|
732
|
+
'#2563EB', // Bright blue
|
|
733
|
+
'#3B82F6', // Primary blue
|
|
734
|
+
'#60A5FA', // Light blue
|
|
735
|
+
'#93C5FD', //
|
|
736
|
+
'#BFDBFE', //
|
|
737
|
+
'#DBEAFE', //
|
|
738
|
+
'#EFF6FF' // Very light blue
|
|
739
739
|
],
|
|
740
740
|
pink: [
|
|
741
741
|
'#831843', '#9D174D', '#BE185D', '#DB2777', '#EC4899',
|
|
@@ -791,9 +791,9 @@ const DARK_THEME = {
|
|
|
791
791
|
},
|
|
792
792
|
states: {
|
|
793
793
|
focusRing: 'rgba(10,132,255,0.55)',
|
|
794
|
-
textSelection: 'rgba(
|
|
795
|
-
highlightText: '#
|
|
796
|
-
highlightBackground: 'rgba(
|
|
794
|
+
textSelection: 'rgba(10, 132, 255, 0.25)', // Primary blue for selection
|
|
795
|
+
highlightText: '#60A5FA', // primary[4] - bright blue for good contrast on dark
|
|
796
|
+
highlightBackground: 'rgba(59, 130, 246, 0.35)' // primary[5] with transparency
|
|
797
797
|
},
|
|
798
798
|
fontFamily: '-apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, sans-serif',
|
|
799
799
|
fontSizes: {
|
|
@@ -882,6 +882,8 @@ const DARK_THEME = {
|
|
|
882
882
|
const optionalModuleCache = new Map();
|
|
883
883
|
const isDev = typeof __DEV__ !== 'undefined' ? __DEV__ : process.env.NODE_ENV !== 'production';
|
|
884
884
|
// Metro bundler requires static string literals for require; keep all optional modules here.
|
|
885
|
+
// NOTE: Do NOT add react-syntax-highlighter here - it causes Metro to fail on native
|
|
886
|
+
// when the package isn't installed. Instead, pass the loader dynamically from web-only code.
|
|
885
887
|
const optionalModuleLoaders = {
|
|
886
888
|
'react-native': () => require('react-native'),
|
|
887
889
|
'expo-clipboard': () => require('expo-clipboard'),
|
|
@@ -890,21 +892,9 @@ const optionalModuleLoaders = {
|
|
|
890
892
|
'expo-document-picker': () => require('expo-document-picker'),
|
|
891
893
|
'react-native-webview': () => require('react-native-webview'),
|
|
892
894
|
'lodash.debounce': () => require('lodash.debounce'),
|
|
893
|
-
'react-syntax-highlighter': () => require('react-syntax-highlighter'),
|
|
894
|
-
'react-syntax-highlighter/dist/esm/languages/prism/jsx': () => require('react-syntax-highlighter/dist/esm/languages/prism/jsx'),
|
|
895
|
-
'react-syntax-highlighter/dist/esm/languages/prism/tsx': () => require('react-syntax-highlighter/dist/esm/languages/prism/tsx'),
|
|
896
|
-
'react-syntax-highlighter/dist/esm/languages/prism/typescript': () => require('react-syntax-highlighter/dist/esm/languages/prism/typescript'),
|
|
897
|
-
'react-syntax-highlighter/dist/esm/languages/prism/javascript': () => require('react-syntax-highlighter/dist/esm/languages/prism/javascript'),
|
|
898
|
-
'react-syntax-highlighter/dist/esm/languages/prism/json': () => require('react-syntax-highlighter/dist/esm/languages/prism/json'),
|
|
899
|
-
'react-syntax-highlighter/dist/esm/languages/prism/bash': () => require('react-syntax-highlighter/dist/esm/languages/prism/bash'),
|
|
900
|
-
'react-syntax-highlighter/dist/esm/styles/prism/prism': () => require('react-syntax-highlighter/dist/esm/styles/prism/prism'),
|
|
901
|
-
'react-syntax-highlighter/dist/esm/styles/prism/vsc-dark-plus': () => require('react-syntax-highlighter/dist/esm/styles/prism/vsc-dark-plus'),
|
|
902
895
|
'expo-audio': () => require('expo-audio'),
|
|
903
896
|
'react-native-gesture-handler': () => require('react-native-gesture-handler'),
|
|
904
897
|
'expo-status-bar': () => require('expo-status-bar'),
|
|
905
|
-
'lottie-react': () => require('lottie-react'),
|
|
906
|
-
'@lottiefiles/dotlottie-react': () => require('@lottiefiles/dotlottie-react'),
|
|
907
|
-
'lottie-react-native': () => require('lottie-react-native'),
|
|
908
898
|
'expo-navigation-bar': () => require('expo-navigation-bar'),
|
|
909
899
|
};
|
|
910
900
|
/**
|
|
@@ -1992,7 +1982,6 @@ function resolveComponentSize(value, scale, options = {}) {
|
|
|
1992
1982
|
}
|
|
1993
1983
|
const firstAvailable = allowed.find(key => scale[key] !== undefined);
|
|
1994
1984
|
if (firstAvailable && scale[firstAvailable] !== undefined) {
|
|
1995
|
-
// eslint-disable-next-line @typescript-eslint/no-non-null-assertion
|
|
1996
1985
|
return scale[firstAvailable];
|
|
1997
1986
|
}
|
|
1998
1987
|
throw new Error('resolveComponentSize: no matching size found in provided scale.');
|
|
@@ -2354,18 +2343,17 @@ function extractSpacingProps(props) {
|
|
|
2354
2343
|
*
|
|
2355
2344
|
* @param props - The layout properties object
|
|
2356
2345
|
* @param props.fullWidth - When true, sets width to 100%
|
|
2357
|
-
* @param props.w -
|
|
2358
|
-
* @param props.
|
|
2359
|
-
* @param props.
|
|
2360
|
-
* @param props.
|
|
2361
|
-
* @param props.
|
|
2362
|
-
* @param props.
|
|
2363
|
-
* @param props.minHeight - Minimum height constraint
|
|
2346
|
+
* @param props.w - Width property (overrides fullWidth)
|
|
2347
|
+
* @param props.h - Height value
|
|
2348
|
+
* @param props.maxW - Maximum width constraint
|
|
2349
|
+
* @param props.minW - Minimum width constraint
|
|
2350
|
+
* @param props.maxH - Maximum height constraint
|
|
2351
|
+
* @param props.minH - Minimum height constraint
|
|
2364
2352
|
*
|
|
2365
2353
|
* @returns A partial ViewStyle object containing the computed layout styles
|
|
2366
2354
|
*
|
|
2367
2355
|
* @remarks
|
|
2368
|
-
* Property precedence for width:
|
|
2356
|
+
* Property precedence for width: w > fullWidth
|
|
2369
2357
|
* The function processes width properties in order of specificity, with more specific
|
|
2370
2358
|
* properties overriding more general ones.
|
|
2371
2359
|
*/
|
|
@@ -2375,43 +2363,38 @@ function getLayoutStyles(props) {
|
|
|
2375
2363
|
if (props.fullWidth) {
|
|
2376
2364
|
styles.width = '100%';
|
|
2377
2365
|
}
|
|
2378
|
-
// Handle
|
|
2366
|
+
// Handle width prop (overrides fullWidth)
|
|
2379
2367
|
if (props.w !== undefined) {
|
|
2380
2368
|
styles.width = props.w;
|
|
2381
2369
|
}
|
|
2382
|
-
|
|
2383
|
-
|
|
2384
|
-
styles.width = props.width;
|
|
2385
|
-
}
|
|
2386
|
-
if (props.height !== undefined) {
|
|
2387
|
-
styles.height = props.height;
|
|
2370
|
+
if (props.h !== undefined) {
|
|
2371
|
+
styles.height = props.h;
|
|
2388
2372
|
}
|
|
2389
|
-
if (props.
|
|
2390
|
-
styles.maxWidth = props.
|
|
2373
|
+
if (props.maxW !== undefined) {
|
|
2374
|
+
styles.maxWidth = props.maxW;
|
|
2391
2375
|
}
|
|
2392
|
-
if (props.
|
|
2393
|
-
styles.minWidth = props.
|
|
2376
|
+
if (props.minW !== undefined) {
|
|
2377
|
+
styles.minWidth = props.minW;
|
|
2394
2378
|
}
|
|
2395
|
-
if (props.
|
|
2396
|
-
styles.maxHeight = props.
|
|
2379
|
+
if (props.maxH !== undefined) {
|
|
2380
|
+
styles.maxHeight = props.maxH;
|
|
2397
2381
|
}
|
|
2398
|
-
if (props.
|
|
2399
|
-
styles.minHeight = props.
|
|
2382
|
+
if (props.minH !== undefined) {
|
|
2383
|
+
styles.minHeight = props.minH;
|
|
2400
2384
|
}
|
|
2401
2385
|
return styles;
|
|
2402
2386
|
}
|
|
2403
2387
|
// Helper to extract layout props from component props
|
|
2404
2388
|
function extractLayoutProps(props) {
|
|
2405
|
-
const { fullWidth, w,
|
|
2389
|
+
const { fullWidth, w, h, maxW, minW, maxH, minH, ...otherProps } = props;
|
|
2406
2390
|
const layoutProps = {
|
|
2407
2391
|
fullWidth,
|
|
2408
2392
|
w,
|
|
2409
|
-
|
|
2410
|
-
|
|
2411
|
-
|
|
2412
|
-
|
|
2413
|
-
|
|
2414
|
-
minHeight
|
|
2393
|
+
h,
|
|
2394
|
+
maxW,
|
|
2395
|
+
minW,
|
|
2396
|
+
maxH,
|
|
2397
|
+
minH
|
|
2415
2398
|
};
|
|
2416
2399
|
return { layoutProps, otherProps };
|
|
2417
2400
|
}
|
|
@@ -2680,7 +2663,7 @@ async function measureAsyncPerformance(name, fn) {
|
|
|
2680
2663
|
const OVERLAY_CACHE_LIMIT = 200;
|
|
2681
2664
|
const overlayPositionCache = new Map();
|
|
2682
2665
|
const formatNumber = (value) => Number.isFinite(value) ? Math.round(value * 100) / 100 : 0;
|
|
2683
|
-
const createOverlayCacheKey = (anchorX, anchorY, anchorWidth, anchorHeight, overlayWidth, overlayHeight, placement, offset, viewport, strategy, flip, shift, boundary) => {
|
|
2666
|
+
const createOverlayCacheKey = (anchorX, anchorY, anchorWidth, anchorHeight, overlayWidth, overlayHeight, placement, offset, viewport, strategy, flip, shift, boundary, matchAnchorWidth) => {
|
|
2684
2667
|
return [
|
|
2685
2668
|
formatNumber(anchorX),
|
|
2686
2669
|
formatNumber(anchorY),
|
|
@@ -2697,6 +2680,7 @@ const createOverlayCacheKey = (anchorX, anchorY, anchorWidth, anchorHeight, over
|
|
|
2697
2680
|
flip ? '1' : '0',
|
|
2698
2681
|
shift ? '1' : '0',
|
|
2699
2682
|
formatNumber(boundary),
|
|
2683
|
+
matchAnchorWidth ? '1' : '0',
|
|
2700
2684
|
reactNative.Platform.OS,
|
|
2701
2685
|
].join('|');
|
|
2702
2686
|
};
|
|
@@ -2742,11 +2726,12 @@ registerViewportListeners();
|
|
|
2742
2726
|
* Enhanced overlay positioning that prevents off-screen rendering with intelligent caching
|
|
2743
2727
|
*/
|
|
2744
2728
|
function calculateOverlayPositionEnhanced(anchor, overlay, options = {}) {
|
|
2745
|
-
const { placement = 'auto', offset = 8, viewport = getViewport(), strategy = 'fixed', flip = true, shift = true, boundary = 8, fallbackPlacements = ['bottom', 'top', 'right', 'left'] } = options;
|
|
2729
|
+
const { placement = 'auto', offset = 8, viewport = getViewport(), strategy = 'fixed', flip = true, shift = true, boundary = 8, fallbackPlacements = ['bottom', 'top', 'right', 'left'], matchAnchorWidth = false, } = options;
|
|
2746
2730
|
// If overlay height is unknown/small (pre-measure), use a heuristic height for decision-making
|
|
2747
2731
|
// This helps avoid choosing "bottom" when near the bottom of the viewport.
|
|
2748
2732
|
const heuristicHeight = Math.max(overlay.height || 0, 240);
|
|
2749
|
-
|
|
2733
|
+
// When matchAnchorWidth is true, use anchor width for overlay width calculations
|
|
2734
|
+
const overlayWidth = matchAnchorWidth ? anchor.width : overlay.width;
|
|
2750
2735
|
const overlayHeight = overlay.height > 0 ? overlay.height : heuristicHeight;
|
|
2751
2736
|
// Account for scroll if using absolute positioning
|
|
2752
2737
|
const scrollX = (reactNative.Platform.OS === 'web' && strategy === 'absolute')
|
|
@@ -2757,7 +2742,7 @@ function calculateOverlayPositionEnhanced(anchor, overlay, options = {}) {
|
|
|
2757
2742
|
const anchorX = anchor.x + scrollX;
|
|
2758
2743
|
const anchorY = anchor.y + scrollY;
|
|
2759
2744
|
// Check cache first
|
|
2760
|
-
const cacheKey = createOverlayCacheKey(anchorX, anchorY, anchor.width, anchor.height, overlayWidth, overlayHeight, placement, offset, viewport, strategy, flip, shift, boundary);
|
|
2745
|
+
const cacheKey = createOverlayCacheKey(anchorX, anchorY, anchor.width, anchor.height, overlayWidth, overlayHeight, placement, offset, viewport, strategy, flip, shift, boundary, matchAnchorWidth);
|
|
2761
2746
|
const cached = getCachedOverlayPosition(cacheKey);
|
|
2762
2747
|
if (cached) {
|
|
2763
2748
|
return cached;
|
|
@@ -2825,10 +2810,14 @@ function calculateOverlayPositionEnhanced(anchor, overlay, options = {}) {
|
|
|
2825
2810
|
// If enforcement moved the overlay to the opposite vertical side to avoid covering the anchor,
|
|
2826
2811
|
// reflect that in the returned placement so arrows/styles are consistent.
|
|
2827
2812
|
const resolvedPlacement = adjustPlacementIfMoved(finalPlacement, result, anchorRect);
|
|
2813
|
+
// When matchAnchorWidth is true, preserve anchor width without constraining to maxWidth
|
|
2814
|
+
const computedFinalWidth = matchAnchorWidth
|
|
2815
|
+
? anchor.width
|
|
2816
|
+
: Math.min(result.finalWidth || overlay.width, result.maxWidth || overlay.width);
|
|
2828
2817
|
const finalResult = {
|
|
2829
2818
|
...result,
|
|
2830
2819
|
placement: resolvedPlacement,
|
|
2831
|
-
finalWidth:
|
|
2820
|
+
finalWidth: computedFinalWidth,
|
|
2832
2821
|
finalHeight: Math.min(result.finalHeight || overlay.height, result.maxHeight || overlay.height),
|
|
2833
2822
|
};
|
|
2834
2823
|
// Cache the result
|
|
@@ -3585,9 +3574,14 @@ const Text = (allProps) => {
|
|
|
3585
3574
|
}
|
|
3586
3575
|
// Platform-specific rendering
|
|
3587
3576
|
if (reactNative.Platform.OS === 'web' && isHTMLVariant(htmlTag)) {
|
|
3588
|
-
const
|
|
3589
|
-
|
|
3590
|
-
|
|
3577
|
+
const styleArray = Array.isArray(style) ? style : [style];
|
|
3578
|
+
const hasDisplayOverride = styleArray.some((item) => item && ((item.display !== undefined) || (item.whiteSpace !== undefined)));
|
|
3579
|
+
const webStyles = convertToWebStyles([
|
|
3580
|
+
textStyles,
|
|
3581
|
+
spacingStyles,
|
|
3582
|
+
style,
|
|
3583
|
+
// default to inline unless caller explicitly requests display/whitespace behavior
|
|
3584
|
+
...(hasDisplayOverride ? [] : [{ display: 'inline' }]),
|
|
3591
3585
|
]);
|
|
3592
3586
|
// Handle text selection for web
|
|
3593
3587
|
if (!selectable) {
|
|
@@ -6263,7 +6257,7 @@ const Button = (allProps) => {
|
|
|
6263
6257
|
// Use the actual measured width instead of character-based estimates
|
|
6264
6258
|
const layoutStyles = {
|
|
6265
6259
|
...baseLayoutStyles,
|
|
6266
|
-
...(loading && measuredWidth && !layoutProps.
|
|
6260
|
+
...(loading && measuredWidth && !layoutProps.w && !layoutProps.fullWidth
|
|
6267
6261
|
? { width: measuredWidth, minWidth: measuredWidth }
|
|
6268
6262
|
: {})
|
|
6269
6263
|
};
|
|
@@ -6697,18 +6691,22 @@ const useSafeSafeAreaInsets = () => {
|
|
|
6697
6691
|
return { top: 0, bottom: 0, left: 0, right: 0 };
|
|
6698
6692
|
}
|
|
6699
6693
|
};
|
|
6700
|
-
function Dialog({ visible, variant = 'modal', title, children, closable = true, backdrop = true, backdropClosable = true, shouldClose = false, onClose,
|
|
6694
|
+
function Dialog({ visible, variant = 'modal', title, children, closable = true, backdrop = true, backdropClosable = true, shouldClose = false, onClose, w, h, radius, style, showHeader = true, bottomSheetSwipeZone = 'container', }) {
|
|
6701
6695
|
const theme = useTheme();
|
|
6702
6696
|
const { isRTL } = useDirection();
|
|
6703
6697
|
const insets = useSafeSafeAreaInsets();
|
|
6704
6698
|
const { width: screenWidth, height: screenHeight } = reactNative.useWindowDimensions();
|
|
6705
6699
|
const horizontalMargin = 32; // safety margin so dialog never touches edges
|
|
6706
6700
|
const isNativePlatform = reactNative.Platform.OS === 'ios' || reactNative.Platform.OS === 'android';
|
|
6707
|
-
const defaultModalMaxWidth = Math.min((
|
|
6701
|
+
const defaultModalMaxWidth = Math.min((w || 500), Math.max(200, screenWidth - horizontalMargin));
|
|
6708
6702
|
const modalEffectiveWidth = variant !== 'modal'
|
|
6709
6703
|
? undefined
|
|
6710
6704
|
: Math.min(defaultModalMaxWidth, screenWidth - horizontalMargin);
|
|
6711
|
-
const bottomSheetMaxWidth = Math.min(
|
|
6705
|
+
const bottomSheetMaxWidth = Math.min(w ? w : (isNativePlatform ? 720 : Math.min(600, screenWidth - horizontalMargin)), screenWidth);
|
|
6706
|
+
const resolvedRadius = radius !== null && radius !== void 0 ? radius : (variant === 'bottomsheet' ? 20 : 16);
|
|
6707
|
+
const resolvedMaxHeight = variant === 'bottomsheet'
|
|
6708
|
+
? (h !== null && h !== void 0 ? h : Math.max(200, screenHeight - insets.top - 24))
|
|
6709
|
+
: (variant === 'fullscreen' ? '100%' : (h || '90%'));
|
|
6712
6710
|
const invokeOnClose = React.useCallback(() => {
|
|
6713
6711
|
onClose === null || onClose === void 0 ? void 0 : onClose();
|
|
6714
6712
|
}, [onClose]);
|
|
@@ -6724,23 +6722,25 @@ function Dialog({ visible, variant = 'modal', title, children, closable = true,
|
|
|
6724
6722
|
}, visible && closable);
|
|
6725
6723
|
// Pan responder for bottomsheet swipe-to-dismiss
|
|
6726
6724
|
const panResponder = React.useRef(reactNative.PanResponder.create({
|
|
6725
|
+
onStartShouldSetPanResponderCapture: () => {
|
|
6726
|
+
// Never capture on touch start — let events reach children (buttons) first
|
|
6727
|
+
return false;
|
|
6728
|
+
},
|
|
6727
6729
|
onStartShouldSetPanResponder: () => {
|
|
6728
|
-
//
|
|
6730
|
+
// Claim in bubble phase (after children had their chance to claim).
|
|
6731
|
+
// If a Button/Pressable already claimed the touch, this won't fire.
|
|
6732
|
+
// If nothing claimed (e.g. drag handle, empty space), we take over for swipe tracking.
|
|
6729
6733
|
return variant === 'bottomsheet' && bottomSheetSwipeZone !== 'none';
|
|
6730
6734
|
},
|
|
6731
|
-
|
|
6732
|
-
//
|
|
6733
|
-
return
|
|
6735
|
+
onMoveShouldSetPanResponderCapture: () => {
|
|
6736
|
+
// Never capture moves — let children handle their own gestures
|
|
6737
|
+
return false;
|
|
6734
6738
|
},
|
|
6735
6739
|
onMoveShouldSetPanResponder: (_, gestureState) => {
|
|
6736
|
-
//
|
|
6740
|
+
// Claim the gesture when there's a clear vertical swipe movement
|
|
6737
6741
|
return variant === 'bottomsheet' && bottomSheetSwipeZone !== 'none' && (Math.abs(gestureState.dy) > Math.abs(gestureState.dx) &&
|
|
6738
6742
|
Math.abs(gestureState.dy) > 2);
|
|
6739
6743
|
},
|
|
6740
|
-
onMoveShouldSetPanResponderCapture: () => {
|
|
6741
|
-
// Already captured on start; keep returning true for consistency
|
|
6742
|
-
return variant === 'bottomsheet' && bottomSheetSwipeZone !== 'none';
|
|
6743
|
-
},
|
|
6744
6744
|
onPanResponderGrant: (evt) => {
|
|
6745
6745
|
// Prevent default browser behavior (text selection, etc.) on web
|
|
6746
6746
|
if (reactNative.Platform.OS === 'web') {
|
|
@@ -6764,20 +6764,12 @@ function Dialog({ visible, variant = 'modal', title, children, closable = true,
|
|
|
6764
6764
|
event.preventDefault();
|
|
6765
6765
|
}
|
|
6766
6766
|
}
|
|
6767
|
-
//
|
|
6768
|
-
const dragDistance = gestureState.dy;
|
|
6769
|
-
|
|
6770
|
-
|
|
6771
|
-
|
|
6772
|
-
|
|
6773
|
-
slideAnim.value = resistedDistance;
|
|
6774
|
-
}
|
|
6775
|
-
else {
|
|
6776
|
-
// Upward movement - apply rubber band effect
|
|
6777
|
-
const upwardResistance = 0.3;
|
|
6778
|
-
const rubberBandDistance = dragDistance * upwardResistance;
|
|
6779
|
-
slideAnim.value = rubberBandDistance;
|
|
6780
|
-
}
|
|
6767
|
+
// Only allow downward movement (dismiss gesture)
|
|
6768
|
+
const dragDistance = Math.max(0, gestureState.dy);
|
|
6769
|
+
// Downward movement - apply subtle resistance for better feel
|
|
6770
|
+
const resistance = 0.8;
|
|
6771
|
+
const resistedDistance = dragDistance * resistance + (dragDistance > 100 ? (dragDistance - 100) * 0.2 : 0);
|
|
6772
|
+
slideAnim.value = resistedDistance;
|
|
6781
6773
|
}
|
|
6782
6774
|
},
|
|
6783
6775
|
onPanResponderRelease: (_, gestureState) => {
|
|
@@ -6934,8 +6926,8 @@ function Dialog({ visible, variant = 'modal', title, children, closable = true,
|
|
|
6934
6926
|
}, [shouldClose]);
|
|
6935
6927
|
const isDark = theme.colorScheme === 'dark';
|
|
6936
6928
|
const surfaceColor = isDark ? theme.backgrounds.surface : '#FFFFFF';
|
|
6937
|
-
|
|
6938
|
-
const headerBg =
|
|
6929
|
+
isDark ? theme.colors.gray[6] : '#E1E3E6';
|
|
6930
|
+
const headerBg = surfaceColor;
|
|
6939
6931
|
const contentBg = surfaceColor;
|
|
6940
6932
|
const dynamicStyles = reactNative.StyleSheet.create({
|
|
6941
6933
|
backdrop: {
|
|
@@ -6946,24 +6938,28 @@ function Dialog({ visible, variant = 'modal', title, children, closable = true,
|
|
|
6946
6938
|
}, // Allow backdropFilter on web
|
|
6947
6939
|
modalContainer: {
|
|
6948
6940
|
backgroundColor: contentBg,
|
|
6949
|
-
borderRadius: variant === 'fullscreen' ? 0 :
|
|
6950
|
-
|
|
6951
|
-
|
|
6941
|
+
borderRadius: variant === 'fullscreen' ? 0 : resolvedRadius,
|
|
6942
|
+
...(variant === 'bottomsheet' ? {
|
|
6943
|
+
borderBottomLeftRadius: 0,
|
|
6944
|
+
borderBottomRightRadius: 0,
|
|
6945
|
+
} : {}),
|
|
6946
|
+
overflow: 'hidden', // Clip content to border radius
|
|
6952
6947
|
// Clamp width to viewport (minus margins) while respecting provided width
|
|
6953
6948
|
maxWidth: variant === 'fullscreen'
|
|
6954
6949
|
? '100%'
|
|
6955
6950
|
: variant === 'bottomsheet'
|
|
6956
6951
|
? bottomSheetMaxWidth
|
|
6957
6952
|
: defaultModalMaxWidth,
|
|
6958
|
-
maxHeight:
|
|
6953
|
+
maxHeight: resolvedMaxHeight,
|
|
6959
6954
|
width: variant === 'fullscreen'
|
|
6960
6955
|
? '100%'
|
|
6961
6956
|
: variant === 'modal'
|
|
6962
6957
|
? modalEffectiveWidth || 'auto'
|
|
6963
6958
|
: '100%',
|
|
6964
|
-
|
|
6965
|
-
|
|
6966
|
-
|
|
6959
|
+
// Fullscreen uses 100% height, others auto-size to content
|
|
6960
|
+
height: variant === 'fullscreen' ? '100%' : undefined,
|
|
6961
|
+
// Only fullscreen should stretch to fill
|
|
6962
|
+
...(variant === 'fullscreen' ? { flex: 1 } : {}),
|
|
6967
6963
|
// Ensure minWidth never exceeds viewport clamp
|
|
6968
6964
|
minWidth: variant === 'modal' ? Math.min(300, Math.max(200, screenWidth - horizontalMargin)) : undefined,
|
|
6969
6965
|
alignSelf: variant === 'bottomsheet' ? 'center' : 'center',
|
|
@@ -6989,24 +6985,27 @@ function Dialog({ visible, variant = 'modal', title, children, closable = true,
|
|
|
6989
6985
|
}
|
|
6990
6986
|
: reactNative.Platform.OS === 'android' && variant !== 'fullscreen'
|
|
6991
6987
|
? { elevation: 16, }
|
|
6992
|
-
:
|
|
6993
|
-
|
|
6994
|
-
|
|
6995
|
-
|
|
6996
|
-
|
|
6988
|
+
: variant === 'fullscreen'
|
|
6989
|
+
? {
|
|
6990
|
+
boxShadow: 'none',
|
|
6991
|
+
height: '100%',
|
|
6992
|
+
position: 'absolute',
|
|
6993
|
+
}
|
|
6994
|
+
: { boxShadow: 'none' }),
|
|
6997
6995
|
}, // Allow boxShadow on web
|
|
6998
6996
|
header: {
|
|
6999
6997
|
alignItems: 'center',
|
|
7000
|
-
backgroundColor: headerBg,
|
|
7001
|
-
borderBottomColor: borderColor,
|
|
7002
|
-
borderBottomWidth: variant
|
|
6998
|
+
backgroundColor: showHeader ? headerBg : 'transparent',
|
|
6999
|
+
// borderBottomColor: showHeader ? borderColor : 'transparent',
|
|
7000
|
+
// borderBottomWidth: showHeader && variant !== 'fullscreen' ? 1 : 0,
|
|
7003
7001
|
flexDirection: isRTL ? 'row-reverse' : 'row',
|
|
7004
7002
|
justifyContent: 'space-between',
|
|
7005
7003
|
padding: 20,
|
|
7004
|
+
paddingBottom: title ? 0 : 20,
|
|
7006
7005
|
},
|
|
7007
7006
|
content: {
|
|
7008
|
-
//
|
|
7009
|
-
...(variant === '
|
|
7007
|
+
// Only fullscreen content should stretch
|
|
7008
|
+
...(variant === 'fullscreen' ? { flex: 1 } : {}),
|
|
7010
7009
|
alignSelf: 'stretch',
|
|
7011
7010
|
backgroundColor: contentBg,
|
|
7012
7011
|
padding: variant === 'fullscreen' ? 0 : 20,
|
|
@@ -7062,8 +7061,10 @@ function Dialog({ visible, variant = 'modal', title, children, closable = true,
|
|
|
7062
7061
|
});
|
|
7063
7062
|
const bottomSheetAnimatedStyle = Animated.useAnimatedStyle(() => {
|
|
7064
7063
|
if (variant === 'bottomsheet') {
|
|
7064
|
+
// Clamp to 0 minimum to prevent seeing "under" the sheet
|
|
7065
|
+
const clampedY = Math.max(0, slideAnim.value);
|
|
7065
7066
|
return {
|
|
7066
|
-
transform: [{ translateY:
|
|
7067
|
+
transform: [{ translateY: clampedY }],
|
|
7067
7068
|
};
|
|
7068
7069
|
}
|
|
7069
7070
|
return {};
|
|
@@ -7080,7 +7081,7 @@ function Dialog({ visible, variant = 'modal', title, children, closable = true,
|
|
|
7080
7081
|
animatedStyle = bottomSheetAnimatedStyle;
|
|
7081
7082
|
}
|
|
7082
7083
|
return (jsxRuntime.jsxs(Animated.View, { style: [dynamicStyles.modalContainer, animatedStyle], ...(variant === 'bottomsheet' && bottomSheetSwipeZone === 'container' && panHandlers ? panHandlers : {}), children: [variant === 'bottomsheet' && (jsxRuntime.jsx(reactNative.View, { style: dynamicStyles.dragHandleContainer, ...(bottomSheetSwipeZone === 'handle' && panHandlers ? panHandlers : {}), children: jsxRuntime.jsx(reactNative.View, { style: dynamicStyles.dragHandle }) })), (title !== null &&
|
|
7083
|
-
title && closable) && (jsxRuntime.jsxs(reactNative.View, { style: dynamicStyles.header, children: [jsxRuntime.jsx(Text, { variant: "h3", color: "text", children: title || '' }), closable && (jsxRuntime.jsx(Button, { variant: "ghost", onPress: handleClose, style: dynamicStyles.closeButton, children: jsxRuntime.jsx(Icon, { name: "x", size: "md" }) }))] })), jsxRuntime.jsx(reactNative.View, { style: [dynamicStyles.content, style], children: children })] }));
|
|
7084
|
+
title && closable) && (jsxRuntime.jsxs(reactNative.View, { style: dynamicStyles.header, children: [jsxRuntime.jsx(Text, { variant: "h3", color: "text", children: title || '' }), closable && variant !== 'bottomsheet' && (jsxRuntime.jsx(Button, { variant: "ghost", onPress: handleClose, style: dynamicStyles.closeButton, children: jsxRuntime.jsx(Icon, { name: "x", size: "md" }) }))] })), jsxRuntime.jsx(reactNative.View, { style: [dynamicStyles.content, style], children: children })] }));
|
|
7084
7085
|
};
|
|
7085
7086
|
return (jsxRuntime.jsx(reactNative.Modal, { visible: visible, transparent: true, animationType: "none", statusBarTranslucent: variant === 'fullscreen', children: jsxRuntime.jsxs(Animated.View, { style: [
|
|
7086
7087
|
dynamicStyles.backdrop,
|
|
@@ -7289,7 +7290,7 @@ function DialogRenderer() {
|
|
|
7289
7290
|
return null;
|
|
7290
7291
|
// Render the topmost dialog
|
|
7291
7292
|
const topDialog = dialogs[dialogs.length - 1];
|
|
7292
|
-
return (jsxRuntime.jsx(Dialog, { visible: true, variant: topDialog.variant, title: topDialog.title, closable: topDialog.closable, backdrop: topDialog.backdrop, backdropClosable: topDialog.backdropClosable, shouldClose: topDialog.isClosing, onClose: () => removeDialog(topDialog.id), children: topDialog.content }));
|
|
7293
|
+
return (jsxRuntime.jsx(Dialog, { visible: true, variant: topDialog.variant, title: topDialog.title, closable: topDialog.closable, backdrop: topDialog.backdrop, backdropClosable: topDialog.backdropClosable, shouldClose: topDialog.isClosing, onClose: () => removeDialog(topDialog.id), w: topDialog.w, h: topDialog.h, radius: topDialog.radius, style: topDialog.style, showHeader: topDialog.showHeader, children: topDialog.content }));
|
|
7293
7294
|
}
|
|
7294
7295
|
|
|
7295
7296
|
const Flex = factory((props, ref) => {
|
|
@@ -8374,7 +8375,14 @@ const getContrastPreference = () => {
|
|
|
8374
8375
|
return 'less';
|
|
8375
8376
|
return 'no-preference';
|
|
8376
8377
|
};
|
|
8377
|
-
const getColorScheme = () => {
|
|
8378
|
+
const getColorScheme = () => {
|
|
8379
|
+
var _a;
|
|
8380
|
+
const scheme = (_a = reactNative.Appearance === null || reactNative.Appearance === void 0 ? void 0 : reactNative.Appearance.getColorScheme) === null || _a === void 0 ? void 0 : _a.call(reactNative.Appearance);
|
|
8381
|
+
// Handle 'unspecified' from newer React Native versions
|
|
8382
|
+
if (scheme === 'light' || scheme === 'dark')
|
|
8383
|
+
return scheme;
|
|
8384
|
+
return 'no-preference';
|
|
8385
|
+
};
|
|
8378
8386
|
const getReducedMotion = async () => {
|
|
8379
8387
|
if (reactNative.Platform.OS === 'web') {
|
|
8380
8388
|
if (typeof window === 'undefined' || typeof window.matchMedia !== 'function')
|
|
@@ -8599,7 +8607,13 @@ function useDeviceInfo(options = {}) {
|
|
|
8599
8607
|
React.useEffect(() => {
|
|
8600
8608
|
var _a;
|
|
8601
8609
|
const colorSubscription = (_a = reactNative.Appearance === null || reactNative.Appearance === void 0 ? void 0 : reactNative.Appearance.addChangeListener) === null || _a === void 0 ? void 0 : _a.call(reactNative.Appearance, ({ colorScheme: scheme }) => {
|
|
8602
|
-
|
|
8610
|
+
// Handle 'unspecified' from newer React Native versions
|
|
8611
|
+
if (scheme === 'light' || scheme === 'dark') {
|
|
8612
|
+
setColorScheme(scheme);
|
|
8613
|
+
}
|
|
8614
|
+
else {
|
|
8615
|
+
setColorScheme('no-preference');
|
|
8616
|
+
}
|
|
8603
8617
|
});
|
|
8604
8618
|
const mediaListeners = [];
|
|
8605
8619
|
let boldSubscription;
|
|
@@ -9144,7 +9158,7 @@ function SpotlightRoot({ query, onQueryChange, children, opened = false, onClose
|
|
|
9144
9158
|
const targetWidth = Math.min(560, Math.max(280, screenWidth - horizontalMargin));
|
|
9145
9159
|
// (Hotkey registration moved to main Spotlight component for access to store.toggle())
|
|
9146
9160
|
const fullscreen = shouldUseModal;
|
|
9147
|
-
return (jsxRuntime.jsx(Dialog, { visible: opened, onClose: onClose, variant: fullscreen ? 'fullscreen' : 'modal', backdrop: true, backdropClosable: true,
|
|
9161
|
+
return (jsxRuntime.jsx(Dialog, { visible: opened, onClose: onClose, variant: fullscreen ? 'fullscreen' : 'modal', backdrop: true, backdropClosable: true, w: fullscreen ? undefined : targetWidth, title: null, style: [
|
|
9148
9162
|
styles$e.spotlightModal,
|
|
9149
9163
|
fullscreen && { width: '100%', height: '100%', maxHeight: '100%', borderRadius: 0, position: 'fixed', top: 0, left: 0 },
|
|
9150
9164
|
!fullscreen && {
|
|
@@ -9706,6 +9720,23 @@ function generateUniversalCSS() {
|
|
|
9706
9720
|
xl: '88em'
|
|
9707
9721
|
};
|
|
9708
9722
|
const universalCSS = `
|
|
9723
|
+
/* Reset browser default input styles to prevent double borders */
|
|
9724
|
+
input, textarea, select {
|
|
9725
|
+
outline: none !important;
|
|
9726
|
+
-webkit-appearance: none !important;
|
|
9727
|
+
-moz-appearance: none !important;
|
|
9728
|
+
appearance: none !important;
|
|
9729
|
+
}
|
|
9730
|
+
|
|
9731
|
+
input:focus, textarea:focus, select:focus {
|
|
9732
|
+
outline: none !important;
|
|
9733
|
+
}
|
|
9734
|
+
|
|
9735
|
+
/* Ensure React Native Web focusable elements don't show browser outlines */
|
|
9736
|
+
[data-focusable="true"]:focus {
|
|
9737
|
+
outline: none !important;
|
|
9738
|
+
}
|
|
9739
|
+
|
|
9709
9740
|
/* Color scheme based visibility */
|
|
9710
9741
|
.platform-blocks-light-hidden {
|
|
9711
9742
|
display: none !important;
|
|
@@ -9752,12 +9783,14 @@ function UniversalCSS() {
|
|
|
9752
9783
|
return;
|
|
9753
9784
|
}
|
|
9754
9785
|
// Check if styles are already injected
|
|
9755
|
-
|
|
9756
|
-
if (
|
|
9786
|
+
let styleElement = document.getElementById('platform-blocks-universal-css');
|
|
9787
|
+
if (styleElement) {
|
|
9788
|
+
// Update content if it exists (in case CSS changed)
|
|
9789
|
+
styleElement.textContent = css;
|
|
9757
9790
|
return;
|
|
9758
9791
|
}
|
|
9759
9792
|
// Create and inject styles
|
|
9760
|
-
|
|
9793
|
+
styleElement = document.createElement('style');
|
|
9761
9794
|
styleElement.id = 'platform-blocks-universal-css';
|
|
9762
9795
|
styleElement.textContent = css;
|
|
9763
9796
|
document.head.appendChild(styleElement);
|
|
@@ -10811,7 +10844,7 @@ const Masonry = factory((props, ref) => {
|
|
|
10811
10844
|
};
|
|
10812
10845
|
const containerStyle = {
|
|
10813
10846
|
...spacingStyle,
|
|
10814
|
-
...style,
|
|
10847
|
+
...reactNative.StyleSheet.flatten(style),
|
|
10815
10848
|
};
|
|
10816
10849
|
// Show loading state
|
|
10817
10850
|
if (loading) {
|
|
@@ -11881,9 +11914,10 @@ const Row = ({ direction = 'row', gap = 'sm', ...props }) => {
|
|
|
11881
11914
|
};
|
|
11882
11915
|
/**
|
|
11883
11916
|
* Column component - alias for Flex with direction="column"
|
|
11917
|
+
* Defaults to fullWidth={true} since vertical layouts typically fill available width
|
|
11884
11918
|
*/
|
|
11885
|
-
const Column = ({ direction = 'column', gap = 'sm', ...props }) => {
|
|
11886
|
-
return jsxRuntime.jsx(Flex, { direction: direction, gap: gap, ...props });
|
|
11919
|
+
const Column = ({ direction = 'column', gap = 'sm', fullWidth = true, ...props }) => {
|
|
11920
|
+
return jsxRuntime.jsx(Flex, { direction: direction, gap: gap, fullWidth: fullWidth, ...props });
|
|
11887
11921
|
};
|
|
11888
11922
|
Row.displayName = 'Row';
|
|
11889
11923
|
|
|
@@ -13998,35 +14032,101 @@ function createNativeHighlighter(theme, isDark, variant = 'code', overrides) {
|
|
|
13998
14032
|
};
|
|
13999
14033
|
}
|
|
14000
14034
|
|
|
14001
|
-
//
|
|
14035
|
+
// Syntax highlighter - only loaded on web, native uses built-in tokenizer
|
|
14036
|
+
// These are initialized lazily on first use to avoid Metro bundling issues
|
|
14002
14037
|
let PrismSyntaxHighlighter = null;
|
|
14003
14038
|
let prismLightTheme = null;
|
|
14004
14039
|
let prismDarkTheme = null;
|
|
14005
|
-
|
|
14006
|
-
|
|
14007
|
-
|
|
14008
|
-
|
|
14009
|
-
|
|
14010
|
-
|
|
14011
|
-
|
|
14012
|
-
|
|
14013
|
-
|
|
14014
|
-
|
|
14040
|
+
let syntaxHighlighterInitialized = false;
|
|
14041
|
+
// Use indirect require via new Function to prevent Metro from statically analyzing imports
|
|
14042
|
+
// Metro bundles ALL require() calls it finds, even in try-catch blocks
|
|
14043
|
+
// new Function() creates a runtime-evaluated require that Metro can't see
|
|
14044
|
+
const safeRequire = (() => {
|
|
14045
|
+
try {
|
|
14046
|
+
// This creates: function(moduleName) { return require(moduleName); }
|
|
14047
|
+
// The string 'require' is not statically analyzable by Metro
|
|
14048
|
+
return new Function('moduleName', 'return require(moduleName)');
|
|
14049
|
+
}
|
|
14050
|
+
catch (_a) {
|
|
14051
|
+
return null;
|
|
14052
|
+
}
|
|
14053
|
+
})();
|
|
14054
|
+
function initSyntaxHighlighter() {
|
|
14055
|
+
if (syntaxHighlighterInitialized)
|
|
14056
|
+
return;
|
|
14057
|
+
syntaxHighlighterInitialized = true;
|
|
14058
|
+
// Only attempt to load on web
|
|
14059
|
+
if (reactNative.Platform.OS !== 'web')
|
|
14060
|
+
return;
|
|
14061
|
+
if (!safeRequire)
|
|
14062
|
+
return;
|
|
14063
|
+
try {
|
|
14064
|
+
const rsh = safeRequire('react-syntax-highlighter');
|
|
14065
|
+
PrismSyntaxHighlighter = rsh.PrismLight;
|
|
14066
|
+
if (PrismSyntaxHighlighter) {
|
|
14067
|
+
// Register languages
|
|
14068
|
+
try {
|
|
14069
|
+
const jsx = safeRequire('react-syntax-highlighter/dist/esm/languages/prism/jsx').default;
|
|
14070
|
+
PrismSyntaxHighlighter.registerLanguage('jsx', jsx);
|
|
14015
14071
|
}
|
|
14016
|
-
|
|
14017
|
-
|
|
14018
|
-
|
|
14019
|
-
|
|
14020
|
-
|
|
14021
|
-
|
|
14022
|
-
|
|
14023
|
-
|
|
14024
|
-
|
|
14025
|
-
|
|
14026
|
-
|
|
14027
|
-
|
|
14028
|
-
|
|
14029
|
-
|
|
14072
|
+
catch (_a) {
|
|
14073
|
+
// Language not available
|
|
14074
|
+
}
|
|
14075
|
+
try {
|
|
14076
|
+
const tsx = safeRequire('react-syntax-highlighter/dist/esm/languages/prism/tsx').default;
|
|
14077
|
+
PrismSyntaxHighlighter.registerLanguage('tsx', tsx);
|
|
14078
|
+
}
|
|
14079
|
+
catch (_b) {
|
|
14080
|
+
// Language not available
|
|
14081
|
+
}
|
|
14082
|
+
try {
|
|
14083
|
+
const ts = safeRequire('react-syntax-highlighter/dist/esm/languages/prism/typescript').default;
|
|
14084
|
+
PrismSyntaxHighlighter.registerLanguage('typescript', ts);
|
|
14085
|
+
}
|
|
14086
|
+
catch (_c) {
|
|
14087
|
+
// Language not available
|
|
14088
|
+
}
|
|
14089
|
+
try {
|
|
14090
|
+
const js = safeRequire('react-syntax-highlighter/dist/esm/languages/prism/javascript').default;
|
|
14091
|
+
PrismSyntaxHighlighter.registerLanguage('javascript', js);
|
|
14092
|
+
}
|
|
14093
|
+
catch (_d) {
|
|
14094
|
+
// Language not available
|
|
14095
|
+
}
|
|
14096
|
+
try {
|
|
14097
|
+
const json = safeRequire('react-syntax-highlighter/dist/esm/languages/prism/json').default;
|
|
14098
|
+
PrismSyntaxHighlighter.registerLanguage('json', json);
|
|
14099
|
+
}
|
|
14100
|
+
catch (_e) {
|
|
14101
|
+
// Language not available
|
|
14102
|
+
}
|
|
14103
|
+
try {
|
|
14104
|
+
const bash = safeRequire('react-syntax-highlighter/dist/esm/languages/prism/bash').default;
|
|
14105
|
+
PrismSyntaxHighlighter.registerLanguage('bash', bash);
|
|
14106
|
+
}
|
|
14107
|
+
catch (_f) {
|
|
14108
|
+
// Language not available
|
|
14109
|
+
}
|
|
14110
|
+
// Load themes
|
|
14111
|
+
try {
|
|
14112
|
+
prismLightTheme = safeRequire('react-syntax-highlighter/dist/esm/styles/prism/prism').default;
|
|
14113
|
+
}
|
|
14114
|
+
catch (_g) {
|
|
14115
|
+
// Theme not available
|
|
14116
|
+
}
|
|
14117
|
+
try {
|
|
14118
|
+
prismDarkTheme = safeRequire('react-syntax-highlighter/dist/esm/styles/prism/vsc-dark-plus').default;
|
|
14119
|
+
}
|
|
14120
|
+
catch (_h) {
|
|
14121
|
+
// Theme not available
|
|
14122
|
+
}
|
|
14123
|
+
}
|
|
14124
|
+
}
|
|
14125
|
+
catch (_j) {
|
|
14126
|
+
// react-syntax-highlighter not installed, will use native fallback
|
|
14127
|
+
if (__DEV__) {
|
|
14128
|
+
console.warn('[platform-blocks] react-syntax-highlighter not found, CodeBlock will use basic formatting');
|
|
14129
|
+
}
|
|
14030
14130
|
}
|
|
14031
14131
|
}
|
|
14032
14132
|
const NO_HIGHLIGHTS = new Set();
|
|
@@ -14250,6 +14350,8 @@ const FloatingCopyControls = ({ visible, code, onCopy, topOffset, isWeb }) => (j
|
|
|
14250
14350
|
}, children: jsxRuntime.jsx(CopyButton, { value: code, onCopy: onCopy, iconOnly: true, size: "sm", tooltip: "Copy code", tooltipPosition: "left", style: { minHeight: 32, minWidth: 32 } }) }));
|
|
14251
14351
|
const CodeBlock = (props) => {
|
|
14252
14352
|
var _a, _b, _c;
|
|
14353
|
+
// Initialize syntax highlighter on first render (web only)
|
|
14354
|
+
React.useMemo(() => initSyntaxHighlighter(), []);
|
|
14253
14355
|
const { children, title, fileName, fileIcon, language = 'tsx', showLineNumbers = false, highlight = true, fullWidth = true, showCopyButton = true, onCopy, style, textStyle, titleStyle, highlightLines, spoiler = false, spoilerMaxHeight = 160, variant = 'code', promptSymbol = '$', githubUrl, fileHeader = false, colors, wrap = true, ...rest } = props;
|
|
14254
14356
|
const { spacingProps, otherProps } = extractSpacingProps(rest);
|
|
14255
14357
|
const spacingStyles = getSpacingStyles(spacingProps);
|
|
@@ -14264,6 +14366,7 @@ const CodeBlock = (props) => {
|
|
|
14264
14366
|
const [hovered, setHovered] = React.useState(false);
|
|
14265
14367
|
const [codeHeight, setCodeHeight] = React.useState(null);
|
|
14266
14368
|
const isWeb = reactNative.Platform.OS === 'web';
|
|
14369
|
+
const webWhitespaceStyle = React.useMemo(() => (isWeb ? { whiteSpace: wrap ? 'pre-wrap' : 'pre', display: 'block' } : null), [isWeb, wrap]);
|
|
14267
14370
|
const showFloatingCopy = showCopyButton && !title && !fileName;
|
|
14268
14371
|
const showCopyVisible = !isWeb ? showFloatingCopy : showFloatingCopy && hovered;
|
|
14269
14372
|
const codeData = React.useMemo(() => {
|
|
@@ -14297,6 +14400,7 @@ const CodeBlock = (props) => {
|
|
|
14297
14400
|
boxSizing: 'border-box',
|
|
14298
14401
|
paddingLeft: showLineNumbers ? 0 : 12,
|
|
14299
14402
|
paddingRight: showLineNumbers ? 0 : 12,
|
|
14403
|
+
whiteSpace: wrap ? 'pre-wrap' : 'pre',
|
|
14300
14404
|
}), [showLineNumbers, wrap]);
|
|
14301
14405
|
const highlightedLineStyle = React.useMemo(() => ({
|
|
14302
14406
|
backgroundColor: highlightBackgroundColor,
|
|
@@ -14308,6 +14412,18 @@ const CodeBlock = (props) => {
|
|
|
14308
14412
|
const tokenLines = React.useMemo(() => (highlight ? nativeHighlighter(codeData.transformed) : null), [highlight, nativeHighlighter, codeData.transformed]);
|
|
14309
14413
|
const shouldVirtualizeNative = !isWeb && codeData.lineCount >= LONG_LIST_THRESHOLD;
|
|
14310
14414
|
const lineHeight = (_c = styles.codeText.lineHeight) !== null && _c !== void 0 ? _c : 18;
|
|
14415
|
+
const normalizeTokenText = React.useCallback((text, tokenIndex) => {
|
|
14416
|
+
if (!isWeb || !text)
|
|
14417
|
+
return text;
|
|
14418
|
+
const replaceSpaces = (value) => value.replace(/\t/g, ' ').replace(/ /g, '\u00A0');
|
|
14419
|
+
if (tokenIndex === 0) {
|
|
14420
|
+
return text.replace(/^[\t ]+/, (match) => replaceSpaces(match));
|
|
14421
|
+
}
|
|
14422
|
+
if (text.trim().length === 0) {
|
|
14423
|
+
return replaceSpaces(text);
|
|
14424
|
+
}
|
|
14425
|
+
return text;
|
|
14426
|
+
}, [isWeb]);
|
|
14311
14427
|
const buildNativeLine = React.useCallback((line, index, appendNewline, includeKey) => {
|
|
14312
14428
|
var _a;
|
|
14313
14429
|
const lineNumber = index + 1;
|
|
@@ -14316,13 +14432,14 @@ const CodeBlock = (props) => {
|
|
|
14316
14432
|
const lineStyles = [
|
|
14317
14433
|
styles.codeText,
|
|
14318
14434
|
textStyle,
|
|
14435
|
+
webWhitespaceStyle,
|
|
14319
14436
|
wrap ? { flexWrap: 'wrap' } : { flexWrap: 'nowrap', width: 'auto' },
|
|
14320
14437
|
];
|
|
14321
14438
|
if (isLineHighlighted) {
|
|
14322
14439
|
lineStyles.push(styles.highlightedLine(isDark, highlightColors));
|
|
14323
14440
|
}
|
|
14324
|
-
return (jsxRuntime.jsxs(Text, { selectable: true, style: lineStyles, children: [showLineNumbers ? (jsxRuntime.jsx(Text, { style: { color: lineNumberColor, opacity: 0.7 }, children: `${String(lineNumber).padStart(lineNumberWidth, ' ')} | ` })) : null, tokens.map((token, tokenIdx) => (jsxRuntime.jsx(Text, { style: { color: token.color }, children: token.text || ' ' }, `${lineNumber}-${tokenIdx}`))), appendNewline ? '\n' : null] }, includeKey ? `line-${lineNumber}` : undefined));
|
|
14325
|
-
}, [fallbackColor, highlightColors, highlightSet, isDark, lineNumberColor, lineNumberWidth, showLineNumbers, styles.codeText, styles.highlightedLine, textStyle, tokenLines, wrap]);
|
|
14441
|
+
return (jsxRuntime.jsxs(Text, { selectable: true, style: lineStyles, children: [showLineNumbers ? (jsxRuntime.jsx(Text, { style: { color: lineNumberColor, opacity: 0.7 }, children: `${String(lineNumber).padStart(lineNumberWidth, ' ')} | ` })) : null, tokens.map((token, tokenIdx) => (jsxRuntime.jsx(Text, { style: { color: token.color }, children: normalizeTokenText(token.text || ' ', tokenIdx) }, `${lineNumber}-${tokenIdx}`))), appendNewline ? '\n' : null] }, includeKey ? `line-${lineNumber}` : undefined));
|
|
14442
|
+
}, [fallbackColor, highlightColors, highlightSet, isDark, lineNumberColor, lineNumberWidth, normalizeTokenText, showLineNumbers, styles.codeText, styles.highlightedLine, textStyle, tokenLines, webWhitespaceStyle, wrap]);
|
|
14326
14443
|
const renderWebCode = React.useMemo(() => {
|
|
14327
14444
|
if (!(isWeb && highlight && PrismSyntaxHighlighter)) {
|
|
14328
14445
|
return null;
|
|
@@ -14336,7 +14453,13 @@ const CodeBlock = (props) => {
|
|
|
14336
14453
|
lineHeight: '18px',
|
|
14337
14454
|
display: 'block',
|
|
14338
14455
|
width: '100%',
|
|
14339
|
-
|
|
14456
|
+
whiteSpace: wrap ? 'pre-wrap' : 'pre',
|
|
14457
|
+
}, codeTagProps: {
|
|
14458
|
+
style: {
|
|
14459
|
+
fontFamily: styles.codeText.fontFamily,
|
|
14460
|
+
whiteSpace: wrap ? 'pre-wrap' : 'pre',
|
|
14461
|
+
},
|
|
14462
|
+
}, wrapLongLines: wrap, wrapLines: wrap, showLineNumbers: prismShowLineNumbers, lineNumberStyle: hideLineNumbersVisually
|
|
14340
14463
|
? { display: 'none' }
|
|
14341
14464
|
: { opacity: 0.55, paddingRight: 12, userSelect: 'none' }, lineProps: (lineNumber) => {
|
|
14342
14465
|
const style = { ...baseLineStyle };
|
|
@@ -14369,20 +14492,21 @@ const CodeBlock = (props) => {
|
|
|
14369
14492
|
]);
|
|
14370
14493
|
const renderNativeCode = React.useMemo(() => {
|
|
14371
14494
|
if (!codeData.lineCount) {
|
|
14372
|
-
return (jsxRuntime.jsx(Text, { selectable: true, style: [styles.codeText, textStyle], children: ' ' }));
|
|
14495
|
+
return (jsxRuntime.jsx(Text, { selectable: true, style: [styles.codeText, textStyle, webWhitespaceStyle], children: ' ' }));
|
|
14373
14496
|
}
|
|
14374
14497
|
if (shouldVirtualizeNative) {
|
|
14375
14498
|
return (jsxRuntime.jsx(reactNative.FlatList, { data: codeData.lines, keyExtractor: (_, index) => `line-${index}`, renderItem: ({ item, index }) => buildNativeLine(item, index, false, false), initialNumToRender: 20, maxToRenderPerBatch: 40, windowSize: 7, removeClippedSubviews: true, getItemLayout: (_, index) => ({ length: lineHeight, offset: lineHeight * index, index }) }));
|
|
14376
14499
|
}
|
|
14377
|
-
return (jsxRuntime.jsx(Text, { selectable: true, style: [styles.codeText, textStyle], children: codeData.lines.map((line, idx) => buildNativeLine(line, idx, idx < codeData.lineCount - 1, true)) }));
|
|
14378
|
-
}, [buildNativeLine, codeData.lineCount, codeData.lines, lineHeight, shouldVirtualizeNative, styles.codeText, textStyle]);
|
|
14500
|
+
return (jsxRuntime.jsx(Text, { selectable: true, style: [styles.codeText, textStyle, webWhitespaceStyle], children: codeData.lines.map((line, idx) => buildNativeLine(line, idx, idx < codeData.lineCount - 1, true)) }));
|
|
14501
|
+
}, [buildNativeLine, codeData.lineCount, codeData.lines, lineHeight, shouldVirtualizeNative, styles.codeText, textStyle, webWhitespaceStyle]);
|
|
14379
14502
|
const codeContent = renderWebCode !== null && renderWebCode !== void 0 ? renderWebCode : renderNativeCode;
|
|
14380
14503
|
const scrollableCodeContent = wrap ? (codeContent) : (jsxRuntime.jsx(reactNative.ScrollView, { horizontal: true, bounces: false, showsHorizontalScrollIndicator: true, showsVerticalScrollIndicator: false, contentContainerStyle: { flexGrow: 1 }, style: { width: '100%' }, children: jsxRuntime.jsx(reactNative.View, { style: { flexGrow: 1 }, children: codeContent }) }));
|
|
14381
14504
|
let wrappedCodeContent = scrollableCodeContent;
|
|
14382
14505
|
if (spoiler) {
|
|
14383
14506
|
wrappedCodeContent = (jsxRuntime.jsx(Spoiler, { maxHeight: spoilerMaxHeight, children: scrollableCodeContent }));
|
|
14384
14507
|
}
|
|
14385
|
-
const
|
|
14508
|
+
const flatStyle = reactNative.StyleSheet.flatten(style);
|
|
14509
|
+
const userHasWidth = Boolean(flatStyle && (flatStyle.width !== undefined || flatStyle.flex !== undefined));
|
|
14386
14510
|
const containerStyle = userHasWidth ? [{ marginBottom: 20 }, style, spacingStyles] : [styles.container, spacingStyles, style];
|
|
14387
14511
|
const showHeaderBar = fileHeader && fileName && variant !== 'terminal';
|
|
14388
14512
|
const inlineTitleVisible = variant === 'code' && (title || fileName);
|
|
@@ -15980,11 +16104,13 @@ const BrandButton = (props) => {
|
|
|
15980
16104
|
return {
|
|
15981
16105
|
backgroundColor: 'transparent',
|
|
15982
16106
|
borderColor: brandConfig.borderColor || brandConfig.backgroundColor,
|
|
16107
|
+
paddingHorizontal: 16,
|
|
15983
16108
|
};
|
|
15984
16109
|
case 'ghost':
|
|
15985
16110
|
return {
|
|
15986
16111
|
backgroundColor: 'transparent',
|
|
15987
16112
|
borderColor: 'transparent',
|
|
16113
|
+
paddingHorizontal: 16,
|
|
15988
16114
|
};
|
|
15989
16115
|
case 'link':
|
|
15990
16116
|
return { backgroundColor: 'transparent', borderColor: 'transparent' };
|
|
@@ -15992,7 +16118,7 @@ const BrandButton = (props) => {
|
|
|
15992
16118
|
return {
|
|
15993
16119
|
backgroundColor: 'white',
|
|
15994
16120
|
borderColor: 'transparent',
|
|
15995
|
-
paddingHorizontal:
|
|
16121
|
+
paddingHorizontal: 16,
|
|
15996
16122
|
minWidth: 0,
|
|
15997
16123
|
height: 'auto',
|
|
15998
16124
|
color: 'black'
|
|
@@ -16001,6 +16127,7 @@ const BrandButton = (props) => {
|
|
|
16001
16127
|
return {
|
|
16002
16128
|
backgroundColor: brandConfig.backgroundColor,
|
|
16003
16129
|
borderColor: brandConfig.borderColor || brandConfig.backgroundColor,
|
|
16130
|
+
paddingHorizontal: 16,
|
|
16004
16131
|
};
|
|
16005
16132
|
}
|
|
16006
16133
|
})();
|
|
@@ -16577,8 +16704,12 @@ const createInputStyles = (theme, isRTL = false) => {
|
|
|
16577
16704
|
// Remove any web-specific styling that could interfere
|
|
16578
16705
|
...(typeof window !== 'undefined' && {
|
|
16579
16706
|
outlineWidth: 0,
|
|
16707
|
+
outlineStyle: 'none',
|
|
16580
16708
|
border: 'none',
|
|
16709
|
+
borderWidth: 0,
|
|
16710
|
+
boxShadow: 'none',
|
|
16581
16711
|
backgroundColor: 'transparent',
|
|
16712
|
+
boxSizing: 'border-box',
|
|
16582
16713
|
}),
|
|
16583
16714
|
},
|
|
16584
16715
|
inputContainer: {
|
|
@@ -17506,7 +17637,7 @@ const TextArea = factory((props, ref) => {
|
|
|
17506
17637
|
const { spacingProps, otherProps: propsAfterSpacing } = extractSpacingProps(props);
|
|
17507
17638
|
const { layoutProps, otherProps } = extractLayoutProps(propsAfterSpacing);
|
|
17508
17639
|
const { value, defaultValue = '', onChangeText, label, disabled = false, required = false, placeholder, error, helperText, description, size = 'md', radius = 'md', rows = 3, minRows = 1, maxRows, autoResize = false, maxLength, showCharCounter = false, resize = 'none', textInputProps = {}, style, testID, clearable, clearButtonLabel, onClear, ...rest } = otherProps;
|
|
17509
|
-
const {
|
|
17640
|
+
const { h } = layoutProps;
|
|
17510
17641
|
const theme = useTheme();
|
|
17511
17642
|
const { getTextAreaStyles } = useTextAreaStyles({ theme });
|
|
17512
17643
|
const [focused, setFocused] = React.useState(false);
|
|
@@ -17570,11 +17701,11 @@ const TextArea = factory((props, ref) => {
|
|
|
17570
17701
|
const inputContainerStyles = [
|
|
17571
17702
|
styles.inputContainer,
|
|
17572
17703
|
radiusStyles,
|
|
17573
|
-
{ height }
|
|
17704
|
+
{ height: h }
|
|
17574
17705
|
];
|
|
17575
17706
|
const textInputStyles = [
|
|
17576
17707
|
styles.textInput,
|
|
17577
|
-
{ height:
|
|
17708
|
+
{ height: h || (autoResize ? currentRows * 24 : rows * 24), // Approximate row height
|
|
17578
17709
|
textAlignVertical: resize === 'none' ? 'top' : undefined,
|
|
17579
17710
|
// Disable resizing by user if resize is 'none'
|
|
17580
17711
|
...(resize === 'none' ? { resizeMode: 'none' } : {})
|
|
@@ -17602,7 +17733,7 @@ const TextArea = factory((props, ref) => {
|
|
|
17602
17733
|
const clearLabel = clearButtonLabel || 'Clear input';
|
|
17603
17734
|
return (jsxRuntime.jsxs(reactNative.View, { style: containerStyles, testID: testID, children: [(label || description) && (jsxRuntime.jsx(FieldHeader, { label: label, description: description, required: required, disabled: disabled, error: !!error })), jsxRuntime.jsxs(reactNative.View, { style: [inputContainerStyles, { position: 'relative' }], children: [jsxRuntime.jsx(reactNative.TextInput, { ref: assignRef,
|
|
17604
17735
|
// style={]}
|
|
17605
|
-
style: { height:
|
|
17736
|
+
style: { height: h || (autoResize ? currentRows * 24 : rows * 24), // Approximate row height
|
|
17606
17737
|
...textInputStyles.reduce((acc, style) => ({ ...acc, ...style }), {}),
|
|
17607
17738
|
textAlignVertical: resize === 'none' ? 'top' : undefined,
|
|
17608
17739
|
// Disable resizing by user if resize is 'none'
|
|
@@ -23928,7 +24059,7 @@ const Select = factory((allProps, ref) => {
|
|
|
23928
24059
|
var _a;
|
|
23929
24060
|
const { spacingProps, otherProps: propsAfterSpacing } = extractSpacingProps(allProps);
|
|
23930
24061
|
const { layoutProps, otherProps } = extractLayoutProps(propsAfterSpacing);
|
|
23931
|
-
const { value: valueProp, defaultValue, onChange, options, placeholder = 'Select…', size = 'md', radius = 'md', disabled, label, helperText, description, error, renderOption, fullWidth,
|
|
24062
|
+
const { value: valueProp, defaultValue, onChange, options, placeholder = 'Select…', size = 'md', radius = 'md', disabled, label, helperText, description, error, renderOption, fullWidth, maxH = 260, closeOnSelect = true, clearable, clearButtonLabel, onClear, refocusAfterSelect, keyboardAvoidance = true, } = otherProps;
|
|
23932
24063
|
const theme = useTheme();
|
|
23933
24064
|
const { shouldUseModal, shouldUseOverlay } = useOverlayMode();
|
|
23934
24065
|
const menuStyles = useMenuStyles();
|
|
@@ -23950,6 +24081,7 @@ const Select = factory((allProps, ref) => {
|
|
|
23950
24081
|
keyboardAvoidance,
|
|
23951
24082
|
closeOnClickOutside: true,
|
|
23952
24083
|
closeOnEscape: true,
|
|
24084
|
+
matchAnchorWidth: true,
|
|
23953
24085
|
onClose: () => setOpen(false),
|
|
23954
24086
|
});
|
|
23955
24087
|
const hasMeasuredDropdownRef = React.useRef(false);
|
|
@@ -24083,11 +24215,11 @@ const Select = factory((allProps, ref) => {
|
|
|
24083
24215
|
}, [position === null || position === void 0 ? void 0 : position.finalWidth, triggerWidth]);
|
|
24084
24216
|
const resolvedDropdownMaxHeight = React.useMemo(() => {
|
|
24085
24217
|
const keyboardMax = typeof (position === null || position === void 0 ? void 0 : position.maxHeight) === 'number' ? position.maxHeight : undefined;
|
|
24086
|
-
if (typeof
|
|
24087
|
-
return keyboardMax ? Math.min(
|
|
24218
|
+
if (typeof maxH === 'number') {
|
|
24219
|
+
return keyboardMax ? Math.min(maxH, keyboardMax) : maxH;
|
|
24088
24220
|
}
|
|
24089
|
-
return keyboardMax !== null && keyboardMax !== void 0 ? keyboardMax :
|
|
24090
|
-
}, [
|
|
24221
|
+
return keyboardMax !== null && keyboardMax !== void 0 ? keyboardMax : maxH;
|
|
24222
|
+
}, [maxH, position === null || position === void 0 ? void 0 : position.maxHeight]);
|
|
24091
24223
|
const handleSelect = React.useCallback((opt) => {
|
|
24092
24224
|
if (opt.disabled)
|
|
24093
24225
|
return;
|
|
@@ -24109,7 +24241,7 @@ const Select = factory((allProps, ref) => {
|
|
|
24109
24241
|
close();
|
|
24110
24242
|
}
|
|
24111
24243
|
}, [closeOnSelect, close, onChange, valueProp, refocusAfterSelect, keyboardManager, focusTrigger, blurTrigger]);
|
|
24112
|
-
const listMaxHeight = resolvedDropdownMaxHeight !== null && resolvedDropdownMaxHeight !== void 0 ? resolvedDropdownMaxHeight :
|
|
24244
|
+
const listMaxHeight = resolvedDropdownMaxHeight !== null && resolvedDropdownMaxHeight !== void 0 ? resolvedDropdownMaxHeight : maxH;
|
|
24113
24245
|
const menu = React.useMemo(() => {
|
|
24114
24246
|
const widthStyle = resolvedDropdownWidth && resolvedDropdownWidth > 0
|
|
24115
24247
|
? { width: resolvedDropdownWidth, minWidth: resolvedDropdownWidth }
|
|
@@ -24122,18 +24254,17 @@ const Select = factory((allProps, ref) => {
|
|
|
24122
24254
|
...(maxHeightStyle !== null && maxHeightStyle !== void 0 ? maxHeightStyle : {}),
|
|
24123
24255
|
...(widthStyle !== null && widthStyle !== void 0 ? widthStyle : {}),
|
|
24124
24256
|
}, children: jsxRuntime.jsx(reactNative.FlatList, { data: options, keyExtractor: o => String(o.value), renderItem: ({ item }) => {
|
|
24125
|
-
var _a;
|
|
24126
24257
|
const selected = item.value === value;
|
|
24127
24258
|
if (renderOption) {
|
|
24128
24259
|
return jsxRuntime.jsx(reactNative.View, { children: renderOption(item, false, selected) });
|
|
24129
24260
|
}
|
|
24130
24261
|
const primaryPalette = theme.colors.primary || [];
|
|
24131
24262
|
const highlightColor = theme.colorScheme === 'dark'
|
|
24132
|
-
? primaryPalette[
|
|
24133
|
-
: primaryPalette[6] || primaryPalette[5] ||
|
|
24263
|
+
? primaryPalette[5] || primaryPalette[4] || '#60A5FA'
|
|
24264
|
+
: primaryPalette[6] || primaryPalette[5] || '#3B82F6';
|
|
24134
24265
|
const baseTextColor = item.disabled ? theme.text.disabled : theme.text.primary;
|
|
24135
|
-
|
|
24136
|
-
return (jsxRuntime.jsx(MenuItemButton, { onPress: () => handleSelect(item), disabled: !!item.disabled, active:
|
|
24266
|
+
item.disabled ? theme.text.disabled : highlightColor;
|
|
24267
|
+
return (jsxRuntime.jsx(MenuItemButton, { onPress: () => handleSelect(item), disabled: !!item.disabled, active: false, tone: "default", hoverTone: "default", activeTone: "default", textColor: baseTextColor, hoverTextColor: baseTextColor, activeTextColor: baseTextColor, startIcon: selected ? jsxRuntime.jsx(Icon, { name: "check", size: 16, color: highlightColor }) : jsxRuntime.jsx(reactNative.View, { style: { width: 16 } }), compact: true, rounded: false, style: { borderRadius: 0 }, children: item.label }));
|
|
24137
24268
|
}, ItemSeparatorComponent: renderOption ? undefined : ListGroupDivider, style: maxHeightStyle, bounces: false }) }) }));
|
|
24138
24269
|
}, [resolvedDropdownWidth, listMaxHeight, menuStyles.dropdown, options, value, renderOption, theme.colors.primary, theme.colors.secondary, theme.colorScheme, theme.text.disabled, theme.text.primary, theme.text.onPrimary, handleSelect]);
|
|
24139
24270
|
React.useEffect(() => {
|
|
@@ -24315,6 +24446,7 @@ const AutoComplete = factory((props, ref) => {
|
|
|
24315
24446
|
offset,
|
|
24316
24447
|
autoUpdate: autoReposition,
|
|
24317
24448
|
fallbackPlacements,
|
|
24449
|
+
matchAnchorWidth: true,
|
|
24318
24450
|
});
|
|
24319
24451
|
// Guard: remember last popover size to avoid re-triggering updatePosition on position-only changes
|
|
24320
24452
|
const lastPopoverSizeRef = React.useRef(null);
|
|
@@ -24338,13 +24470,12 @@ const AutoComplete = factory((props, ref) => {
|
|
|
24338
24470
|
}, radiusStyles), [inputStyleFactory, size, focused, error, disabled, showClearButton, radiusStyles]);
|
|
24339
24471
|
const clearLabel = clearButtonLabel || 'Clear input';
|
|
24340
24472
|
const menuHighlightColor = React.useMemo(() => {
|
|
24341
|
-
var _a;
|
|
24342
24473
|
const primaryPalette = theme.colors.primary || [];
|
|
24343
24474
|
if (theme.colorScheme === 'dark') {
|
|
24344
|
-
return primaryPalette[
|
|
24475
|
+
return primaryPalette[5] || primaryPalette[4] || '#60A5FA';
|
|
24345
24476
|
}
|
|
24346
|
-
return primaryPalette[6] || primaryPalette[5] ||
|
|
24347
|
-
}, [theme.colors.primary, theme.
|
|
24477
|
+
return primaryPalette[6] || primaryPalette[5] || '#3B82F6';
|
|
24478
|
+
}, [theme.colors.primary, theme.colorScheme]);
|
|
24348
24479
|
const selectedCount = (_a = selectedValues === null || selectedValues === void 0 ? void 0 : selectedValues.length) !== null && _a !== void 0 ? _a : 0;
|
|
24349
24480
|
const hasSelectedValues = multiSelect && selectedCount > 0;
|
|
24350
24481
|
const currentQueryRef = React.useRef(query);
|
|
@@ -24662,8 +24793,8 @@ const AutoComplete = factory((props, ref) => {
|
|
|
24662
24793
|
const defaultRenderItem = React.useCallback((item, index, isSelected = false) => {
|
|
24663
24794
|
const highlightQuery = highlightMatches ? currentQueryRef.current : undefined;
|
|
24664
24795
|
const baseTextColor = item.disabled ? theme.text.disabled : theme.text.primary;
|
|
24665
|
-
|
|
24666
|
-
return (jsxRuntime.jsx(MenuItemButton, { onPress: () => handleSelectSuggestion(item), disabled: item.disabled, active:
|
|
24796
|
+
item.disabled ? theme.text.disabled : menuHighlightColor;
|
|
24797
|
+
return (jsxRuntime.jsx(MenuItemButton, { onPress: () => handleSelectSuggestion(item), disabled: item.disabled, active: false, tone: "default", hoverTone: "default", activeTone: "default", textColor: baseTextColor, hoverTextColor: baseTextColor, activeTextColor: baseTextColor, startIcon: isSelected ? jsxRuntime.jsx(Icon, { name: "check", size: 16, color: menuHighlightColor }) : jsxRuntime.jsx(reactNative.View, { style: { width: 16 } }), compact: true, rounded: false, style: [styles.menuItemButton, suggestionItemStyle], ...(reactNative.Platform.OS === 'web' ? {
|
|
24667
24798
|
onMouseDown: (event) => {
|
|
24668
24799
|
if (event === null || event === void 0 ? void 0 : event.preventDefault) {
|
|
24669
24800
|
event.preventDefault();
|
|
@@ -27172,7 +27303,7 @@ const DatePickerInput = React.forwardRef(function DatePickerInputInner({ value,
|
|
|
27172
27303
|
} }));
|
|
27173
27304
|
}
|
|
27174
27305
|
if (dropdownType === 'modal') {
|
|
27175
|
-
return (jsxRuntime.jsxs(reactNative.View, { ref: ref, children: [renderInput(), jsxRuntime.jsx(Dialog, { visible: isOpen, variant: "modal", onClose: handleClose,
|
|
27306
|
+
return (jsxRuntime.jsxs(reactNative.View, { ref: ref, children: [renderInput(), jsxRuntime.jsx(Dialog, { visible: isOpen, variant: "modal", onClose: handleClose, w: numberOfMonths > 1 ? Math.min(700, 380 * numberOfMonths + 40) : 400, title: type === 'range'
|
|
27176
27307
|
? 'Select Date Range'
|
|
27177
27308
|
: type === 'multiple'
|
|
27178
27309
|
? 'Select Dates'
|
|
@@ -27201,7 +27332,7 @@ const DatePickerInput = React.forwardRef(function DatePickerInputInner({ value,
|
|
|
27201
27332
|
backgroundColor: pressed ? theme.colors.primary[6] : theme.colors.primary[5],
|
|
27202
27333
|
}), children: jsxRuntime.jsx(Text, { size: "sm", weight: "semibold", style: { color: 'white' }, children: "Done" }) })] })] }) }))] }) })] }));
|
|
27203
27334
|
}
|
|
27204
|
-
return (jsxRuntime.jsxs(reactNative.View, { ref: ref, children: [renderInput(), jsxRuntime.jsx(Dialog, { visible: isOpen, variant: "modal", onClose: handleClose,
|
|
27335
|
+
return (jsxRuntime.jsxs(reactNative.View, { ref: ref, children: [renderInput(), jsxRuntime.jsx(Dialog, { visible: isOpen, variant: "modal", onClose: handleClose, w: numberOfMonths > 1 ? Math.min(600, 320 * numberOfMonths + 40) : 350, children: jsxRuntime.jsxs(reactNative.View, { ref: focusTrapRef, style: { padding: DESIGN_TOKENS.spacing.lg }, accessible: true, accessibilityLabel: type === 'range'
|
|
27205
27336
|
? 'Date range picker dialog'
|
|
27206
27337
|
: type === 'multiple'
|
|
27207
27338
|
? 'Multiple date picker dialog'
|
|
@@ -27296,7 +27427,7 @@ const MonthPickerInput = React.forwardRef(function MonthPickerInput({ value, def
|
|
|
27296
27427
|
pointerEvents: 'none',
|
|
27297
27428
|
accessible: false,
|
|
27298
27429
|
focusable: false,
|
|
27299
|
-
} }) }), jsxRuntime.jsx(Dialog, { visible: opened, variant: "modal", onClose: handleClose, title: modalTitle,
|
|
27430
|
+
} }) }), jsxRuntime.jsx(Dialog, { visible: opened, variant: "modal", onClose: handleClose, title: modalTitle, w: 360, children: jsxRuntime.jsx(reactNative.View, { style: {
|
|
27300
27431
|
padding: DESIGN_TOKENS.spacing.lg,
|
|
27301
27432
|
}, children: jsxRuntime.jsx(MonthPicker, { ...restMonthPickerProps, value: currentValue, onChange: handleMonthChange, locale: resolvedLocale, size: resolvedSize }) }) })] }));
|
|
27302
27433
|
});
|
|
@@ -27359,7 +27490,7 @@ const YearPickerInput = React.forwardRef(function YearPickerInput({ value, defau
|
|
|
27359
27490
|
pointerEvents: 'none',
|
|
27360
27491
|
accessible: false,
|
|
27361
27492
|
focusable: false,
|
|
27362
|
-
} }) }), jsxRuntime.jsx(Dialog, { visible: opened, variant: "modal", onClose: handleClose, title: modalTitle,
|
|
27493
|
+
} }) }), jsxRuntime.jsx(Dialog, { visible: opened, variant: "modal", onClose: handleClose, title: modalTitle, w: 360, children: jsxRuntime.jsx(reactNative.View, { style: {
|
|
27363
27494
|
padding: DESIGN_TOKENS.spacing.lg,
|
|
27364
27495
|
}, children: jsxRuntime.jsx(YearPicker, { ...restYearPickerProps, value: currentValue, onChange: handleYearChange, size: resolvedSize }) }) })] }));
|
|
27365
27496
|
});
|
|
@@ -27524,7 +27655,7 @@ const TimePickerInput = ({ value, defaultValue, onChange, format = 24, withSecon
|
|
|
27524
27655
|
}
|
|
27525
27656
|
}, label: label, placeholder: is12h ? 'hh:mm AM' : 'hh:mm', endSection: jsxRuntime.jsx(Icon, { name: "clock", size: 16, color: disabled ? theme.text.disabled : theme.text.muted }), disabled: disabled, error: error, helperText: helperText, size: size, fullWidth: fullWidth, clearable: clearable && hasValue, clearButtonLabel: clearButtonLabel, onClear: clearValue }) }), jsxRuntime.jsx(Dialog, { visible: open,
|
|
27526
27657
|
// variant="fullscreen"
|
|
27527
|
-
onClose: handleClose,
|
|
27658
|
+
onClose: handleClose, w: typeof computedPanelWidth === 'number' ? computedPanelWidth : 360, title: title || 'Select Time', children: jsxRuntime.jsxs(reactNative.Pressable, { style: {
|
|
27528
27659
|
flex: 1,
|
|
27529
27660
|
width: '100%',
|
|
27530
27661
|
justifyContent: 'center',
|
|
@@ -28476,303 +28607,6 @@ const EmojiPicker = factory((props, ref) => {
|
|
|
28476
28607
|
});
|
|
28477
28608
|
EmojiPicker.displayName = 'EmojiPicker';
|
|
28478
28609
|
|
|
28479
|
-
function useRichTextEditorStyles() {
|
|
28480
|
-
const theme = useTheme();
|
|
28481
|
-
return React.useMemo(() => reactNative.StyleSheet.create({
|
|
28482
|
-
characterCount: {
|
|
28483
|
-
fontSize: 12,
|
|
28484
|
-
marginTop: 4,
|
|
28485
|
-
textAlign: 'right',
|
|
28486
|
-
},
|
|
28487
|
-
container: {
|
|
28488
|
-
width: '100%',
|
|
28489
|
-
},
|
|
28490
|
-
disabled: {
|
|
28491
|
-
opacity: 0.5,
|
|
28492
|
-
},
|
|
28493
|
-
editorContainer: {
|
|
28494
|
-
backgroundColor: theme.backgrounds.surface,
|
|
28495
|
-
borderColor: theme.backgrounds.border,
|
|
28496
|
-
borderRadius: parseInt(theme.radii.md, 10),
|
|
28497
|
-
borderWidth: 1,
|
|
28498
|
-
overflow: 'hidden',
|
|
28499
|
-
},
|
|
28500
|
-
errorText: {
|
|
28501
|
-
fontSize: 12,
|
|
28502
|
-
marginTop: 4,
|
|
28503
|
-
},
|
|
28504
|
-
helperText: {
|
|
28505
|
-
fontSize: 12,
|
|
28506
|
-
marginTop: 4,
|
|
28507
|
-
},
|
|
28508
|
-
textInput: {
|
|
28509
|
-
fontSize: 16,
|
|
28510
|
-
lineHeight: 24,
|
|
28511
|
-
padding: parseInt(theme.spacing.md, 10),
|
|
28512
|
-
},
|
|
28513
|
-
toolButton: {
|
|
28514
|
-
alignItems: 'center',
|
|
28515
|
-
backgroundColor: 'transparent',
|
|
28516
|
-
borderColor: theme.backgrounds.border,
|
|
28517
|
-
borderRadius: parseInt(theme.radii.sm, 10),
|
|
28518
|
-
borderWidth: 1,
|
|
28519
|
-
height: 32,
|
|
28520
|
-
justifyContent: 'center',
|
|
28521
|
-
width: 32,
|
|
28522
|
-
},
|
|
28523
|
-
toolSeparator: {
|
|
28524
|
-
backgroundColor: theme.backgrounds.border,
|
|
28525
|
-
height: 24,
|
|
28526
|
-
marginHorizontal: 4,
|
|
28527
|
-
width: 1,
|
|
28528
|
-
},
|
|
28529
|
-
toolbar: {
|
|
28530
|
-
backgroundColor: theme.backgrounds.elevated,
|
|
28531
|
-
borderBottomColor: theme.backgrounds.border,
|
|
28532
|
-
borderBottomWidth: 1,
|
|
28533
|
-
},
|
|
28534
|
-
toolbarContent: {
|
|
28535
|
-
alignItems: 'center',
|
|
28536
|
-
flexDirection: 'row',
|
|
28537
|
-
gap: 4,
|
|
28538
|
-
paddingHorizontal: parseInt(theme.spacing.sm, 10),
|
|
28539
|
-
paddingVertical: parseInt(theme.spacing.xs, 10),
|
|
28540
|
-
},
|
|
28541
|
-
}), [theme]);
|
|
28542
|
-
}
|
|
28543
|
-
|
|
28544
|
-
// Default toolbar configuration
|
|
28545
|
-
const DEFAULT_TOOLBAR_TOOLS = [
|
|
28546
|
-
'bold',
|
|
28547
|
-
'italic',
|
|
28548
|
-
'underline',
|
|
28549
|
-
'separator',
|
|
28550
|
-
'heading',
|
|
28551
|
-
'separator',
|
|
28552
|
-
'align',
|
|
28553
|
-
'separator',
|
|
28554
|
-
'list',
|
|
28555
|
-
'separator',
|
|
28556
|
-
'link',
|
|
28557
|
-
'separator',
|
|
28558
|
-
'color',
|
|
28559
|
-
];
|
|
28560
|
-
const RichTextEditor = React.memo(({ defaultValue, value, onChange, onSelectionChange, onFocus, onBlur, placeholder = 'Start typing...', readOnly = false, disabled = false, toolbar = {
|
|
28561
|
-
enabled: true,
|
|
28562
|
-
position: 'top',
|
|
28563
|
-
tools: DEFAULT_TOOLBAR_TOOLS,
|
|
28564
|
-
}, formats = {
|
|
28565
|
-
fontFamilies: ['Arial', 'Georgia', 'Times New Roman', 'Courier New'],
|
|
28566
|
-
fontSizes: [12, 14, 16, 18, 20, 24, 28, 32],
|
|
28567
|
-
colors: ['#000000', '#333333', '#666666', '#999999', '#CCCCCC', '#FF0000', '#00FF00', '#0000FF'],
|
|
28568
|
-
headings: [1, 2, 3, 4, 5, 6],
|
|
28569
|
-
}, images = { enabled: true }, links = { enabled: true, openInNewTab: true }, plugins = [], autosave, spellCheck = true, maxLength, minHeight = 200, maxHeight = 600, className, theme: themeOverride = 'auto', error, helperText, style, ...props }) => {
|
|
28570
|
-
const theme = useTheme();
|
|
28571
|
-
const styles = useRichTextEditorStyles();
|
|
28572
|
-
const [content, setContent] = React.useState(value || defaultValue || { html: '', text: '' });
|
|
28573
|
-
const [selection, setSelection] = React.useState({
|
|
28574
|
-
index: 0,
|
|
28575
|
-
length: 0,
|
|
28576
|
-
});
|
|
28577
|
-
const [activeFormats, setActiveFormats] = React.useState({});
|
|
28578
|
-
const [isFocused, setIsFocused] = React.useState(false);
|
|
28579
|
-
const editorRef = React.useRef(null);
|
|
28580
|
-
const autosaveTimerRef = React.useRef(null);
|
|
28581
|
-
// Update content when value prop changes
|
|
28582
|
-
React.useEffect(() => {
|
|
28583
|
-
if (value && value !== content) {
|
|
28584
|
-
setContent(value);
|
|
28585
|
-
}
|
|
28586
|
-
}, [value]);
|
|
28587
|
-
// Autosave functionality
|
|
28588
|
-
React.useEffect(() => {
|
|
28589
|
-
if ((autosave === null || autosave === void 0 ? void 0 : autosave.enabled) && autosave.onSave) {
|
|
28590
|
-
if (autosaveTimerRef.current) {
|
|
28591
|
-
clearTimeout(autosaveTimerRef.current);
|
|
28592
|
-
}
|
|
28593
|
-
autosaveTimerRef.current = setTimeout(() => {
|
|
28594
|
-
autosave.onSave(content);
|
|
28595
|
-
}, autosave.interval || 5000);
|
|
28596
|
-
return () => {
|
|
28597
|
-
if (autosaveTimerRef.current) {
|
|
28598
|
-
clearTimeout(autosaveTimerRef.current);
|
|
28599
|
-
}
|
|
28600
|
-
};
|
|
28601
|
-
}
|
|
28602
|
-
}, [content, autosave]);
|
|
28603
|
-
const handleContentChange = React.useCallback((text) => {
|
|
28604
|
-
const newContent = {
|
|
28605
|
-
text,
|
|
28606
|
-
html: text, // For now, treating as plain text
|
|
28607
|
-
};
|
|
28608
|
-
setContent(newContent);
|
|
28609
|
-
onChange === null || onChange === void 0 ? void 0 : onChange(newContent);
|
|
28610
|
-
}, [onChange]);
|
|
28611
|
-
const handleSelectionChange = React.useCallback((selection) => {
|
|
28612
|
-
const newSelection = {
|
|
28613
|
-
index: selection.start,
|
|
28614
|
-
length: selection.end - selection.start,
|
|
28615
|
-
format: activeFormats,
|
|
28616
|
-
};
|
|
28617
|
-
setSelection(newSelection);
|
|
28618
|
-
onSelectionChange === null || onSelectionChange === void 0 ? void 0 : onSelectionChange(newSelection);
|
|
28619
|
-
}, [activeFormats, onSelectionChange]);
|
|
28620
|
-
const handleFocus = React.useCallback(() => {
|
|
28621
|
-
setIsFocused(true);
|
|
28622
|
-
onFocus === null || onFocus === void 0 ? void 0 : onFocus();
|
|
28623
|
-
}, [onFocus]);
|
|
28624
|
-
const handleBlur = React.useCallback(() => {
|
|
28625
|
-
setIsFocused(false);
|
|
28626
|
-
onBlur === null || onBlur === void 0 ? void 0 : onBlur();
|
|
28627
|
-
}, [onBlur]);
|
|
28628
|
-
const applyFormat = React.useCallback((format) => {
|
|
28629
|
-
if (readOnly || disabled)
|
|
28630
|
-
return;
|
|
28631
|
-
const newFormats = { ...activeFormats, ...format };
|
|
28632
|
-
setActiveFormats(newFormats);
|
|
28633
|
-
// In a real implementation, this would apply formatting to the selected text
|
|
28634
|
-
// For this demo, we'll just track the format state
|
|
28635
|
-
}, [activeFormats, readOnly, disabled]);
|
|
28636
|
-
const toggleFormat = React.useCallback((formatKey) => {
|
|
28637
|
-
if (readOnly || disabled)
|
|
28638
|
-
return;
|
|
28639
|
-
const currentValue = activeFormats[formatKey];
|
|
28640
|
-
applyFormat({ [formatKey]: !currentValue });
|
|
28641
|
-
}, [activeFormats, applyFormat, readOnly, disabled]);
|
|
28642
|
-
const insertText = React.useCallback((text) => {
|
|
28643
|
-
if (readOnly || disabled)
|
|
28644
|
-
return;
|
|
28645
|
-
const currentText = content.text;
|
|
28646
|
-
const { index } = selection;
|
|
28647
|
-
const newText = currentText.slice(0, index) + text + currentText.slice(index);
|
|
28648
|
-
handleContentChange(newText);
|
|
28649
|
-
}, [content.text, selection, handleContentChange, readOnly, disabled]);
|
|
28650
|
-
const insertLink = React.useCallback(() => {
|
|
28651
|
-
if (!(links === null || links === void 0 ? void 0 : links.enabled) || readOnly || disabled)
|
|
28652
|
-
return;
|
|
28653
|
-
// In a real implementation, this would show a link dialog
|
|
28654
|
-
const url = prompt('Enter URL:');
|
|
28655
|
-
if (url && (!links.validate || links.validate(url))) {
|
|
28656
|
-
applyFormat({ link: url });
|
|
28657
|
-
}
|
|
28658
|
-
}, [links, applyFormat, readOnly, disabled]);
|
|
28659
|
-
React.useCallback(async () => {
|
|
28660
|
-
if (!(images === null || images === void 0 ? void 0 : images.enabled) || readOnly || disabled)
|
|
28661
|
-
return;
|
|
28662
|
-
// In a real implementation, this would show a file picker
|
|
28663
|
-
// For now, we'll just insert a placeholder
|
|
28664
|
-
insertText('[Image]');
|
|
28665
|
-
}, [images, insertText, readOnly, disabled]);
|
|
28666
|
-
React.useCallback((level) => {
|
|
28667
|
-
applyFormat({ heading: level });
|
|
28668
|
-
}, [applyFormat]);
|
|
28669
|
-
const setAlignment = React.useCallback((align) => {
|
|
28670
|
-
applyFormat({ align });
|
|
28671
|
-
}, [applyFormat]);
|
|
28672
|
-
const setList = React.useCallback((listType) => {
|
|
28673
|
-
applyFormat({ list: listType });
|
|
28674
|
-
}, [applyFormat]);
|
|
28675
|
-
const getToolButtonStyle = React.useCallback((isActive) => [
|
|
28676
|
-
styles.toolButton,
|
|
28677
|
-
{
|
|
28678
|
-
backgroundColor: isActive
|
|
28679
|
-
? (theme.colorScheme === 'dark' ? theme.colors.primary[7] : theme.colors.primary[1])
|
|
28680
|
-
: 'transparent',
|
|
28681
|
-
borderColor: isActive ? theme.colors.primary[4] : theme.backgrounds.border,
|
|
28682
|
-
},
|
|
28683
|
-
(disabled || readOnly) && styles.disabled,
|
|
28684
|
-
], [styles.toolButton, theme, disabled, readOnly]);
|
|
28685
|
-
const renderToolButton = React.useCallback((tool, icon, onPress, isActive = false) => (jsxRuntime.jsx(reactNative.TouchableOpacity, { onPress: onPress, disabled: disabled || readOnly, style: getToolButtonStyle(isActive), children: jsxRuntime.jsx(Icon, { name: icon, size: 16, color: isActive ? theme.colors.primary[5] : theme.text.secondary }) }, tool)), [theme, disabled, readOnly, getToolButtonStyle]);
|
|
28686
|
-
const renderToolSeparator = React.useCallback((index) => (jsxRuntime.jsx(reactNative.View, { style: styles.toolSeparator }, `separator-${index}`)), [styles.toolSeparator]);
|
|
28687
|
-
const renderToolbar = React.useCallback(() => {
|
|
28688
|
-
if (!(toolbar === null || toolbar === void 0 ? void 0 : toolbar.enabled))
|
|
28689
|
-
return null;
|
|
28690
|
-
const tools = toolbar.tools || DEFAULT_TOOLBAR_TOOLS;
|
|
28691
|
-
return (jsxRuntime.jsx(reactNative.View, { style: styles.toolbar, children: jsxRuntime.jsx(reactNative.ScrollView, { horizontal: true, showsHorizontalScrollIndicator: false, contentContainerStyle: styles.toolbarContent, children: tools.map((tool, index) => {
|
|
28692
|
-
if (tool === 'separator') {
|
|
28693
|
-
return renderToolSeparator(index);
|
|
28694
|
-
}
|
|
28695
|
-
switch (tool) {
|
|
28696
|
-
case 'bold':
|
|
28697
|
-
return renderToolButton('bold', 'bold', () => toggleFormat('bold'), !!activeFormats.bold);
|
|
28698
|
-
case 'italic':
|
|
28699
|
-
return renderToolButton('italic', 'italic', () => toggleFormat('italic'), !!activeFormats.italic);
|
|
28700
|
-
case 'underline':
|
|
28701
|
-
return renderToolButton('underline', 'underline', () => toggleFormat('underline'), !!activeFormats.underline);
|
|
28702
|
-
case 'strikethrough':
|
|
28703
|
-
return renderToolButton('strikethrough', 'strikethrough', () => toggleFormat('strikethrough'), !!activeFormats.strikethrough);
|
|
28704
|
-
case 'heading':
|
|
28705
|
-
return renderToolButton('heading', 'heading', () => applyFormat({ heading: activeFormats.heading ? null : 2 }), !!activeFormats.heading);
|
|
28706
|
-
case 'align':
|
|
28707
|
-
return renderToolButton('align', 'alignLeft', // Default to left align icon, could be dynamic based on current align
|
|
28708
|
-
() => setAlignment(activeFormats.align === 'left' ? 'center' : 'left'), !!activeFormats.align);
|
|
28709
|
-
case 'list':
|
|
28710
|
-
return renderToolButton('list', 'listUnordered', // Default to unordered list icon, could be dynamic
|
|
28711
|
-
() => setList(activeFormats.list === 'unordered' ? 'ordered' : 'unordered'), !!activeFormats.list);
|
|
28712
|
-
case 'link':
|
|
28713
|
-
return renderToolButton('link', 'link', insertLink, !!activeFormats.link);
|
|
28714
|
-
case 'image':
|
|
28715
|
-
return renderToolButton('image', 'image', () => { }, // TODO: Implement image insertion
|
|
28716
|
-
false);
|
|
28717
|
-
case 'code':
|
|
28718
|
-
return renderToolButton('code', 'code', () => toggleFormat('code'), !!activeFormats.code);
|
|
28719
|
-
case 'quote':
|
|
28720
|
-
return renderToolButton('quote', 'quote', () => toggleFormat('quote'), !!activeFormats.quote);
|
|
28721
|
-
case 'color':
|
|
28722
|
-
return renderToolButton('color', 'color', () => { }, // TODO: Implement color picker
|
|
28723
|
-
!!activeFormats.color);
|
|
28724
|
-
default:
|
|
28725
|
-
return null;
|
|
28726
|
-
}
|
|
28727
|
-
}) }) }));
|
|
28728
|
-
}, [toolbar, theme, activeFormats, renderToolButton, renderToolSeparator, toggleFormat, insertLink, styles.toolbar, styles.toolbarContent]);
|
|
28729
|
-
const renderEditor = React.useCallback(() => (jsxRuntime.jsx(reactNative.View, { style: [
|
|
28730
|
-
styles.editorContainer,
|
|
28731
|
-
{
|
|
28732
|
-
borderColor: isFocused ? theme.colors.primary[5] : theme.backgrounds.border,
|
|
28733
|
-
minHeight,
|
|
28734
|
-
maxHeight,
|
|
28735
|
-
},
|
|
28736
|
-
error && { borderColor: theme.colors.error[5] },
|
|
28737
|
-
(disabled || readOnly) && styles.disabled,
|
|
28738
|
-
], children: jsxRuntime.jsx(reactNative.TextInput, { ref: editorRef, value: content.text, onChangeText: handleContentChange, onSelectionChange: (event) => handleSelectionChange(event.nativeEvent.selection), onFocus: handleFocus, onBlur: handleBlur, placeholder: placeholder, placeholderTextColor: theme.text.muted, multiline: true, textAlignVertical: "top", editable: !disabled && !readOnly, spellCheck: spellCheck, maxLength: maxLength, style: [
|
|
28739
|
-
styles.textInput,
|
|
28740
|
-
reactNative.Platform.OS === 'web' ? { outlineWidth: 0 } : null,
|
|
28741
|
-
{
|
|
28742
|
-
color: theme.text.primary,
|
|
28743
|
-
fontSize: activeFormats.fontSize || 16,
|
|
28744
|
-
fontFamily: activeFormats.fontFamily || theme.fontFamily,
|
|
28745
|
-
fontWeight: activeFormats.bold ? 'bold' : 'normal',
|
|
28746
|
-
fontStyle: activeFormats.italic ? 'italic' : 'normal',
|
|
28747
|
-
textDecorationLine: activeFormats.underline ? 'underline' : 'none',
|
|
28748
|
-
textAlign: activeFormats.align || 'left',
|
|
28749
|
-
},
|
|
28750
|
-
], ...props }) })), [
|
|
28751
|
-
content.text,
|
|
28752
|
-
handleContentChange,
|
|
28753
|
-
handleSelectionChange,
|
|
28754
|
-
handleFocus,
|
|
28755
|
-
handleBlur,
|
|
28756
|
-
placeholder,
|
|
28757
|
-
disabled,
|
|
28758
|
-
readOnly,
|
|
28759
|
-
spellCheck,
|
|
28760
|
-
maxLength,
|
|
28761
|
-
isFocused,
|
|
28762
|
-
theme,
|
|
28763
|
-
minHeight,
|
|
28764
|
-
maxHeight,
|
|
28765
|
-
error,
|
|
28766
|
-
activeFormats,
|
|
28767
|
-
props,
|
|
28768
|
-
styles.editorContainer,
|
|
28769
|
-
styles.disabled,
|
|
28770
|
-
styles.textInput,
|
|
28771
|
-
]);
|
|
28772
|
-
return (jsxRuntime.jsxs(reactNative.View, { style: [styles.container, style], children: [(toolbar === null || toolbar === void 0 ? void 0 : toolbar.position) === 'top' && renderToolbar(), renderEditor(), (toolbar === null || toolbar === void 0 ? void 0 : toolbar.position) === 'bottom' && renderToolbar(), maxLength && (jsxRuntime.jsxs(reactNative.Text, { style: [styles.characterCount, { color: theme.text.secondary }], children: [content.text.length, "/", maxLength] })), error && (jsxRuntime.jsx(reactNative.Text, { style: [styles.errorText, { color: theme.colors.error[5] }], children: error })), helperText && !error && (jsxRuntime.jsx(reactNative.Text, { style: [styles.helperText, { color: theme.text.secondary }], children: helperText }))] }));
|
|
28773
|
-
});
|
|
28774
|
-
RichTextEditor.displayName = 'RichTextEditor';
|
|
28775
|
-
|
|
28776
28610
|
function RatingBase(rawProps, ref) {
|
|
28777
28611
|
const { disclaimerProps: disclaimerData, otherProps: propsAfterDisclaimer } = extractDisclaimerProps(rawProps);
|
|
28778
28612
|
const { spacingProps, otherProps: props } = extractSpacingProps(propsAfterDisclaimer);
|
|
@@ -29524,7 +29358,7 @@ function useMenuContext() {
|
|
|
29524
29358
|
return context;
|
|
29525
29359
|
}
|
|
29526
29360
|
function MenuBase(props, ref) {
|
|
29527
|
-
const { opened: controlledOpened, trigger = 'click', position = 'auto', offset = 4, closeOnClickOutside = true, closeOnEscape = true, onOpen, onClose,
|
|
29361
|
+
const { opened: controlledOpened, trigger = 'click', position = 'auto', offset = 4, closeOnClickOutside = true, closeOnEscape = true, onOpen, onClose, w = 'auto', maxH = 300, shadow = 'md', radius = 'md', children, testID, disabled = false, strategy = reactNative.Platform.OS === 'web' ? 'fixed' : 'portal', ...spacingProps } = props;
|
|
29528
29362
|
const [internalOpened, setInternalOpened] = React.useState(false);
|
|
29529
29363
|
// Derive menu dropdown items from children each render for reactivity
|
|
29530
29364
|
const { menuItems, menuDropdownProps } = React.useMemo(() => {
|
|
@@ -29599,11 +29433,11 @@ function MenuBase(props, ref) {
|
|
|
29599
29433
|
const listGroupStyle = {
|
|
29600
29434
|
...styles.dropdown,
|
|
29601
29435
|
...(dropdownSpacingStyles || {}),
|
|
29602
|
-
maxHeight,
|
|
29436
|
+
maxHeight: maxH,
|
|
29603
29437
|
width: resolvedWidth,
|
|
29604
29438
|
};
|
|
29605
|
-
return (jsxRuntime.jsx(MenuContext.Provider, { value: menuContextValueOpened, children: jsxRuntime.jsx(ListGroup, { variant: "default", size: "sm", style: listGroupStyle, children: scrollable ? (jsxRuntime.jsx(reactNative.ScrollView, { showsVerticalScrollIndicator: false, keyboardShouldPersistTaps: "handled", style: { maxHeight }, children: jsxRuntime.jsx(ListGroupBody, { children: menuItems }) })) : (jsxRuntime.jsx(reactNative.View, { style: { maxHeight, overflow: 'hidden' }, children: jsxRuntime.jsx(ListGroupBody, { children: menuItems }) })) }) }));
|
|
29606
|
-
}, [menuItems, menuDropdownProps, styles.dropdown, dropdownSpacingStyles,
|
|
29439
|
+
return (jsxRuntime.jsx(MenuContext.Provider, { value: menuContextValueOpened, children: jsxRuntime.jsx(ListGroup, { variant: "default", size: "sm", style: listGroupStyle, children: scrollable ? (jsxRuntime.jsx(reactNative.ScrollView, { showsVerticalScrollIndicator: false, keyboardShouldPersistTaps: "handled", style: { maxHeight: maxH }, children: jsxRuntime.jsx(ListGroupBody, { children: menuItems }) })) : (jsxRuntime.jsx(reactNative.View, { style: { maxHeight: maxH, overflow: 'hidden' }, children: jsxRuntime.jsx(ListGroupBody, { children: menuItems }) })) }) }));
|
|
29440
|
+
}, [menuItems, menuDropdownProps, styles.dropdown, dropdownSpacingStyles, maxH, menuContextValueOpened]);
|
|
29607
29441
|
const handleOpen = React.useCallback(async (opts) => {
|
|
29608
29442
|
var _a, _b, _c, _d, _e, _f;
|
|
29609
29443
|
// Use ref to avoid stale isOpened value after async close from backdrop click
|
|
@@ -29635,7 +29469,7 @@ function MenuBase(props, ref) {
|
|
|
29635
29469
|
}
|
|
29636
29470
|
// Calculate base overlay size
|
|
29637
29471
|
const estimatedMenuHeight = 120; // Estimate for typical menu with 3-4 items
|
|
29638
|
-
const resolvedWidth =
|
|
29472
|
+
const resolvedWidth = w === 'target' ? triggerRect.width : (typeof w === 'number' ? w : (w === 'auto' ? 200 : 200));
|
|
29639
29473
|
const overlaySize = {
|
|
29640
29474
|
width: resolvedWidth,
|
|
29641
29475
|
height: estimatedMenuHeight,
|
|
@@ -29703,7 +29537,7 @@ function MenuBase(props, ref) {
|
|
|
29703
29537
|
catch (error) {
|
|
29704
29538
|
console.warn('Failed to open menu:', error);
|
|
29705
29539
|
}
|
|
29706
|
-
}, [disabled,
|
|
29540
|
+
}, [disabled, w, position, offset, strategy, closeOnClickOutside, closeOnEscape, onOpen, menuItems, trigger, buildMenuDropdown, onClose]);
|
|
29707
29541
|
// When menu content changes while open, update overlay content in place
|
|
29708
29542
|
React.useEffect(() => {
|
|
29709
29543
|
var _a;
|
|
@@ -29715,14 +29549,14 @@ function MenuBase(props, ref) {
|
|
|
29715
29549
|
return; // no structural change
|
|
29716
29550
|
lastSignatureRef.current = menuItemsSignature;
|
|
29717
29551
|
const currentId = overlayIdRef.current;
|
|
29718
|
-
const resolvedWidth = (_a = lastResolvedWidthRef.current) !== null && _a !== void 0 ? _a : (typeof
|
|
29552
|
+
const resolvedWidth = (_a = lastResolvedWidthRef.current) !== null && _a !== void 0 ? _a : (typeof w === 'number' ? w : undefined);
|
|
29719
29553
|
const menuDropdown = buildMenuDropdown(resolvedWidth);
|
|
29720
29554
|
if (!menuDropdown)
|
|
29721
29555
|
return;
|
|
29722
29556
|
updateOverlay(currentId, {
|
|
29723
29557
|
content: menuDropdown,
|
|
29724
29558
|
});
|
|
29725
|
-
}, [menuItemsSignature, menuItems, updateOverlay,
|
|
29559
|
+
}, [menuItemsSignature, menuItems, updateOverlay, w, buildMenuDropdown]);
|
|
29726
29560
|
const handleToggle = React.useCallback(() => {
|
|
29727
29561
|
if (isOpenedRef.current) {
|
|
29728
29562
|
handleClose();
|
|
@@ -31145,7 +30979,7 @@ function Avatar({ size = 'md', src, fallback, backgroundColor, textColor = 'whit
|
|
|
31145
30979
|
};
|
|
31146
30980
|
const containerStyle = {
|
|
31147
30981
|
position: 'relative',
|
|
31148
|
-
...style,
|
|
30982
|
+
...reactNative.StyleSheet.flatten(style),
|
|
31149
30983
|
};
|
|
31150
30984
|
const content = (jsxRuntime.jsxs(reactNative.View, { style: containerStyle, children: [jsxRuntime.jsx(reactNative.View, { style: avatarStyle, children: src ? (jsxRuntime.jsx(reactNative.Image, { source: { uri: src }, style: {
|
|
31151
30985
|
width: avatarSize,
|
|
@@ -31166,7 +31000,7 @@ function AvatarGroup({ children, limit, spacing = -8, style, size, bordered = tr
|
|
|
31166
31000
|
const containerStyle = {
|
|
31167
31001
|
flexDirection: 'row',
|
|
31168
31002
|
alignItems: 'center',
|
|
31169
|
-
...style,
|
|
31003
|
+
...reactNative.StyleSheet.flatten(style),
|
|
31170
31004
|
};
|
|
31171
31005
|
const avatarWrapperStyle = (index) => ({
|
|
31172
31006
|
marginLeft: index > 0 ? spacing : 0,
|
|
@@ -31654,7 +31488,7 @@ const DEFAULT_ARROW_SIZE = 7;
|
|
|
31654
31488
|
const PopoverBase = (props, ref) => {
|
|
31655
31489
|
var _a;
|
|
31656
31490
|
const { children, opened: controlledOpened, defaultOpened = false, onChange, onOpen, onClose, onDismiss, trigger = 'click', disabled = false, closeOnClickOutside = true, closeOnEscape = true, clickOutsideEvents, // currently not implemented
|
|
31657
|
-
trapFocus = false, keepMounted = false, returnFocus = false, withinPortal = true, withOverlay = false, overlayProps,
|
|
31491
|
+
trapFocus = false, keepMounted = false, returnFocus = false, withinPortal = true, withOverlay = false, overlayProps, w, minW, minH, maxW, maxH, radius, shadow, zIndex = 300, position = 'bottom', offset = 8, floatingStrategy = 'fixed', middlewares, preventPositionChangeWhenVisible = false, hideDetached = true, viewport, keyboardAvoidance = true, fallbackPlacements, boundary, withRoles = true, id, withArrow = false, arrowSize = DEFAULT_ARROW_SIZE, arrowRadius = 0, arrowOffset = 5, arrowPosition = 'center', onPositionChange, testID, ...rest } = props;
|
|
31658
31492
|
const theme = useTheme();
|
|
31659
31493
|
const { spacingProps } = extractSpacingProps(rest);
|
|
31660
31494
|
const spacingStyles = getSpacingStyles(spacingProps);
|
|
@@ -31871,29 +31705,29 @@ const PopoverBase = (props, ref) => {
|
|
|
31871
31705
|
: undefined;
|
|
31872
31706
|
const widthOverride = (() => {
|
|
31873
31707
|
var _a, _b;
|
|
31874
|
-
if (typeof
|
|
31875
|
-
return
|
|
31876
|
-
if (
|
|
31708
|
+
if (typeof w === 'number')
|
|
31709
|
+
return w;
|
|
31710
|
+
if (w === 'target') {
|
|
31877
31711
|
return (_b = (_a = anchorMeasurementsRef.current) === null || _a === void 0 ? void 0 : _a.width) !== null && _b !== void 0 ? _b : computedFinalWidth;
|
|
31878
31712
|
}
|
|
31879
31713
|
return computedFinalWidth;
|
|
31880
31714
|
})();
|
|
31881
31715
|
const sizeStyles = {};
|
|
31882
|
-
if (typeof
|
|
31883
|
-
sizeStyles.minWidth =
|
|
31884
|
-
if (typeof
|
|
31885
|
-
sizeStyles.minHeight =
|
|
31886
|
-
if (typeof
|
|
31887
|
-
sizeStyles.maxWidth =
|
|
31716
|
+
if (typeof minW === 'number')
|
|
31717
|
+
sizeStyles.minWidth = minW;
|
|
31718
|
+
if (typeof minH === 'number')
|
|
31719
|
+
sizeStyles.minHeight = minH;
|
|
31720
|
+
if (typeof maxW === 'number')
|
|
31721
|
+
sizeStyles.maxWidth = maxW;
|
|
31888
31722
|
const computedMaxHeight = positioningResult.maxHeight;
|
|
31889
31723
|
const resolvedMaxHeight = (() => {
|
|
31890
|
-
if (typeof
|
|
31724
|
+
if (typeof maxH === 'number') {
|
|
31891
31725
|
if (typeof computedMaxHeight === 'number') {
|
|
31892
|
-
return Math.min(
|
|
31726
|
+
return Math.min(maxH, computedMaxHeight);
|
|
31893
31727
|
}
|
|
31894
|
-
return
|
|
31728
|
+
return maxH;
|
|
31895
31729
|
}
|
|
31896
|
-
return typeof computedMaxHeight === 'number' ? computedMaxHeight :
|
|
31730
|
+
return typeof computedMaxHeight === 'number' ? computedMaxHeight : maxH;
|
|
31897
31731
|
})();
|
|
31898
31732
|
if (typeof resolvedMaxHeight === 'number')
|
|
31899
31733
|
sizeStyles.maxHeight = resolvedMaxHeight;
|
|
@@ -31917,7 +31751,7 @@ const PopoverBase = (props, ref) => {
|
|
|
31917
31751
|
zIndex,
|
|
31918
31752
|
});
|
|
31919
31753
|
onPositionChange === null || onPositionChange === void 0 ? void 0 : onPositionChange(positioningResult.placement);
|
|
31920
|
-
}, [opened, dropdownState, positioningResult, popoverRef, showOverlay, hideOverlay, popoverStyles.dropdown, popoverStyles.wrapper,
|
|
31754
|
+
}, [opened, dropdownState, positioningResult, popoverRef, showOverlay, hideOverlay, popoverStyles.dropdown, popoverStyles.wrapper, w, maxH, minW, minH, maxW, withArrow, arrowSize, arrowRadius, arrowOffset, arrowPosition, theme, zIndex, onPositionChange, schedulePositionUpdate, trigger, isPositioning]);
|
|
31921
31755
|
React.useEffect(() => {
|
|
31922
31756
|
return () => {
|
|
31923
31757
|
hideOverlay();
|
|
@@ -32205,7 +32039,7 @@ const getSpacingValue = (spacing, theme) => {
|
|
|
32205
32039
|
// Table Cell Components
|
|
32206
32040
|
const TableTh = (allProps) => {
|
|
32207
32041
|
const { spacingProps, otherProps } = extractSpacingProps(allProps);
|
|
32208
|
-
const { children, w, align = 'left',
|
|
32042
|
+
const { children, w, align = 'left', minW, maxW, flex, widthStrategy = 'auto', style } = otherProps;
|
|
32209
32043
|
const theme = useTheme();
|
|
32210
32044
|
const { isRTL } = useDirection();
|
|
32211
32045
|
// Swap alignment in RTL
|
|
@@ -32236,10 +32070,10 @@ const TableTh = (allProps) => {
|
|
|
32236
32070
|
else if (widthStrategy === 'auto') {
|
|
32237
32071
|
widthStyle.flex = 1;
|
|
32238
32072
|
}
|
|
32239
|
-
if (
|
|
32240
|
-
widthStyle.minWidth =
|
|
32241
|
-
if (
|
|
32242
|
-
widthStyle.maxWidth =
|
|
32073
|
+
if (minW)
|
|
32074
|
+
widthStyle.minWidth = minW;
|
|
32075
|
+
if (maxW)
|
|
32076
|
+
widthStyle.maxWidth = maxW;
|
|
32243
32077
|
return widthStyle;
|
|
32244
32078
|
};
|
|
32245
32079
|
const cellStyle = [
|
|
@@ -32260,7 +32094,7 @@ const TableTh = (allProps) => {
|
|
|
32260
32094
|
};
|
|
32261
32095
|
const TableTd = (allProps) => {
|
|
32262
32096
|
const { spacingProps, otherProps } = extractSpacingProps(allProps);
|
|
32263
|
-
const { children, w, align = 'left',
|
|
32097
|
+
const { children, w, align = 'left', minW, maxW, flex, widthStrategy = 'auto', style } = otherProps;
|
|
32264
32098
|
const theme = useTheme();
|
|
32265
32099
|
const { isRTL } = useDirection();
|
|
32266
32100
|
// Swap alignment in RTL
|
|
@@ -32291,10 +32125,10 @@ const TableTd = (allProps) => {
|
|
|
32291
32125
|
else if (widthStrategy === 'auto') {
|
|
32292
32126
|
widthStyle.flex = 1;
|
|
32293
32127
|
}
|
|
32294
|
-
if (
|
|
32295
|
-
widthStyle.minWidth =
|
|
32296
|
-
if (
|
|
32297
|
-
widthStyle.maxWidth =
|
|
32128
|
+
if (minW)
|
|
32129
|
+
widthStyle.minWidth = minW;
|
|
32130
|
+
if (maxW)
|
|
32131
|
+
widthStyle.maxWidth = maxW;
|
|
32298
32132
|
return widthStyle;
|
|
32299
32133
|
};
|
|
32300
32134
|
const cellStyle = [
|
|
@@ -32373,16 +32207,16 @@ const TableCaption = (allProps) => {
|
|
|
32373
32207
|
// Scroll Container Component
|
|
32374
32208
|
const TableScrollContainer = (allProps) => {
|
|
32375
32209
|
const { spacingProps, otherProps } = extractSpacingProps(allProps);
|
|
32376
|
-
const { children,
|
|
32210
|
+
const { children, minW = 500, maxH, type = 'native', style } = otherProps;
|
|
32377
32211
|
const containerStyle = [
|
|
32378
32212
|
{
|
|
32379
32213
|
width: '100%',
|
|
32380
|
-
maxHeight
|
|
32214
|
+
maxHeight: maxH
|
|
32381
32215
|
},
|
|
32382
32216
|
getSpacingStyles(spacingProps),
|
|
32383
32217
|
style
|
|
32384
32218
|
];
|
|
32385
|
-
const scrollViewStyle =
|
|
32219
|
+
const scrollViewStyle = minW ? { minWidth: minW } : undefined;
|
|
32386
32220
|
return (jsxRuntime.jsx(reactNative.View, { style: containerStyle, children: jsxRuntime.jsx(reactNative.ScrollView, { horizontal: true, showsHorizontalScrollIndicator: reactNative.Platform.OS === 'web', contentContainerStyle: scrollViewStyle, children: jsxRuntime.jsx(reactNative.ScrollView, { style: { flex: 1 }, showsVerticalScrollIndicator: reactNative.Platform.OS === 'web', children: children }) }) }));
|
|
32387
32221
|
};
|
|
32388
32222
|
// Main Table Component
|
|
@@ -33320,7 +33154,7 @@ expandableRowRender, initialExpandedRows = [], expandedRows: controlledExpandedR
|
|
|
33320
33154
|
alignItems: 'center',
|
|
33321
33155
|
marginBottom: DESIGN_TOKENS.spacing.md,
|
|
33322
33156
|
paddingHorizontal: DESIGN_TOKENS.spacing.xs
|
|
33323
|
-
}, children: [jsxRuntime.jsx(Flex, { gap: DESIGN_TOKENS.spacing.md, align: "center", children: selectedRows.length > 0 && bulkActions.length > 0 && (jsxRuntime.jsxs(Flex, { gap: 8, children: [jsxRuntime.jsxs(Text, { variant: "small", colorVariant: "muted", children: [selectedRows.length, " selected"] }), bulkActions.map(action => (jsxRuntime.jsx(Button, { variant: "outline", size: "sm", startIcon: action.icon, onPress: () => action.action(selectedRows, data), children: action.label }, action.key)))] })) }), jsxRuntime.jsxs(Flex, { gap: 8, children: [(searchable || columns.some(c => c.filterable)) && (jsxRuntime.jsxs(Popover, { position: "bottom-end", offset: { mainAxis: 12 },
|
|
33157
|
+
}, children: [jsxRuntime.jsx(Flex, { gap: DESIGN_TOKENS.spacing.md, align: "center", children: selectedRows.length > 0 && bulkActions.length > 0 && (jsxRuntime.jsxs(Flex, { gap: 8, children: [jsxRuntime.jsxs(Text, { variant: "small", colorVariant: "muted", children: [selectedRows.length, " selected"] }), bulkActions.map(action => (jsxRuntime.jsx(Button, { variant: "outline", size: "sm", startIcon: action.icon, onPress: () => action.action(selectedRows, data), children: action.label }, action.key)))] })) }), jsxRuntime.jsxs(Flex, { gap: 8, children: [(searchable || columns.some(c => c.filterable)) && (jsxRuntime.jsxs(Popover, { position: "bottom-end", offset: { mainAxis: 12 }, w: 320, trapFocus: true, children: [jsxRuntime.jsx(Popover.Target, { children: jsxRuntime.jsxs(Button, { variant: "outline", size: "sm", startIcon: jsxRuntime.jsx(Icon, { name: "search", size: 14 }), children: ["Search", (searchValue || activeFilters.length > 0) && (jsxRuntime.jsx(reactNative.View, { style: {
|
|
33324
33158
|
width: 6,
|
|
33325
33159
|
height: 6,
|
|
33326
33160
|
borderRadius: 3,
|
|
@@ -33350,7 +33184,7 @@ expandableRowRender, initialExpandedRows = [], expandedRows: controlledExpandedR
|
|
|
33350
33184
|
}) })), jsxRuntime.jsx(Flex, { direction: "column", gap: DESIGN_TOKENS.spacing.sm, children: columns.filter(c => c.filterable).map(column => {
|
|
33351
33185
|
const currentFilter = getColumnFilter(column.key);
|
|
33352
33186
|
return (jsxRuntime.jsx(reactNative.View, { children: renderFilterControl(column) }, `${column.key}-${(currentFilter === null || currentFilter === void 0 ? void 0 : currentFilter.value) || 'no-filter'}`));
|
|
33353
|
-
}) })] }))] }) })] })), onEditModeChange && (jsxRuntime.jsx(Button, { variant: editMode ? 'filled' : 'outline', size: "sm", onPress: () => onEditModeChange(!editMode), children: editMode ? 'Exit Edit' : 'Edit' })), showColumnVisibilityManager && (jsxRuntime.jsxs(Popover, { position: "bottom-end", offset: { mainAxis: 12 },
|
|
33187
|
+
}) })] }))] }) })] })), onEditModeChange && (jsxRuntime.jsx(Button, { variant: editMode ? 'filled' : 'outline', size: "sm", onPress: () => onEditModeChange(!editMode), children: editMode ? 'Exit Edit' : 'Edit' })), showColumnVisibilityManager && (jsxRuntime.jsxs(Popover, { position: "bottom-end", offset: { mainAxis: 12 }, w: 280, trapFocus: true, children: [jsxRuntime.jsx(Popover.Target, { children: jsxRuntime.jsx(Button, { variant: "outline", size: "sm", startIcon: jsxRuntime.jsx(Icon, { name: "eye", size: 14 }), children: "Columns" }) }), jsxRuntime.jsx(Popover.Dropdown, { children: jsxRuntime.jsxs(reactNative.View, { style: { padding: 8, maxHeight: 300, width: 260 }, children: [jsxRuntime.jsx(ComponentWithDisclaimer, { disclaimer: "Selected view determines the layout style", disclaimerProps: { colorVariant: 'muted', size: 'sm' }, children: jsxRuntime.jsxs(Row, { children: [jsxRuntime.jsx(Button, { size: "xs", title: "Deselect All", variant: hiddenColumns.length === columns.length ? 'filled' : 'outline', onPress: () => setHiddenColumns(columns.map(c => c.key)), style: { marginBottom: 8 } }), jsxRuntime.jsx(Button, { size: "xs", title: "Select All", variant: hiddenColumns.length === 0 ? 'filled' : 'outline', onPress: () => setHiddenColumns([]), style: { marginBottom: 8 } })] }) }), jsxRuntime.jsx(reactNative.ScrollView, { style: { maxHeight: 200 }, children: columns.map(col => (jsxRuntime.jsx(Checkbox, { label: tempHeaderEdits[col.key] || col.header, onChange: () => {
|
|
33354
33188
|
if (hiddenColumns.includes(col.key)) {
|
|
33355
33189
|
setHiddenColumns(prev => prev.filter(h => h !== col.key));
|
|
33356
33190
|
}
|
|
@@ -33724,9 +33558,9 @@ const resolveTokenColor = (token, theme) => {
|
|
|
33724
33558
|
return token; // assume raw color string
|
|
33725
33559
|
};
|
|
33726
33560
|
// Item
|
|
33727
|
-
const TimelineItem = React.forwardRef(({ children, title, bullet, colorVariant, lineVariant = 'solid', color, active, itemIndex = 0, isLastItem = false, itemAlign, ...rest }, ref) => {
|
|
33561
|
+
const TimelineItem = React.forwardRef(({ children, title, timestamp, bullet, colorVariant, lineVariant = 'solid', color, titleColor, descriptionColor, timestampColor, active, itemIndex = 0, isLastItem = false, itemAlign, ...rest }, ref) => {
|
|
33728
33562
|
const theme = useTheme();
|
|
33729
|
-
const { active: timelineActive, color: timelineColor, lineWidth, bulletSize: contextBulletSize, align, reverseActive, size, centerMode, metrics, } = useTimelineContext();
|
|
33563
|
+
const { active: timelineActive, color: timelineColor, lineWidth, bulletSize: contextBulletSize, align, reverseActive, size, centerMode, metrics, titleColor: timelineTitleColor, descriptionColor: timelineDescriptionColor, timestampColor: timelineTimestampColor, } = useTimelineContext();
|
|
33730
33564
|
const sizeConfig = metrics;
|
|
33731
33565
|
const finalBulletSize = contextBulletSize || sizeConfig.bulletSize;
|
|
33732
33566
|
const showAllColored = timelineActive === undefined;
|
|
@@ -33741,6 +33575,9 @@ const TimelineItem = React.forwardRef(({ children, title, bullet, colorVariant,
|
|
|
33741
33575
|
const resolvedItemColor = color
|
|
33742
33576
|
? color
|
|
33743
33577
|
: (colorVariant ? resolveTokenColor(colorVariant, theme) : timelineColor);
|
|
33578
|
+
const resolvedTitleColor = titleColor !== null && titleColor !== void 0 ? titleColor : timelineTitleColor;
|
|
33579
|
+
const resolvedDescriptionColor = descriptionColor !== null && descriptionColor !== void 0 ? descriptionColor : timelineDescriptionColor;
|
|
33580
|
+
const resolvedTimestampColor = timestampColor !== null && timestampColor !== void 0 ? timestampColor : timelineTimestampColor;
|
|
33744
33581
|
// Active logic
|
|
33745
33582
|
const isActive = showAllColored
|
|
33746
33583
|
? true
|
|
@@ -33826,10 +33663,16 @@ const TimelineItem = React.forwardRef(({ children, title, bullet, colorVariant,
|
|
|
33826
33663
|
const getTitleStyle = () => ({
|
|
33827
33664
|
fontSize: sizeConfig.fontSize,
|
|
33828
33665
|
fontWeight: '600',
|
|
33829
|
-
color: theme.text.primary,
|
|
33666
|
+
color: resolvedTitleColor !== null && resolvedTitleColor !== void 0 ? resolvedTitleColor : theme.text.primary,
|
|
33830
33667
|
marginBottom: title && children ? 4 : 0,
|
|
33831
33668
|
textAlign: effectiveAlign === 'right' ? 'right' : 'left',
|
|
33832
33669
|
});
|
|
33670
|
+
const getTimestampStyle = () => ({
|
|
33671
|
+
fontSize: Math.max(10, Math.round(sizeConfig.fontSize * 0.8)),
|
|
33672
|
+
color: resolvedTimestampColor !== null && resolvedTimestampColor !== void 0 ? resolvedTimestampColor : theme.text.secondary,
|
|
33673
|
+
marginBottom: (title || children) ? 4 : 0,
|
|
33674
|
+
textAlign: effectiveAlign === 'right' ? 'right' : 'left',
|
|
33675
|
+
});
|
|
33833
33676
|
const getItemWrapperStyle = () => {
|
|
33834
33677
|
if (centerMode) {
|
|
33835
33678
|
return {
|
|
@@ -33845,36 +33688,53 @@ const TimelineItem = React.forwardRef(({ children, title, bullet, colorVariant,
|
|
|
33845
33688
|
alignItems: 'flex-start',
|
|
33846
33689
|
};
|
|
33847
33690
|
};
|
|
33691
|
+
const applyTextStyle = (nodes, styleOverride) => {
|
|
33692
|
+
if (!styleOverride)
|
|
33693
|
+
return nodes;
|
|
33694
|
+
return React.Children.map(nodes, (child) => {
|
|
33695
|
+
var _a;
|
|
33696
|
+
if (typeof child === 'string' || typeof child === 'number') {
|
|
33697
|
+
return jsxRuntime.jsx(reactNative.Text, { style: styleOverride, children: child });
|
|
33698
|
+
}
|
|
33699
|
+
if (!React.isValidElement(child))
|
|
33700
|
+
return child;
|
|
33701
|
+
const props = child.props || {};
|
|
33702
|
+
const isTextLike = ((_a = child.type) === null || _a === void 0 ? void 0 : _a.displayName) === 'Text' || child.type === reactNative.Text || typeof props.children === 'string';
|
|
33703
|
+
if (isTextLike) {
|
|
33704
|
+
const mergedStyle = Array.isArray(props.style)
|
|
33705
|
+
? [...props.style, styleOverride]
|
|
33706
|
+
: [props.style, styleOverride];
|
|
33707
|
+
return React.cloneElement(child, { style: mergedStyle });
|
|
33708
|
+
}
|
|
33709
|
+
if (props.children) {
|
|
33710
|
+
return React.cloneElement(child, { children: applyTextStyle(props.children, styleOverride) });
|
|
33711
|
+
}
|
|
33712
|
+
return child;
|
|
33713
|
+
});
|
|
33714
|
+
};
|
|
33848
33715
|
if (centerMode) {
|
|
33849
33716
|
// Three column layout: left content | bullet/line | right content
|
|
33850
33717
|
const leftContent = effectiveAlign === 'left' && (title || children);
|
|
33851
33718
|
const rightContent = effectiveAlign === 'right' && (title || children);
|
|
33852
33719
|
// Helper to clone Text children with alignment
|
|
33853
33720
|
const alignChildText = (nodes, side) => {
|
|
33854
|
-
|
|
33855
|
-
|
|
33856
|
-
|
|
33857
|
-
|
|
33858
|
-
|
|
33859
|
-
const isTextLike = ((_a = child.type) === null || _a === void 0 ? void 0 : _a.displayName) === 'Text' || (typeof props.children === 'string');
|
|
33860
|
-
if (isTextLike) {
|
|
33861
|
-
const mergedStyle = Array.isArray(props.style)
|
|
33862
|
-
? [...props.style, { textAlign: side }]
|
|
33863
|
-
: [props.style, { textAlign: side }];
|
|
33864
|
-
return React.cloneElement(child, { style: mergedStyle });
|
|
33865
|
-
}
|
|
33866
|
-
if (props.children) {
|
|
33867
|
-
return React.cloneElement(child, { children: alignChildText(props.children, side) });
|
|
33868
|
-
}
|
|
33869
|
-
return child;
|
|
33870
|
-
});
|
|
33721
|
+
const styleOverride = {
|
|
33722
|
+
textAlign: side,
|
|
33723
|
+
...(resolvedDescriptionColor ? { color: resolvedDescriptionColor } : {}),
|
|
33724
|
+
};
|
|
33725
|
+
return applyTextStyle(nodes, styleOverride);
|
|
33871
33726
|
};
|
|
33872
|
-
return (jsxRuntime.jsxs(reactNative.View, { ref: ref, style: getItemWrapperStyle(), ...rest, children: [jsxRuntime.jsx(reactNative.View, { style: { flex: 1, paddingRight: sizeConfig.spacing, alignItems: 'flex-end' }, children: leftContent && (jsxRuntime.jsxs(reactNative.View, { style: { width: '100%', alignItems: 'flex-end' }, children: [title && jsxRuntime.jsx(reactNative.Text, { style: [getTitleStyle(), { textAlign: 'right' }], children: title }), alignChildText(children, 'right')] })) }), jsxRuntime.jsxs(reactNative.View, { style: { width: finalBulletSize, alignItems: 'center', position: 'relative' }, children: [getLine(), jsxRuntime.jsx(reactNative.View, { style: getBulletStyle(), children: bullet })] }), jsxRuntime.jsx(reactNative.View, { style: { flex: 1, paddingLeft: sizeConfig.spacing, alignItems: 'flex-start' }, children: rightContent && (jsxRuntime.jsxs(reactNative.View, { style: { width: '100%', alignItems: 'flex-start' }, children: [title && jsxRuntime.jsx(reactNative.Text, { style: [getTitleStyle(), { textAlign: 'left' }], children: title }), alignChildText(children, 'left')] })) })] }));
|
|
33727
|
+
return (jsxRuntime.jsxs(reactNative.View, { ref: ref, style: getItemWrapperStyle(), ...rest, children: [jsxRuntime.jsx(reactNative.View, { style: { flex: 1, paddingRight: sizeConfig.spacing, alignItems: 'flex-end' }, children: leftContent && (jsxRuntime.jsxs(reactNative.View, { style: { width: '100%', alignItems: 'flex-end' }, children: [timestamp && (jsxRuntime.jsx(reactNative.Text, { style: [getTimestampStyle(), { textAlign: 'right' }], children: timestamp })), title && jsxRuntime.jsx(reactNative.Text, { style: [getTitleStyle(), { textAlign: 'right' }], children: title }), alignChildText(children, 'right')] })) }), jsxRuntime.jsxs(reactNative.View, { style: { width: finalBulletSize, alignItems: 'center', position: 'relative' }, children: [getLine(), jsxRuntime.jsx(reactNative.View, { style: getBulletStyle(), children: bullet })] }), jsxRuntime.jsx(reactNative.View, { style: { flex: 1, paddingLeft: sizeConfig.spacing, alignItems: 'flex-start' }, children: rightContent && (jsxRuntime.jsxs(reactNative.View, { style: { width: '100%', alignItems: 'flex-start' }, children: [timestamp && (jsxRuntime.jsx(reactNative.Text, { style: [getTimestampStyle(), { textAlign: 'left' }], children: timestamp })), title && jsxRuntime.jsx(reactNative.Text, { style: [getTitleStyle(), { textAlign: 'left' }], children: title }), alignChildText(children, 'left')] })) })] }));
|
|
33873
33728
|
}
|
|
33874
|
-
return (jsxRuntime.jsxs(reactNative.View, { ref: ref, style: getItemWrapperStyle(), ...rest, children: [getLine(), jsxRuntime.jsx(reactNative.View, { style: getBulletStyle(), children: bullet }), (title || children) && (jsxRuntime.jsxs(reactNative.View, { style: getContentStyle(), children: [
|
|
33729
|
+
return (jsxRuntime.jsxs(reactNative.View, { ref: ref, style: getItemWrapperStyle(), ...rest, children: [getLine(), jsxRuntime.jsx(reactNative.View, { style: getBulletStyle(), children: bullet }), (title || children) && (jsxRuntime.jsxs(reactNative.View, { style: getContentStyle(), children: [timestamp && jsxRuntime.jsx(reactNative.Text, { style: getTimestampStyle(), children: timestamp }), title && jsxRuntime.jsx(reactNative.Text, { style: getTitleStyle(), children: title }), resolvedDescriptionColor
|
|
33730
|
+
? applyTextStyle(children, {
|
|
33731
|
+
color: resolvedDescriptionColor,
|
|
33732
|
+
textAlign: effectiveAlign === 'right' ? 'right' : 'left',
|
|
33733
|
+
})
|
|
33734
|
+
: children] }))] }));
|
|
33875
33735
|
});
|
|
33876
33736
|
// Root Timeline
|
|
33877
|
-
const Timeline = React.forwardRef(({ children, active, color, colorVariant, lineWidth, bulletSize, align = 'left', reverseActive = false, size = 'md', centerMode = false, ...rest }, ref) => {
|
|
33737
|
+
const Timeline = React.forwardRef(({ children, active, color, colorVariant, titleColor, descriptionColor, timestampColor, lineWidth, bulletSize, align = 'left', reverseActive = false, size = 'md', centerMode = false, ...rest }, ref) => {
|
|
33878
33738
|
const theme = useTheme();
|
|
33879
33739
|
const clampedSize = clampComponentSize(size, TIMELINE_ALLOWED_SIZES);
|
|
33880
33740
|
const baseMetrics = resolveTimelineMetrics(clampedSize);
|
|
@@ -33896,6 +33756,9 @@ const Timeline = React.forwardRef(({ children, active, color, colorVariant, line
|
|
|
33896
33756
|
size: clampedSize,
|
|
33897
33757
|
metrics,
|
|
33898
33758
|
centerMode,
|
|
33759
|
+
titleColor,
|
|
33760
|
+
descriptionColor,
|
|
33761
|
+
timestampColor,
|
|
33899
33762
|
};
|
|
33900
33763
|
const items = [];
|
|
33901
33764
|
React.Children.forEach(children, (child, index) => {
|
|
@@ -34613,7 +34476,7 @@ const Notice = factory(NoticeBase);
|
|
|
34613
34476
|
Notice.displayName = 'Notice';
|
|
34614
34477
|
|
|
34615
34478
|
function SkeletonBase(props, ref) {
|
|
34616
|
-
const { shape = 'rectangle',
|
|
34479
|
+
const { shape = 'rectangle', w, h, size = 'md', radius, animate = true, animationDuration = 1500, colors, style, testID, ...rest } = props;
|
|
34617
34480
|
const { spacingProps, otherProps } = extractSpacingProps(rest);
|
|
34618
34481
|
const spacingStyles = getSpacingStyles(spacingProps);
|
|
34619
34482
|
const theme = useTheme();
|
|
@@ -34634,36 +34497,36 @@ function SkeletonBase(props, ref) {
|
|
|
34634
34497
|
switch (shape) {
|
|
34635
34498
|
case 'text':
|
|
34636
34499
|
return {
|
|
34637
|
-
width:
|
|
34638
|
-
height:
|
|
34500
|
+
width: w || '100%',
|
|
34501
|
+
height: h || getSpacing('md')
|
|
34639
34502
|
};
|
|
34640
34503
|
case 'chip':
|
|
34641
34504
|
return {
|
|
34642
|
-
width:
|
|
34643
|
-
height:
|
|
34505
|
+
width: w || (sizeValue * 3),
|
|
34506
|
+
height: h || sizeValue
|
|
34644
34507
|
};
|
|
34645
34508
|
case 'avatar':
|
|
34646
34509
|
case 'circle':
|
|
34647
34510
|
return {
|
|
34648
|
-
width:
|
|
34649
|
-
height:
|
|
34511
|
+
width: w || sizeValue,
|
|
34512
|
+
height: h || sizeValue
|
|
34650
34513
|
};
|
|
34651
34514
|
case 'button':
|
|
34652
34515
|
return {
|
|
34653
|
-
width:
|
|
34654
|
-
height:
|
|
34516
|
+
width: w || (sizeValue * 4),
|
|
34517
|
+
height: h || sizeValue
|
|
34655
34518
|
};
|
|
34656
34519
|
case 'card':
|
|
34657
34520
|
return {
|
|
34658
|
-
width:
|
|
34659
|
-
height:
|
|
34521
|
+
width: w || '100%',
|
|
34522
|
+
height: h || (sizeValue * 6)
|
|
34660
34523
|
};
|
|
34661
34524
|
case 'rectangle':
|
|
34662
34525
|
case 'rounded':
|
|
34663
34526
|
default:
|
|
34664
34527
|
return {
|
|
34665
|
-
width:
|
|
34666
|
-
height:
|
|
34528
|
+
width: w || '100%',
|
|
34529
|
+
height: h || sizeValue
|
|
34667
34530
|
};
|
|
34668
34531
|
}
|
|
34669
34532
|
};
|
|
@@ -35731,7 +35594,7 @@ const styles$6 = reactNative.StyleSheet.create({
|
|
|
35731
35594
|
},
|
|
35732
35595
|
});
|
|
35733
35596
|
|
|
35734
|
-
const WaveformSkeleton = ({
|
|
35597
|
+
const WaveformSkeleton = ({ w = 300, h = 60, fullWidth = false, barsCount = 20, }) => {
|
|
35735
35598
|
const theme = useTheme();
|
|
35736
35599
|
const styles = reactNative.StyleSheet.create({
|
|
35737
35600
|
animatedBar: {
|
|
@@ -35747,18 +35610,18 @@ const WaveformSkeleton = ({ width = 300, height = 60, fullWidth = false, barsCou
|
|
|
35747
35610
|
backgroundColor: theme.colors.gray[1],
|
|
35748
35611
|
borderRadius: 4,
|
|
35749
35612
|
flexDirection: 'row',
|
|
35750
|
-
height,
|
|
35613
|
+
height: h,
|
|
35751
35614
|
justifyContent: 'space-between',
|
|
35752
35615
|
paddingHorizontal: 4,
|
|
35753
|
-
width: fullWidth ? '100%' :
|
|
35616
|
+
width: fullWidth ? '100%' : w,
|
|
35754
35617
|
},
|
|
35755
35618
|
});
|
|
35756
35619
|
// Generate random heights for skeleton bars
|
|
35757
35620
|
const barHeights = Array.from({ length: barsCount }, () => Math.random() * 0.6 + 0.2 // Heights between 20% and 80% of container
|
|
35758
35621
|
);
|
|
35759
|
-
const barWidth = fullWidth ? 'auto' : Math.max(1, (
|
|
35622
|
+
const barWidth = fullWidth ? 'auto' : Math.max(1, (w - 40) / barsCount - 2);
|
|
35760
35623
|
return (jsxRuntime.jsx(reactNative.View, { style: styles.container, children: barHeights.map((heightRatio, index) => {
|
|
35761
|
-
const barHeight =
|
|
35624
|
+
const barHeight = h * heightRatio;
|
|
35762
35625
|
const isAnimated = index % 3 === 0; // Animate every 3rd bar for shimmer effect
|
|
35763
35626
|
return (jsxRuntime.jsx(reactNative.View, { style: [
|
|
35764
35627
|
styles.bar,
|
|
@@ -35773,7 +35636,7 @@ const WaveformSkeleton = ({ width = 300, height = 60, fullWidth = false, barsCou
|
|
|
35773
35636
|
}) }));
|
|
35774
35637
|
};
|
|
35775
35638
|
|
|
35776
|
-
const Waveform = React.memo(({ peaks,
|
|
35639
|
+
const Waveform = React.memo(({ peaks, w = 300, h = 60, color = 'primary', barWidth = 2, barGap = 1, strokeWidth = 2, minBarHeight = 1, variant = 'bars', gradientColors, progress = 0, progressColor, interactive = false, normalize = false, fullWidth = false, onSeek, onDragStart, onDrag, onDragEnd, accessibilityLabel, accessibilityHint, style, maxVisibleBars, showProgressLine = false, progressLineStyle, showTimeStamps = false, duration, timeStampInterval,
|
|
35777
35640
|
// New features
|
|
35778
35641
|
loading = false, error, loadingProgress, selection, onSelectionChange, zoomLevel = 1, zoomCenter = 0.5, onZoomChange, enableAnimations = true, showRMS = false, rmsData, markers = [], enablePerformanceMonitoring = false, onPerformanceMetrics, ...restProps }) => {
|
|
35779
35642
|
const theme = useTheme();
|
|
@@ -35860,12 +35723,12 @@ loading = false, error, loadingProgress, selection, onSelectionChange, zoomLevel
|
|
|
35860
35723
|
targetBars = maxVisibleBars || peaks.length;
|
|
35861
35724
|
}
|
|
35862
35725
|
else {
|
|
35863
|
-
// For fixed
|
|
35864
|
-
const maxBars = Math.floor(
|
|
35726
|
+
// For fixed w, calculate how many bars fit
|
|
35727
|
+
const maxBars = Math.floor(w / totalBarSpace);
|
|
35865
35728
|
targetBars = maxVisibleBars ? Math.min(maxBars, maxVisibleBars) : maxBars;
|
|
35866
35729
|
}
|
|
35867
35730
|
if (targetBars <= 0) {
|
|
35868
|
-
console.warn('Waveform: Not enough
|
|
35731
|
+
console.warn('Waveform: Not enough w to render any bars');
|
|
35869
35732
|
return [];
|
|
35870
35733
|
}
|
|
35871
35734
|
// If we have fewer peaks than target bars, return all peaks
|
|
@@ -35888,7 +35751,7 @@ loading = false, error, loadingProgress, selection, onSelectionChange, zoomLevel
|
|
|
35888
35751
|
downsampled.push(maxValue);
|
|
35889
35752
|
}
|
|
35890
35753
|
return downsampled;
|
|
35891
|
-
}, [peaks,
|
|
35754
|
+
}, [peaks, w, barWidth, barGap, fullWidth, maxVisibleBars]);
|
|
35892
35755
|
// Normalize peaks if requested
|
|
35893
35756
|
const normalizedPeaks = React.useMemo(() => {
|
|
35894
35757
|
if (!normalize || processedPeaks.length === 0) {
|
|
@@ -35911,16 +35774,16 @@ loading = false, error, loadingProgress, selection, onSelectionChange, zoomLevel
|
|
|
35911
35774
|
if (fullWidth) {
|
|
35912
35775
|
return {
|
|
35913
35776
|
width: '100%',
|
|
35914
|
-
height:
|
|
35915
|
-
viewBox: `0 0 ${actualWaveformWidth} ${
|
|
35777
|
+
height: h,
|
|
35778
|
+
viewBox: `0 0 ${actualWaveformWidth} ${h}`,
|
|
35916
35779
|
preserveAspectRatio: 'none'
|
|
35917
35780
|
};
|
|
35918
35781
|
}
|
|
35919
35782
|
return {
|
|
35920
|
-
width:
|
|
35921
|
-
height:
|
|
35783
|
+
width: w,
|
|
35784
|
+
height: h
|
|
35922
35785
|
};
|
|
35923
|
-
}, [fullWidth, actualWaveformWidth,
|
|
35786
|
+
}, [fullWidth, actualWaveformWidth, h, w]);
|
|
35924
35787
|
const handleLayout = React.useCallback((event) => {
|
|
35925
35788
|
const { width: containerWidth, height: containerHeight } = event.nativeEvent.layout;
|
|
35926
35789
|
setContainerDimensions({ width: containerWidth, height: containerHeight });
|
|
@@ -35935,7 +35798,7 @@ loading = false, error, loadingProgress, selection, onSelectionChange, zoomLevel
|
|
|
35935
35798
|
}
|
|
35936
35799
|
else {
|
|
35937
35800
|
// Fallback if container hasn't been measured yet
|
|
35938
|
-
position = locationX / (
|
|
35801
|
+
position = locationX / (w || 300);
|
|
35939
35802
|
}
|
|
35940
35803
|
}
|
|
35941
35804
|
else {
|
|
@@ -35943,7 +35806,7 @@ loading = false, error, loadingProgress, selection, onSelectionChange, zoomLevel
|
|
|
35943
35806
|
position = Math.min(locationX, actualWaveformWidth) / actualWaveformWidth;
|
|
35944
35807
|
}
|
|
35945
35808
|
return Math.max(0, Math.min(1, position));
|
|
35946
|
-
}, [fullWidth, containerDimensions.width,
|
|
35809
|
+
}, [fullWidth, containerDimensions.width, w, actualWaveformWidth]);
|
|
35947
35810
|
const handleResponderGrant = React.useCallback((event) => {
|
|
35948
35811
|
var _a, _b, _c;
|
|
35949
35812
|
if (!interactive)
|
|
@@ -36030,8 +35893,8 @@ loading = false, error, loadingProgress, selection, onSelectionChange, zoomLevel
|
|
|
36030
35893
|
const renderBars = () => {
|
|
36031
35894
|
return normalizedPeaks.map((peak, index) => {
|
|
36032
35895
|
const x = index * (barWidth + barGap);
|
|
36033
|
-
const barHeight = Math.max(minBarHeight, Math.abs(peak) *
|
|
36034
|
-
const y = (
|
|
35896
|
+
const barHeight = Math.max(minBarHeight, Math.abs(peak) * h * 0.8);
|
|
35897
|
+
const y = (h - barHeight) / 2;
|
|
36035
35898
|
const isProgress = x < progressX;
|
|
36036
35899
|
const fillColor = isProgress ? actualProgressColor : waveformColor;
|
|
36037
35900
|
return (jsxRuntime.jsx(Svg.Rect, { x: x, y: y, width: barWidth, height: barHeight, fill: fillColor, rx: variant === 'rounded' ? barWidth / 2 : 0 }, index));
|
|
@@ -36045,7 +35908,7 @@ loading = false, error, loadingProgress, selection, onSelectionChange, zoomLevel
|
|
|
36045
35908
|
const stepX = actualWaveformWidth / (normalizedPeaks.length - 1);
|
|
36046
35909
|
normalizedPeaks.forEach((peak, index) => {
|
|
36047
35910
|
const x = index * stepX;
|
|
36048
|
-
const y =
|
|
35911
|
+
const y = h / 2 + (peak * h * 0.4);
|
|
36049
35912
|
const lineCommand = index === 0 ? `M ${x} ${y}` : ` L ${x} ${y}`;
|
|
36050
35913
|
pathData += lineCommand;
|
|
36051
35914
|
// Build progress path up to the progress position
|
|
@@ -36059,8 +35922,8 @@ loading = false, error, loadingProgress, selection, onSelectionChange, zoomLevel
|
|
|
36059
35922
|
const renderGradient = () => {
|
|
36060
35923
|
return (jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [jsxRuntime.jsx(Svg.Defs, { children: jsxRuntime.jsx(Svg.LinearGradient, { id: gradientId, x1: "0%", y1: "0%", x2: "100%", y2: "0%", children: resolvedGradientColors.map((color, index) => (jsxRuntime.jsx(Svg.Stop, { offset: `${(index / (resolvedGradientColors.length - 1 || 1)) * 100}%`, stopColor: color }, index))) }) }), normalizedPeaks.map((peak, index) => {
|
|
36061
35924
|
const x = index * (barWidth + barGap);
|
|
36062
|
-
const barHeight = Math.max(minBarHeight, Math.abs(peak) *
|
|
36063
|
-
const y = (
|
|
35925
|
+
const barHeight = Math.max(minBarHeight, Math.abs(peak) * h * 0.8);
|
|
35926
|
+
const y = (h - barHeight) / 2;
|
|
36064
35927
|
return (jsxRuntime.jsx(Svg.Rect, { x: x, y: y, width: barWidth, height: barHeight, fill: `url(#${gradientId})` }, index));
|
|
36065
35928
|
})] }));
|
|
36066
35929
|
};
|
|
@@ -36070,8 +35933,8 @@ loading = false, error, loadingProgress, selection, onSelectionChange, zoomLevel
|
|
|
36070
35933
|
return null;
|
|
36071
35934
|
const clampedProgress = Math.max(0, Math.min(1, progress));
|
|
36072
35935
|
const progressX = clampedProgress * actualWaveformWidth;
|
|
36073
|
-
return (jsxRuntime.jsx(Svg.Line, { x1: progressX, y1: 0, x2: progressX, y2:
|
|
36074
|
-
}, [showProgressLine, progress, actualWaveformWidth,
|
|
35936
|
+
return (jsxRuntime.jsx(Svg.Line, { x1: progressX, y1: 0, x2: progressX, y2: h, stroke: (progressLineStyle === null || progressLineStyle === void 0 ? void 0 : progressLineStyle.color) || theme.colors.gray[7], strokeWidth: (progressLineStyle === null || progressLineStyle === void 0 ? void 0 : progressLineStyle.width) || 2, strokeOpacity: (progressLineStyle === null || progressLineStyle === void 0 ? void 0 : progressLineStyle.opacity) || 0.8 }));
|
|
35937
|
+
}, [showProgressLine, progress, actualWaveformWidth, h, progressLineStyle, theme.colors.gray]);
|
|
36075
35938
|
// Timestamp markers component
|
|
36076
35939
|
const TimeStamps = React.useMemo(() => {
|
|
36077
35940
|
if (!showTimeStamps || !duration || !timeStampInterval)
|
|
@@ -36092,10 +35955,10 @@ loading = false, error, loadingProgress, selection, onSelectionChange, zoomLevel
|
|
|
36092
35955
|
}
|
|
36093
35956
|
return `${mins}:${secs.toString().padStart(2, '0')}`;
|
|
36094
35957
|
};
|
|
36095
|
-
timestamps.push(jsxRuntime.jsxs(Svg.G, { children: [jsxRuntime.jsx(Svg.Line, { x1: x, y1:
|
|
35958
|
+
timestamps.push(jsxRuntime.jsxs(Svg.G, { children: [jsxRuntime.jsx(Svg.Line, { x1: x, y1: h - 10, x2: x, y2: h, stroke: theme.colors.gray[5], strokeWidth: 1, strokeOpacity: 0.6 }), jsxRuntime.jsx(Svg.Text, { x: x, y: h + 15, fill: theme.colors.gray[6], fontSize: 10, textAnchor: "middle", opacity: 0.8, children: formatTime(time) })] }, i));
|
|
36096
35959
|
}
|
|
36097
35960
|
return jsxRuntime.jsx(Svg.G, { children: timestamps });
|
|
36098
|
-
}, [showTimeStamps, duration, timeStampInterval, actualWaveformWidth,
|
|
35961
|
+
}, [showTimeStamps, duration, timeStampInterval, actualWaveformWidth, h, theme.colors]);
|
|
36099
35962
|
// Selection overlay component
|
|
36100
35963
|
const SelectionOverlay = React.useMemo(() => {
|
|
36101
35964
|
if (!selection || selection[0] === selection[1])
|
|
@@ -36104,8 +35967,8 @@ loading = false, error, loadingProgress, selection, onSelectionChange, zoomLevel
|
|
|
36104
35967
|
const startX = start * actualWaveformWidth;
|
|
36105
35968
|
const endX = end * actualWaveformWidth;
|
|
36106
35969
|
const selectionWidth = endX - startX;
|
|
36107
|
-
return (jsxRuntime.jsx(Svg.Rect, { x: startX, y: 0, width: selectionWidth, height:
|
|
36108
|
-
}, [selection, actualWaveformWidth,
|
|
35970
|
+
return (jsxRuntime.jsx(Svg.Rect, { x: startX, y: 0, width: selectionWidth, height: h, fill: theme.colors.primary[3], opacity: 0.3, stroke: theme.colors.primary[5], strokeWidth: 1, strokeOpacity: 0.8 }));
|
|
35971
|
+
}, [selection, actualWaveformWidth, h, theme.colors.primary]);
|
|
36109
35972
|
// Markers component
|
|
36110
35973
|
const Markers = React.useMemo(() => {
|
|
36111
35974
|
if (!markers || markers.length === 0)
|
|
@@ -36115,16 +35978,16 @@ loading = false, error, loadingProgress, selection, onSelectionChange, zoomLevel
|
|
|
36115
35978
|
const markerColor = marker.color || theme.colors.warning[5];
|
|
36116
35979
|
switch (marker.type || 'line') {
|
|
36117
35980
|
case 'line':
|
|
36118
|
-
return (jsxRuntime.jsxs(Svg.G, { children: [jsxRuntime.jsx(Svg.Line, { x1: x, y1: 0, x2: x, y2:
|
|
35981
|
+
return (jsxRuntime.jsxs(Svg.G, { children: [jsxRuntime.jsx(Svg.Line, { x1: x, y1: 0, x2: x, y2: h, stroke: markerColor, strokeWidth: 2, strokeOpacity: 0.8 }), marker.label && (jsxRuntime.jsx(Svg.Text, { x: x, y: -5, fill: markerColor, fontSize: 10, textAnchor: "middle", fontWeight: "bold", children: marker.label }))] }, index));
|
|
36119
35982
|
case 'flag':
|
|
36120
|
-
return (jsxRuntime.jsxs(Svg.G, { children: [jsxRuntime.jsx(Svg.Line, { x1: x, y1: 0, x2: x, y2:
|
|
35983
|
+
return (jsxRuntime.jsxs(Svg.G, { children: [jsxRuntime.jsx(Svg.Line, { x1: x, y1: 0, x2: x, y2: h, stroke: markerColor, strokeWidth: 1, strokeOpacity: 0.6 }), jsxRuntime.jsx(Svg.Rect, { x: x + 2, y: 2, width: marker.label ? marker.label.length * 6 + 4 : 20, height: 14, fill: markerColor, rx: 2 }), marker.label && (jsxRuntime.jsx(Svg.Text, { x: x + 4, y: 12, fill: "white", fontSize: 9, fontWeight: "bold", children: marker.label }))] }, index));
|
|
36121
35984
|
case 'dot':
|
|
36122
|
-
return (jsxRuntime.jsxs(Svg.G, { children: [jsxRuntime.jsx("circle", { cx: x, cy:
|
|
35985
|
+
return (jsxRuntime.jsxs(Svg.G, { children: [jsxRuntime.jsx("circle", { cx: x, cy: h / 2, r: 4, fill: markerColor, stroke: "white", strokeWidth: 1 }), marker.label && (jsxRuntime.jsx(Svg.Text, { x: x, y: h / 2 + 20, fill: markerColor, fontSize: 10, textAnchor: "middle", fontWeight: "bold", children: marker.label }))] }, index));
|
|
36123
35986
|
default:
|
|
36124
35987
|
return null;
|
|
36125
35988
|
}
|
|
36126
35989
|
}) }));
|
|
36127
|
-
}, [markers, actualWaveformWidth,
|
|
35990
|
+
}, [markers, actualWaveformWidth, h, theme.colors.warning]);
|
|
36128
35991
|
// RMS visualization component
|
|
36129
35992
|
const RMSBars = React.useMemo(() => {
|
|
36130
35993
|
if (!showRMS || !rmsData || rmsData.length === 0)
|
|
@@ -36132,11 +35995,11 @@ loading = false, error, loadingProgress, selection, onSelectionChange, zoomLevel
|
|
|
36132
35995
|
const processedRMS = rmsData.slice(0, normalizedPeaks.length);
|
|
36133
35996
|
return (jsxRuntime.jsx(Svg.G, { opacity: 0.5, children: processedRMS.map((rms, index) => {
|
|
36134
35997
|
const x = index * (barWidth + barGap);
|
|
36135
|
-
const rmsHeight = Math.max(minBarHeight, Math.abs(rms) *
|
|
36136
|
-
const y = (
|
|
35998
|
+
const rmsHeight = Math.max(minBarHeight, Math.abs(rms) * h * 0.4); // RMS bars are shorter
|
|
35999
|
+
const y = (h - rmsHeight) / 2;
|
|
36137
36000
|
return (jsxRuntime.jsx(Svg.Rect, { x: x, y: y, width: barWidth, height: rmsHeight, fill: theme.colors.gray[4], rx: variant === 'rounded' ? barWidth / 2 : 0 }, `rms-${index}`));
|
|
36138
36001
|
}) }));
|
|
36139
|
-
}, [showRMS, rmsData, normalizedPeaks, barWidth, barGap, minBarHeight,
|
|
36002
|
+
}, [showRMS, rmsData, normalizedPeaks, barWidth, barGap, minBarHeight, h, variant, theme.colors.gray]);
|
|
36140
36003
|
const renderWaveform = () => {
|
|
36141
36004
|
switch (variant) {
|
|
36142
36005
|
case 'line':
|
|
@@ -36173,17 +36036,17 @@ loading = false, error, loadingProgress, selection, onSelectionChange, zoomLevel
|
|
|
36173
36036
|
};
|
|
36174
36037
|
// Early return for empty state
|
|
36175
36038
|
if (normalizedPeaks.length === 0) {
|
|
36176
|
-
return (jsxRuntime.jsx(reactNative.View, { style: [style, fullWidth ? { width: '100%' } : { width }, { height, justifyContent: 'center', alignItems: 'center' }], accessibilityRole: "image", accessibilityLabel: accessibilityLabel || 'Empty waveform', ...restProps, children: jsxRuntime.jsx(Svg, { ...svgProps, children: jsxRuntime.jsx(Svg.Rect, { x: 0, y:
|
|
36039
|
+
return (jsxRuntime.jsx(reactNative.View, { style: [style, fullWidth ? { width: '100%' } : { width: w }, { height: h, justifyContent: 'center', alignItems: 'center' }], accessibilityRole: "image", accessibilityLabel: accessibilityLabel || 'Empty waveform', ...restProps, children: jsxRuntime.jsx(Svg, { ...svgProps, children: jsxRuntime.jsx(Svg.Rect, { x: 0, y: h / 2 - 1, width: fullWidth ? '100%' : w, height: 2, fill: waveformColor, opacity: 0.3 }) }) }));
|
|
36177
36040
|
}
|
|
36178
36041
|
if (loading) {
|
|
36179
|
-
return (jsxRuntime.jsx(WaveformSkeleton, {
|
|
36042
|
+
return (jsxRuntime.jsx(WaveformSkeleton, { w: w, h: h, fullWidth: fullWidth, barsCount: maxVisibleBars || 20 }));
|
|
36180
36043
|
}
|
|
36181
36044
|
if (error) {
|
|
36182
36045
|
return (jsxRuntime.jsx(reactNative.View, { style: [
|
|
36183
36046
|
style,
|
|
36184
|
-
fullWidth ? { width: '100%' } : { width },
|
|
36047
|
+
fullWidth ? { width: '100%' } : { width: w },
|
|
36185
36048
|
{
|
|
36186
|
-
height,
|
|
36049
|
+
height: h,
|
|
36187
36050
|
justifyContent: 'center',
|
|
36188
36051
|
alignItems: 'center',
|
|
36189
36052
|
backgroundColor: theme.colors.error[1],
|
|
@@ -36193,7 +36056,7 @@ loading = false, error, loadingProgress, selection, onSelectionChange, zoomLevel
|
|
|
36193
36056
|
}
|
|
36194
36057
|
], accessibilityRole: "alert", accessibilityLabel: `Waveform error: ${error}`, ...restProps, children: jsxRuntime.jsx(reactNative.Text, { style: { color: theme.colors.error[7], fontSize: 12, textAlign: 'center' }, children: error }) }));
|
|
36195
36058
|
}
|
|
36196
|
-
return (jsxRuntime.jsx(WrapperComponent, { ref: containerRef, style: [style, fullWidth ? { width: '100%' } : { width }], accessible: true, focusable: interactive, onFocus: () => setIsFocused(true), onBlur: () => setIsFocused(false), ...wrapperProps, ...restProps, children: jsxRuntime.jsxs(Svg, { ...svgProps, children: [SelectionOverlay, RMSBars, renderWaveform(), ProgressLine, TimeStamps, Markers] }) }));
|
|
36059
|
+
return (jsxRuntime.jsx(WrapperComponent, { ref: containerRef, style: [style, fullWidth ? { width: '100%' } : { width: w }], accessible: true, focusable: interactive, onFocus: () => setIsFocused(true), onBlur: () => setIsFocused(false), ...wrapperProps, ...restProps, children: jsxRuntime.jsxs(Svg, { ...svgProps, children: [SelectionOverlay, RMSBars, renderWaveform(), ProgressLine, TimeStamps, Markers] }) }));
|
|
36197
36060
|
});
|
|
36198
36061
|
Waveform.displayName = 'Waveform';
|
|
36199
36062
|
|
|
@@ -36215,7 +36078,7 @@ const AudioPlayer = React.forwardRef(({ source, peaks: providedPeaks, autoPlay =
|
|
|
36215
36078
|
channel: 'mix',
|
|
36216
36079
|
}, showTime = true, timeFormat = 'mm:ss', showMetadata = false, metadata, showSpectrum = false, spectrumOptions, enableKeyboardShortcuts = true, enableGestures = true, onLoad, onPlaybackStateChange, onProgress, onEnd, onError, onBuffer,
|
|
36217
36080
|
// Waveform props
|
|
36218
|
-
|
|
36081
|
+
w = 300, h = 60, color = 'primary', interactive = true, onSeek, style, ...waveformProps }, ref) => {
|
|
36219
36082
|
const theme = useTheme();
|
|
36220
36083
|
const { playSound } = useSound();
|
|
36221
36084
|
// Refs
|
|
@@ -36562,7 +36425,7 @@ width = 300, height = 60, color = 'primary', interactive = true, onSeek, style,
|
|
|
36562
36425
|
alignSelf: 'flex-start',
|
|
36563
36426
|
}, children: jsxRuntime.jsx(reactNative.Text, { style: { color: 'white', fontSize: DESIGN_TOKENS.typography.fontSize.sm }, children: "Retry" }) }))] }));
|
|
36564
36427
|
}
|
|
36565
|
-
return (jsxRuntime.jsxs(reactNative.View, { style: [{ width: '100%' }, style], children: [controlsPosition === 'top' && renderMetadata(), controlsPosition === 'top' && renderControls(), controls.waveform && peaks.length > 0 && (jsxRuntime.jsx(reactNative.View, { style: { marginVertical: DESIGN_TOKENS.spacing.sm }, children: jsxRuntime.jsx(Waveform, { peaks: peaks,
|
|
36428
|
+
return (jsxRuntime.jsxs(reactNative.View, { style: [{ width: '100%' }, style], children: [controlsPosition === 'top' && renderMetadata(), controlsPosition === 'top' && renderControls(), controls.waveform && peaks.length > 0 && (jsxRuntime.jsx(reactNative.View, { style: { marginVertical: DESIGN_TOKENS.spacing.sm }, children: jsxRuntime.jsx(Waveform, { peaks: peaks, w: w, h: h, color: color, progress: progress, interactive: interactive, onSeek: handleWaveformSeek, showProgressLine: true, progressLineStyle: {
|
|
36566
36429
|
color: theme.colors.primary[5],
|
|
36567
36430
|
width: 2,
|
|
36568
36431
|
opacity: 0.8,
|
|
@@ -37291,14 +37154,14 @@ const IMAGE_SIZES = {
|
|
|
37291
37154
|
'2xl': 80,
|
|
37292
37155
|
'3xl': 96,
|
|
37293
37156
|
};
|
|
37294
|
-
function Image({ src, source, alt, accessibilityLabel, resizeMode = 'cover', size,
|
|
37157
|
+
function Image({ src, source, alt, accessibilityLabel, resizeMode = 'cover', size, w, h, aspectRatio, borderWidth, borderColor, rounded, circle, fallback, loading, onLoad, onError, onLoadStart, onLoadEnd, containerStyle, imageStyle, testID, style, ...rest }) {
|
|
37295
37158
|
const theme = useTheme();
|
|
37296
37159
|
const [loadError, setLoadError] = React.useState(false);
|
|
37297
37160
|
const [isLoading, setIsLoading] = React.useState(true);
|
|
37298
37161
|
const { spacingProps } = extractSpacingProps(rest);
|
|
37299
37162
|
// Determine dimensions
|
|
37300
|
-
let finalWidth =
|
|
37301
|
-
let finalHeight =
|
|
37163
|
+
let finalWidth = w;
|
|
37164
|
+
let finalHeight = h;
|
|
37302
37165
|
if (size && typeof size === 'string' && IMAGE_SIZES[size]) {
|
|
37303
37166
|
finalWidth = finalWidth || IMAGE_SIZES[size];
|
|
37304
37167
|
finalHeight = finalHeight || IMAGE_SIZES[size];
|
|
@@ -37323,7 +37186,7 @@ function Image({ src, source, alt, accessibilityLabel, resizeMode = 'cover', siz
|
|
|
37323
37186
|
const spacingStyles = getSpacingStyles(spacingProps);
|
|
37324
37187
|
const containerStyles = {
|
|
37325
37188
|
...spacingStyles,
|
|
37326
|
-
...containerStyle,
|
|
37189
|
+
...reactNative.StyleSheet.flatten(containerStyle),
|
|
37327
37190
|
};
|
|
37328
37191
|
const imageStyles = {
|
|
37329
37192
|
width: finalWidth,
|
|
@@ -37332,7 +37195,7 @@ function Image({ src, source, alt, accessibilityLabel, resizeMode = 'cover', siz
|
|
|
37332
37195
|
borderWidth,
|
|
37333
37196
|
borderColor: borderColor || theme.colors.gray[3],
|
|
37334
37197
|
borderRadius,
|
|
37335
|
-
...imageStyle,
|
|
37198
|
+
...reactNative.StyleSheet.flatten(imageStyle),
|
|
37336
37199
|
};
|
|
37337
37200
|
if (finalWidth !== undefined) {
|
|
37338
37201
|
containerStyles.width = finalWidth;
|
|
@@ -39106,7 +38969,7 @@ function QRCode(props) {
|
|
|
39106
38969
|
});
|
|
39107
38970
|
}
|
|
39108
38971
|
}, [copy, copyValue, toast, otherProps.copyToastMessage, otherProps.copyToastTitle]);
|
|
39109
|
-
const content = (jsxRuntime.jsxs(reactNative.View, { style: { borderRadius: 8, overflow: 'hidden' }, children: [jsxRuntime.jsx(QRCodeSVG, { value: value, size: size,
|
|
38972
|
+
const content = (jsxRuntime.jsxs(reactNative.View, { style: { borderRadius: 8, overflow: 'hidden' }, children: [jsxRuntime.jsx(QRCodeSVG, { value: value, size: size, maxW: '100%', backgroundColor: backgroundColor, color: resolvedColor, errorCorrectionLevel: errorCorrectionLevel, quietZone: quietZone, logo: logo, style: style, testID: testID, accessibilityLabel: accessibilityLabel, onError: onError, ...spacingProps, ...layoutProps, ...rest }), otherProps.showCopyButton && (jsxRuntime.jsx(CopyButton, { value: copyValue, iconOnly: true, size: "sm", style: { position: 'absolute', top: 8, right: 8 }, onCopy: () => { } }))] }));
|
|
39110
38973
|
if (shouldCopyOnPress) {
|
|
39111
38974
|
return (jsxRuntime.jsx(reactNative.Pressable, { onPress: handleCopy, accessibilityLabel: accessibilityLabel || 'QR code', children: content }));
|
|
39112
38975
|
}
|
|
@@ -39756,111 +39619,6 @@ const styles$2 = reactNative.StyleSheet.create({
|
|
|
39756
39619
|
},
|
|
39757
39620
|
});
|
|
39758
39621
|
|
|
39759
|
-
// Optional imports for web compatibility
|
|
39760
|
-
const LottieReact = reactNative.Platform.OS === 'web'
|
|
39761
|
-
? resolveOptionalModule('lottie-react', {
|
|
39762
|
-
accessor: mod => { var _a; return (_a = mod.default) !== null && _a !== void 0 ? _a : mod; },
|
|
39763
|
-
})
|
|
39764
|
-
: null;
|
|
39765
|
-
const DotLottieReact = reactNative.Platform.OS === 'web'
|
|
39766
|
-
? resolveOptionalModule('@lottiefiles/dotlottie-react', {
|
|
39767
|
-
accessor: mod => mod.DotLottieReact,
|
|
39768
|
-
})
|
|
39769
|
-
: null;
|
|
39770
|
-
let cachedNativeStatus = null;
|
|
39771
|
-
let nativeLottieComponent;
|
|
39772
|
-
let nativeModuleLoadWarningLogged = false;
|
|
39773
|
-
let nativeModuleConfigWarningLogged = false;
|
|
39774
|
-
const loadNativeLottieComponent = () => {
|
|
39775
|
-
if (nativeLottieComponent !== undefined) {
|
|
39776
|
-
return nativeLottieComponent;
|
|
39777
|
-
}
|
|
39778
|
-
const module = resolveOptionalModule('lottie-react-native', {
|
|
39779
|
-
accessor: mod => { var _a; return (_a = mod === null || mod === void 0 ? void 0 : mod.default) !== null && _a !== void 0 ? _a : mod; },
|
|
39780
|
-
});
|
|
39781
|
-
if (!module && !nativeModuleLoadWarningLogged && __DEV__) {
|
|
39782
|
-
console.warn('[Lottie] Failed to load lottie-react-native module. Rendering fallback instead.');
|
|
39783
|
-
nativeModuleLoadWarningLogged = true;
|
|
39784
|
-
}
|
|
39785
|
-
nativeLottieComponent = module !== null && module !== void 0 ? module : null;
|
|
39786
|
-
return nativeLottieComponent;
|
|
39787
|
-
};
|
|
39788
|
-
const getNativeLottieStatus = () => {
|
|
39789
|
-
var _a, _b, _c;
|
|
39790
|
-
if (cachedNativeStatus) {
|
|
39791
|
-
return cachedNativeStatus;
|
|
39792
|
-
}
|
|
39793
|
-
if (reactNative.Platform.OS === 'web') {
|
|
39794
|
-
cachedNativeStatus = { component: null, available: false };
|
|
39795
|
-
return cachedNativeStatus;
|
|
39796
|
-
}
|
|
39797
|
-
const component = loadNativeLottieComponent();
|
|
39798
|
-
if (!component) {
|
|
39799
|
-
cachedNativeStatus = { component: null, available: false };
|
|
39800
|
-
return cachedNativeStatus;
|
|
39801
|
-
}
|
|
39802
|
-
let viewManagerAvailable = false;
|
|
39803
|
-
try {
|
|
39804
|
-
const viewManager = (_c = (_b = (_a = reactNative.UIManager === null || reactNative.UIManager === void 0 ? void 0 : reactNative.UIManager.getViewManagerConfig) === null || _a === void 0 ? void 0 : _a.call(reactNative.UIManager, 'LottieAnimationView')) !== null && _b !== void 0 ? _b : reactNative.UIManager === null || reactNative.UIManager === void 0 ? void 0 : reactNative.UIManager.LottieAnimationView) !== null && _c !== void 0 ? _c : reactNative.NativeModules === null || reactNative.NativeModules === void 0 ? void 0 : reactNative.NativeModules.LottieAnimationView;
|
|
39805
|
-
viewManagerAvailable = !!viewManager;
|
|
39806
|
-
}
|
|
39807
|
-
catch (error) {
|
|
39808
|
-
viewManagerAvailable = false;
|
|
39809
|
-
}
|
|
39810
|
-
if (!viewManagerAvailable && !nativeModuleConfigWarningLogged && __DEV__) {
|
|
39811
|
-
console.warn('[Lottie] Native LottieAnimationView is unavailable. Run `npx expo install lottie-react-native` and rebuild to enable animations.');
|
|
39812
|
-
nativeModuleConfigWarningLogged = true;
|
|
39813
|
-
}
|
|
39814
|
-
cachedNativeStatus = {
|
|
39815
|
-
component,
|
|
39816
|
-
available: viewManagerAvailable,
|
|
39817
|
-
};
|
|
39818
|
-
return cachedNativeStatus;
|
|
39819
|
-
};
|
|
39820
|
-
/**
|
|
39821
|
-
* Lottie component with safe fallback when native module not present or on unsupported platforms.
|
|
39822
|
-
*/
|
|
39823
|
-
const Lottie = React.forwardRef(function LottieCmp(props, ref) {
|
|
39824
|
-
const { source, autoPlay = true, loop = true, progress, speed = 1, style, testID, paused, resizeMode = 'contain', onAnimationFinish } = props;
|
|
39825
|
-
const internalRef = React.useRef(null);
|
|
39826
|
-
const nativeStatus = getNativeLottieStatus();
|
|
39827
|
-
const NativeLottieView = nativeStatus.component;
|
|
39828
|
-
React.useImperativeHandle(ref, () => ({
|
|
39829
|
-
play: (...args) => { var _a, _b; return (_b = (_a = internalRef.current) === null || _a === void 0 ? void 0 : _a.play) === null || _b === void 0 ? void 0 : _b.call(_a, ...args); },
|
|
39830
|
-
pause: () => { var _a, _b; return (_b = (_a = internalRef.current) === null || _a === void 0 ? void 0 : _a.pause) === null || _b === void 0 ? void 0 : _b.call(_a); },
|
|
39831
|
-
reset: () => { var _a, _b; return (_b = (_a = internalRef.current) === null || _a === void 0 ? void 0 : _a.reset) === null || _b === void 0 ? void 0 : _b.call(_a); },
|
|
39832
|
-
setProgress: (p) => { var _a, _b; return (_b = (_a = internalRef.current) === null || _a === void 0 ? void 0 : _a.setProgress) === null || _b === void 0 ? void 0 : _b.call(_a, p); },
|
|
39833
|
-
}), []);
|
|
39834
|
-
React.useEffect(() => {
|
|
39835
|
-
var _a;
|
|
39836
|
-
if (progress != null && ((_a = internalRef.current) === null || _a === void 0 ? void 0 : _a.setProgress)) {
|
|
39837
|
-
internalRef.current.setProgress(progress);
|
|
39838
|
-
}
|
|
39839
|
-
}, [progress]);
|
|
39840
|
-
// Web implementation
|
|
39841
|
-
if (reactNative.Platform.OS === 'web') {
|
|
39842
|
-
// Check if source is a string (URL) and ends with .lottie
|
|
39843
|
-
const isLottieFile = typeof source === 'string' && source.endsWith('.lottie');
|
|
39844
|
-
if (isLottieFile && DotLottieReact) {
|
|
39845
|
-
// Use DotLottieReact for .lottie files
|
|
39846
|
-
return (jsxRuntime.jsx(DotLottieReact, { src: source, autoplay: autoPlay, loop: loop, speed: speed, style: style, "data-testid": testID }));
|
|
39847
|
-
}
|
|
39848
|
-
else if (LottieReact) {
|
|
39849
|
-
// Use lottie-react for standard Lottie JSON
|
|
39850
|
-
return (jsxRuntime.jsx(LottieReact, { animationData: source, autoplay: autoPlay, loop: loop, style: style, "data-testid": testID }));
|
|
39851
|
-
}
|
|
39852
|
-
else {
|
|
39853
|
-
return jsxRuntime.jsx(Text, { children: "Lottie not available on web" });
|
|
39854
|
-
}
|
|
39855
|
-
}
|
|
39856
|
-
// Native implementation using lottie-react-native
|
|
39857
|
-
if (!nativeStatus.available || !NativeLottieView) {
|
|
39858
|
-
return (jsxRuntime.jsx(reactNative.View, { style: [{ justifyContent: 'center', alignItems: 'center' }, style], testID: testID, children: jsxRuntime.jsx(Text, { style: { textAlign: 'center', opacity: 0.7 }, children: "Lottie animations require the native `lottie-react-native` module. Install it and rebuild the app, or view this example on the web." }) }));
|
|
39859
|
-
}
|
|
39860
|
-
return (jsxRuntime.jsx(NativeLottieView, { ref: internalRef, source: source, autoPlay: autoPlay, loop: loop, speed: speed, progress: progress, style: style, testID: testID, resizeMode: resizeMode, onAnimationFinish: onAnimationFinish, ...(paused != null ? { paused } : {}) }));
|
|
39861
|
-
});
|
|
39862
|
-
Lottie.displayName = 'Lottie';
|
|
39863
|
-
|
|
39864
39622
|
const PLAYBACK_RATES = [0.25, 0.5, 0.75, 1, 1.25, 1.5, 1.75, 2];
|
|
39865
39623
|
function formatTime(seconds) {
|
|
39866
39624
|
const hours = Math.floor(seconds / 3600);
|
|
@@ -40808,7 +40566,7 @@ const DEFAULT_CONTROLS = {
|
|
|
40808
40566
|
autoHide: true,
|
|
40809
40567
|
autoHideTimeout: 3000,
|
|
40810
40568
|
};
|
|
40811
|
-
const Video = React.forwardRef(({ source,
|
|
40569
|
+
const Video = React.forwardRef(({ source, w, h, aspectRatio = 16 / 9, poster, autoPlay = false, loop = false, muted = false, volume = 1, playbackRate = 1, quality = 'auto', controls = true, timeline = [], youtubeOptions, onPlay, onPause, onSeek, onTimeUpdate, onDurationChange, onVolumeChange, onPlaybackRateChange, onQualityChange, onFullscreenChange, onError, onLoad, onLoadStart, onBuffer, onTimelineEvent, style, videoStyle, controlsStyle, accessibilityLabel, testID, ...rest }, ref) => {
|
|
40812
40570
|
const theme = useTheme();
|
|
40813
40571
|
const { spacingProps } = extractSpacingProps(rest);
|
|
40814
40572
|
// Internal state
|
|
@@ -41058,24 +40816,24 @@ const Video = React.forwardRef(({ source, width, height, aspectRatio = 16 / 9, p
|
|
|
41058
40816
|
// overflow: 'hidden',
|
|
41059
40817
|
// position: 'relative',
|
|
41060
40818
|
};
|
|
41061
|
-
if (
|
|
41062
|
-
baseStyle.width =
|
|
41063
|
-
baseStyle.height =
|
|
40819
|
+
if (w && h) {
|
|
40820
|
+
baseStyle.width = w;
|
|
40821
|
+
baseStyle.height = h;
|
|
41064
40822
|
}
|
|
41065
|
-
else if (
|
|
41066
|
-
baseStyle.width =
|
|
41067
|
-
baseStyle.height = typeof
|
|
40823
|
+
else if (w) {
|
|
40824
|
+
baseStyle.width = w;
|
|
40825
|
+
baseStyle.height = typeof w === 'number' ? w / aspectRatio : '100%';
|
|
41068
40826
|
}
|
|
41069
|
-
else if (
|
|
41070
|
-
baseStyle.height =
|
|
41071
|
-
baseStyle.width = typeof
|
|
40827
|
+
else if (h) {
|
|
40828
|
+
baseStyle.height = h;
|
|
40829
|
+
baseStyle.width = typeof h === 'number' ? h * aspectRatio : '100%';
|
|
41072
40830
|
}
|
|
41073
40831
|
else {
|
|
41074
40832
|
baseStyle.width = '100%';
|
|
41075
40833
|
baseStyle.aspectRatio = aspectRatio;
|
|
41076
40834
|
}
|
|
41077
40835
|
return baseStyle;
|
|
41078
|
-
}, [theme.colors.surface,
|
|
40836
|
+
}, [theme.colors.surface, w, h, aspectRatio]);
|
|
41079
40837
|
// Handle touch events for control visibility
|
|
41080
40838
|
const handleContainerPress = React.useCallback(() => {
|
|
41081
40839
|
if (controlsConfig && controlsConfig.autoHide) {
|
|
@@ -41298,7 +41056,6 @@ exports.ListGroupDivider = ListGroupDivider;
|
|
|
41298
41056
|
exports.ListGroupItem = ListGroupItem;
|
|
41299
41057
|
exports.Loader = Loader;
|
|
41300
41058
|
exports.LoadingOverlay = LoadingOverlay;
|
|
41301
|
-
exports.Lottie = Lottie;
|
|
41302
41059
|
exports.MacAppStoreButton = MacAppStoreButton;
|
|
41303
41060
|
exports.Mark = Mark;
|
|
41304
41061
|
exports.Markdown = Markdown;
|
|
@@ -41334,7 +41091,6 @@ exports.RadioGroup = RadioGroup;
|
|
|
41334
41091
|
exports.RangeSlider = RangeSlider;
|
|
41335
41092
|
exports.Rating = Rating;
|
|
41336
41093
|
exports.RedditJoinBadge = RedditJoinBadge;
|
|
41337
|
-
exports.RichTextEditor = RichTextEditor;
|
|
41338
41094
|
exports.Ring = Ring;
|
|
41339
41095
|
exports.Row = Row;
|
|
41340
41096
|
exports.SIZE_SCALES = SIZE_SCALES;
|