@@ -452,7 +452,7 @@ Snapshot Diff:
tabIndex="0"
/>
@@ -511,7 +511,7 @@ Snapshot Diff:
type="button"
/>
@@ -537,7 +537,7 @@ Snapshot Diff:
tabIndex="0"
/>
@@ -574,56 +574,20 @@ Snapshot Diff:
`;
exports[`ColorPicker should render color picker 1`] = `
-.emotion-0 {
- border: 0;
- -webkit-clip: rect( 1px,1px,1px,1px );
- clip: rect( 1px,1px,1px,1px );
- -webkit-clip-path: inset( 50% );
- -webkit-clip-path: inset( 50% );
- clip-path: inset( 50% );
- height: 1px;
- margin: -1px;
- overflow: hidden;
- padding: 0;
- position: absolute;
- width: 1px;
- word-wrap: normal !important;
-}
-
-.emotion-0:focus {
- background-color: #edeff0;
- -webkit-clip: auto !important;
- clip: auto !important;
- -webkit-clip-path: none;
- clip-path: none;
- color: #444;
- display: block;
- font-size: 1em;
- height: auto;
- left: 5px;
- line-height: normal;
- padding: 15px 23px 14px;
- -webkit-text-decoration: none;
- text-decoration: none;
- top: 5px;
- width: auto;
- z-index: 100000;
-}
-
-.emotion-10 {
+.emotion-4 {
font-family: -apple-system,BlinkMacSystemFont,'Segoe UI',Roboto,Oxygen-Sans,Ubuntu,Cantarell,'Helvetica Neue',sans-serif;
font-size: 13px;
}
-.emotion-8 {
+.emotion-2 {
margin-bottom: 8px;
}
-.components-panel__row .emotion-8 {
+.components-panel__row .emotion-2 {
margin-bottom: inherit;
}
-.emotion-6 {
+.emotion-0 {
display: inline-block;
margin-bottom: 8px;
}
@@ -667,7 +631,7 @@ exports[`ColorPicker should render color picker 1`] = `
type="button"
/>
Use your arrow keys to change the base color. Move up to lighten the color, down to darken, left to decrease saturation, and right to increase saturation.
@@ -727,7 +691,7 @@ exports[`ColorPicker should render color picker 1`] = `
tabIndex="0"
/>
Move the arrow left or right to change hue.
@@ -744,13 +708,13 @@ exports[`ColorPicker should render color picker 1`] = `
className="components-color-picker__inputs-fields"
>
Color value in hexadecimal
diff --git a/packages/components/src/style.scss b/packages/components/src/style.scss
index 255bb2caefaf2c..13c2049b894bf5 100644
--- a/packages/components/src/style.scss
+++ b/packages/components/src/style.scss
@@ -46,3 +46,4 @@
@import "./toolbar-button/style.scss";
@import "./toolbar-group/style.scss";
@import "./tooltip/style.scss";
+@import "./visually-hidden/style.scss";
diff --git a/packages/components/src/ui/form-group/form-group-label.js b/packages/components/src/ui/form-group/form-group-label.js
index 1b3e3665205f76..fd4af178cf6203 100644
--- a/packages/components/src/ui/form-group/form-group-label.js
+++ b/packages/components/src/ui/form-group/form-group-label.js
@@ -18,7 +18,7 @@ function FormGroupLabel( { children, id, labelHidden = false, ...props } ) {
if ( labelHidden ) {
return (
-
+
{ children }
);
diff --git a/packages/components/src/ui/index.js b/packages/components/src/ui/index.js
index fb4ceeeba33a6f..7f0213b0a25dc2 100644
--- a/packages/components/src/ui/index.js
+++ b/packages/components/src/ui/index.js
@@ -10,3 +10,4 @@ export * from './shortcut';
export * from './spinner';
export * from './v-stack';
export * from './view';
+export * from './visually-hidden';
diff --git a/packages/components/src/ui/visually-hidden/README.md b/packages/components/src/ui/visually-hidden/README.md
new file mode 100644
index 00000000000000..6200eed80dacb1
--- /dev/null
+++ b/packages/components/src/ui/visually-hidden/README.md
@@ -0,0 +1,17 @@
+# VisuallyHidden
+
+`VisuallyHidden` is a component used to render text intended to be visually hidden, but will show for alternate devices, for example a screen reader.
+
+## Usage
+
+```jsx
+import { View, VisuallyHidden } from '@wordpress/components/ui';
+
+function Example() {
+ return (
+
+ Code is Poetry
+
+ );
+}
+```
diff --git a/packages/components/src/visually-hidden/component.js b/packages/components/src/ui/visually-hidden/component.js
similarity index 76%
rename from packages/components/src/visually-hidden/component.js
rename to packages/components/src/ui/visually-hidden/component.js
index a8da730c72f1c1..6912caa4e08433 100644
--- a/packages/components/src/visually-hidden/component.js
+++ b/packages/components/src/ui/visually-hidden/component.js
@@ -1,7 +1,7 @@
/**
* Internal dependencies
*/
-import { createComponent } from '../ui/utils';
+import { createComponent } from '../utils';
import { useVisuallyHidden } from './hook';
/**
@@ -10,12 +10,12 @@ import { useVisuallyHidden } from './hook';
*
* @example
* ```jsx
- * import { VisuallyHidden } from `@wordpress/components`;
+ * import { View, VisuallyHidden } from `@wordpress/components/ui`;
*
* function Example() {
* return (
*
- * Code is Poetry
+ * Code is Poetry
*
* );
* }
diff --git a/packages/components/src/visually-hidden/hook.js b/packages/components/src/ui/visually-hidden/hook.js
similarity index 54%
rename from packages/components/src/visually-hidden/hook.js
rename to packages/components/src/ui/visually-hidden/hook.js
index 61205a5cf23351..d46c65cb8cbfe9 100644
--- a/packages/components/src/visually-hidden/hook.js
+++ b/packages/components/src/ui/visually-hidden/hook.js
@@ -8,13 +8,16 @@ import { cx } from 'emotion';
*/
import * as styles from './styles';
+// duplicate this for the sake of being able to export it, it'll be removed when we replace VisuallyHidden in components/src anyway
+/** @typedef {import('../context').ViewOwnProps<{}, 'div'>} Props */
+
/**
- * @param {import('../ui/context').ViewOwnProps<{}, 'div'>} props
+ * @param {import('../context').ViewOwnProps<{}, 'div'>} props
*/
export function useVisuallyHidden( { className, ...props } ) {
// circumvent the context system and write the classnames ourselves
const classes = cx(
- 'components-visually-hidden',
+ 'components-visually-hidden wp-components-visually-hidden',
className,
styles.VisuallyHidden
);
diff --git a/packages/components/src/ui/visually-hidden/index.js b/packages/components/src/ui/visually-hidden/index.js
new file mode 100644
index 00000000000000..8bbed8b73ac9eb
--- /dev/null
+++ b/packages/components/src/ui/visually-hidden/index.js
@@ -0,0 +1,2 @@
+export { default as VisuallyHidden } from './component';
+export * from './hook';
diff --git a/packages/components/src/ui/visually-hidden/stories/index.js b/packages/components/src/ui/visually-hidden/stories/index.js
new file mode 100644
index 00000000000000..b5f55c1fa1d24d
--- /dev/null
+++ b/packages/components/src/ui/visually-hidden/stories/index.js
@@ -0,0 +1,42 @@
+/**
+ * Internal dependencies
+ */
+import { VisuallyHidden } from '..';
+
+export default {
+ title: 'G2 Components (Experimental)/VisuallyHidden',
+ component: VisuallyHidden,
+};
+
+export const _default = () => (
+ <>
+ This should not show.
+
+ This text will{ ' ' }
+ but not inline always
+ show.
+
+ >
+);
+
+export const withForwardedProps = () => (
+ <>
+ Additional props can be passed to VisuallyHidden and are forwarded to
+ the rendered element.{ ' ' }
+
+ Check out my data attribute!{ ' ' }
+
+ Inspect the HTML to see!
+ >
+);
+
+export const withAdditionalClassNames = () => (
+ <>
+ Additional class names passed to VisuallyHidden extend the component
+ class name.{ ' ' }
+
+ Check out my class!{ ' ' }
+
+ Inspect the HTML to see!
+ >
+);
diff --git a/packages/components/src/visually-hidden/styles.js b/packages/components/src/ui/visually-hidden/styles.js
similarity index 92%
rename from packages/components/src/visually-hidden/styles.js
rename to packages/components/src/ui/visually-hidden/styles.js
index fe034ae7e94d61..9265d0c0aee604 100644
--- a/packages/components/src/visually-hidden/styles.js
+++ b/packages/components/src/ui/visually-hidden/styles.js
@@ -2,11 +2,10 @@
* External dependencies
*/
import { css } from 'emotion';
-
/**
* Internal dependencies
*/
-import { COLORS } from '../utils/colors-values';
+import { COLORS } from '../../utils/colors-values';
export const VisuallyHidden = css`
border: 0;
diff --git a/packages/components/src/visually-hidden/test/__snapshots__/index.js.snap b/packages/components/src/ui/visually-hidden/test/__snapshots__/index.js.snap
similarity index 89%
rename from packages/components/src/visually-hidden/test/__snapshots__/index.js.snap
rename to packages/components/src/ui/visually-hidden/test/__snapshots__/index.js.snap
index c144748136e7e7..e6a1b7bd905bd3 100644
--- a/packages/components/src/visually-hidden/test/__snapshots__/index.js.snap
+++ b/packages/components/src/ui/visually-hidden/test/__snapshots__/index.js.snap
@@ -38,7 +38,7 @@ exports[`VisuallyHidden should render correctly 1`] = `
}
This is hidden
diff --git a/packages/components/src/visually-hidden/test/index.js b/packages/components/src/ui/visually-hidden/test/index.js
similarity index 92%
rename from packages/components/src/visually-hidden/test/index.js
rename to packages/components/src/ui/visually-hidden/test/index.js
index f753a7c41f050a..6925edbee9eefb 100644
--- a/packages/components/src/visually-hidden/test/index.js
+++ b/packages/components/src/ui/visually-hidden/test/index.js
@@ -6,7 +6,7 @@ import { render } from '@testing-library/react';
/**
* Internal dependencies
*/
-import VisuallyHidden, { useVisuallyHidden } from '..';
+import { VisuallyHidden, useVisuallyHidden } from '..';
describe( 'useVisuallyHidden', () => {
it( 'should apply the expected classnames', () => {
diff --git a/packages/components/src/visually-hidden/README.md b/packages/components/src/visually-hidden/README.md
index 9da03aeeb3b7b8..1f490f5134af26 100644
--- a/packages/components/src/visually-hidden/README.md
+++ b/packages/components/src/visually-hidden/README.md
@@ -1,17 +1,9 @@
# VisuallyHidden
-`VisuallyHidden` is a component used to render text intended to be visually hidden, but will show for alternate devices, for example a screen reader.
+A component used to render text intended to be visually hidden, but will show for alternate devices, for example a screen reader.
-## Usage
+### Usage
```jsx
-import { VisuallyHidden } from '@wordpress/components';
-
-function Example() {
- return (
-
- Code is Poetry
-
- );
-}
+ Show text for screenreader.
```
diff --git a/packages/components/src/visually-hidden/index.js b/packages/components/src/visually-hidden/index.js
index 4c59b9138c4f21..92801940d38b9c 100644
--- a/packages/components/src/visually-hidden/index.js
+++ b/packages/components/src/visually-hidden/index.js
@@ -1,2 +1,46 @@
-export { default } from './component';
-export * from './hook';
+/**
+ * External dependencies
+ */
+import classnames from 'classnames';
+
+/**
+ * WordPress dependencies
+ */
+import { forwardRef } from '@wordpress/element';
+
+/**
+ * Internal dependencies
+ */
+import { renderAsRenderProps } from './utils';
+import { withNextComponent } from './next';
+
+/**
+ * @template {keyof JSX.IntrinsicElements | import('react').JSXElementConstructor} T
+ * @typedef OwnProps
+ * @property {T} [as='div'] Component to render, e.g. `"div"` or `MyComponent`.
+ */
+
+/**
+ * @template {keyof JSX.IntrinsicElements | import('react').JSXElementConstructor} T
+ * @typedef {OwnProps & import('react').ComponentPropsWithRef} Props
+ */
+
+/**
+ * VisuallyHidden component to render text out non-visually
+ * for use in devices such as a screen reader.
+ *
+ * @template {keyof JSX.IntrinsicElements | import('react').JSXElementConstructor} T T
+ * @param {Props} props
+ * @param {import('react').Ref} forwardedRef
+ * @return {JSX.Element} Element
+ */
+function VisuallyHidden( { as = 'div', className, ...props }, forwardedRef ) {
+ return renderAsRenderProps( {
+ as,
+ className: classnames( 'components-visually-hidden', className ),
+ ...props,
+ ref: forwardedRef,
+ } );
+}
+
+export default withNextComponent( forwardRef( VisuallyHidden ) );
diff --git a/packages/components/src/visually-hidden/next.js b/packages/components/src/visually-hidden/next.js
new file mode 100644
index 00000000000000..088f90f6be5ed6
--- /dev/null
+++ b/packages/components/src/visually-hidden/next.js
@@ -0,0 +1,31 @@
+/**
+ * Internal dependencies
+ */
+import { VisuallyHidden as NextVisuallyHidden } from '../ui/visually-hidden';
+import { withNext } from '../ui/context';
+
+const VisuallyHidden =
+ process.env.COMPONENT_SYSTEM_PHASE === 1 ? NextVisuallyHidden : undefined;
+
+/**
+ * There is nothing to adapt, the props are equal.
+ *
+ * @param {import('.').Props} props
+ * @return {import('../ui/visually-hidden/hook').Props} Adapted props
+ */
+const adapter = ( props ) =>
+ /** @type {import('../ui/visually-hidden/hook').Props} */ ( props );
+
+/**
+ * The generic type is too difficult to type here, default to any to circumvent that.
+ *
+ * @param {import('react').ForwardRefExoticComponent>} Current
+ */
+export function withNextComponent( Current ) {
+ return withNext(
+ Current,
+ VisuallyHidden,
+ 'WPComponentsVisuallyHidden',
+ adapter
+ );
+}
diff --git a/packages/components/src/visually-hidden/stories/index.js b/packages/components/src/visually-hidden/stories/index.js
index 497fb0c2ab23d8..2b45ad1d15121c 100644
--- a/packages/components/src/visually-hidden/stories/index.js
+++ b/packages/components/src/visually-hidden/stories/index.js
@@ -1,7 +1,7 @@
/**
* Internal dependencies
*/
-import { VisuallyHidden } from '..';
+import VisuallyHidden from '../';
export default {
title: 'Components/VisuallyHidden',
diff --git a/packages/components/src/visually-hidden/style.scss b/packages/components/src/visually-hidden/style.scss
new file mode 100644
index 00000000000000..8c8d8472d57793
--- /dev/null
+++ b/packages/components/src/visually-hidden/style.scss
@@ -0,0 +1,30 @@
+.components-visually-hidden {
+ border: 0;
+ clip: rect(1px, 1px, 1px, 1px);
+ -webkit-clip-path: inset(50%);
+ clip-path: inset(50%);
+ height: 1px;
+ margin: -1px;
+ overflow: hidden;
+ padding: 0;
+ position: absolute;
+ width: 1px;
+ word-wrap: normal !important;
+}
+
+.components-visually-hidden:focus {
+ background-color: $gray-300;
+ clip: auto !important;
+ clip-path: none;
+ color: #444;
+ display: block;
+ font-size: 1em;
+ height: auto;
+ left: 5px;
+ line-height: normal;
+ padding: 15px 23px 14px;
+ text-decoration: none;
+ top: 5px;
+ width: auto;
+ z-index: 100000;
+}
diff --git a/packages/components/src/visually-hidden/utils.js b/packages/components/src/visually-hidden/utils.js
new file mode 100644
index 00000000000000..d8be9e759c6145
--- /dev/null
+++ b/packages/components/src/visually-hidden/utils.js
@@ -0,0 +1,31 @@
+/**
+ * @template {keyof JSX.IntrinsicElements | import('react').JSXElementConstructor} T
+ * @typedef OwnProps
+ * @property {T} [as='div'] Component to render
+ * @property {import('react').ReactNode | ((props: import('react').ComponentProps) => JSX.Element) } [children] Children or render props function
+ */
+
+/**
+ * @template {keyof JSX.IntrinsicElements | import('react').JSXElementConstructor} T
+ * @typedef {OwnProps & import('react').ComponentProps} Props
+ */
+
+/**
+ * renderAsRenderProps is used to wrap a component and convert
+ * the passed property "as" either a string or component, to the
+ * rendered tag if a string, or component.
+ *
+ * See VisuallyHidden hidden for example.
+ *
+ * @template {keyof JSX.IntrinsicElements | import('react').JSXElementConstructor} T
+ * @param {Props} props
+ * @return {JSX.Element} The rendered element.
+ */
+function renderAsRenderProps( { as: Component = 'div', ...props } ) {
+ if ( typeof props.children === 'function' ) {
+ return props.children( props );
+ }
+ return ;
+}
+
+export { renderAsRenderProps };
diff --git a/packages/editor/src/components/post-preview-button/test/__snapshots__/index.js.snap b/packages/editor/src/components/post-preview-button/test/__snapshots__/index.js.snap
index e03484534e4ab0..220042a8a41aa7 100644
--- a/packages/editor/src/components/post-preview-button/test/__snapshots__/index.js.snap
+++ b/packages/editor/src/components/post-preview-button/test/__snapshots__/index.js.snap
@@ -10,11 +10,11 @@ exports[`PostPreviewButton render() should render currentPostLink otherwise 1`]
target="wp-preview-1"
>
Preview
-
(opens in a new tab)
-
+
`;
@@ -28,10 +28,10 @@ exports[`PostPreviewButton render() should render previewLink if provided 1`] =
target="wp-preview-1"
>
Preview
-
(opens in a new tab)
-
+
`;