OHIF-333: Split Button (#1988)
* ohif-333: add component foundation * ohif-333: add expandable content and mocked data * ohif-333: improve ListMenu component for the new toolbar button and add radio behavior * ohif-333: add click outside behavior and update primary and secondary props * ohif-333: separate classes from markup * ohif-333: fix layout issues * ohif-333: extract window level component * ohif-333: update component returns * ohif-333: update chevron thickness * ohif-333: remove is active prop * Delete lerna-debug.log * ohif-333: clean toolbar and use example in ui package * ohif-333: update styles to avoid word break * ohif-333: fix ui package build Co-authored-by: Erik Ziegler <erik.sweed@gmail.com> Co-authored-by: Danny Brown <danny.ri.brown@gmail.com>
This commit is contained in:
parent
42b02a62d3
commit
8cea1a04d6
@ -101,10 +101,10 @@ function ToolbarSecondary({ servicesManager }) {
|
||||
if (
|
||||
btn.props &&
|
||||
btn.props.commands &&
|
||||
evt.value &&
|
||||
btn.props.commands[evt.value]
|
||||
evt.item && evt.item.value &&
|
||||
btn.props.commands[evt.item.value]
|
||||
) {
|
||||
const { commandName, commandOptions } = btn.props.commands[evt.value];
|
||||
const { commandName, commandOptions } = btn.props.commands[evt.item.value];
|
||||
commandsManager.runCommand(commandName, commandOptions);
|
||||
}
|
||||
};
|
||||
|
||||
@ -1,8 +1,6 @@
|
||||
// TODO: torn, can either bake this here; or have to create a whole new button type
|
||||
// Only ways that you can pass in a custom React component for render :l
|
||||
import React from 'react';
|
||||
import classnames from 'classnames';
|
||||
import { ExpandableToolbarButton, ListMenu } from '@ohif/ui';
|
||||
import { ExpandableToolbarButton, ListMenu, WindowLevelMenuItem } from '@ohif/ui';
|
||||
import { defaults } from '@ohif/core';
|
||||
|
||||
const { windowLevelPresets } = defaults;
|
||||
@ -66,26 +64,14 @@ export default [
|
||||
type: 'primary',
|
||||
content: ListMenu,
|
||||
contentProps: {
|
||||
options: [
|
||||
items: [
|
||||
{ value: 1, title: 'Soft tissue', subtitle: '400 / 40' },
|
||||
{ value: 2, title: 'Lung', subtitle: '1500 / -600' },
|
||||
{ value: 3, title: 'Liver', subtitle: '150 / 90' },
|
||||
{ value: 4, title: 'Bone', subtitle: '80 / 40' },
|
||||
{ value: 5, title: 'Brain', subtitle: '2500 / 480' },
|
||||
],
|
||||
renderer: ({ title, subtitle, isActive, index }) => (
|
||||
<>
|
||||
<div>
|
||||
<span className={classnames(isActive ? "text-black" : "text-white", "mr-2 text-base")}>
|
||||
{title}
|
||||
</span>
|
||||
<span className={classnames(isActive ? "text-black" : "text-aqua-pale", "font-thin text-sm")}>
|
||||
{subtitle}
|
||||
</span>
|
||||
</div>
|
||||
<span className={classnames(isActive ? "text-black" : "text-primary-active", "text-sm")}>{index + 1}</span>
|
||||
</>
|
||||
)
|
||||
renderer: WindowLevelMenuItem
|
||||
}
|
||||
},
|
||||
},
|
||||
|
||||
@ -11,5 +11,5 @@ export default {
|
||||
// 'Other',
|
||||
],
|
||||
ignore: ['README.md'],
|
||||
base: '/ui/'
|
||||
base: '/ui/',
|
||||
};
|
||||
|
||||
@ -65,6 +65,7 @@ export {
|
||||
Select,
|
||||
SegmentationTable,
|
||||
SidePanel,
|
||||
SplitButton,
|
||||
StudyBrowser,
|
||||
StudyItem,
|
||||
StudyListExpandedRow,
|
||||
@ -94,6 +95,7 @@ export {
|
||||
ViewportDownloadForm,
|
||||
ViewportGrid,
|
||||
ViewportPane,
|
||||
WindowLevelMenuItem
|
||||
} from './src/components';
|
||||
|
||||
/** VIEWS */
|
||||
|
||||
@ -44,8 +44,9 @@
|
||||
"react-dnd-touch-backend": "10.0.2",
|
||||
"react-dom": "16.11.0",
|
||||
"react-draggable": "4.4.3",
|
||||
"react-error-boundary": "2.2.3",
|
||||
"react-modal": "3.11.2",
|
||||
"react-error-boundary": "2.2.x",
|
||||
"react-outside-click-handler": "^1.3.0",
|
||||
"react-powerplug": "1.0.0",
|
||||
"react-select": "3.0.8",
|
||||
"theme-ui": "0.2.x"
|
||||
|
||||
@ -1,3 +1,3 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 20 20">
|
||||
<path fill="currentColor" fill-rule="evenodd" d="M10 13L5 7.737 5.7 7 10 11.526 14.3 7 15 7.737z"/>
|
||||
<path fill="currentColor" fill-rule="evenodd" stroke="currentColor" d="M10 13L5 7.737 5.7 7 10 11.526 14.3 7 15 7.737z"/>
|
||||
</svg>
|
||||
|
||||
|
Before Width: | Height: | Size: 195 B After Width: | Height: | Size: 217 B |
@ -55,4 +55,4 @@ import { ExpandableToolbarButton, ListMenu } from '@ohif/ui';
|
||||
|
||||
## Properties
|
||||
|
||||
<Props of={ToolbarButton} />
|
||||
<Props of={ExpandableToolbarButton} />
|
||||
|
||||
@ -2,47 +2,35 @@ import React, { useState } from 'react';
|
||||
import classnames from 'classnames';
|
||||
import PropTypes from 'prop-types';
|
||||
|
||||
const ListMenu = ({ options = [], renderer, onClick }) => {
|
||||
const ListMenu = ({ items = [], renderer, onClick }) => {
|
||||
const [selectedIndex, setSelectedIndex] = useState(null);
|
||||
|
||||
const ListItem = (props) => {
|
||||
const ListItem = ({ item, index, isSelected }) => {
|
||||
const flex = 'flex flex-row justify-between items-center';
|
||||
const theme = 'bg-indigo-dark';
|
||||
const hover = 'hover:bg-primary-dark';
|
||||
const spacing = 'p-3 h-8';
|
||||
|
||||
const onClickHandler = () => {
|
||||
setSelectedIndex(index);
|
||||
onClick({ item, selectedIndex: index });
|
||||
if (item.onClick) item.onClick({ ...item, index, isSelected });
|
||||
};
|
||||
|
||||
return (
|
||||
<div
|
||||
className={classnames(
|
||||
flex,
|
||||
theme,
|
||||
spacing,
|
||||
'cursor-pointer',
|
||||
!props.isActive && hover,
|
||||
props.isActive && 'bg-primary-light',
|
||||
)}
|
||||
onClick={props.onClick}
|
||||
>
|
||||
{renderer && renderer(props)}
|
||||
<div className={classnames(flex, theme, 'cursor-pointer')} onClick={onClickHandler}>
|
||||
{renderer && renderer({ ...item, index, isSelected })}
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="flex flex-col rounded-md bg-secondary-dark pt-2 pb-2">
|
||||
{options.map((option, index) => {
|
||||
const onClickHandler = () => {
|
||||
setSelectedIndex(index);
|
||||
onClick({ ...option, index });
|
||||
};
|
||||
|
||||
{items.map((item, index) => {
|
||||
return (
|
||||
<ListItem
|
||||
key={`ListItem${index}`}
|
||||
{...option}
|
||||
index={index}
|
||||
isActive={selectedIndex === index}
|
||||
onClick={onClickHandler}
|
||||
isSelected={selectedIndex === index}
|
||||
item={item}
|
||||
/>
|
||||
);
|
||||
})}
|
||||
@ -53,7 +41,7 @@ const ListMenu = ({ options = [], renderer, onClick }) => {
|
||||
const noop = () => { };
|
||||
|
||||
ListMenu.propTypes = {
|
||||
options: PropTypes.array.isRequired,
|
||||
items: PropTypes.array.isRequired,
|
||||
renderer: PropTypes.func.isRequired,
|
||||
onClick: PropTypes.func
|
||||
};
|
||||
|
||||
@ -6,7 +6,7 @@ route: components/listMenu
|
||||
|
||||
import { useState } from 'react';
|
||||
import { Playground, Props } from 'docz';
|
||||
import { ListMenu } from '../';
|
||||
import { ListMenu, ToolbarButton } from '../';
|
||||
|
||||
# List Menu
|
||||
|
||||
@ -15,13 +15,13 @@ List Menus are used to populate expandable Toolbar.
|
||||
## Import
|
||||
|
||||
```javascript
|
||||
import { ListMenu } from '@ohif/ui';
|
||||
import { ListMenu, ToolbarButton } from '@ohif/ui';
|
||||
```
|
||||
|
||||
<Playground>
|
||||
{() => {
|
||||
return (
|
||||
<ToolbarButton options={[
|
||||
<ToolbarButton items={[
|
||||
{ value: 'windowLevelPreset1', title: 'Soft tissue', subtitle: '400 / 40' },
|
||||
{ value: 'windowLevelPreset2', title: 'Lung', subtitle: '1500 / -600' },
|
||||
{ value: 'windowLevelPreset3', title: 'Liver', subtitle: '150 / 90' },
|
||||
@ -49,4 +49,4 @@ import { ListMenu } from '@ohif/ui';
|
||||
|
||||
## Properties
|
||||
|
||||
<Props of={ToolbarButton} />
|
||||
<Props of={ListMenu} />
|
||||
|
||||
@ -27,7 +27,7 @@ import { MeasurementTable } from '@ohif/ui';
|
||||
data: new Array(10).fill({}).map((el, i) => ({
|
||||
id: i + 1,
|
||||
label: 'Label short description',
|
||||
displayText: '24.0 x 24.0 mm (S:4, I:22)',
|
||||
displayText: ['24.0 x 24.0 mm (S:4, I:22)'],
|
||||
isActive: activeMeasurementItem === i + 1,
|
||||
})),
|
||||
onClick: (id) => setActiveMeasurementItem((s) => (s === id ? null : id)),
|
||||
|
||||
194
platform/ui/src/components/SplitButton/SplitButton.jsx
Normal file
194
platform/ui/src/components/SplitButton/SplitButton.jsx
Normal file
@ -0,0 +1,194 @@
|
||||
import React, { useState } from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import classNames from 'classnames';
|
||||
import OutsideClickHandler from 'react-outside-click-handler';
|
||||
|
||||
import { Icon, Tooltip, ListMenu } from '@ohif/ui';
|
||||
|
||||
const baseClasses = {
|
||||
Button: 'h-12 flex items-center rounded-md border-transparent border-2 cursor-pointer',
|
||||
Primary: 'h-full flex flex-1 items-center rounded-md rounded-tr-none rounded-br-none',
|
||||
Secondary: 'h-full flex items-center justify-center rounded-tr-md rounded-br-md w-4',
|
||||
PrimaryIcon: 'w-5 h-5',
|
||||
SecondaryIcon: 'w-4 h-full stroke-1',
|
||||
Separator: 'border-l pt-2 pb-2',
|
||||
Content: 'absolute z-10 top-0 mt-16'
|
||||
};
|
||||
|
||||
const classes = {
|
||||
Button: ({ isExpanded, primary }) => classNames(
|
||||
baseClasses.Button,
|
||||
!isExpanded && !primary.isActive && 'hover:bg-primary-dark hover:border-primary-dark'
|
||||
),
|
||||
Interface: 'h-full flex flex-row items-center',
|
||||
Primary: ({ primary, isExpanded }) => classNames(
|
||||
baseClasses.Primary,
|
||||
primary.isActive && !isExpanded ? 'bg-primary-light rounded-tr-md rounded-br-md' :
|
||||
isExpanded ? 'bg-primary-dark' : 'bg-secondary-dark hover:bg-primary-dark'
|
||||
),
|
||||
Secondary: ({ isExpanded, primary }) => classNames(
|
||||
baseClasses.Secondary,
|
||||
isExpanded ? 'bg-primary-light rounded-tr-md rounded-br-md'
|
||||
: primary.isActive ? 'bg-secondary-dark' : 'hover:bg-primary-dark bg-secondary-dark'
|
||||
),
|
||||
PrimaryIcon: ({ primary, isExpanded }) => classNames(
|
||||
baseClasses.PrimaryIcon,
|
||||
primary.isActive && !isExpanded ? 'text-primary-dark' : 'text-common-bright'
|
||||
),
|
||||
SecondaryIcon: ({ isExpanded }) => classNames(
|
||||
baseClasses.SecondaryIcon,
|
||||
isExpanded ? 'text-primary-dark' : 'text-primary-active hover:text-common-bright'
|
||||
),
|
||||
Separator: ({ primary, isExpanded, isHovering }) => classNames(
|
||||
baseClasses.Separator,
|
||||
isHovering || isExpanded || primary.isActive ? 'border-transparent' : 'border-primary-active'
|
||||
),
|
||||
Content: ({ isExpanded }) => classNames(baseClasses.Content, isExpanded ? 'block' : 'hidden')
|
||||
};
|
||||
|
||||
const SplitButton = ({
|
||||
isRadio,
|
||||
isAction,
|
||||
primary: _primary,
|
||||
secondary,
|
||||
onClick,
|
||||
items: _items,
|
||||
renderer,
|
||||
}) => {
|
||||
/* Bubbles up individual item clicks */
|
||||
const getSplitButtonItems = items => items.map((item, index) => ({
|
||||
...item,
|
||||
index,
|
||||
onClick: () => {
|
||||
if (item.onClick) item.onClick({ ...item, index });
|
||||
onClick({ item, index });
|
||||
|
||||
setState(state => ({
|
||||
...state,
|
||||
primary: !isAction ? { ...item, index } : state.primary,
|
||||
isExpanded: false,
|
||||
items: getSplitButtonItems(_items).filter(item => isRadio && !isAction ? item.index !== index : true)
|
||||
}));
|
||||
}
|
||||
}));
|
||||
|
||||
const [state, setState] = useState({
|
||||
primary: _primary,
|
||||
items: getSplitButtonItems(_items),
|
||||
isHovering: false,
|
||||
isExpanded: false
|
||||
});
|
||||
|
||||
const onSecondaryClickHandler = () => setState(state => ({ ...state, isExpanded: !state.isExpanded }));
|
||||
const onMouseEnterHandler = () => setState(state => ({ ...state, isHovering: true }));
|
||||
const onMouseLeaveHandler = () => setState(state => ({ ...state, isHovering: false }));
|
||||
const outsideClickHandler = () => setState(state => ({ ...state, isExpanded: false }));
|
||||
const onPrimaryClickHandler = () => {
|
||||
const primary = { ...state.primary, isActive: !state.primary.isActive };
|
||||
state.primary.onClick(primary);
|
||||
setState(state => ({ ...state, isExpanded: false, primary }));
|
||||
};
|
||||
|
||||
return (
|
||||
<OutsideClickHandler onOutsideClick={outsideClickHandler}>
|
||||
<div name='SplitButton' className="relative">
|
||||
<div
|
||||
className={classes.Button({ ...state })}
|
||||
onMouseEnter={onMouseEnterHandler}
|
||||
onMouseLeave={onMouseLeaveHandler}
|
||||
>
|
||||
<div className={classes.Interface}>
|
||||
<div onClick={onPrimaryClickHandler} className={classes.Primary({ ...state })}>
|
||||
<Tooltip isDisabled={!state.primary.tooltip} content={state.primary.tooltip}>
|
||||
<div className='p-3 flex items-center justify-center h-full w-full'>
|
||||
<Icon name={state.primary.icon} className={classes.PrimaryIcon({ ...state })} />
|
||||
</div>
|
||||
</Tooltip>
|
||||
</div>
|
||||
<div className={classes.Separator({ ...state })}></div>
|
||||
<div className={classes.Secondary({ ...state })} onClick={onSecondaryClickHandler}>
|
||||
<Tooltip
|
||||
isDisabled={state.isExpanded || !secondary.tooltip}
|
||||
content={secondary.tooltip}
|
||||
className="h-full"
|
||||
>
|
||||
<Icon name={secondary.icon} className={classes.SecondaryIcon({ ...state })} />
|
||||
</Tooltip>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div className={classes.Content({ ...state })}>
|
||||
<ListMenu items={state.items} renderer={renderer} />
|
||||
</div>
|
||||
</div>
|
||||
</OutsideClickHandler>
|
||||
);
|
||||
};
|
||||
|
||||
const DefaultListItemRenderer = ({ icon, label, isActive }) => (
|
||||
<div className={classNames(
|
||||
'flex flex-row items-center p-3 h-8 w-full hover:bg-primary-dark',
|
||||
isActive && 'bg-primary-dark'
|
||||
)}
|
||||
>
|
||||
<span className='text-common-bright mr-4 text-base'>
|
||||
<Icon name={icon} className='w-5 h-5 text-common-bright' />
|
||||
</span>
|
||||
<span className='text-common-bright text-base mr-5'>
|
||||
{label}
|
||||
</span>
|
||||
</div >
|
||||
);
|
||||
|
||||
const noop = () => { };
|
||||
|
||||
SplitButton.defaultProps = {
|
||||
isRadio: false,
|
||||
isAction: false,
|
||||
primary: {
|
||||
label: null,
|
||||
tooltip: null,
|
||||
isActive: true,
|
||||
onClick: noop
|
||||
},
|
||||
secondary: {
|
||||
icon: 'chevron-down',
|
||||
label: null,
|
||||
isActive: true,
|
||||
tooltip: 'More Measure Tools'
|
||||
},
|
||||
items: [],
|
||||
renderer: DefaultListItemRenderer,
|
||||
onClick: noop
|
||||
};
|
||||
|
||||
SplitButton.propTypes = {
|
||||
primary: PropTypes.shape({
|
||||
id: PropTypes.string,
|
||||
icon: PropTypes.string,
|
||||
label: PropTypes.string,
|
||||
tooltip: PropTypes.string,
|
||||
isActive: PropTypes.bool,
|
||||
}),
|
||||
secondary: PropTypes.shape({
|
||||
id: PropTypes.string,
|
||||
icon: PropTypes.string,
|
||||
label: PropTypes.string,
|
||||
tooltip: PropTypes.string,
|
||||
isActive: PropTypes.bool
|
||||
}),
|
||||
onClick: PropTypes.func,
|
||||
renderer: PropTypes.func,
|
||||
items: PropTypes.arrayOf(
|
||||
PropTypes.shape({
|
||||
id: PropTypes.string.isRequired,
|
||||
icon: PropTypes.string,
|
||||
label: PropTypes.string,
|
||||
tooltip: PropTypes.string,
|
||||
onClick: PropTypes.func,
|
||||
isActive: PropTypes.bool,
|
||||
})
|
||||
)
|
||||
};
|
||||
|
||||
export default SplitButton;
|
||||
62
platform/ui/src/components/SplitButton/SplitButton.mdx
Normal file
62
platform/ui/src/components/SplitButton/SplitButton.mdx
Normal file
@ -0,0 +1,62 @@
|
||||
---
|
||||
name: Split Button
|
||||
menu: General
|
||||
route: components/splitButton
|
||||
---
|
||||
|
||||
import { useState } from 'react';
|
||||
import { Playground, Props } from 'docz';
|
||||
import { SplitButton, WindowLevelMenuItem } from '@ohif/ui';
|
||||
|
||||
# Split Button
|
||||
|
||||
Split Buttons are used to populate the Toolbar.
|
||||
|
||||
## Import
|
||||
|
||||
```javascript
|
||||
import { SplitButton, WindowLevelMenuItem } from '@ohif/ui';
|
||||
```
|
||||
|
||||
<Playground>
|
||||
{() => {
|
||||
const mockedProps = {
|
||||
primary: {
|
||||
tooltip: 'W/L',
|
||||
icon: 'tool-window-level',
|
||||
onClick: (args) => console.debug('Primary click!', args)
|
||||
},
|
||||
secondary: {
|
||||
icon: 'chevron-down',
|
||||
label: '',
|
||||
isActive: true,
|
||||
tooltip: 'More Measure Tools',
|
||||
},
|
||||
items: [
|
||||
{ id: '1', icon: 'tool-layout', label: 'Layout', onClick: (args) => console.debug('Item click!', args) },
|
||||
{ id: '2', icon: 'tool-window-level', label: 'W/L', onClick: (args) => console.debug('Item click!', args) },
|
||||
{ id: '3', icon: 'tool-length', label: 'Length', onClick: (args) => console.debug('Item click!', args) }
|
||||
],
|
||||
onClick: (args) => console.debug('Any click!', args)
|
||||
};
|
||||
return (
|
||||
<div className="mb-2">
|
||||
<div className="flex flex-row min-h-16 w-full justify-center items-center bg-secondary-dark">
|
||||
<SplitButton {...mockedProps} isRadio />
|
||||
<SplitButton {...mockedProps} isAction renderer={WindowLevelMenuItem} items={[
|
||||
{ id: '1', value: 1, title: 'Soft tissue', subtitle: '400 / 40' },
|
||||
{ id: '2', value: 2, title: 'Lung', subtitle: '1500 / -600' },
|
||||
{ id: '3', value: 3, title: 'Liver', subtitle: '150 / 90' },
|
||||
{ id: '4', value: 4, title: 'Bone', subtitle: '80 / 40' },
|
||||
{ id: '5', value: 5, title: 'Brain', subtitle: '2500 / 480' },
|
||||
]} />
|
||||
<SplitButton {...mockedProps} />
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}}
|
||||
</Playground>
|
||||
|
||||
## Properties
|
||||
|
||||
<Props of={SplitButton} />
|
||||
2
platform/ui/src/components/SplitButton/index.js
Normal file
2
platform/ui/src/components/SplitButton/index.js
Normal file
@ -0,0 +1,2 @@
|
||||
import SplitButton from './SplitButton';
|
||||
export default SplitButton;
|
||||
@ -95,7 +95,7 @@ import { StudyBrowser } from '@ohif/ui';
|
||||
return (
|
||||
<div className="flex flex-1" style={{height: '400px'}}>
|
||||
<div className="overflow-hidden w-64">
|
||||
<StudyBrowser tabs={tabs} />
|
||||
<StudyBrowser tabs={tabs} activeTabName='primary' expandedStudyInstanceUIDs={[]} />
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
|
||||
@ -6,14 +6,15 @@ route: components/studyListFilter
|
||||
|
||||
import { useState } from 'react';
|
||||
import { Playground, Props } from 'docz';
|
||||
import { StudyListFilter } from '../';
|
||||
import { StudyListFilter, Modal } from '../';
|
||||
import { ModalProvider } from '../../contextProviders';
|
||||
|
||||
# Study List Filter
|
||||
|
||||
## Import
|
||||
|
||||
```javascript
|
||||
import { StudyListFilter } from '@ohif/ui';
|
||||
import { StudyListFilter, ModalProvider, Modal } from '@ohif/ui';
|
||||
```
|
||||
|
||||
## Basic usage
|
||||
@ -101,14 +102,16 @@ import { StudyListFilter } from '@ohif/ui';
|
||||
});
|
||||
};
|
||||
return (
|
||||
<StudyListFilter
|
||||
numOfStudies={100}
|
||||
filtersMeta={filtersMeta}
|
||||
filterValues={filterValues}
|
||||
onChange={setFilterValues}
|
||||
clearFilters={() => setFilterValues(defaultFilterValues)}
|
||||
isFiltering={isFiltering(filterValues, defaultFilterValues)}
|
||||
/>
|
||||
<ModalProvider modal={Modal}>
|
||||
<StudyListFilter
|
||||
numOfStudies={100}
|
||||
filtersMeta={filtersMeta}
|
||||
filterValues={filterValues}
|
||||
onChange={setFilterValues}
|
||||
clearFilters={() => setFilterValues(defaultFilterValues)}
|
||||
isFiltering={isFiltering(filterValues, defaultFilterValues)}
|
||||
/>
|
||||
</ModalProvider>
|
||||
);
|
||||
}}
|
||||
</Playground>
|
||||
|
||||
@ -26,7 +26,7 @@ import { ThumbnailTracked } from '@ohif/ui';
|
||||
seriesNumber={4}
|
||||
numInstances={902}
|
||||
onClick={() => alert('Thumbnail was clicked!')}
|
||||
viewportIdentificator="A"
|
||||
viewportIdentificator={["A"]}
|
||||
isTracked={true}
|
||||
isActive={false}
|
||||
/>
|
||||
@ -43,7 +43,7 @@ const Tooltip = ({ content, isSticky, position, tight, children, isDisabled }) =
|
||||
|
||||
return (
|
||||
<div
|
||||
className="relative "
|
||||
className="relative h-full"
|
||||
onMouseOver={handleMouseOver}
|
||||
onFocus={handleMouseOver}
|
||||
onMouseOut={handleMouseOut}
|
||||
@ -88,7 +88,7 @@ Tooltip.defaultProps = {
|
||||
};
|
||||
|
||||
Tooltip.propTypes = {
|
||||
/** prevents tooltip from rendering despite hover/active/sticky */
|
||||
/** prevents tooltip from rendering despite hover/active/sticky */
|
||||
isDisabled: PropTypes.bool,
|
||||
content: PropTypes.oneOfType([PropTypes.node, PropTypes.func]),
|
||||
position: PropTypes.oneOf([
|
||||
|
||||
@ -0,0 +1,30 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import classNames from 'classnames';
|
||||
|
||||
const WindowLevelMenuItem = ({ title, subtitle, isSelected, index }) => (
|
||||
<>
|
||||
<div className={classNames(
|
||||
'flex flex-row items-center p-3 h-8 w-full hover:bg-primary-dark',
|
||||
isSelected && 'bg-primary-dark'
|
||||
)}
|
||||
>
|
||||
<span className='text-common-bright mr-2 text-base whitespace-no-wrap'>
|
||||
{title}
|
||||
</span>
|
||||
<span className='flex-1 text-aqua-pale font-thin text-sm whitespace-no-wrap'>
|
||||
{subtitle}
|
||||
</span>
|
||||
<span className='text-primary-active ml-5 text-sm whitespace-no-wrap'>{index + 1}</span>
|
||||
</div>
|
||||
</>
|
||||
);
|
||||
|
||||
WindowLevelMenuItem.propTypes = {
|
||||
title: PropTypes.string.isRequired,
|
||||
subtitle: PropTypes.string.isRequired,
|
||||
isSelected: PropTypes.bool.isRequired,
|
||||
index: PropTypes.number.isRequired,
|
||||
};
|
||||
|
||||
export default WindowLevelMenuItem;
|
||||
@ -0,0 +1,33 @@
|
||||
---
|
||||
name: Window Level Menu Item
|
||||
menu: General
|
||||
route: components/windowLevelMenuItem
|
||||
---
|
||||
|
||||
import { useState } from 'react';
|
||||
import { Playground, Props } from 'docz';
|
||||
import { ListMenu, WindowLevelMenuItem } from '@ohif/ui';
|
||||
|
||||
# Window Level Menu Item
|
||||
|
||||
Window Level Menu Item are used as renderer of the ListMenu.
|
||||
|
||||
## Import
|
||||
|
||||
```javascript
|
||||
import { WindowLevelMenuItem, ListMenu } from '@ohif/ui';
|
||||
```
|
||||
|
||||
<Playground>
|
||||
{() => {
|
||||
return (
|
||||
<div className="py-10 flex justify-center">
|
||||
<ListMenu renderer={WindowLevelMenuItem} items={[]} />
|
||||
</div>
|
||||
);
|
||||
}}
|
||||
</Playground>
|
||||
|
||||
## Properties
|
||||
|
||||
<Props of={WindowLevelMenuItem} />
|
||||
2
platform/ui/src/components/WindowLevelMenuItem/index.js
Normal file
2
platform/ui/src/components/WindowLevelMenuItem/index.js
Normal file
@ -0,0 +1,2 @@
|
||||
import WindowLevelMenuItem from './WindowLevelMenuItem';
|
||||
export default WindowLevelMenuItem;
|
||||
@ -25,6 +25,7 @@ import Notification from './Notification';
|
||||
import Select from './Select';
|
||||
import SegmentationTable from './SegmentationTable';
|
||||
import SidePanel from './SidePanel';
|
||||
import SplitButton from './SplitButton';
|
||||
import StudyBrowser from './StudyBrowser';
|
||||
import StudyItem from './StudyItem';
|
||||
import StudyListExpandedRow from './StudyListExpandedRow';
|
||||
@ -55,6 +56,7 @@ import ViewportActionBar from './ViewportActionBar';
|
||||
import ViewportDownloadForm from './ViewportDownloadForm';
|
||||
import ViewportGrid from './ViewportGrid';
|
||||
import ViewportPane from './ViewportPane';
|
||||
import WindowLevelMenuItem from './WindowLevelMenuItem';
|
||||
import UserPreferences from './UserPreferences';
|
||||
import HotkeysPreferences from './HotkeysPreferences';
|
||||
import HotkeyField from './HotkeyField';
|
||||
@ -94,6 +96,7 @@ export {
|
||||
Select,
|
||||
SegmentationTable,
|
||||
SidePanel,
|
||||
SplitButton,
|
||||
StudyBrowser,
|
||||
StudyItem,
|
||||
StudyListExpandedRow,
|
||||
@ -123,4 +126,5 @@ export {
|
||||
ViewportDownloadForm,
|
||||
ViewportGrid,
|
||||
ViewportPane,
|
||||
WindowLevelMenuItem
|
||||
};
|
||||
|
||||
@ -39,17 +39,6 @@ const ModalProvider = ({ children, modal: Modal, service }) => {
|
||||
|
||||
const [options, setOptions] = useState(DEFAULT_OPTIONS);
|
||||
|
||||
/**
|
||||
* Sets the implementation of a modal service that can be used by extensions.
|
||||
*
|
||||
* @returns void
|
||||
*/
|
||||
useEffect(() => {
|
||||
if (service) {
|
||||
service.setServiceImplementation({ hide, show });
|
||||
}
|
||||
}, [hide, service, show]);
|
||||
|
||||
/**
|
||||
* Show the modal and override its configuration props.
|
||||
*
|
||||
@ -69,6 +58,17 @@ const ModalProvider = ({ children, modal: Modal, service }) => {
|
||||
DEFAULT_OPTIONS,
|
||||
]);
|
||||
|
||||
/**
|
||||
* Sets the implementation of a modal service that can be used by extensions.
|
||||
*
|
||||
* @returns void
|
||||
*/
|
||||
useEffect(() => {
|
||||
if (service) {
|
||||
service.setServiceImplementation({ hide, show });
|
||||
}
|
||||
}, [hide, service, show]);
|
||||
|
||||
const {
|
||||
content: ModalContent,
|
||||
contentProps,
|
||||
|
||||
@ -1,21 +1,14 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import classnames from 'classnames';
|
||||
import tailwindConfig from './tailwind.config';
|
||||
|
||||
const BackgroundColor = ({ color }) => {
|
||||
const getColorValue = () => {
|
||||
const currentColor = color.split('-');
|
||||
const { colors } = tailwindConfig.theme;
|
||||
return colors[currentColor[0]][currentColor[1]];
|
||||
};
|
||||
return (
|
||||
<div
|
||||
className={classnames(
|
||||
`mb-4 w-56 h-10 flex items-center justify-center flex-col text-white text-lg bg-${color} py-8`
|
||||
)}
|
||||
>
|
||||
<p>{getColorValue()}</p>
|
||||
<p>bg-{color}</p>
|
||||
</div>
|
||||
);
|
||||
|
||||
@ -1,818 +0,0 @@
|
||||
module.exports = {
|
||||
prefix: '',
|
||||
important: false,
|
||||
separator: ':',
|
||||
theme: {
|
||||
screens: {
|
||||
sm: '640px',
|
||||
md: '768px',
|
||||
lg: '1024px',
|
||||
xl: '1280px',
|
||||
},
|
||||
colors: {
|
||||
overlay: 'rgba(0, 0, 0, 0.8)',
|
||||
transparent: 'transparent',
|
||||
black: '#000',
|
||||
white: '#fff',
|
||||
initial: 'initial',
|
||||
inherit: 'inherit',
|
||||
|
||||
indigo: {
|
||||
dark: '#0b1a42',
|
||||
},
|
||||
aqua: {
|
||||
pale: '#7bb2ce',
|
||||
},
|
||||
|
||||
primary: {
|
||||
light: '#5acce6',
|
||||
main: '#0944b3',
|
||||
dark: '#090c29',
|
||||
active: '#348cfd',
|
||||
},
|
||||
|
||||
secondary: {
|
||||
light: '#3a3f99',
|
||||
main: '#2b166b',
|
||||
dark: '#041c4a',
|
||||
active: '#1f1f27',
|
||||
},
|
||||
|
||||
common: {
|
||||
bright: '#e1e1e1',
|
||||
light: '#a19fad',
|
||||
main: '#fff',
|
||||
dark: '#726f7e',
|
||||
active: '#2c3074',
|
||||
},
|
||||
|
||||
gray: {
|
||||
100: '#f7fafc',
|
||||
200: '#edf2f7',
|
||||
300: '#e2e8f0',
|
||||
400: '#cbd5e0',
|
||||
500: '#a0aec0',
|
||||
600: '#718096',
|
||||
700: '#4a5568',
|
||||
800: '#2d3748',
|
||||
900: '#1a202c',
|
||||
},
|
||||
red: {
|
||||
100: '#fff5f5',
|
||||
200: '#fed7d7',
|
||||
300: '#feb2b2',
|
||||
400: '#fc8181',
|
||||
500: '#f56565',
|
||||
600: '#e53e3e',
|
||||
700: '#c53030',
|
||||
800: '#9b2c2c',
|
||||
900: '#742a2a',
|
||||
},
|
||||
orange: {
|
||||
100: '#fffaf0',
|
||||
200: '#feebc8',
|
||||
300: '#fbd38d',
|
||||
400: '#f6ad55',
|
||||
500: '#ed8936',
|
||||
600: '#dd6b20',
|
||||
700: '#c05621',
|
||||
800: '#9c4221',
|
||||
900: '#7b341e',
|
||||
},
|
||||
yellow: {
|
||||
100: '#fffff0',
|
||||
200: '#fefcbf',
|
||||
300: '#faf089',
|
||||
400: '#f6e05e',
|
||||
500: '#ecc94b',
|
||||
600: '#d69e2e',
|
||||
700: '#b7791f',
|
||||
800: '#975a16',
|
||||
900: '#744210',
|
||||
},
|
||||
green: {
|
||||
100: '#f0fff4',
|
||||
200: '#c6f6d5',
|
||||
300: '#9ae6b4',
|
||||
400: '#68d391',
|
||||
500: '#48bb78',
|
||||
600: '#38a169',
|
||||
700: '#2f855a',
|
||||
800: '#276749',
|
||||
900: '#22543d',
|
||||
},
|
||||
teal: {
|
||||
100: '#e6fffa',
|
||||
200: '#b2f5ea',
|
||||
300: '#81e6d9',
|
||||
400: '#4fd1c5',
|
||||
500: '#38b2ac',
|
||||
600: '#319795',
|
||||
700: '#2c7a7b',
|
||||
800: '#285e61',
|
||||
900: '#234e52',
|
||||
},
|
||||
blue: {
|
||||
100: '#ebf8ff',
|
||||
200: '#bee3f8',
|
||||
300: '#90cdf4',
|
||||
400: '#63b3ed',
|
||||
500: '#4299e1',
|
||||
600: '#3182ce',
|
||||
700: '#2b6cb0',
|
||||
800: '#2c5282',
|
||||
900: '#2a4365',
|
||||
},
|
||||
indigo: {
|
||||
100: '#ebf4ff',
|
||||
200: '#c3dafe',
|
||||
300: '#a3bffa',
|
||||
400: '#7f9cf5',
|
||||
500: '#667eea',
|
||||
600: '#5a67d8',
|
||||
700: '#4c51bf',
|
||||
800: '#434190',
|
||||
900: '#3c366b',
|
||||
},
|
||||
purple: {
|
||||
100: '#faf5ff',
|
||||
200: '#e9d8fd',
|
||||
300: '#d6bcfa',
|
||||
400: '#b794f4',
|
||||
500: '#9f7aea',
|
||||
600: '#805ad5',
|
||||
700: '#6b46c1',
|
||||
800: '#553c9a',
|
||||
900: '#44337a',
|
||||
},
|
||||
pink: {
|
||||
100: '#fff5f7',
|
||||
200: '#fed7e2',
|
||||
300: '#fbb6ce',
|
||||
400: '#f687b3',
|
||||
500: '#ed64a6',
|
||||
600: '#d53f8c',
|
||||
700: '#b83280',
|
||||
800: '#97266d',
|
||||
900: '#702459',
|
||||
},
|
||||
},
|
||||
spacing: {
|
||||
px: '1px',
|
||||
'0': '0',
|
||||
'1': '0.15rem',
|
||||
'2': '0.5rem',
|
||||
'3': '0.75rem',
|
||||
'4': '1rem',
|
||||
'5': '1.25rem',
|
||||
'6': '1.5rem',
|
||||
'8': '2rem',
|
||||
'10': '2.5rem',
|
||||
'12': '3rem',
|
||||
'14': '3.5rem',
|
||||
'16': '4rem',
|
||||
'18': '4.5rem',
|
||||
'20': '5rem',
|
||||
'24': '6rem',
|
||||
'32': '8rem',
|
||||
'40': '10rem',
|
||||
'48': '12rem',
|
||||
'56': '14rem',
|
||||
'64': '16rem',
|
||||
'72': '18rem',
|
||||
'80': '20rem',
|
||||
'88': '22rem',
|
||||
'96': '24rem',
|
||||
'104': '26rem',
|
||||
'112': '28rem',
|
||||
'250px': '250px',
|
||||
},
|
||||
backgroundColor: theme => theme('colors'),
|
||||
backgroundPosition: {
|
||||
bottom: 'bottom',
|
||||
center: 'center',
|
||||
left: 'left',
|
||||
'left-bottom': 'left bottom',
|
||||
'left-top': 'left top',
|
||||
right: 'right',
|
||||
'right-bottom': 'right bottom',
|
||||
'right-top': 'right top',
|
||||
top: 'top',
|
||||
},
|
||||
backgroundSize: {
|
||||
auto: 'auto',
|
||||
cover: 'cover',
|
||||
contain: 'contain',
|
||||
},
|
||||
borderColor: theme => ({
|
||||
...theme('colors'),
|
||||
default: theme('colors.gray.300', 'currentColor'),
|
||||
}),
|
||||
borderRadius: {
|
||||
none: '0',
|
||||
sm: '0.125rem',
|
||||
default: '0.25rem',
|
||||
md: '0.375rem',
|
||||
lg: '0.5rem',
|
||||
full: '9999px',
|
||||
},
|
||||
borderWidth: {
|
||||
default: '1px',
|
||||
'0': '0',
|
||||
'2': '2px',
|
||||
'4': '4px',
|
||||
'8': '8px',
|
||||
},
|
||||
boxShadow: {
|
||||
xs: '0 0 0 1px rgba(0, 0, 0, 0.05)',
|
||||
sm: '0 1px 2px 0 rgba(0, 0, 0, 0.05)',
|
||||
default:
|
||||
'0 1px 3px 0 rgba(0, 0, 0, 0.1), 0 1px 2px 0 rgba(0, 0, 0, 0.06)',
|
||||
md:
|
||||
'0 4px 6px -1px rgba(0, 0, 0, 0.1), 0 2px 4px -1px rgba(0, 0, 0, 0.06)',
|
||||
lg:
|
||||
'0 10px 15px -3px rgba(0, 0, 0, 0.1), 0 4px 6px -2px rgba(0, 0, 0, 0.05)',
|
||||
xl:
|
||||
'0 20px 25px -5px rgba(0, 0, 0, 0.1), 0 10px 10px -5px rgba(0, 0, 0, 0.04)',
|
||||
'2xl': '0 25px 50px -12px rgba(0, 0, 0, 0.25)',
|
||||
inner: 'inset 0 2px 4px 0 rgba(0, 0, 0, 0.06)',
|
||||
outline: '0 0 0 3px rgba(66, 153, 225, 0.5)',
|
||||
none: 'none',
|
||||
},
|
||||
container: {},
|
||||
cursor: {
|
||||
auto: 'auto',
|
||||
default: 'default',
|
||||
pointer: 'pointer',
|
||||
wait: 'wait',
|
||||
text: 'text',
|
||||
move: 'move',
|
||||
'not-allowed': 'not-allowed',
|
||||
},
|
||||
fill: {
|
||||
current: 'currentColor',
|
||||
},
|
||||
flex: {
|
||||
'1': '1 1 0%',
|
||||
'0.3': '0.3 0.3 0%',
|
||||
'0.5': '0.5 0.5 0%',
|
||||
auto: '1 1 auto',
|
||||
initial: '0 1 auto',
|
||||
none: 'none',
|
||||
},
|
||||
flexGrow: {
|
||||
'0': '0',
|
||||
default: '1',
|
||||
},
|
||||
flexShrink: {
|
||||
'0': '0',
|
||||
default: '1',
|
||||
},
|
||||
fontFamily: {
|
||||
sans: [
|
||||
'Lato',
|
||||
'system-ui',
|
||||
'-apple-system',
|
||||
'BlinkMacSystemFont',
|
||||
'"Segoe UI"',
|
||||
'Roboto',
|
||||
'"Helvetica Neue"',
|
||||
'Arial',
|
||||
'"Noto Sans"',
|
||||
'sans-serif',
|
||||
'"Apple Color Emoji"',
|
||||
'"Segoe UI Emoji"',
|
||||
'"Segoe UI Symbol"',
|
||||
'"Noto Color Emoji"',
|
||||
],
|
||||
serif: ['Georgia', 'Cambria', '"Times New Roman"', 'Times', 'serif'],
|
||||
mono: [
|
||||
'Menlo',
|
||||
'Monaco',
|
||||
'Consolas',
|
||||
'"Liberation Mono"',
|
||||
'"Courier New"',
|
||||
'monospace',
|
||||
],
|
||||
},
|
||||
fontSize: {
|
||||
xs: '0.65rem',
|
||||
sm: '0.75rem',
|
||||
base: '0.875rem',
|
||||
lg: '1rem',
|
||||
xl: '1.25rem',
|
||||
'2xl': '1.5rem',
|
||||
'3xl': '1.875rem',
|
||||
'4xl': '2.25rem',
|
||||
'5xl': '3rem',
|
||||
'6xl': '4rem',
|
||||
},
|
||||
fontWeight: {
|
||||
hairline: '100',
|
||||
thin: '200',
|
||||
light: '300',
|
||||
normal: '400',
|
||||
medium: '500',
|
||||
semibold: '600',
|
||||
bold: '700',
|
||||
extrabold: '800',
|
||||
black: '900',
|
||||
},
|
||||
height: theme => ({
|
||||
auto: 'auto',
|
||||
...theme('spacing'),
|
||||
full: '100%',
|
||||
screen: '100vh',
|
||||
}),
|
||||
inset: {
|
||||
'0': '0',
|
||||
auto: 'auto',
|
||||
full: '100%',
|
||||
viewport: '0.5rem',
|
||||
'1/2': '50%',
|
||||
'viewport-scrollbar': '1.3rem',
|
||||
},
|
||||
letterSpacing: {
|
||||
tighter: '-0.05em',
|
||||
tight: '-0.025em',
|
||||
normal: '0',
|
||||
wide: '0.025em',
|
||||
wider: '0.05em',
|
||||
widest: '0.1em',
|
||||
},
|
||||
lineHeight: {
|
||||
none: '1',
|
||||
tight: '1.25',
|
||||
snug: '1.375',
|
||||
normal: '1.5',
|
||||
relaxed: '1.625',
|
||||
loose: '2',
|
||||
'3': '.75rem',
|
||||
'4': '1rem',
|
||||
'5': '1.25rem',
|
||||
'6': '1.5rem',
|
||||
'7': '1.75rem',
|
||||
'8': '2rem',
|
||||
'9': '2.25rem',
|
||||
'10': '2.5rem',
|
||||
},
|
||||
listStyleType: {
|
||||
none: 'none',
|
||||
disc: 'disc',
|
||||
decimal: 'decimal',
|
||||
},
|
||||
margin: (theme, { negative }) => ({
|
||||
auto: 'auto',
|
||||
...theme('spacing'),
|
||||
...negative(theme('spacing')),
|
||||
}),
|
||||
maxHeight: theme => ({
|
||||
full: '100%',
|
||||
screen: '100vh',
|
||||
...theme('spacing'),
|
||||
}),
|
||||
maxWidth: (theme, { breakpoints }) => ({
|
||||
none: 'none',
|
||||
xs: '20rem',
|
||||
sm: '24rem',
|
||||
md: '28rem',
|
||||
lg: '32rem',
|
||||
xl: '36rem',
|
||||
'2xl': '42rem',
|
||||
'3xl': '48rem',
|
||||
'4xl': '56rem',
|
||||
'5xl': '64rem',
|
||||
'6xl': '72rem',
|
||||
full: '100%',
|
||||
...breakpoints(theme('screens')),
|
||||
...theme('spacing'),
|
||||
}),
|
||||
minHeight: theme => ({
|
||||
...theme('spacing'),
|
||||
'0': '0',
|
||||
full: '100%',
|
||||
screen: '100vh',
|
||||
}),
|
||||
minWidth: theme => ({
|
||||
...theme('spacing'),
|
||||
'0': '0',
|
||||
xs: '2rem',
|
||||
sm: '4rem',
|
||||
md: '6rem',
|
||||
lg: '8rem',
|
||||
xl: '10rem',
|
||||
full: '100%',
|
||||
}),
|
||||
objectPosition: {
|
||||
bottom: 'bottom',
|
||||
center: 'center',
|
||||
left: 'left',
|
||||
'left-bottom': 'left bottom',
|
||||
'left-top': 'left top',
|
||||
right: 'right',
|
||||
'right-bottom': 'right bottom',
|
||||
'right-top': 'right top',
|
||||
top: 'top',
|
||||
},
|
||||
opacity: {
|
||||
'0': '0',
|
||||
'5': '.5',
|
||||
'10': '.10',
|
||||
'15': '.15',
|
||||
'20': '.20',
|
||||
'25': '.25',
|
||||
'30': '.30',
|
||||
'35': '.35',
|
||||
'40': '.40',
|
||||
'45': '.45',
|
||||
'50': '.50',
|
||||
'55': '.55',
|
||||
'60': '.60',
|
||||
'65': '.65',
|
||||
'70': '.70',
|
||||
'75': '.75',
|
||||
'80': '.80',
|
||||
'85': '.85',
|
||||
'90': '.90',
|
||||
'95': '.95',
|
||||
'100': '1',
|
||||
},
|
||||
order: {
|
||||
first: '-9999',
|
||||
last: '9999',
|
||||
none: '0',
|
||||
'1': '1',
|
||||
'2': '2',
|
||||
'3': '3',
|
||||
'4': '4',
|
||||
'5': '5',
|
||||
'6': '6',
|
||||
'7': '7',
|
||||
'8': '8',
|
||||
'9': '9',
|
||||
'10': '10',
|
||||
'11': '11',
|
||||
'12': '12',
|
||||
},
|
||||
padding: theme => theme('spacing'),
|
||||
placeholderColor: theme => theme('colors'),
|
||||
stroke: theme => ({
|
||||
...theme('colors'),
|
||||
current: 'currentColor',
|
||||
}),
|
||||
strokeWidth: {
|
||||
'0': '0',
|
||||
'1': '1',
|
||||
'2': '2',
|
||||
},
|
||||
textColor: theme => theme('colors'),
|
||||
width: theme => ({
|
||||
auto: 'auto',
|
||||
...theme('spacing'),
|
||||
'1/2': '50%',
|
||||
'1/3': '33.333333%',
|
||||
'2/3': '66.666667%',
|
||||
'1/4': '25%',
|
||||
'2/4': '50%',
|
||||
'3/4': '75%',
|
||||
'1/5': '20%',
|
||||
'2/5': '40%',
|
||||
'3/5': '60%',
|
||||
'4/5': '80%',
|
||||
'1/6': '16.666667%',
|
||||
'2/6': '33.333333%',
|
||||
'3/6': '50%',
|
||||
'4/6': '66.666667%',
|
||||
'5/6': '83.333333%',
|
||||
'1/12': '8.333333%',
|
||||
'2/12': '16.666667%',
|
||||
'3/12': '25%',
|
||||
'4/12': '33.333333%',
|
||||
'5/12': '41.666667%',
|
||||
'6/12': '50%',
|
||||
'7/12': '58.333333%',
|
||||
'8/12': '66.666667%',
|
||||
'9/12': '75%',
|
||||
'10/12': '83.333333%',
|
||||
'11/12': '91.666667%',
|
||||
'1/24': '4.166666667%',
|
||||
'2/24': '8.333333333%',
|
||||
'3/24': '12.5%',
|
||||
'4/24': '16.66666667%',
|
||||
'5/24': '20.83333333%',
|
||||
'6/24': '25%',
|
||||
'7/24': '29.16666667%',
|
||||
'8/24': '33.33333333%',
|
||||
'9/24': '37.5%',
|
||||
'10/24': '41.66666667%',
|
||||
'11/24': '45.83333333%',
|
||||
'12/24': '50%',
|
||||
'13/24': '54.16666667%',
|
||||
'14/24': '58.33333333%',
|
||||
'15/24': '62.5%',
|
||||
'16/24': '66.66666667%',
|
||||
'17/24': '70.83333333%',
|
||||
'18/24': '75%',
|
||||
'19/24': '79.16666667%',
|
||||
'20/24': '83.33333333%',
|
||||
'21/24': '87.5%',
|
||||
'22/24': '91.66666667%',
|
||||
'23/24': '95.83333333%',
|
||||
full: '100%',
|
||||
screen: '100vw',
|
||||
'max-content': 'max-content',
|
||||
}),
|
||||
zIndex: {
|
||||
auto: 'auto',
|
||||
'0': '0',
|
||||
'10': '10',
|
||||
'20': '20',
|
||||
'30': '30',
|
||||
'40': '40',
|
||||
'50': '50',
|
||||
},
|
||||
gap: theme => theme('spacing'),
|
||||
gridTemplateColumns: {
|
||||
none: 'none',
|
||||
'1': 'repeat(1, minmax(0, 1fr))',
|
||||
'2': 'repeat(2, minmax(0, 1fr))',
|
||||
'3': 'repeat(3, minmax(0, 1fr))',
|
||||
'4': 'repeat(4, minmax(0, 1fr))',
|
||||
'5': 'repeat(5, minmax(0, 1fr))',
|
||||
'6': 'repeat(6, minmax(0, 1fr))',
|
||||
'7': 'repeat(7, minmax(0, 1fr))',
|
||||
'8': 'repeat(8, minmax(0, 1fr))',
|
||||
'9': 'repeat(9, minmax(0, 1fr))',
|
||||
'10': 'repeat(10, minmax(0, 1fr))',
|
||||
'11': 'repeat(11, minmax(0, 1fr))',
|
||||
'12': 'repeat(12, minmax(0, 1fr))',
|
||||
},
|
||||
gridColumn: {
|
||||
auto: 'auto',
|
||||
'span-1': 'span 1 / span 1',
|
||||
'span-2': 'span 2 / span 2',
|
||||
'span-3': 'span 3 / span 3',
|
||||
'span-4': 'span 4 / span 4',
|
||||
'span-5': 'span 5 / span 5',
|
||||
'span-6': 'span 6 / span 6',
|
||||
'span-7': 'span 7 / span 7',
|
||||
'span-8': 'span 8 / span 8',
|
||||
'span-9': 'span 9 / span 9',
|
||||
'span-10': 'span 10 / span 10',
|
||||
'span-11': 'span 11 / span 11',
|
||||
'span-12': 'span 12 / span 12',
|
||||
},
|
||||
gridColumnStart: {
|
||||
auto: 'auto',
|
||||
'1': '1',
|
||||
'2': '2',
|
||||
'3': '3',
|
||||
'4': '4',
|
||||
'5': '5',
|
||||
'6': '6',
|
||||
'7': '7',
|
||||
'8': '8',
|
||||
'9': '9',
|
||||
'10': '10',
|
||||
'11': '11',
|
||||
'12': '12',
|
||||
'13': '13',
|
||||
},
|
||||
gridColumnEnd: {
|
||||
auto: 'auto',
|
||||
'1': '1',
|
||||
'2': '2',
|
||||
'3': '3',
|
||||
'4': '4',
|
||||
'5': '5',
|
||||
'6': '6',
|
||||
'7': '7',
|
||||
'8': '8',
|
||||
'9': '9',
|
||||
'10': '10',
|
||||
'11': '11',
|
||||
'12': '12',
|
||||
'13': '13',
|
||||
},
|
||||
gridTemplateRows: {
|
||||
none: 'none',
|
||||
'1': 'repeat(1, minmax(0, 1fr))',
|
||||
'2': 'repeat(2, minmax(0, 1fr))',
|
||||
'3': 'repeat(3, minmax(0, 1fr))',
|
||||
'4': 'repeat(4, minmax(0, 1fr))',
|
||||
'5': 'repeat(5, minmax(0, 1fr))',
|
||||
'6': 'repeat(6, minmax(0, 1fr))',
|
||||
},
|
||||
gridRow: {
|
||||
auto: 'auto',
|
||||
'span-1': 'span 1 / span 1',
|
||||
'span-2': 'span 2 / span 2',
|
||||
'span-3': 'span 3 / span 3',
|
||||
'span-4': 'span 4 / span 4',
|
||||
'span-5': 'span 5 / span 5',
|
||||
'span-6': 'span 6 / span 6',
|
||||
},
|
||||
gridRowStart: {
|
||||
auto: 'auto',
|
||||
'1': '1',
|
||||
'2': '2',
|
||||
'3': '3',
|
||||
'4': '4',
|
||||
'5': '5',
|
||||
'6': '6',
|
||||
'7': '7',
|
||||
},
|
||||
gridRowEnd: {
|
||||
auto: 'auto',
|
||||
'1': '1',
|
||||
'2': '2',
|
||||
'3': '3',
|
||||
'4': '4',
|
||||
'5': '5',
|
||||
'6': '6',
|
||||
'7': '7',
|
||||
},
|
||||
transformOrigin: {
|
||||
center: 'center',
|
||||
top: 'top',
|
||||
'top-right': 'top right',
|
||||
right: 'right',
|
||||
'bottom-right': 'bottom right',
|
||||
bottom: 'bottom',
|
||||
'bottom-left': 'bottom left',
|
||||
left: 'left',
|
||||
'top-left': 'top left',
|
||||
},
|
||||
scale: {
|
||||
'0': '0',
|
||||
'50': '.5',
|
||||
'75': '.75',
|
||||
'90': '.9',
|
||||
'95': '.95',
|
||||
'100': '1',
|
||||
'105': '1.05',
|
||||
'110': '1.1',
|
||||
'125': '1.25',
|
||||
'150': '1.5',
|
||||
},
|
||||
rotate: {
|
||||
'-180': '-180deg',
|
||||
'-90': '-90deg',
|
||||
'-45': '-45deg',
|
||||
'0': '0',
|
||||
'45': '45deg',
|
||||
'90': '90deg',
|
||||
'180': '180deg',
|
||||
},
|
||||
translate: (theme, { negative }) => ({
|
||||
...theme('spacing'),
|
||||
...negative(theme('spacing')),
|
||||
'-full': '-100%',
|
||||
'-1/2': '-50%',
|
||||
'1/2': '50%',
|
||||
full: '100%',
|
||||
}),
|
||||
skew: {
|
||||
'-12': '-12deg',
|
||||
'-6': '-6deg',
|
||||
'-3': '-3deg',
|
||||
'0': '0',
|
||||
'3': '3deg',
|
||||
'6': '6deg',
|
||||
'12': '12deg',
|
||||
},
|
||||
transitionProperty: {
|
||||
none: 'none',
|
||||
all: 'all',
|
||||
height: 'height',
|
||||
default:
|
||||
'background-color, border-color, color, fill, stroke, opacity, box-shadow, transform',
|
||||
colors: 'background-color, border-color, color, fill, stroke',
|
||||
opacity: 'opacity',
|
||||
shadow: 'box-shadow',
|
||||
transform: 'transform',
|
||||
},
|
||||
transitionTimingFunction: {
|
||||
linear: 'linear',
|
||||
in: 'cubic-bezier(0.4, 0, 1, 1)',
|
||||
out: 'cubic-bezier(0, 0, 0.2, 1)',
|
||||
'in-out': 'cubic-bezier(0.4, 0, 0.2, 1)',
|
||||
},
|
||||
transitionDuration: {
|
||||
'75': '75ms',
|
||||
'100': '100ms',
|
||||
'150': '150ms',
|
||||
'200': '200ms',
|
||||
'300': '300ms',
|
||||
'500': '500ms',
|
||||
'700': '700ms',
|
||||
'1000': '1000ms',
|
||||
},
|
||||
},
|
||||
variants: {
|
||||
accessibility: ['responsive', 'focus'],
|
||||
alignContent: ['responsive'],
|
||||
alignItems: ['responsive'],
|
||||
alignSelf: ['responsive'],
|
||||
appearance: ['responsive'],
|
||||
backgroundAttachment: ['responsive'],
|
||||
backgroundColor: [
|
||||
'responsive',
|
||||
'hover',
|
||||
'focus',
|
||||
'active',
|
||||
'group-focus',
|
||||
'group-hover',
|
||||
],
|
||||
backgroundPosition: ['responsive'],
|
||||
backgroundRepeat: ['responsive'],
|
||||
backgroundSize: ['responsive'],
|
||||
borderCollapse: ['responsive'],
|
||||
borderColor: [
|
||||
'responsive',
|
||||
'hover',
|
||||
'focus',
|
||||
'active',
|
||||
'group-focus',
|
||||
'group-hover',
|
||||
],
|
||||
borderRadius: ['responsive', 'focus', 'first', 'last'],
|
||||
borderStyle: ['responsive', 'focus'],
|
||||
borderWidth: ['responsive', 'focus', 'first', 'last'],
|
||||
boxShadow: ['responsive', 'hover', 'focus'],
|
||||
boxSizing: ['responsive'],
|
||||
cursor: ['responsive'],
|
||||
display: ['responsive'],
|
||||
fill: ['responsive'],
|
||||
flex: ['responsive'],
|
||||
flexDirection: ['responsive'],
|
||||
flexGrow: ['responsive'],
|
||||
flexShrink: ['responsive'],
|
||||
flexWrap: ['responsive'],
|
||||
float: ['responsive'],
|
||||
clear: ['responsive'],
|
||||
fontFamily: ['responsive'],
|
||||
fontSize: ['responsive'],
|
||||
fontSmoothing: ['responsive'],
|
||||
fontStyle: ['responsive'],
|
||||
fontWeight: ['responsive', 'hover', 'focus'],
|
||||
height: ['responsive'],
|
||||
inset: ['responsive'],
|
||||
justifyContent: ['responsive'],
|
||||
letterSpacing: ['responsive'],
|
||||
lineHeight: ['responsive'],
|
||||
listStylePosition: ['responsive'],
|
||||
listStyleType: ['responsive'],
|
||||
margin: ['responsive'],
|
||||
maxHeight: ['responsive'],
|
||||
maxWidth: ['responsive'],
|
||||
minHeight: ['responsive'],
|
||||
minWidth: ['responsive'],
|
||||
objectFit: ['responsive'],
|
||||
objectPosition: ['responsive'],
|
||||
opacity: ['responsive', 'hover', 'focus', 'active'],
|
||||
order: ['responsive'],
|
||||
outline: ['responsive', 'focus'],
|
||||
overflow: ['responsive'],
|
||||
padding: ['responsive', 'first'],
|
||||
placeholderColor: ['responsive', 'focus'],
|
||||
pointerEvents: ['responsive'],
|
||||
position: ['responsive'],
|
||||
resize: ['responsive'],
|
||||
stroke: ['responsive'],
|
||||
strokeWidth: ['responsive'],
|
||||
tableLayout: ['responsive'],
|
||||
textAlign: ['responsive'],
|
||||
textColor: ['responsive', 'hover', 'focus', 'active', 'group-hover'],
|
||||
textDecoration: ['responsive', 'hover', 'focus'],
|
||||
textTransform: ['responsive'],
|
||||
userSelect: ['responsive'],
|
||||
verticalAlign: ['responsive'],
|
||||
visibility: ['responsive'],
|
||||
whitespace: ['responsive'],
|
||||
width: ['responsive'],
|
||||
wordBreak: ['responsive'],
|
||||
zIndex: ['responsive'],
|
||||
gap: ['responsive'],
|
||||
gridAutoFlow: ['responsive'],
|
||||
gridTemplateColumns: ['responsive'],
|
||||
gridColumn: ['responsive'],
|
||||
gridColumnStart: ['responsive'],
|
||||
gridColumnEnd: ['responsive'],
|
||||
gridTemplateRows: ['responsive'],
|
||||
gridRow: ['responsive'],
|
||||
gridRowStart: ['responsive'],
|
||||
gridRowEnd: ['responsive'],
|
||||
transform: ['responsive'],
|
||||
transformOrigin: ['responsive'],
|
||||
scale: ['responsive', 'hover', 'focus'],
|
||||
rotate: ['responsive', 'hover', 'focus'],
|
||||
translate: ['responsive', 'hover', 'focus'],
|
||||
skew: ['responsive', 'hover', 'focus'],
|
||||
transitionProperty: ['responsive'],
|
||||
transitionTimingFunction: ['responsive'],
|
||||
transitionDuration: ['responsive'],
|
||||
},
|
||||
corePlugins: {},
|
||||
plugins: [],
|
||||
};
|
||||
@ -14,7 +14,6 @@ import {
|
||||
StudyListTable,
|
||||
StudyListFilter,
|
||||
} from '../../components';
|
||||
|
||||
import utils from '../../utils';
|
||||
|
||||
// fix imports after refactor
|
||||
@ -285,10 +284,10 @@ const StudyList = () => {
|
||||
/>
|
||||
</>
|
||||
) : (
|
||||
<div className="flex flex-col items-center justify-center pt-48">
|
||||
<EmptyStudies />
|
||||
</div>
|
||||
)}
|
||||
<div className="flex flex-col items-center justify-center pt-48">
|
||||
<EmptyStudies />
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
@ -7,8 +7,6 @@ route: examples/studyList
|
||||
import { useState } from 'react';
|
||||
import { Playground } from 'docz';
|
||||
import {
|
||||
StudyList,
|
||||
utils,
|
||||
Icon,
|
||||
StudyListExpandedRow,
|
||||
Button,
|
||||
@ -20,6 +18,7 @@ import {
|
||||
StudyListPagination,
|
||||
StudyListFilter
|
||||
} from '../../components';
|
||||
import utils from '../../utils';
|
||||
|
||||
|
||||
import classnames from 'classnames';
|
||||
@ -18,13 +18,14 @@ import {
|
||||
StudyBrowser,
|
||||
ViewportActionBar,
|
||||
Notification,
|
||||
DragAndDropProvider,
|
||||
Viewport,
|
||||
ViewportGrid,
|
||||
ViewportPane,
|
||||
StudySummary,
|
||||
MeasurementTable,
|
||||
} from '../../components';
|
||||
|
||||
import Header from './components/Header';
|
||||
import { DragAndDropProvider } from '../../contextProviders';
|
||||
|
||||
import { tabs } from './studyBrowserMockData';
|
||||
|
||||
@ -67,9 +68,7 @@ import { tabs } from './studyBrowserMockData';
|
||||
iconLabel: 'Studies',
|
||||
label: 'Studies',
|
||||
name: 'studies',
|
||||
content: (
|
||||
<StudyBrowser tabs={tabs} />
|
||||
)
|
||||
content: <StudyBrowser tabs={tabs} />
|
||||
}}
|
||||
/>
|
||||
{/* TOOLBAR + GRID */}
|
||||
25
yarn.lock
25
yarn.lock
@ -1787,27 +1787,13 @@
|
||||
core-js-pure "^3.0.0"
|
||||
regenerator-runtime "^0.13.4"
|
||||
|
||||
"@babel/runtime@7.1.2":
|
||||
version "7.1.2"
|
||||
resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.1.2.tgz#81c89935f4647706fc54541145e6b4ecfef4b8e3"
|
||||
integrity sha512-Y3SCjmhSupzFB6wcv1KmmFucH6gDVnI30WjOcicV10ju0cZjak3Jcs67YLIXBrmZYw1xCrVeJPbycFwrqNyxpg==
|
||||
dependencies:
|
||||
regenerator-runtime "^0.12.0"
|
||||
|
||||
"@babel/runtime@7.7.6", "@babel/runtime@^7.0.0", "@babel/runtime@^7.1.2", "@babel/runtime@^7.2.0", "@babel/runtime@^7.3.1", "@babel/runtime@^7.4.4", "@babel/runtime@^7.4.5", "@babel/runtime@^7.5.5", "@babel/runtime@^7.7.2", "@babel/runtime@^7.7.4":
|
||||
"@babel/runtime@7.1.2", "@babel/runtime@7.7.6", "@babel/runtime@^7.0.0", "@babel/runtime@^7.1.2", "@babel/runtime@^7.10.2", "@babel/runtime@^7.10.3", "@babel/runtime@^7.2.0", "@babel/runtime@^7.3.1", "@babel/runtime@^7.4.4", "@babel/runtime@^7.4.5", "@babel/runtime@^7.5.5", "@babel/runtime@^7.7.2", "@babel/runtime@^7.7.4", "@babel/runtime@^7.7.7", "@babel/runtime@^7.8.4", "@babel/runtime@^7.8.7", "@babel/runtime@^7.9.2", "@babel/runtime@^7.9.6":
|
||||
version "7.7.6"
|
||||
resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.7.6.tgz#d18c511121aff1b4f2cd1d452f1bac9601dd830f"
|
||||
integrity sha512-BWAJxpNVa0QlE5gZdWjSxXtemZyZ9RmrmVozxt3NUXeZhVIJ5ANyqmMc0JDrivBZyxUuQvFxlvH4OWWOogGfUw==
|
||||
dependencies:
|
||||
regenerator-runtime "^0.13.2"
|
||||
|
||||
"@babel/runtime@^7.10.2", "@babel/runtime@^7.10.3", "@babel/runtime@^7.7.7", "@babel/runtime@^7.8.4", "@babel/runtime@^7.8.7", "@babel/runtime@^7.9.2", "@babel/runtime@^7.9.6":
|
||||
version "7.11.2"
|
||||
resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.11.2.tgz#f549c13c754cc40b87644b9fa9f09a6a95fe0736"
|
||||
integrity sha512-TeWkU52so0mPtDcaCTxNBI/IHiz0pZgr8VEFqXFtZWpYD08ZB6FaSwVAS8MKRQAP3bYKiVjwysOJgMFY28o6Tw==
|
||||
dependencies:
|
||||
regenerator-runtime "^0.13.4"
|
||||
|
||||
"@babel/standalone@^7.10.2", "@babel/standalone@^7.4.5":
|
||||
version "7.10.2"
|
||||
resolved "https://registry.yarnpkg.com/@babel/standalone/-/standalone-7.10.2.tgz#49dbbadcbc4b199df064d7d8b3e21c915b84abdb"
|
||||
@ -19997,7 +19983,7 @@ react-dropzone@^10.1.7:
|
||||
file-selector "^0.1.12"
|
||||
prop-types "^15.7.2"
|
||||
|
||||
react-error-boundary@2.2.3:
|
||||
react-error-boundary@2.2.x:
|
||||
version "2.2.3"
|
||||
resolved "https://registry.yarnpkg.com/react-error-boundary/-/react-error-boundary-2.2.3.tgz#34c8238012d3b4148cec47a1b3cec669d5206578"
|
||||
integrity sha512-Jiaiu6CJ4ho3sMCVI7gg+O/JB5vlFFZGwlnpFBTCOSyheYRTzz+FhBMo7tfnCTB/ZR0LaMzAPGbZGrEzAOd0eg==
|
||||
@ -20131,7 +20117,7 @@ react-moment-proptypes@^1.6.0:
|
||||
dependencies:
|
||||
moment ">=1.6.0"
|
||||
|
||||
react-outside-click-handler@^1.2.4:
|
||||
react-outside-click-handler@^1.2.4, react-outside-click-handler@^1.3.0:
|
||||
version "1.3.0"
|
||||
resolved "https://registry.yarnpkg.com/react-outside-click-handler/-/react-outside-click-handler-1.3.0.tgz#3831d541ac059deecd38ec5423f81e80ad60e115"
|
||||
integrity sha512-Te/7zFU0oHpAnctl//pP3hEAeobfeHMyygHB8MnjP6sX5OR8KHT1G3jmLsV3U9RnIYo+Yn+peJYWu+D5tUS8qQ==
|
||||
@ -20746,11 +20732,6 @@ regenerator-runtime@^0.11.0:
|
||||
resolved "https://registry.yarnpkg.com/regenerator-runtime/-/regenerator-runtime-0.11.1.tgz#be05ad7f9bf7d22e056f9726cee5017fbf19e2e9"
|
||||
integrity sha512-MguG95oij0fC3QV3URf4V2SDYGJhJnJGqvIIgdECeODCT98wSWDAJ94SSuVpYQUoTcGUIL6L4yNB7j1DFFHSBg==
|
||||
|
||||
regenerator-runtime@^0.12.0:
|
||||
version "0.12.1"
|
||||
resolved "https://registry.yarnpkg.com/regenerator-runtime/-/regenerator-runtime-0.12.1.tgz#fa1a71544764c036f8c49b13a08b2594c9f8a0de"
|
||||
integrity sha512-odxIc1/vDlo4iZcfXqRYFj0vpXFNoGdKMAUieAlFYO6m/nl5e9KR/beGf41z4a1FI+aQgtjhuaSlDxQ0hmkrHg==
|
||||
|
||||
regenerator-runtime@^0.13.1, regenerator-runtime@^0.13.2, regenerator-runtime@^0.13.4:
|
||||
version "0.13.5"
|
||||
resolved "https://registry.yarnpkg.com/regenerator-runtime/-/regenerator-runtime-0.13.5.tgz#d878a1d094b4306d10b9096484b33ebd55e26697"
|
||||
|
||||
Loading…
Reference in New Issue
Block a user