@wordpress/components 25.11.0 → 25.12.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/CHANGELOG.md +29 -0
- package/build/disclosure/index.js +37 -7
- package/build/disclosure/index.js.map +1 -1
- package/build/disclosure/types.js +6 -0
- package/build/disclosure/types.js.map +1 -0
- package/build/divider/component.js +5 -3
- package/build/divider/component.js.map +1 -1
- package/build/divider/types.js.map +1 -1
- package/build/dropdown-menu-v2-ariakit/index.js +26 -16
- package/build/dropdown-menu-v2-ariakit/index.js.map +1 -1
- package/build/dropdown-menu-v2-ariakit/types.js.map +1 -1
- package/build/gradient-picker/index.js +1 -1
- package/build/gradient-picker/index.js.map +1 -1
- package/build/index.native.js +8 -1
- package/build/index.native.js.map +1 -1
- package/build/mobile/audio-player/index.native.js +8 -9
- package/build/mobile/audio-player/index.native.js.map +1 -1
- package/build/mobile/global-styles-context/utils.native.js +44 -3
- package/build/mobile/global-styles-context/utils.native.js.map +1 -1
- package/build/radio-group/context.js +22 -0
- package/build/radio-group/context.js.map +1 -0
- package/build/radio-group/index.js +27 -23
- package/build/radio-group/index.js.map +1 -1
- package/build/radio-group/radio.js +58 -0
- package/build/radio-group/radio.js.map +1 -0
- package/build/radio-group/types.js +6 -0
- package/build/radio-group/types.js.map +1 -0
- package/build/tabs/styles.js +14 -7
- package/build/tabs/styles.js.map +1 -1
- package/build/tabs/tab.js +3 -5
- package/build/tabs/tab.js.map +1 -1
- package/build/tabs/tablist.js +3 -5
- package/build/tabs/tablist.js.map +1 -1
- package/build/tabs/tabpanel.js +6 -9
- package/build/tabs/tabpanel.js.map +1 -1
- package/build/tabs/types.js.map +1 -1
- package/build/text-control/index.js +5 -1
- package/build/text-control/index.js.map +1 -1
- package/build/text-control/types.js.map +1 -1
- package/build/toggle-group-control/toggle-group-control/component.js +4 -2
- package/build/toggle-group-control/toggle-group-control/component.js.map +1 -1
- package/build/toggle-group-control/toggle-group-control/styles.js +13 -9
- package/build/toggle-group-control/toggle-group-control/styles.js.map +1 -1
- package/build/toggle-group-control/types.js.map +1 -1
- package/build-module/disclosure/index.js +33 -8
- package/build-module/disclosure/index.js.map +1 -1
- package/build-module/disclosure/types.js +2 -0
- package/build-module/disclosure/types.js.map +1 -0
- package/build-module/divider/component.js +3 -3
- package/build-module/divider/component.js.map +1 -1
- package/build-module/divider/types.js.map +1 -1
- package/build-module/dropdown-menu-v2-ariakit/index.js +27 -17
- package/build-module/dropdown-menu-v2-ariakit/index.js.map +1 -1
- package/build-module/dropdown-menu-v2-ariakit/types.js.map +1 -1
- package/build-module/gradient-picker/index.js +1 -1
- package/build-module/gradient-picker/index.js.map +1 -1
- package/build-module/index.native.js +1 -1
- package/build-module/index.native.js.map +1 -1
- package/build-module/mobile/audio-player/index.native.js +9 -10
- package/build-module/mobile/audio-player/index.native.js.map +1 -1
- package/build-module/mobile/global-styles-context/utils.native.js +43 -4
- package/build-module/mobile/global-styles-context/utils.native.js.map +1 -1
- package/build-module/radio-group/context.js +14 -0
- package/build-module/radio-group/context.js.map +1 -0
- package/build-module/radio-group/index.js +24 -23
- package/build-module/radio-group/index.js.map +1 -1
- package/build-module/radio-group/radio.js +46 -0
- package/build-module/radio-group/radio.js.map +1 -0
- package/build-module/radio-group/types.js +2 -0
- package/build-module/radio-group/types.js.map +1 -0
- package/build-module/tabs/styles.js +11 -5
- package/build-module/tabs/styles.js.map +1 -1
- package/build-module/tabs/tab.js +3 -5
- package/build-module/tabs/tab.js.map +1 -1
- package/build-module/tabs/tablist.js +3 -5
- package/build-module/tabs/tablist.js.map +1 -1
- package/build-module/tabs/tabpanel.js +6 -7
- package/build-module/tabs/tabpanel.js.map +1 -1
- package/build-module/tabs/types.js.map +1 -1
- package/build-module/text-control/index.js +6 -1
- package/build-module/text-control/index.js.map +1 -1
- package/build-module/text-control/types.js.map +1 -1
- package/build-module/toggle-group-control/toggle-group-control/component.js +4 -2
- package/build-module/toggle-group-control/toggle-group-control/component.js.map +1 -1
- package/build-module/toggle-group-control/toggle-group-control/styles.js +13 -9
- package/build-module/toggle-group-control/toggle-group-control/styles.js.map +1 -1
- package/build-module/toggle-group-control/types.js.map +1 -1
- package/build-style/style-rtl.css +21 -3
- package/build-style/style.css +21 -3
- package/build-types/card/card-divider/component.d.ts +1 -1
- package/build-types/card/card-divider/hook.d.ts +162 -162
- package/build-types/disclosure/index.d.ts +7 -1
- package/build-types/disclosure/index.d.ts.map +1 -1
- package/build-types/disclosure/types.d.ts +12 -0
- package/build-types/disclosure/types.d.ts.map +1 -0
- package/build-types/divider/component.d.ts +5 -1
- package/build-types/divider/component.d.ts.map +1 -1
- package/build-types/divider/stories/index.story.d.ts.map +1 -1
- package/build-types/divider/styles.d.ts +1 -1
- package/build-types/divider/types.d.ts +2 -2
- package/build-types/divider/types.d.ts.map +1 -1
- package/build-types/dropdown-menu-v2-ariakit/index.d.ts.map +1 -1
- package/build-types/dropdown-menu-v2-ariakit/stories/index.story.d.ts.map +1 -1
- package/build-types/dropdown-menu-v2-ariakit/types.d.ts +1 -1
- package/build-types/radio-group/context.d.ts +10 -0
- package/build-types/radio-group/context.d.ts.map +1 -0
- package/build-types/radio-group/index.d.ts +7 -9
- package/build-types/radio-group/index.d.ts.map +1 -1
- package/build-types/radio-group/radio.d.ts +8 -0
- package/build-types/radio-group/radio.d.ts.map +1 -0
- package/build-types/radio-group/stories/index.story.d.ts +14 -0
- package/build-types/radio-group/stories/index.story.d.ts.map +1 -0
- package/build-types/radio-group/types.d.ts +40 -0
- package/build-types/radio-group/types.d.ts.map +1 -0
- package/build-types/tabs/index.d.ts +3 -3
- package/build-types/tabs/stories/index.story.d.ts.map +1 -1
- package/build-types/tabs/styles.d.ts +10 -0
- package/build-types/tabs/styles.d.ts.map +1 -1
- package/build-types/tabs/tab.d.ts +1 -1
- package/build-types/tabs/tab.d.ts.map +1 -1
- package/build-types/tabs/tablist.d.ts +1 -1
- package/build-types/tabs/tablist.d.ts.map +1 -1
- package/build-types/tabs/tabpanel.d.ts +4 -1
- package/build-types/tabs/tabpanel.d.ts.map +1 -1
- package/build-types/tabs/types.d.ts +7 -31
- package/build-types/tabs/types.d.ts.map +1 -1
- package/build-types/text-control/index.d.ts +2 -1
- package/build-types/text-control/index.d.ts.map +1 -1
- package/build-types/text-control/types.d.ts +6 -0
- package/build-types/text-control/types.d.ts.map +1 -1
- package/build-types/toggle-group-control/toggle-group-control/component.d.ts +1 -0
- package/build-types/toggle-group-control/toggle-group-control/component.d.ts.map +1 -1
- package/build-types/toggle-group-control/toggle-group-control/styles.d.ts +2 -2
- package/build-types/toggle-group-control/toggle-group-control/styles.d.ts.map +1 -1
- package/build-types/toggle-group-control/types.d.ts +6 -0
- package/build-types/toggle-group-control/types.d.ts.map +1 -1
- package/package.json +19 -20
- package/src/disclosure/index.tsx +44 -0
- package/src/disclosure/types.tsx +10 -0
- package/src/divider/component.tsx +3 -3
- package/src/divider/stories/index.story.tsx +8 -0
- package/src/divider/types.ts +2 -2
- package/src/dropdown-menu/style.scss +4 -0
- package/src/dropdown-menu-v2-ariakit/README.md +0 -7
- package/src/dropdown-menu-v2-ariakit/index.tsx +31 -15
- package/src/dropdown-menu-v2-ariakit/stories/index.story.tsx +1 -4
- package/src/dropdown-menu-v2-ariakit/test/index.tsx +0 -26
- package/src/dropdown-menu-v2-ariakit/types.ts +1 -1
- package/src/gradient-picker/index.tsx +1 -1
- package/src/index.native.js +1 -0
- package/src/mobile/audio-player/index.native.js +9 -13
- package/src/mobile/global-styles-context/utils.native.js +52 -3
- package/src/radio-group/context.tsx +18 -0
- package/src/radio-group/index.tsx +65 -0
- package/src/radio-group/radio.tsx +55 -0
- package/src/radio-group/stories/index.story.tsx +90 -0
- package/src/radio-group/types.ts +39 -0
- package/src/tabs/README.md +3 -33
- package/src/tabs/stories/index.story.tsx +9 -1
- package/src/tabs/styles.ts +16 -0
- package/src/tabs/tab.tsx +6 -6
- package/src/tabs/tablist.tsx +21 -20
- package/src/tabs/tabpanel.tsx +24 -23
- package/src/tabs/test/index.tsx +71 -16
- package/src/tabs/types.ts +7 -32
- package/src/text-control/index.tsx +5 -1
- package/src/text-control/style.scss +5 -0
- package/src/text-control/types.ts +6 -0
- package/src/toggle-group-control/toggle-group-control/component.tsx +8 -2
- package/src/toggle-group-control/toggle-group-control/styles.ts +13 -4
- package/src/toggle-group-control/types.ts +6 -0
- package/src/toolbar/toolbar-button/style.scss +0 -5
- package/tsconfig.tsbuildinfo +1 -1
- package/build/radio-group/radio/index.js +0 -49
- package/build/radio-group/radio/index.js.map +0 -1
- package/build/radio-group/radio-context/index.js +0 -18
- package/build/radio-group/radio-context/index.js.map +0 -1
- package/build-module/radio-group/radio/index.js +0 -40
- package/build-module/radio-group/radio/index.js.map +0 -1
- package/build-module/radio-group/radio-context/index.js +0 -10
- package/build-module/radio-group/radio-context/index.js.map +0 -1
- package/build-types/radio-group/radio/index.d.ts +0 -7
- package/build-types/radio-group/radio/index.d.ts.map +0 -1
- package/build-types/radio-group/radio-context/index.d.ts +0 -6
- package/build-types/radio-group/radio-context/index.d.ts.map +0 -1
- package/src/disclosure/index.js +0 -11
- package/src/radio-group/index.js +0 -51
- package/src/radio-group/radio/index.js +0 -40
- package/src/radio-group/radio-context/index.js +0 -11
- package/src/radio-group/stories/index.story.js +0 -83
|
@@ -14,7 +14,7 @@ import { default as VideoPlayer } from 'react-native-video';
|
|
|
14
14
|
* WordPress dependencies
|
|
15
15
|
*/
|
|
16
16
|
import { View } from '@wordpress/primitives';
|
|
17
|
-
import { Icon } from '@wordpress/components';
|
|
17
|
+
import { Icon, useEditorColorScheme } from '@wordpress/components';
|
|
18
18
|
import { withPreferredColorScheme } from '@wordpress/compose';
|
|
19
19
|
import { __ } from '@wordpress/i18n';
|
|
20
20
|
import { audio, warning } from '@wordpress/icons';
|
|
@@ -34,7 +34,6 @@ import { parseAudioUrl } from './audio-url-parser.native';
|
|
|
34
34
|
const isIOS = Platform.OS === 'ios';
|
|
35
35
|
|
|
36
36
|
function Player( {
|
|
37
|
-
getStylesFromColorScheme,
|
|
38
37
|
isUploadInProgress,
|
|
39
38
|
isUploadFailed,
|
|
40
39
|
attributes,
|
|
@@ -70,14 +69,14 @@ function Player( {
|
|
|
70
69
|
}
|
|
71
70
|
};
|
|
72
71
|
|
|
73
|
-
const containerStyle =
|
|
72
|
+
const containerStyle = useEditorColorScheme(
|
|
74
73
|
styles.container,
|
|
75
74
|
styles.containerDark
|
|
76
75
|
);
|
|
77
76
|
|
|
78
|
-
const iconStyle =
|
|
77
|
+
const iconStyle = useEditorColorScheme( styles.icon, styles.iconDark );
|
|
79
78
|
|
|
80
|
-
const iconDisabledStyle =
|
|
79
|
+
const iconDisabledStyle = useEditorColorScheme(
|
|
81
80
|
styles.iconDisabled,
|
|
82
81
|
styles.iconDisabledDark
|
|
83
82
|
);
|
|
@@ -89,7 +88,7 @@ function Player( {
|
|
|
89
88
|
...( isDisabled && iconDisabledStyle ),
|
|
90
89
|
};
|
|
91
90
|
|
|
92
|
-
const iconContainerStyle =
|
|
91
|
+
const iconContainerStyle = useEditorColorScheme(
|
|
93
92
|
styles.iconContainer,
|
|
94
93
|
styles.iconContainerDark
|
|
95
94
|
);
|
|
@@ -99,17 +98,14 @@ function Player( {
|
|
|
99
98
|
...( isIOS ? styles.titleContainerIOS : styles.titleContainerAndroid ),
|
|
100
99
|
};
|
|
101
100
|
|
|
102
|
-
const titleStyle =
|
|
103
|
-
styles.title,
|
|
104
|
-
styles.titleDark
|
|
105
|
-
);
|
|
101
|
+
const titleStyle = useEditorColorScheme( styles.title, styles.titleDark );
|
|
106
102
|
|
|
107
|
-
const uploadFailedStyle =
|
|
103
|
+
const uploadFailedStyle = useEditorColorScheme(
|
|
108
104
|
styles.uploadFailed,
|
|
109
105
|
styles.uploadFailedDark
|
|
110
106
|
);
|
|
111
107
|
|
|
112
|
-
const subtitleStyle =
|
|
108
|
+
const subtitleStyle = useEditorColorScheme(
|
|
113
109
|
styles.subtitle,
|
|
114
110
|
styles.subtitleDark
|
|
115
111
|
);
|
|
@@ -119,7 +115,7 @@ function Player( {
|
|
|
119
115
|
...( isUploadFailed && uploadFailedStyle ),
|
|
120
116
|
};
|
|
121
117
|
|
|
122
|
-
const buttonBackgroundStyle =
|
|
118
|
+
const buttonBackgroundStyle = useEditorColorScheme(
|
|
123
119
|
styles.buttonBackground,
|
|
124
120
|
styles.buttonBackgroundDark
|
|
125
121
|
);
|
|
@@ -3,6 +3,7 @@
|
|
|
3
3
|
*/
|
|
4
4
|
import { camelCase } from 'change-case';
|
|
5
5
|
import { Dimensions } from 'react-native';
|
|
6
|
+
import { colord } from 'colord';
|
|
6
7
|
|
|
7
8
|
/**
|
|
8
9
|
* WordPress dependencies
|
|
@@ -11,7 +12,14 @@ import {
|
|
|
11
12
|
getPxFromCssUnit,
|
|
12
13
|
useSettings,
|
|
13
14
|
useMultipleOriginColorsAndGradients,
|
|
15
|
+
SETTINGS_DEFAULTS,
|
|
14
16
|
} from '@wordpress/block-editor';
|
|
17
|
+
import { usePreferredColorSchemeStyle } from '@wordpress/compose';
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* Internal dependencies
|
|
21
|
+
*/
|
|
22
|
+
import { useGlobalStyles } from './index.native';
|
|
15
23
|
|
|
16
24
|
export const BLOCK_STYLE_ATTRIBUTES = [
|
|
17
25
|
'textColor',
|
|
@@ -355,13 +363,17 @@ export function useMobileGlobalStylesColors( type = 'colors' ) {
|
|
|
355
363
|
[]
|
|
356
364
|
);
|
|
357
365
|
// Default editor colors/gradients if it's not a block-based theme.
|
|
358
|
-
const
|
|
366
|
+
const defaultPaletteSetting =
|
|
359
367
|
type === 'colors' ? 'color.palette' : 'color.gradients';
|
|
360
|
-
const [
|
|
368
|
+
const [ defaultPaletteValue ] = useSettings( defaultPaletteSetting );
|
|
369
|
+
// In edge cases, the default palette might be undefined. To avoid
|
|
370
|
+
// exceptions across the editor in that case, we explicitly return
|
|
371
|
+
// the default editor colors.
|
|
372
|
+
const defaultPalette = defaultPaletteValue ?? SETTINGS_DEFAULTS.colors;
|
|
361
373
|
|
|
362
374
|
return availableThemeColors.length >= 1
|
|
363
375
|
? availableThemeColors
|
|
364
|
-
:
|
|
376
|
+
: defaultPalette;
|
|
365
377
|
}
|
|
366
378
|
|
|
367
379
|
export function getColorsAndGradients(
|
|
@@ -436,3 +448,40 @@ export function getGlobalStyles( rawStyles, rawFeatures ) {
|
|
|
436
448
|
__experimentalGlobalStylesBaseStyles: globalStyles,
|
|
437
449
|
};
|
|
438
450
|
}
|
|
451
|
+
|
|
452
|
+
/**
|
|
453
|
+
* Determine and apply appropriate color scheme based on global styles or device's light/dark mode.
|
|
454
|
+
*
|
|
455
|
+
* The function first attempts to retrieve the editor's background color from global styles.
|
|
456
|
+
* If the detected background color is light, light styles are applied, and dark styles otherwise.
|
|
457
|
+
* If no custom background color is defined, styles are applied using the device's dark/light setting.
|
|
458
|
+
*
|
|
459
|
+
* @param {Object} baseStyle - An object representing the base (light theme) styles for the editor.
|
|
460
|
+
* @param {Object} darkStyle - An object representing the additional styles to apply when the editor is in dark mode.
|
|
461
|
+
*
|
|
462
|
+
* @return {Object} - The combined style object that should be applied to the editor.
|
|
463
|
+
*/
|
|
464
|
+
export const useEditorColorScheme = ( baseStyle, darkStyle ) => {
|
|
465
|
+
const globalStyles = useGlobalStyles();
|
|
466
|
+
|
|
467
|
+
const deviceColorScheme = usePreferredColorSchemeStyle(
|
|
468
|
+
baseStyle,
|
|
469
|
+
darkStyle
|
|
470
|
+
);
|
|
471
|
+
|
|
472
|
+
const editorColors = globalStyles?.baseColors?.color;
|
|
473
|
+
const editorBackgroundColor = editorColors?.background;
|
|
474
|
+
|
|
475
|
+
const isBackgroundColorDefined =
|
|
476
|
+
typeof editorBackgroundColor !== 'undefined' &&
|
|
477
|
+
editorBackgroundColor !== 'undefined';
|
|
478
|
+
|
|
479
|
+
if ( isBackgroundColorDefined ) {
|
|
480
|
+
const isEditorBackgroundDark = colord( editorBackgroundColor ).isDark();
|
|
481
|
+
return isEditorBackgroundDark
|
|
482
|
+
? { ...baseStyle, ...darkStyle }
|
|
483
|
+
: baseStyle;
|
|
484
|
+
}
|
|
485
|
+
|
|
486
|
+
return deviceColorScheme;
|
|
487
|
+
};
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* External dependencies
|
|
3
|
+
*/
|
|
4
|
+
// eslint-disable-next-line no-restricted-imports
|
|
5
|
+
import type * as Ariakit from '@ariakit/react';
|
|
6
|
+
|
|
7
|
+
/**
|
|
8
|
+
* WordPress dependencies
|
|
9
|
+
*/
|
|
10
|
+
import { createContext } from '@wordpress/element';
|
|
11
|
+
|
|
12
|
+
export const RadioGroupContext = createContext< {
|
|
13
|
+
store?: Ariakit.RadioStore;
|
|
14
|
+
disabled?: boolean;
|
|
15
|
+
} >( {
|
|
16
|
+
store: undefined,
|
|
17
|
+
disabled: undefined,
|
|
18
|
+
} );
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* External dependencies
|
|
3
|
+
*/
|
|
4
|
+
// eslint-disable-next-line no-restricted-imports
|
|
5
|
+
import * as Ariakit from '@ariakit/react';
|
|
6
|
+
|
|
7
|
+
/**
|
|
8
|
+
* WordPress dependencies
|
|
9
|
+
*/
|
|
10
|
+
import { useMemo, forwardRef } from '@wordpress/element';
|
|
11
|
+
|
|
12
|
+
/**
|
|
13
|
+
* Internal dependencies
|
|
14
|
+
*/
|
|
15
|
+
import ButtonGroup from '../button-group';
|
|
16
|
+
import type { WordPressComponentProps } from '../context';
|
|
17
|
+
import { RadioGroupContext } from './context';
|
|
18
|
+
import type { RadioGroupProps } from './types';
|
|
19
|
+
|
|
20
|
+
function UnforwardedRadioGroup(
|
|
21
|
+
{
|
|
22
|
+
label,
|
|
23
|
+
checked,
|
|
24
|
+
defaultChecked,
|
|
25
|
+
disabled,
|
|
26
|
+
onChange,
|
|
27
|
+
children,
|
|
28
|
+
...props
|
|
29
|
+
}: WordPressComponentProps< RadioGroupProps, 'div', false >,
|
|
30
|
+
ref: React.ForwardedRef< any >
|
|
31
|
+
) {
|
|
32
|
+
const radioStore = Ariakit.useRadioStore( {
|
|
33
|
+
value: checked,
|
|
34
|
+
defaultValue: defaultChecked,
|
|
35
|
+
setValue: ( newValue ) => {
|
|
36
|
+
onChange?.( newValue ?? undefined );
|
|
37
|
+
},
|
|
38
|
+
} );
|
|
39
|
+
|
|
40
|
+
const contextValue = useMemo(
|
|
41
|
+
() => ( {
|
|
42
|
+
store: radioStore,
|
|
43
|
+
disabled,
|
|
44
|
+
} ),
|
|
45
|
+
[ radioStore, disabled ]
|
|
46
|
+
);
|
|
47
|
+
|
|
48
|
+
return (
|
|
49
|
+
<RadioGroupContext.Provider value={ contextValue }>
|
|
50
|
+
<Ariakit.RadioGroup
|
|
51
|
+
store={ radioStore }
|
|
52
|
+
render={ <ButtonGroup>{ children }</ButtonGroup> }
|
|
53
|
+
aria-label={ label }
|
|
54
|
+
ref={ ref }
|
|
55
|
+
{ ...props }
|
|
56
|
+
/>
|
|
57
|
+
</RadioGroupContext.Provider>
|
|
58
|
+
);
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
/**
|
|
62
|
+
* @deprecated Use `RadioControl` or `ToggleGroupControl` instead.
|
|
63
|
+
*/
|
|
64
|
+
export const RadioGroup = forwardRef( UnforwardedRadioGroup );
|
|
65
|
+
export default RadioGroup;
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* WordPress dependencies
|
|
3
|
+
*/
|
|
4
|
+
import { forwardRef, useContext } from '@wordpress/element';
|
|
5
|
+
|
|
6
|
+
/**
|
|
7
|
+
* External dependencies
|
|
8
|
+
*/
|
|
9
|
+
// eslint-disable-next-line no-restricted-imports
|
|
10
|
+
import * as Ariakit from '@ariakit/react';
|
|
11
|
+
|
|
12
|
+
/**
|
|
13
|
+
* Internal dependencies
|
|
14
|
+
*/
|
|
15
|
+
import Button from '../button';
|
|
16
|
+
import { RadioGroupContext } from './context';
|
|
17
|
+
import type { WordPressComponentProps } from '../context';
|
|
18
|
+
import type { RadioProps } from './types';
|
|
19
|
+
|
|
20
|
+
function UnforwardedRadio(
|
|
21
|
+
{
|
|
22
|
+
value,
|
|
23
|
+
children,
|
|
24
|
+
...props
|
|
25
|
+
}: WordPressComponentProps< RadioProps, 'button', false >,
|
|
26
|
+
ref: React.ForwardedRef< any >
|
|
27
|
+
) {
|
|
28
|
+
const { store, disabled } = useContext( RadioGroupContext );
|
|
29
|
+
|
|
30
|
+
const selectedValue = store?.useState( 'value' );
|
|
31
|
+
const isChecked = selectedValue !== undefined && selectedValue === value;
|
|
32
|
+
|
|
33
|
+
return (
|
|
34
|
+
<Ariakit.Radio
|
|
35
|
+
disabled={ disabled }
|
|
36
|
+
store={ store }
|
|
37
|
+
ref={ ref }
|
|
38
|
+
value={ value }
|
|
39
|
+
render={
|
|
40
|
+
<Button
|
|
41
|
+
variant={ isChecked ? 'primary' : 'secondary' }
|
|
42
|
+
{ ...props }
|
|
43
|
+
/>
|
|
44
|
+
}
|
|
45
|
+
>
|
|
46
|
+
{ children || value }
|
|
47
|
+
</Ariakit.Radio>
|
|
48
|
+
);
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
/**
|
|
52
|
+
* @deprecated Use `RadioControl` or `ToggleGroupControl` instead.
|
|
53
|
+
*/
|
|
54
|
+
export const Radio = forwardRef( UnforwardedRadio );
|
|
55
|
+
export default Radio;
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* External dependencies
|
|
3
|
+
*/
|
|
4
|
+
import type { Meta, StoryFn } from '@storybook/react';
|
|
5
|
+
|
|
6
|
+
/**
|
|
7
|
+
* Internal dependencies
|
|
8
|
+
*/
|
|
9
|
+
import { RadioGroup } from '..';
|
|
10
|
+
import { Radio } from '../radio';
|
|
11
|
+
|
|
12
|
+
/**
|
|
13
|
+
* WordPress dependencies
|
|
14
|
+
*/
|
|
15
|
+
import { useState } from '@wordpress/element';
|
|
16
|
+
|
|
17
|
+
const meta: Meta< typeof RadioGroup > = {
|
|
18
|
+
title: 'Components (Deprecated)/RadioGroup',
|
|
19
|
+
component: RadioGroup,
|
|
20
|
+
// @ts-expect-error - See https://github.com/storybookjs/storybook/issues/23170
|
|
21
|
+
subcomponents: { Radio },
|
|
22
|
+
argTypes: {
|
|
23
|
+
onChange: { control: { type: null } },
|
|
24
|
+
children: { control: { type: null } },
|
|
25
|
+
checked: { control: { type: 'text' } },
|
|
26
|
+
},
|
|
27
|
+
parameters: {
|
|
28
|
+
actions: { argTypesRegex: '^on.*' },
|
|
29
|
+
controls: { expanded: true },
|
|
30
|
+
docs: { canvas: { sourceState: 'shown' } },
|
|
31
|
+
},
|
|
32
|
+
};
|
|
33
|
+
export default meta;
|
|
34
|
+
|
|
35
|
+
const Template: StoryFn< typeof RadioGroup > = ( props ) => {
|
|
36
|
+
return <RadioGroup { ...props } />;
|
|
37
|
+
};
|
|
38
|
+
|
|
39
|
+
export const Default: StoryFn< typeof RadioGroup > = Template.bind( {} );
|
|
40
|
+
Default.args = {
|
|
41
|
+
id: 'default-radiogroup',
|
|
42
|
+
label: 'options',
|
|
43
|
+
defaultChecked: 'option2',
|
|
44
|
+
children: (
|
|
45
|
+
<>
|
|
46
|
+
<Radio value="option1">Option 1</Radio>
|
|
47
|
+
<Radio value="option2">Option 2</Radio>
|
|
48
|
+
<Radio value="option3">Option 3</Radio>
|
|
49
|
+
</>
|
|
50
|
+
),
|
|
51
|
+
};
|
|
52
|
+
|
|
53
|
+
export const Disabled: StoryFn< typeof RadioGroup > = Template.bind( {} );
|
|
54
|
+
Disabled.args = {
|
|
55
|
+
...Default.args,
|
|
56
|
+
id: 'disabled-radiogroup',
|
|
57
|
+
disabled: true,
|
|
58
|
+
};
|
|
59
|
+
|
|
60
|
+
const ControlledTemplate: StoryFn< typeof RadioGroup > = ( {
|
|
61
|
+
checked: checkedProp,
|
|
62
|
+
onChange: onChangeProp,
|
|
63
|
+
...props
|
|
64
|
+
} ) => {
|
|
65
|
+
const [ checked, setChecked ] =
|
|
66
|
+
useState< React.ComponentProps< typeof RadioGroup >[ 'checked' ] >(
|
|
67
|
+
checkedProp
|
|
68
|
+
);
|
|
69
|
+
|
|
70
|
+
const onChange: typeof onChangeProp = ( value ) => {
|
|
71
|
+
setChecked( value );
|
|
72
|
+
onChangeProp?.( value );
|
|
73
|
+
};
|
|
74
|
+
|
|
75
|
+
return (
|
|
76
|
+
<RadioGroup { ...props } onChange={ onChange } checked={ checked } />
|
|
77
|
+
);
|
|
78
|
+
};
|
|
79
|
+
|
|
80
|
+
export const Controlled: StoryFn< typeof RadioGroup > = ControlledTemplate.bind(
|
|
81
|
+
{}
|
|
82
|
+
);
|
|
83
|
+
Controlled.args = {
|
|
84
|
+
...Default.args,
|
|
85
|
+
checked: 'option2',
|
|
86
|
+
id: 'controlled-radiogroup',
|
|
87
|
+
};
|
|
88
|
+
Controlled.argTypes = {
|
|
89
|
+
checked: { control: { type: null } },
|
|
90
|
+
};
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
export type RadioGroupProps = {
|
|
2
|
+
/**
|
|
3
|
+
* Accessible label for the radio group
|
|
4
|
+
*/
|
|
5
|
+
label: string;
|
|
6
|
+
/**
|
|
7
|
+
* The `value` of the `Radio` element which should be selected.
|
|
8
|
+
* Indicates controlled usage of the component.
|
|
9
|
+
*/
|
|
10
|
+
checked?: string | number;
|
|
11
|
+
/**
|
|
12
|
+
* The value of the radio element which is initially selected.
|
|
13
|
+
*/
|
|
14
|
+
defaultChecked?: string | number;
|
|
15
|
+
/**
|
|
16
|
+
* Whether the `RadioGroup` should be disabled.
|
|
17
|
+
*/
|
|
18
|
+
disabled?: boolean;
|
|
19
|
+
/**
|
|
20
|
+
* Called when a `Radio` element has been selected.
|
|
21
|
+
* Receives the `value` of the selected element as an argument.
|
|
22
|
+
*/
|
|
23
|
+
onChange?: ( value: string | number | undefined ) => void;
|
|
24
|
+
/**
|
|
25
|
+
* The children elements, which should be a series of `Radio` components.
|
|
26
|
+
*/
|
|
27
|
+
children: React.ReactNode;
|
|
28
|
+
};
|
|
29
|
+
|
|
30
|
+
export type RadioProps = {
|
|
31
|
+
/**
|
|
32
|
+
* The actual value of the radio element.
|
|
33
|
+
*/
|
|
34
|
+
value: string | number;
|
|
35
|
+
/**
|
|
36
|
+
* Content displayed on the Radio element. If there aren't any children, `value` is displayed.
|
|
37
|
+
*/
|
|
38
|
+
children?: React.ReactNode;
|
|
39
|
+
};
|
package/src/tabs/README.md
CHANGED
|
@@ -159,19 +159,6 @@ The children elements, which should be a series of `Tabs.TabPanel` components.
|
|
|
159
159
|
|
|
160
160
|
- Required: No
|
|
161
161
|
|
|
162
|
-
###### `className`: `string`
|
|
163
|
-
|
|
164
|
-
The class name to apply to the tablist.
|
|
165
|
-
|
|
166
|
-
- Required: No
|
|
167
|
-
- Default: ''
|
|
168
|
-
|
|
169
|
-
###### `style`: `React.CSSProperties`
|
|
170
|
-
|
|
171
|
-
Custom CSS styles for the tablist.
|
|
172
|
-
|
|
173
|
-
- Required: No
|
|
174
|
-
|
|
175
162
|
#### Tab
|
|
176
163
|
|
|
177
164
|
##### Props
|
|
@@ -182,24 +169,12 @@ The id of the tab, which is prepended with the `Tabs` instance ID.
|
|
|
182
169
|
|
|
183
170
|
- Required: Yes
|
|
184
171
|
|
|
185
|
-
###### `style`: `React.CSSProperties`
|
|
186
|
-
|
|
187
|
-
Custom CSS styles for the tab.
|
|
188
|
-
|
|
189
|
-
- Required: No
|
|
190
|
-
|
|
191
172
|
###### `children`: `React.ReactNode`
|
|
192
173
|
|
|
193
174
|
The children elements, generally the text to display on the tab.
|
|
194
175
|
|
|
195
176
|
- Required: No
|
|
196
177
|
|
|
197
|
-
###### `className`: `string`
|
|
198
|
-
|
|
199
|
-
The class name to apply to the tab.
|
|
200
|
-
|
|
201
|
-
- Required: No
|
|
202
|
-
|
|
203
178
|
###### `disabled`: `boolean`
|
|
204
179
|
|
|
205
180
|
Determines if the tab button should be disabled.
|
|
@@ -229,14 +204,9 @@ The id of the tabpanel, which is combined with the `Tabs` instance ID and the su
|
|
|
229
204
|
|
|
230
205
|
- Required: Yes
|
|
231
206
|
|
|
232
|
-
###### `
|
|
233
|
-
|
|
234
|
-
The class name to apply to the tabpanel.
|
|
235
|
-
|
|
236
|
-
- Required: No
|
|
237
|
-
|
|
238
|
-
###### `style`: `React.CSSProperties`
|
|
207
|
+
###### `focusable`: `boolean`
|
|
239
208
|
|
|
240
|
-
|
|
209
|
+
Determines whether or not the tabpanel element should be focusable. If `false`, pressing the tab key will skip over the tabpanel, and instead focus on the first focusable element in the panel (if there is one).
|
|
241
210
|
|
|
242
211
|
- Required: No
|
|
212
|
+
- Default: `true`
|
|
@@ -42,8 +42,16 @@ const Template: StoryFn< typeof Tabs > = ( props ) => {
|
|
|
42
42
|
<Tabs.TabPanel id={ 'tab2' }>
|
|
43
43
|
<p>Selected tab: Tab 2</p>
|
|
44
44
|
</Tabs.TabPanel>
|
|
45
|
-
<Tabs.TabPanel id={ 'tab3' }>
|
|
45
|
+
<Tabs.TabPanel id={ 'tab3' } focusable={ false }>
|
|
46
46
|
<p>Selected tab: Tab 3</p>
|
|
47
|
+
<p>
|
|
48
|
+
This tabpanel has its <code>focusable</code> prop set to
|
|
49
|
+
<code> false</code>, so it won't get a tab stop.
|
|
50
|
+
<br />
|
|
51
|
+
Instead, the [Tab] key will move focus to the first
|
|
52
|
+
focusable element within the panel.
|
|
53
|
+
</p>
|
|
54
|
+
<Button variant="primary">I'm a button!</Button>
|
|
47
55
|
</Tabs.TabPanel>
|
|
48
56
|
</Tabs>
|
|
49
57
|
);
|
package/src/tabs/styles.ts
CHANGED
|
@@ -101,3 +101,19 @@ export const Tab = styled( Ariakit.Tab )`
|
|
|
101
101
|
}
|
|
102
102
|
}
|
|
103
103
|
`;
|
|
104
|
+
|
|
105
|
+
export const TabPanel = styled( Ariakit.TabPanel )`
|
|
106
|
+
&:focus {
|
|
107
|
+
box-shadow: none;
|
|
108
|
+
outline: none;
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
&:focus-visible {
|
|
112
|
+
border-radius: 2px;
|
|
113
|
+
box-shadow: 0 0 0 var( --wp-admin-border-width-focus )
|
|
114
|
+
${ COLORS.theme.accent };
|
|
115
|
+
// Windows high contrast mode.
|
|
116
|
+
outline: 2px solid transparent;
|
|
117
|
+
outline-offset: 0;
|
|
118
|
+
}
|
|
119
|
+
`;
|
package/src/tabs/tab.tsx
CHANGED
|
@@ -11,11 +11,12 @@ import type { TabProps } from './types';
|
|
|
11
11
|
import warning from '@wordpress/warning';
|
|
12
12
|
import { TabsContext } from './context';
|
|
13
13
|
import { Tab as StyledTab } from './styles';
|
|
14
|
+
import type { WordPressComponentProps } from '../context';
|
|
14
15
|
|
|
15
|
-
export const Tab = forwardRef<
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
) {
|
|
16
|
+
export const Tab = forwardRef<
|
|
17
|
+
HTMLButtonElement,
|
|
18
|
+
WordPressComponentProps< TabProps, 'button', false >
|
|
19
|
+
>( function Tab( { children, id, disabled, render, ...otherProps }, ref ) {
|
|
19
20
|
const context = useContext( TabsContext );
|
|
20
21
|
if ( ! context ) {
|
|
21
22
|
warning( '`Tabs.TabList` must be wrapped in a `Tabs` component.' );
|
|
@@ -28,10 +29,9 @@ export const Tab = forwardRef< HTMLButtonElement, TabProps >( function Tab(
|
|
|
28
29
|
ref={ ref }
|
|
29
30
|
store={ store }
|
|
30
31
|
id={ instancedTabId }
|
|
31
|
-
className={ className }
|
|
32
|
-
style={ style }
|
|
33
32
|
disabled={ disabled }
|
|
34
33
|
render={ render }
|
|
34
|
+
{ ...otherProps }
|
|
35
35
|
>
|
|
36
36
|
{ children }
|
|
37
37
|
</StyledTab>
|
package/src/tabs/tablist.tsx
CHANGED
|
@@ -16,25 +16,26 @@ import { forwardRef } from '@wordpress/element';
|
|
|
16
16
|
import type { TabListProps } from './types';
|
|
17
17
|
import { useTabsContext } from './context';
|
|
18
18
|
import { TabListWrapper } from './styles';
|
|
19
|
+
import type { WordPressComponentProps } from '../context';
|
|
19
20
|
|
|
20
|
-
export const TabList = forwardRef<
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
return (
|
|
29
|
-
<Ariakit.TabList
|
|
30
|
-
ref={ ref }
|
|
31
|
-
style={ style }
|
|
32
|
-
store={ store }
|
|
33
|
-
className={ className }
|
|
34
|
-
render={ <TabListWrapper /> }
|
|
35
|
-
>
|
|
36
|
-
{ children }
|
|
37
|
-
</Ariakit.TabList>
|
|
38
|
-
);
|
|
21
|
+
export const TabList = forwardRef<
|
|
22
|
+
HTMLDivElement,
|
|
23
|
+
WordPressComponentProps< TabListProps, 'div', false >
|
|
24
|
+
>( function TabList( { children, ...otherProps }, ref ) {
|
|
25
|
+
const context = useTabsContext();
|
|
26
|
+
if ( ! context ) {
|
|
27
|
+
warning( '`Tabs.TabList` must be wrapped in a `Tabs` component.' );
|
|
28
|
+
return null;
|
|
39
29
|
}
|
|
40
|
-
|
|
30
|
+
const { store } = context;
|
|
31
|
+
return (
|
|
32
|
+
<Ariakit.TabList
|
|
33
|
+
ref={ ref }
|
|
34
|
+
store={ store }
|
|
35
|
+
render={ <TabListWrapper /> }
|
|
36
|
+
{ ...otherProps }
|
|
37
|
+
>
|
|
38
|
+
{ children }
|
|
39
|
+
</Ariakit.TabList>
|
|
40
|
+
);
|
|
41
|
+
} );
|
package/src/tabs/tabpanel.tsx
CHANGED
|
@@ -1,8 +1,6 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* External dependencies
|
|
3
3
|
*/
|
|
4
|
-
// eslint-disable-next-line no-restricted-imports
|
|
5
|
-
import * as Ariakit from '@ariakit/react';
|
|
6
4
|
|
|
7
5
|
/**
|
|
8
6
|
* WordPress dependencies
|
|
@@ -14,29 +12,32 @@ import { forwardRef, useContext } from '@wordpress/element';
|
|
|
14
12
|
* Internal dependencies
|
|
15
13
|
*/
|
|
16
14
|
import type { TabPanelProps } from './types';
|
|
15
|
+
import { TabPanel as StyledTabPanel } from './styles';
|
|
17
16
|
|
|
18
17
|
import warning from '@wordpress/warning';
|
|
19
18
|
import { TabsContext } from './context';
|
|
19
|
+
import type { WordPressComponentProps } from '../context';
|
|
20
20
|
|
|
21
|
-
export const TabPanel = forwardRef<
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
return (
|
|
31
|
-
<Ariakit.TabPanel
|
|
32
|
-
ref={ ref }
|
|
33
|
-
style={ style }
|
|
34
|
-
store={ store }
|
|
35
|
-
id={ `${ instanceId }-${ id }-view` }
|
|
36
|
-
className={ className }
|
|
37
|
-
>
|
|
38
|
-
{ children }
|
|
39
|
-
</Ariakit.TabPanel>
|
|
40
|
-
);
|
|
21
|
+
export const TabPanel = forwardRef<
|
|
22
|
+
HTMLDivElement,
|
|
23
|
+
WordPressComponentProps< TabPanelProps, 'div', false >
|
|
24
|
+
>( function TabPanel( { children, id, focusable = true, ...otherProps }, ref ) {
|
|
25
|
+
const context = useContext( TabsContext );
|
|
26
|
+
if ( ! context ) {
|
|
27
|
+
warning( '`Tabs.TabPanel` must be wrapped in a `Tabs` component.' );
|
|
28
|
+
return null;
|
|
41
29
|
}
|
|
42
|
-
|
|
30
|
+
const { store, instanceId } = context;
|
|
31
|
+
|
|
32
|
+
return (
|
|
33
|
+
<StyledTabPanel
|
|
34
|
+
ref={ ref }
|
|
35
|
+
store={ store }
|
|
36
|
+
id={ `${ instanceId }-${ id }-view` }
|
|
37
|
+
focusable={ focusable }
|
|
38
|
+
{ ...otherProps }
|
|
39
|
+
>
|
|
40
|
+
{ children }
|
|
41
|
+
</StyledTabPanel>
|
|
42
|
+
);
|
|
43
|
+
} );
|