diff --git a/scripts/jest/jest.config.js b/scripts/jest/jest.config.js index 64835fabe1..8cc5d744a2 100644 --- a/scripts/jest/jest.config.js +++ b/scripts/jest/jest.config.js @@ -8,6 +8,7 @@ module.exports = { moduleNameMapper: { 'box-ui-elements-locale-data': '/i18n/en-US.js', 'box-locale-data': '/node_modules/@box/cldr-data/locale-data/en-US', + '^elements/(.*)$': '/src/elements/$1', '\\.(jpg|jpeg|png|gif|eot|otf|webp|svg|ttf|woff|woff2|mp4|webm|wav|mp3|m4a|aac|oga)$': '/scripts/jest/mocks/fileMock.js', '\\.(css|less|scss|md)$': '/scripts/jest/mocks/styleMock.js', diff --git a/src/components/sidebar-toggle-button/SidebarToggleButton.js b/src/components/sidebar-toggle-button/SidebarToggleButton.js index 3564febd1f..8153f164b7 100644 --- a/src/components/sidebar-toggle-button/SidebarToggleButton.js +++ b/src/components/sidebar-toggle-button/SidebarToggleButton.js @@ -4,8 +4,12 @@ import classNames from 'classnames'; import { injectIntl } from 'react-intl'; import type { IntlShape } from 'react-intl'; +import { IconButton } from '@box/blueprint-web'; +import { useFeatureConfig } from 'elements/common/feature-checking'; import IconHide from '../../icons/general/IconHide'; import IconShow from '../../icons/general/IconShow'; +import IconRightSidebarChevronOpen from '../../icons/general/IconRightSidebarChevronOpen'; +import IconRightSidebarChevronClose from '../../icons/general/IconRightSidebarChevronClose'; import PlainButton from '../plain-button'; import Tooltip from '../tooltip'; @@ -40,18 +44,49 @@ const SidebarToggleButton = ({ }); const tooltipPosition = direction === DIRECTION_LEFT ? 'middle-right' : 'middle-left'; + const { enabled: isPreviewModernizationEnabled } = useFeatureConfig('previewModernization'); + const renderButton = () => { - if (direction === DIRECTION_LEFT) { - return isOpen ? : ; + if (isPreviewModernizationEnabled) { + if (direction === DIRECTION_LEFT) { + return ( + + ); + } + return ( + + ); } - return isOpen ? : ; + + const renderIcon = () => { + if (direction === DIRECTION_LEFT) { + return isOpen ? : ; + } + return isOpen ? : ; + }; + + return ( + + {renderIcon()} + + ); }; return ( - - {renderButton()} - + {renderButton()} ); }; diff --git a/src/components/sidebar-toggle-button/__tests__/SidebarToggleButton.test.js b/src/components/sidebar-toggle-button/__tests__/SidebarToggleButton.test.js index 9cfc881dc8..fb372219c8 100644 --- a/src/components/sidebar-toggle-button/__tests__/SidebarToggleButton.test.js +++ b/src/components/sidebar-toggle-button/__tests__/SidebarToggleButton.test.js @@ -2,7 +2,19 @@ import * as React from 'react'; import SidebarToggleButton from '..'; +jest.mock('elements/common/feature-checking', () => ({ + useFeatureConfig: jest.fn(), +})); + +const { useFeatureConfig } = require('elements/common/feature-checking'); + +const mockUseFeatureConfig = useFeatureConfig; + describe('components/sidebar-toggle-button/SidebarToggleButton', () => { + beforeEach(() => { + mockUseFeatureConfig.mockReturnValue({ enabled: false }); + }); + test('should render correctly as open', () => { const wrapper = mount(); @@ -32,4 +44,61 @@ describe('components/sidebar-toggle-button/SidebarToggleButton', () => { expect(wrapper).toMatchSnapshot(); }); + + describe('previewModernization feature enabled', () => { + beforeEach(() => { + mockUseFeatureConfig.mockReturnValue({ enabled: true }); + }); + + test('should render IconButton when previewModernization is enabled and sidebar is open (right direction)', () => { + const wrapper = mount(); + + expect(wrapper.find('IconButton')).toHaveLength(1); + expect(wrapper.find('PlainButton')).toHaveLength(0); + expect(wrapper).toMatchSnapshot(); + }); + + test('should render IconButton when previewModernization is enabled and sidebar is closed (right direction)', () => { + const wrapper = mount(); + + expect(wrapper.find('IconButton')).toHaveLength(1); + expect(wrapper.find('PlainButton')).toHaveLength(0); + expect(wrapper).toMatchSnapshot(); + }); + + test('should render IconButton when previewModernization is enabled and sidebar is open (left direction)', () => { + const wrapper = mount(); + + expect(wrapper.find('IconButton')).toHaveLength(1); + expect(wrapper.find('PlainButton')).toHaveLength(0); + expect(wrapper).toMatchSnapshot(); + }); + + test('should render IconButton when previewModernization is enabled and sidebar is closed (left direction)', () => { + const wrapper = mount(); + + expect(wrapper.find('IconButton')).toHaveLength(1); + expect(wrapper.find('PlainButton')).toHaveLength(0); + expect(wrapper).toMatchSnapshot(); + }); + + test('should call onClick when IconButton is clicked', () => { + const onClick = jest.fn(); + const wrapper = mount(); + + wrapper.find('IconButton').simulate('click'); + + expect(onClick).toHaveBeenCalledTimes(1); + }); + + test('should render IconButton with correct props when previewModernization is enabled', () => { + const onClick = jest.fn(); + const wrapper = mount(); + + const iconButton = wrapper.find('IconButton'); + expect(iconButton.prop('size')).toBe('large'); + expect(iconButton.prop('variant')).toBe('high-contrast'); + expect(iconButton.prop('onClick')).toBe(onClick); + }); + }); }); diff --git a/src/components/sidebar-toggle-button/__tests__/__snapshots__/SidebarToggleButton.test.js.snap b/src/components/sidebar-toggle-button/__tests__/__snapshots__/SidebarToggleButton.test.js.snap index d25c9f336a..18316a6b16 100644 --- a/src/components/sidebar-toggle-button/__tests__/__snapshots__/SidebarToggleButton.test.js.snap +++ b/src/components/sidebar-toggle-button/__tests__/__snapshots__/SidebarToggleButton.test.js.snap @@ -1,5 +1,509 @@ // Jest Snapshot v1, https://goo.gl/fbAQLP +exports[`components/sidebar-toggle-button/SidebarToggleButton previewModernization feature enabled should render IconButton when previewModernization is enabled and sidebar is closed (left direction) 1`] = ` + + + + } + classPrefix="tooltip" + constraints={ + [ + { + "attachment": "together", + "to": "window", + }, + ] + } + enabled={false} + renderElementTag="div" + renderElementTo={null} + targetAttachment="middle right" + > + + + + + + + + + +`; + +exports[`components/sidebar-toggle-button/SidebarToggleButton previewModernization feature enabled should render IconButton when previewModernization is enabled and sidebar is closed (right direction) 1`] = ` + + + + } + classPrefix="tooltip" + constraints={ + [ + { + "attachment": "together", + "to": "window", + }, + ] + } + enabled={false} + renderElementTag="div" + renderElementTo={null} + targetAttachment="middle left" + > + + + + + + + + + +`; + +exports[`components/sidebar-toggle-button/SidebarToggleButton previewModernization feature enabled should render IconButton when previewModernization is enabled and sidebar is open (left direction) 1`] = ` + + + + } + classPrefix="tooltip" + constraints={ + [ + { + "attachment": "together", + "to": "window", + }, + ] + } + enabled={false} + renderElementTag="div" + renderElementTo={null} + targetAttachment="middle right" + > + + + + + + + + + +`; + +exports[`components/sidebar-toggle-button/SidebarToggleButton previewModernization feature enabled should render IconButton when previewModernization is enabled and sidebar is open (right direction) 1`] = ` + + + + } + classPrefix="tooltip" + constraints={ + [ + { + "attachment": "together", + "to": "window", + }, + ] + } + enabled={false} + renderElementTag="div" + renderElementTo={null} + targetAttachment="middle left" + > + + + + + + + + + +`; + exports[`components/sidebar-toggle-button/SidebarToggleButton should render correctly as closed 1`] = ` ( + + + + +); + +export default IconRightSidebarChevronClose; diff --git a/src/icons/general/IconRightSidebarChevronClose.tsx b/src/icons/general/IconRightSidebarChevronClose.tsx new file mode 100644 index 0000000000..e093f31bf6 --- /dev/null +++ b/src/icons/general/IconRightSidebarChevronClose.tsx @@ -0,0 +1,25 @@ +import * as React from 'react'; + +import AccessibleSVG from '../accessible-svg'; + +import { Icon } from '../iconTypes'; + +// Copied from Figma - will replace with blueprint icon once available +const IconRightSidebarChevronClose = ({ className = '', color = '#000000', height = 24, title, width = 24 }: Icon) => ( + + + + +); + +export default IconRightSidebarChevronClose; diff --git a/src/icons/general/IconRightSidebarChevronOpen.js.flow b/src/icons/general/IconRightSidebarChevronOpen.js.flow new file mode 100644 index 0000000000..2a59a6738a --- /dev/null +++ b/src/icons/general/IconRightSidebarChevronOpen.js.flow @@ -0,0 +1,26 @@ +// @flow +import * as React from 'react'; + +import AccessibleSVG from '../accessible-svg'; + +import { Icon } from '../iconTypes'; + +// Copied from Figma - will replace with blueprint icon once available +const IconRightSidebarChevronOpen = ({ className = '', color = '#000000', height = 24, title, width = 24 }: Icon) => ( + + + + +); + +export default IconRightSidebarChevronOpen; diff --git a/src/icons/general/IconRightSidebarChevronOpen.tsx b/src/icons/general/IconRightSidebarChevronOpen.tsx new file mode 100644 index 0000000000..bd0d28b1fb --- /dev/null +++ b/src/icons/general/IconRightSidebarChevronOpen.tsx @@ -0,0 +1,25 @@ +import * as React from 'react'; + +import AccessibleSVG from '../accessible-svg'; + +import { Icon } from '../iconTypes'; + +// Copied from Figma - will replace with blueprint icon once available +const IconRightSidebarChevronOpen = ({ className = '', color = '#000000', height = 24, title, width = 24 }: Icon) => ( + + + + +); + +export default IconRightSidebarChevronOpen;