Options
All
  • Public
  • Public/Protected
  • All
Menu

Module @rws-air/webcomponents

logo

Rijkswaterstaat Webcomponents

Standard Webcomponents for AIR projects


Project Status

GitHub

Bundle Sizes

npm bundle size npm bundle size

Versions

npm

Our Badges

website slack trello Pivotal Tracked Sketch Designed Zeplin Based

Installation

yarn add @rws-air/webcomponents

Usage

import React, { FC } from 'react';

import { Button } from '@rws-air/webcomponents';

const Example: FC = () => <Button label='test' onClick={() => undefined} variant='contained' color='primary' />;

API Documentation

Check out the docs on github pages

Index

Type aliases

CheckboxChangeEvent

CheckboxChangeEvent: ChangeEvent<{ checked: boolean }>

ComponentOwnProps

ComponentOwnProps<CP, Params>: CP & NonUndefined<RouteComponentProps<Params>>

Type wrapper that combines component props and route params to create an object of both the component props and all Router props with params set internally.

example
interface RouteParams {
  userId: string;
}

interface RoutedComponentProps {
  name: string;
}

export const RoutedComponent = (props: PropsWithChildren<ComponentOwnProps<RoutedComponentProps, RouteParams>>) => (
  <div>
    The UserID is: {props.match.params.userId}
    The name is: {props.name}
  </div>
)

Type parameters

  • CP: Record<PropertyKey, unknown>

  • Params: {}

MutatedMUITablePaginationProps

MutatedMUITablePaginationProps: TablePaginationTypeMap<Record<PropertyKey, unknown>, ComponentType<TablePaginationBaseProps>>["props"]

OptionValue

OptionValue: string | number | boolean

The possible types for the option value

PaginationActionsProps

PaginationActionsProps: TablePaginationActionsProps & { data-qa?: undefined | string }

RouteParamId

RouteParamId: string | number

Generic type for a parameter in a route

example
interface RouteParams {
  userId: RouteParamId
}

RouteProps

RouteProps<Params>: NonUndefined<RouteComponentProps<Params>>

Type wrapper to set the params on Router props "match" object

example
interface RouteParams {
  userId: string;
}

export const handleGetUser = createAsyncAction(...)<RouteProps<RouteParams>['match'], unknown, Error>();

Type parameters

  • Params: {}

SelectMenuOptionValues

SelectMenuOptionValues: string | number | string[]

The possible types for the option value

TableLabels

TableLabels: Pick<ToolbarProps, "searchplaceholderlabel"> & Pick<PaginationProps, "labelRowsPerPage" | "labelPaginationOf"> & Pick<HeaderCellProps, "tooltiplabel">

Variables

Const ActionBar

ActionBar: NamedExoticComponent<ActionBarProps> & { type: T } = memo(({title,'data-qa': dataQa,shouldDisableButton = false,shouldHaveButton = false,buttonAction,buttonLabel,BoxProps,TypographyProps}: ActionBarProps) => {const getTitle = useMemo<ActionBarProps['title']>(() => {if (typeof title === 'string') {return (<Typographyvariant='h1'data-qa='action-bar-title'color='textPrimary'{...TypographyProps}className={clsx(css.actionHeader, TypographyProps?.className, TypographyProps?.classes)}>{title}</Typography>);}if (typeof title === 'function') return title();return title;}, [TypographyProps, title]);return (<Box component='div' data-qa={dataQa} {...BoxProps} className={clsx(css.actionBar, BoxProps?.className)}><Gridcontainerdirection='row'justifyContent='space-between'alignItems='center'className={css.actionGridLeft}><Grid item key={1} xs={6}>{getTitle}</Grid><When condition={Boolean(shouldHaveButton)}><Grid item key={2} xs={5} sm={6} className={css.actionGridRight}><Buttondata-qa='action-bar-button'variant='contained'color='primary'label={buttonLabel}onClick={() => (buttonAction ? buttonAction() : null)}disabled={Boolean(shouldDisableButton)}/></Grid></When></Grid></Box>);})

Creates an action bar using pre-defined Rijkswaterstaat styling

param

Props to pass to the actionbar

example
<ActionBar title='Cool title' />

Const Bar

Bar: NamedExoticComponent<BarProps & { children?: ReactNode | undefined }> & { type: T } = memo(({ classes, children, ...props }: PropsWithChildren<BarProps>) => (<Box {...props} component='div' className={clsx(css.bar, classes)}>{children}</Box>))

Constructs a horizontal Bar section using pre-defined Rijkswaterstaat styling

example
<Bar>
  <div> Some Children </div>
</Bar>

Const BodyCell

BodyCell: NamedExoticComponent<BodyCellProps> & { type: T } = memo(({ customclasses, scope, component, content, 'data-qa': dataQa, ...props }: BodyCellProps) => (<MUITableCell{...props}data-qa={dataQa}className={clsx(css.tableCells, customclasses)}component={component}scope={scope}>{content}</MUITableCell>))

Constructs a table body cell using pre-defined Rijkswaterstaat styling

param

Props to pass to the body cell

example
<BodyCell content='Cool Content' />

Const Button

Button: NamedExoticComponent<{} & RefAttributes<HTMLButtonElement>> & { type: T } = memo(forwardRef<HTMLButtonElement, MUIButtonProps<'button', ButtonProps>>((props, ref) => {const classes = useStyles();return (<MUIButton{...props}ref={ref}data-qa={props['data-qa']}onClick={props.onClick}variant={props.variant}color={props.color}disabled={props.disabled}className={clsx(props.customclasses, props.className)}classes={{...props.classes,root: clsx(css.button, props.classes?.root),label: clsx(css.buttonLabel, props.customlabelclasses),disabled: clsx(css.buttonDisabled, props.classes?.disabled),containedPrimary: clsx(css.buttonPrimary, classes.buttonShadow, props.classes?.containedPrimary),containedSecondary: clsx(css.buttonSecondary, classes.buttonShadow, props.classes?.containedSecondary),outlined: clsx(css.buttonOutlined, classes.buttonShadow, props.classes?.outlined),outlinedPrimary: clsx(css.buttonOutlined, classes.buttonShadow, props.classes?.outlinedPrimary),outlinedSecondary: clsx(css.buttonOutlinedSecondary, classes.buttonShadow, props.classes?.outlinedSecondary)}}href={undefined}>{props.label}</MUIButton>);}))

Constructs a button using pre-defined Rijkswaterstaat styling

remark

Ref is forwarded to the Material-UI button to allow for wrapping this button with a Tooltip

param

Props to pass to the button

example
<Button label='button' onClick={() => undefined} variant='contained' color='primary' />

Const Checkbox

Checkbox: ForwardRefExoticComponent<{} & RefAttributes<HTMLButtonElement>> = forwardRef<HTMLButtonElement, CheckboxProps>(({ label, value, name, onChange, tooltipText, TooltipProps, FormControlLabelProps, checked = false, ...props },ref) => (<Field type='checkbox'>{({ field }: FieldProps<string>) => (<Tooltip title={tooltipText} placement='top' {...TooltipProps}><FormControlLabel{...field}ref={ref}label={label}classes={{ label: css.label }}control={<MUICheckbox{...props}color='primary'checkedIcon={<CheckBoxOutlineFilledIcon fontSize='small' />}icon={<CheckBoxOutlineBlankIcon className={css.checkBox} fontSize='small' />}value={value}name={name}checked={checked}onChange={onChange}/>}{...FormControlLabelProps}/></Tooltip>)}</Field>))

Constructs a Checkbox with formik validation

param

Props to pass to the Checkbox component

example
 <FieldArray
   name='fieldArrayName'
   render={arrayHelpers =>
     arrayWithStrings((entry, index) => (
       <Grid item xs={4} key={index}>
         <Checkbox
           name={entry}
           value={entry}
           label={t(`form.fieldArrayName.labels.${entry}`)}
           tooltipText={t(`form.fieldArrayName.tooltips.${entry}`)}
           data-qa={`checkbox-${entry.toLowerCase()}`}
           checked={values['fieldArrayName'].includes(entry)}
           onChange={(e: CheckboxChangeEvent) => {
             if (e.target.checked) {
               arrayHelpers.push(entry);
             } else {
               const idx = values['fieldArrayName'].indexOf(entry);
               arrayHelpers.remove(idx);
             }
           }}
         />
       </Grid>
     ))
   }
 />

Const ConfirmationModal

ConfirmationModal: NamedExoticComponent<ConfirmationModalProps> & { type: T } = memo((props: ConfirmationModalProps) => {const handleConfirmKeyPress = (event: KeyboardEvent) => {return event.key.toLowerCase() === 'enter' ? props.confirmAction() : undefined;};const renderModalActions = useMemo(() => {return (<DialogActions classes={{ root: css.modalActions }} data-qa={props.modalqas?.actions || 'modal-actions'}><Buttondata-qa={props.modalqas?.actionCancel || 'modal-cancel-button'}onClick={props.closeAction}variant='outlined'color='primary'label={props.cancelButtonText ? props.cancelButtonText : 'cancel'}customclasses={css.modalButtonCancel}/><Buttondata-qa={props.modalqas?.actionConfirm || 'modal-confirm-button'}onClick={props.confirmAction}variant='contained'color='primary'label={props.okButtonText ? props.okButtonText : 'ok'}customclasses={css.modalButtonOk}/></DialogActions>);}, [props.modalqas, props.closeAction, props.cancelButtonText, props.confirmAction, props.okButtonText]);const renderModalTitleIcon = useMemo(() => {if (props.modalType === 'warning') return <WarningIcon color='error' className={clsx(css.titleIcon)} />;return <CheckCircle color='inherit' className={clsx(css.titleIcon, css.titleIconCheckCircle)} />;}, [props.modalType]);return (<DialogdisableBackdropClickdisableEscapeKeyDownopen={Boolean(props.open)}classes={{ root: css.modal }}onKeyPress={handleConfirmKeyPress}data-qa={props.modalqas?.modal || 'modal'}><DialogTitle data-qa={props.modalqas?.title || 'modal-title'} className={clsx(css.title, css.titleIconOffset)}><Fragment>{renderModalTitleIcon}{props.topic}</Fragment></DialogTitle><DialogContentclasses={{ root: css.modalBody }}className={css.modalContentSmall}data-qa={props.modalqas?.content || 'modal-content'}>{props.dialogContent}</DialogContent>{renderModalActions}</Dialog>);})

Constructs a confirmation modal using pre-defined Rijkswaterstaat styling

param

Props to pass to the confirmation modal

example
<ConfirmationModal
  modalType='warning'
  open={true}
  topic='SAMPLE TOPIC'
  cancelButtonText='CANCEL'
  okButtonText='OK'
  confirmAction={console.log}
  closeAction={console.log}
  modalqas={{
     modal: 'sample',
     content: 'sample-content',
     title: 'sample-title',
     actions: 'sample-actions',
     actionCancel: 'sample-action-cancel',
     actionConfirm: 'sample-action-confirm',
  }}
  dialogContent={ <ModalContent><div>SAMPLE</div></ModalContent> }
/>

Const Dropdownbutton

Dropdownbutton: NamedExoticComponent<DropdownbuttonProps> & { type: T } = memo((props: DropdownbuttonProps) => {const [open, setOpen] = useState(false);const anchorRef = useRef<HTMLDivElement>(null);const [selectedIndex, setSelectedIndex] = useState(props.defaultOptionId || 0);const handleMenuItemClick = (_event: ReactMouseEvent<HTMLLIElement, MouseEvent>, index: number) => {setSelectedIndex(index);setOpen(false);};const handleToggle = () => {setOpen((prevOpen) => !prevOpen);};const handleClose = (event: ReactMouseEvent<Document, MouseEvent>) => {if (anchorRef.current && anchorRef.current.contains(event.target as HTMLElement)) {return;}setOpen(false);};return (<Grid item container direction='column'><Grid item xs={12}><ButtonGroupvariant={props.variant || 'contained'}color={props.color || 'primary'}ref={anchorRef}aria-label='split button'data-qa={props.buttonGroupDataQa}className={clsx(css.buttonGroup, props.buttonGroupCustomClasses)}classes={{ root: clsx({ [css.buttonGroupDisabled]: props.disabled }) }}disabled={props.disabled}><Buttonvariant={props.variant || 'contained'}color={props.color || 'primary'}size='small'aria-owns={open ? 'menu-list-grow' : undefined}aria-haspopup='true'onClick={handleToggle}startIcon={<ArrowDropDownIcon />}label={cutText(props.options[selectedIndex], props.maxTextLength || 30)}className={css.buttonOverwritesLeft}customlabelclasses={css.labelOverwrites}data-qa={props.dropdownButtonDataQa}customclasses={props.dropdownButtonCustomClasses}/><Buttonvariant={props.variant || 'contained'}color={props.color || 'primary'}onClick={() => props.onClick(props.options[selectedIndex])}label={props.ButtonIcon}className={css.buttonOverwritesRight}data-qa={props.iconButtonDataQa}customclasses={props.iconButtonCustomClasses}/></ButtonGroup><Popperopen={open}data-qa={props.popperDataQa}anchorEl={anchorRef.current}transitionplacement='bottom-start'disablePortal>{({ TransitionProps, placement }) => (<Grow{...TransitionProps}style={{transformOrigin: placement === 'bottom' ? 'center top' : 'center bottom'}}><Paper id='menu-list-grow'><ClickAwayListener onClickAway={handleClose}><MenuList>{props.options.map((option, index) => (<MenuItemdata-qa={`${props.menuItemDataQa}-${index}`}key={option}disabled={props.disabledOptionIds ? props.disabledOptionIds.includes(index) : false}selected={index === selectedIndex}onClick={(event) => handleMenuItemClick(event, index)}>{option}</MenuItem>))}</MenuList></ClickAwayListener></Paper></Grow>)}</Popper></Grid></Grid>);})

Constructs a button with dropdown menu options using pre-defined Rijkswaterstaat styling

example
<Dropdownbutton ButtonIcon={<CloudDownload/>} onClick={() => undefined} options={[ 'one', 'two' ]} />

Const FloatingActionButton

FloatingActionButton: NamedExoticComponent<FabProps> & { type: T } = memo(({ children, tooltipContent, disableTooltip, TooltipProps, ...props }: FabProps) => {const classes = useStyles();if (disableTooltip) {return (<Fab {...props} className={classes.fab} color='primary'>{children}</Fab>);}return (<Tooltip {...TooltipProps} title={tooltipContent ?? ''}><Fab {...props} className={classes.fab} color='primary'>{children}</Fab></Tooltip>);})

Constructs a Floating Action Button using pre-defined Rijkswaterstaat styling

param

Props to pass to the Floating Action Button. Also supports all properties applicable to Material-UI's Fab API and webcomponents TooltipProps

example
<FloatingActionButton tooltipContent='Cool Tooltip' children={<SearchIcon/>}/>

Const HeaderCell

HeaderCell: NamedExoticComponent<HeaderCellProps> & { type: T } = memo((props: HeaderCellProps) => {const renderTableHeaderCell = () => {if (props.isActionButtonCell) {return (<TableSortLabeldata-qa={`tableSortLabel_${props.header.label}`}active={false}hideSortIcononClick={() => undefined}>{props.header.label}</TableSortLabel>);}return (<Tooltiptitle={props.tooltiplabel ?? ''}placement={props.tooltipplacement || 'top'}data-qa={`table-header-${props['data-qa']}`}><TableSortLabeldata-qa={`tableSortLabel_${props.header.label}`}classes={{ icon: css.sortIcon }}active={props.orderby === props.header.label}direction={props.order}onClick={() => props.onRequestSort(props.header.label)}>{props.header.label}</TableSortLabel></Tooltip>);};return (<MUITableCelldata-qa={props['data-qa']}align={props.header.numeric ? 'right' : 'left'}padding={props.header.disablePadding ? 'none' : 'normal'}sortDirection={props.orderby === props.header.label ? props.order : false}className={clsx(css.tableCells, { [css.actionHeaderCell]: props.isActionButtonCell }, props.customclasses)}>{renderTableHeaderCell()}</MUITableCell>);})

Constructs a table header cell using pre-defined Rijkswaterstaat styling

param

Props to pass to the TableHeader cell

Const ItalicTrans

ItalicTrans: NamedExoticComponent<ItalicTransProps> & { type: T } = memo(({ titleKey, italicKey }: ItalicTransProps) => (<Fragment><Trans i18nKey={titleKey} /><em><Trans i18nKey={italicKey} /></em></Fragment>))

Creates a Trans body with one part regular and one part italic

param

Props to pass to the ItalicTrans component

example
<ItalicTrans titleKey='sample.key.normal' italicKey='sample.key.italic'/>

Const LinkTab

LinkTab: NamedExoticComponent<LinkTabProps> & { type: T } = memo(({ to, label, external = false, openInNewTab = false, ...props }: LinkTabProps) => {if (external) {return (<Tab{...props}component='a'href={to}label={label}target={openInNewTab ? '_blank' : '_self'}rel={openInNewTab ? 'noreferrer noopener' : undefined}classes={{ wrapper: css.linkText, selected: css.selectedTab, textColorInherit: css.linkTextInherit }}/>);}return (<Tab{...props}component={Link}to={to}label={label}classes={{ wrapper: css.linkText, selected: css.selectedTab, textColorInherit: css.linkTextInherit }}/>);})

Const LoadingSkeleton

LoadingSkeleton: NamedExoticComponent<LoadingSkeletonProps> & { type: T } = memo(({ width, height, circle, style, 'data-qa': dataQa, ...props }: LoadingSkeletonProps) => {const cssStyle: CSSProperties = {...style,width: width,height: height,borderRadius: height && width && circle ? '50%' : '0%'};// Content is a zero-width-non-joinerreturn (<span {...props} data-qa={dataQa} className={clsx(css.skeleton, props.customclasses)} style={cssStyle}>&zwnj;</span>);})

Constructs a loading skeleton to reserve space for loading data

param

Props to pass to the loading skeleton

example
<LoadingSkeleton
  data-qa='loading-skeleton'
  width={500} height={50}
/>

Const Logo

Logo: NamedExoticComponent<{} & { ref?: Exclude<R, string> | undefined }> & { type: T } = memo((props: LogoProps) => <LogoSVG {...props} />)

Creates a logo using pre-defined Rijkswaterstaat SVG

example

<Logo height={125} width={314}/>

Const Modal

Modal: NamedExoticComponent<ModalProps> & { type: T } = memo(({ DialogContentProps, DialogTitleProps, DialogProps, ...props }: ModalProps) => {return (<Dialog{...DialogProps}disableBackdropClickdisableEscapeKeyDownopen={Boolean(props.open)}classes={{ root: css.modal }}data-qa={props.modalqas?.modal || 'modal'}><DialogTitle {...DialogTitleProps} className={css.title} data-qa={props.modalqas?.title || 'modal-title'}><Grid container alignContent='flex-end' alignItems='flex-end' justifyContent='space-between'><Grid item>{props.topic}</Grid><Grid item classes={{ root: css.closeIcon }}><IconButtononClick={props.closeAction}size='small'edge='end'disableFocusRippledisableTouchRippledisableRipplecolor='primary'><CloseIcon classes={{ root: css.closeIconSVG }} /></IconButton></Grid></Grid></DialogTitle><DialogContent{...DialogContentProps}className={css.content}data-qa={props.modalqas?.content || 'modal-content'}>{props.dialogContent}</DialogContent></Dialog>);})

Constructs a modal using pre-defined Rijkswaterstaat styling

param

Props to pass to the modal - ModalProps

example
<Modal
  topic='topic'
  modalqas={{
    modal: 'modal',
    content: 'content',
    title: 'title',
  }}
  dialogContent={<div>SAMPLE</div>}
  open={true}
/>

Const ModalContent

ModalContent: NamedExoticComponent<object> = memo((props) => (<div {...props} className={css.content}>{props.children}</div>))

Creates modal content using pre-defined Rijkswaterstaat styling

param

Props to pass to the modal content

example
<ModalContent>
  <p>{text}</p>
</ModalContent>

Const NavBar

NavBar: NamedExoticComponent<NavBarProps> & { type: T } = memo(({ActionBarProps,AppBarProps,TabsProps,ToolbarProps,actionBarTitle,activeTab,onTabChange,tabs}: NavBarProps) => (<Fragment><AppBar {...AppBarProps} position='static' color='secondary' classes={{ root: css.appBar }}><Toolbar {...ToolbarProps} variant='dense'><Tabs{...TabsProps}variant='standard'value={activeTab}onChange={onTabChange}classes={{ indicator: css.tabIndicator }}>{tabs.map((tab, index) => (<LinkTabkey={index}label={tab.label}to={tab.to}external={tab.external}data-qa={`link-tab-${tab.label.toLowerCase().replace(/\s/g, '')}`}/>))}</Tabs></Toolbar></AppBar><Grid container direction='row' justifyContent='center' alignItems='flex-start'><Grid key={1} item xs={12}><ActionBar {...ActionBarProps} title={actionBarTitle} /></Grid></Grid></Fragment>))

Const Pagination

Pagination: NamedExoticComponent<PaginationProps> & { type: T } = memo((props: PaginationProps) => {const isOnMobile = useMediaQuery('(max-width: 1024px)');return (<MUITablePaginationcomponent='span'count={props.count}page={props.page}labelRowsPerPage={props.labelRowsPerPage}labelDisplayedRows={({ from, to, count }) =>`${from <= 9 ? `0${from}` : from}-${to} ${props.labelPaginationOf} ${count}`}// TODO -as- 20210708 on next major MUI release, remove props.onPageChangeonPageChange={props.onPageChange || props.onChangePage}// TODO -as- 20210708 on next major MUI release, remove props.onChangeRowsPerPageonRowsPerPageChange={props.onRowsPerPageChange || props.onChangeRowsPerPage}className={clsx(css.tablePagination, { [css.tablePaginationMobile]: isOnMobile }, props.customClasses)}classes={{ root: css.text, selectIcon: css.selectIcon, menuItem: css.text }}rowsPerPage={props.rowsPerPage}rowsPerPageOptions={props.rowsPerPageOptions}ActionsComponent={PaginationActions}data-qa={props['data-qa']}/>);})

Constructs a Table pagination using pre-defined Rijkswaterstaat styling

param

Props to pass to the table pagination

example
<TablePagination
  labelRowsPerPage='rows per page'
  labelPaginationOf='of'
  rowsPerPageOptions={[1, 5, 10]}
  rowsPerPage={10}
  page={0}
  count={20}
  onPageChange={console.log}
  onRowsPerPageChange={console.log}
  data-qa='table-pagination'
/>

Const PaginationActions

PaginationActions: NamedExoticComponent<TablePaginationActionsProps & { data-qa?: undefined | string }> & { type: T } = memo(({ onPageChange, count, rowsPerPage, page: currentPageIndex, 'data-qa': dataQa }: PaginationActionsProps) => {const isOnMobile = useMediaQuery('(max-width: 1024px)');const totalPages = Math.ceil(count / rowsPerPage);const handleFirstPageButtonClick = (event: React.MouseEvent<any, any>): void =>onPageChange(event, FIRST_PAGE_INDEX);const handleBackButtonClick = (event: React.MouseEvent<any, any>): void =>onPageChange(event, currentPageIndex - 1);const handleNextButtonClick = (event: React.MouseEvent<any, any>): void =>onPageChange(event, currentPageIndex + 1);const handleLastPageButtonClick = (event: React.MouseEvent<any, any>): void =>onPageChange(event, Math.max(0, totalPages - 1));const handlePageClick =(page: number) =>(event: React.MouseEvent<any, any>): void =>onPageChange(event, page);const nextButtonShouldBeDisabled = currentPageIndex >= totalPages - 1;const previousButtonShouldBeDisabled = currentPageIndex === FIRST_PAGE_INDEX;return (<Box style={{ display: 'flex', alignItems: 'center' }} data-qa={dataQa}><PaginationButtondata-qa={`${dataQa ? `${dataQa}-` : ''}first-page-button`}onClick={handleFirstPageButtonClick}disabled={previousButtonShouldBeDisabled}icon={<FirstPageIcon />}/><PaginationButtondata-qa={`${dataQa ? `${dataQa}-` : ''}previous-page-button`}onClick={handleBackButtonClick}disabled={previousButtonShouldBeDisabled}icon={<KeyboardArrowLeft />}/><If condition={isOnMobile}><Then>{renderCurrentPage(1, currentPageIndex + 1, handlePageClick)}</Then><Else>{renderPages(totalPages, currentPageIndex, handlePageClick)}</Else></If><PaginationButtondata-qa={`${dataQa ? `${dataQa}-` : ''}next-page-button`}onClick={handleNextButtonClick}disabled={nextButtonShouldBeDisabled}icon={<KeyboardArrowRight />}/><PaginationButtondata-qa={`${dataQa ? `${dataQa}-` : ''}last-page-button`}onClick={handleLastPageButtonClick}disabled={nextButtonShouldBeDisabled}icon={<LastPageIcon />}/></Box>);})

Constructs a table pagination action navigators using pre-defined Rijkswaterstaat styling

param

Props to pass to the table pagination

Const PaginationButton

PaginationButton: NamedExoticComponent<PaginationButtonProps> & { type: T } = memo(({ onClick, disabled, icon, ...props }: PaginationButtonProps) => (<IconButton {...props} disabled={disabled} onClick={onClick} color='primary' className={css.noHoverBackground}>{icon}</IconButton>))

Const Router

Router: NamedExoticComponent<RouterProps & { children?: ReactNode | undefined }> & { type: T } = memo(({ defaultComponent, otherComponents, ...props }: PropsWithChildren<RouterProps>) => {return (<Switch><AppRoute exact path={defaultComponent.path} component={defaultComponent.component} {...props} />{otherComponents?.map((child, index) => (<AppRoute key={index} exact path={child.path} component={child.component} {...child.reactRouterProps} />))}<AppRoute component={defaultComponent.component} {...props} /></Switch>);})

Constructs a Router with provided routes and components

param

Includes list of paths and components as well as the option to pass data-qa and additional props

example
 <div>
   <Router
     defaultComponent={{ path: '/', component: () => <div>TEST</div> }}
     data-qa='TestRouter'
     otherComponents={[
       { path: '/app', component: () => <div>APP</div>, 'data-qa': 'AppRoute' },
       { path: '/contact', component: () => <Contact />, 'data-qa': 'ContactRoute' }
     ]}
   />
 </div>

Const SearchBar

SearchBar: NamedExoticComponent<SearchBarProps> & { type: T } = memo(({onFocus,onBlur,onChange,onCancelSearch,onRequestSearch,cancelOnEscape,onKeyUp,paperElevation,disabled,clearSearch = false,'data-qa': dataQa,placeholder,...props}: SearchBarProps) => {const [value, setValue] = useState('');const searchPlaceholder = placeholder || 'Search...';const handleFocus = (event: any): void => {if (onFocus) onFocus(event);};const handleBlur = (event: any): void => {if (value && value.trim().length === 0) setValue('');if (onBlur) onBlur(event);};const handleInput = (event: ChangeEvent<HTMLInputElement>): void => {setValue(event.target.value);if (onChange) onChange(event);};const handleCancel = (): void => {setValue('');if (onCancelSearch) onCancelSearch();};const handleRequestSearch = (): void => {if (onRequestSearch) onRequestSearch(value);};const handleKeyUp = (event: KeyboardEvent<HTMLInputElement>): void => {if (event.charCode === 13 || event.key === 'Enter') {handleRequestSearch();} else if (cancelOnEscape && (event.charCode === 27 || event.key === 'Escape')) {handleCancel();}if (onKeyUp) onKeyUp(event);};useEffect(() => {setValue('');}, [clearSearch]);return (<Paper className={css.paper} elevation={paperElevation} square><InputBase{...props}className={css.input}placeholder={searchPlaceholder}inputProps={{ 'aria-label': searchPlaceholder }}onBlur={handleBlur}value={value}onChange={handleInput}onKeyUp={handleKeyUp}onFocus={handleFocus}disabled={disabled}data-qa={dataQa}fullWidth/>{!value ? (<IconButtonaria-label={searchPlaceholder}className={css.inputButton}onClick={handleRequestSearch}disabled={disabled}size='small'color='primary'data-qa='search-button'><SearchIcon className={css.inputSVG} /></IconButton>) : (<IconButtonaria-label={searchPlaceholder}className={css.inputButton}onClick={handleCancel}disabled={disabled}size='small'color='primary'data-qa='search-close-button'><CloseIcon className={css.inputSVG} /></IconButton>)}</Paper>);})

Constructs a search bar using pre-defined Rijkswaterstaat styling

param

Props to pass to the searchbar

example
<SearchBar
  data-qa='table-search-bar'
  placeholder='Search...'
  onChange={e => debouncedSearch(e.target.value)}
  onCancelSearch={console.log}
  paperElevation={2}
/>

Const Table

Table: NamedExoticComponent<TableProps> & { type: T } = memo(({ showTopPagination = false, showBottomPagination = false, disableToolbar = false, ...props }: TableProps) => {const addCustomClasses = (component: keyof TableCustomClasses, baseClass?: string): string[] => {const classes: string[] = [];if (baseClass) classes.push(baseClass);if (props.tablecss && props.tablecss[component]) classes.push(...props.tablecss[component]!); // eslint-disable-line @typescript-eslint/no-non-null-assertionreturn classes;};// TODO -as- 20210421 a toolbar in a table component is too much for one component. Deprecated the toolbar props.// use the separate Toolbar component.return (<Fragment><When condition={disableToolbar === false}><Toolbar{...props.ToolbarProps}clearSearch={props.clearSearch}searchplaceholderlabel={props.labels.searchplaceholderlabel}onsearchinput={props.onsearchinput}onsearchclear={props.onsearchclear}searchdebounce={props.searchdebounce}data-qa={props.tableqas.toolbar}customclasses={clsx(addCustomClasses('tableToolbar'))}customSearchbarClasses={clsx(addCustomClasses('tableSearchbar'))}paperElevation={props.paperElevation}extraIcons={props.extraIcons}/></When><When condition={showTopPagination}>{renderTablePagination(props, clsx(addCustomClasses('tablePagination', css.tableTopPagination)))}</When><MUITable{...props.TableProps}stickyHeader={props.stickyHeader}className={clsx(addCustomClasses('table', css.table))}data-qa={props.tableqas.table}>{renderTableHead(props, addCustomClasses)}<TableBody data-qa={props.tableqas.tableBody} className={clsx(addCustomClasses('tableBody'))}>{props.tablebodycontent}</TableBody></MUITable><When condition={showBottomPagination}>{renderTablePagination(props, clsx(addCustomClasses('tablePagination')))}</When></Fragment>);})

Constructs a table using pre-defined Rijkswaterstaat styling

param

Props to pass to the table

example
<Table
  showBottomPagination
  showTopPagination
  paperElevation={1}
  onsearchclear={props.handleSearchClear}
  onsearchinput={props.handleSearchInput}
  onRequestSort={props.handleRequestSort}
  onPageChange={props.handleChangePage}
  onRowsPerPageChange={props.handleChangeRowsPerPage}
  tooltipplacement='bottom-start'
  order={props.tableOrder}
  orderby={props.tableOrderBy}
  rowsPerPage={props.tableRowsPerPage}
  rowsPerPageOptions={tableRowsPerPage}
  page={props.tablePage}
  headers={tableHeaders}
  headermapping={tableHeaderMapping}
  rowcount={props.data.length}
  labels={{
    labelPaginationOf: t('table.generic.pagination.of_label'),
    labelRowsPerPage: t('table.generic.pagination.rows_per_page'),
    searchplaceholderlabel: t('table.generic.searchLabel'),
    tooltiplabel: t('table.generic.sortTooltipLabel'),
  }}
  tableqas={{
    header: 'table-header',
    headerRow: 'table-header-row',
    pagination: 'table-pagination',
    table: 'table',
    toolbar: 'table-toolbar',
    headerCell: 'table-header-cell',
    tableBody: 'table-body',
  }}
  extraIcons={[
    {
      icon: <CloudDownload />,
      clickEvent: () => console.log('Clicked button!'),
      tooltipText: 'Tooltip on button',
    }
  ]}
  tablebodycontent={(
    <Fragment>
      {props.data
        .slice(props.tablePage * props.tableRowsPerPage, props.tablePage * props.tableRowsPerPage + Number(props.tableRowsPerPage))
        .map((item, index) => {
          return (
            <TableRow hover tabIndex={-1} key={index} data-qa='table-body-row'>
              <TableBodyCell content={item.name} />
              <TableBodyCell content={item.email} />
            </TableRow>
          );
        })
      }
    </Fragment>
  )}
/>

Const Toolbar

Toolbar: NamedExoticComponent<ToolbarProps> & { type: T } = memo(({extraIcons,clearSearch,searchplaceholderlabel,onsearchclear,onsearchinput,customSearchbarClasses,customclasses,searchdebounce,paperElevation,SearchbarProps,'data-qa': dataQa,...props}: ToolbarProps) => {const debouncedSearch = debouncer((input: string) => onsearchinput(input), searchdebounce || 400);return (<div {...props} className={clsx(css.toolbar, customclasses)} data-qa={dataQa}><Grid container direction='row' justifyContent='flex-end' alignItems='center' spacing={2}>{extraIcons && extraIcons.length ? renderIcons(extraIcons) : <Fragment />}<Grid item key={2}><SearchBar{...SearchbarProps}clearSearch={clearSearch}data-qa='table-search-bar'placeholder={`${searchplaceholderlabel}...`}onChange={(e) => debouncedSearch(e.target.value)}onCancelSearch={onsearchclear}className={clsx(css.searchFieldContent, css.ie11SearchBarTextCorrection, customSearchbarClasses)}paperElevation={paperElevation}/></Grid><Grid item key={1} /></Grid></div>);})

Constructs a table toolbar using pre-defined Rijkswaterstaat styling

param

Props to pass to the Toolbar

example
<Toolbar
  searchplaceholderlabel='Search...'
  onsearchinput={console.log}
  onsearchclear={console.log}
  searchdebounce={console.log}
  data-qa={{ ...tableQas }}
  extraIcons={props.extraIcons}
/>

Const ToolbarButton

ToolbarButton: NamedExoticComponent<ToolbarButtonProps> & { type: T } = memo((props: ToolbarButtonProps) => {const elevation = useMemo(() => (Reflect.has(props, 'paperElevation') ? props.paperElevation : 2), [props]);const renderWithTooltip = useMemo(() => (<Tooltipdata-qa={props['tooltip-data-qa']}customclasses={props.tooltipCustomClasses}placement={props.tooltipPlacement || 'top'}title={props.tooltipText || 'Click Me'}><IconButtondisabled={props.disabled}data-qa={props['iconButton-data-qa']}className={clsx(css.inputButton, props.iconButtonCustomclasses)}onClick={props.onClick}size='small'color='primary'>{props.icon}</IconButton></Tooltip>),[props]);const renderWithoutTooltip = useMemo(() => (<IconButtondisabled={props.disabled}data-qa={props['iconButton-data-qa']}className={clsx(css.inputButton, props.iconButtonCustomclasses)}onClick={props.onClick}size='small'color='primary'>{props.icon}</IconButton>),[props]);const customRender = useMemo(() => {if (props.disabled) return renderWithoutTooltip;if (props.disableTooltip) return renderWithoutTooltip;return renderWithTooltip;}, [props.disabled, props.disableTooltip, renderWithoutTooltip, renderWithTooltip]);return (<PaperclassName={clsx(css.paper, props.paperCustomclasses)}elevation={elevation}data-qa={props['paper-data-qa']}square>{customRender}</Paper>);})

Constructs a ToolbarButton (elevated button with Material Paper) using pre-defined Rijkswaterstaat styling

param

Props to pass to the ToolbarButton

example
<ToolbarButton
  icon={<CloudDownload/>}
  disabled={false}
  onClick={console.log}
  tooltipText='SAMPLE'
  tooltipPlacement={'top'}
  disableTooltip={false}
/>

Const Tooltip

Tooltip: NamedExoticComponent<TooltipProps> & { type: T } = memo(({ 'data-qa': qaTag, title, placement, enterDelay, customclasses, style, children, ...props }: TooltipProps) => (<MUITooltip{...props}title={<Box data-qa={qaTag} className={css.box}>{title}</Box>}placement={placement || 'top'}enterDelay={enterDelay || 300}classes={{ tooltip: clsx(css.tooltip, customclasses), popper: css.popper }}style={style}>{children}</MUITooltip>))

Constructs a tooltip using pre-defined Rijkswaterstaat styling

param

Props to pass to the Tooltip

example
<Tooltip title='Tooltip Content' placement='top'>
  <IconButton>
    <CloudDownload color='primary' />
  </IconButton>
</Tooltip>

Const UserInfo

UserInfo: NamedExoticComponent<UserInfoProps> & { type: T } = memo(({ email, onReloginClick, reloginText, EmailProps, ButtonProps }: UserInfoProps) => (<Box component='div' className={css.authInfo}><Box component='div' data-qa='logged-in-email'><When condition={email !== undefined}><Typography {...EmailProps} color='textPrimary' variant='subtitle2' align='center'>{email}</Typography></When></Box><Button {...ButtonProps} data-qa='re-login-link' size='small' className={css.relogin} onClick={onReloginClick}><Typography color='textPrimary' variant='subtitle2' align='center'>{reloginText}</Typography></Button></Box>))

Constructs a UserInfo section using pre-defined Rijkswaterstaat styling

param

Props to pass to the UserInfo tooltip

example
<UserInfo email='a.cool.email' reloginText='relogin' onReloginClick={() => console.log('void')} />

Const ZeroWidthSpace

ZeroWidthSpace: NamedExoticComponent<ZeroWidthSpaceProps> & { type: T } = memo(({ variant, style, customclasses, 'data-qa': dataQa, ...props }: ZeroWidthSpaceProps) => (<Typography{...props}variant={variant || 'caption'}style={style}className={clsx(customclasses)}data-qa={dataQa}>&#8203;</Typography>))

Inserts a Zero Width Space as a React component

param

Props to pass to the Zero-Width Space

example
<ZeroWidthSpace />

Functions

Const DatePicker

  • DatePicker(__namedParameters: { label: string; minDate: Date; props: props }): Element

Const RadioGroup

  • RadioGroup<T>(__namedParameters: { dataQa: undefined | string; options: Option<T>[]; props: props }): Element
  • Constructs a radio button group with formik validation

    example
    <Field
      component={RadioGroup}
      name='type'
      data-qa='sample-radio-group'
      required
      options={ [{ value: 'JOHN', label: 'John'}, { value: 'CONNOR', label: 'Connor'}] }
    />

    Type parameters

    Parameters

    • __namedParameters: { dataQa: undefined | string; options: Option<T>[]; props: props }
      • dataQa: undefined | string
      • options: Option<T>[]
      • props: props

    Returns Element

Const SelectMenu

  • SelectMenu<T>(__namedParameters: { autoFocus: undefined | false | true; className: undefined | string; label: string; options: SelectMenuOption<T>[]; placeholder: undefined | string; props: props; required: undefined | false | true }): Element
  • Constructs a Select Menu with the formik validation

    example
    <Field
      component={SelectMenu}
      name='type'
      type='text'
      required
      placeholder='Example Placeholder'
      variant='outlined'
      data-qa='sample-select-menu'
      label='Example'
      options={ [{ value: 'JOHN', label: 'John'}, { value: 'CONNOR', label: 'Connor'}] }
    />

    Type parameters

    Parameters

    • __namedParameters: { autoFocus: undefined | false | true; className: undefined | string; label: string; options: SelectMenuOption<T>[]; placeholder: undefined | string; props: props; required: undefined | false | true }
      • autoFocus: undefined | false | true
      • className: undefined | string
      • label: string
      • options: SelectMenuOption<T>[]
      • placeholder: undefined | string
      • props: props
      • required: undefined | false | true

    Returns Element

Const SelectMenuMultiple

  • SelectMenuMultiple<T>(__namedParameters: { autoFocus: undefined | false | true; className: undefined | string; label: string; options: SelectMenuOption<T>[]; placeholder: undefined | string; props: props; required: undefined | false | true }): Element
  • Constructs a Select Menu with the formik validation

    remark

    supports selecting multiple entries, active entries will have a checked Checkbox

    example
    const dropdownOptions = [{ value: 'JOHN', label: 'John'}, { value: 'CONNOR', label: 'Connor'}];
    
    <Field
      component={SelectMenuMultiple}
      name='type'
      type='text'
      required
      placeholder='Example Placeholder'
      variant='outlined'
      data-qa='sample-select-menu'
      label='Example'
      options={dropdownOptions}
      style={{ marginBottom: theme.spacing(5), height: values.selectMultiple.length ? 'unset' : null }}
      renderValue={(selected: unknown) => (
          <Box className={classes.chips}>
          {(selected as string[]).map((value) => (
              <Chip
              color='secondary'
              key={value}
              label={dropdownOptions.find((p) => p.value === value)?.label ?? 'Unknown'}
              className={classes.chip}
              size='small'
              />
          ))}
          </Box>
     />

    Type parameters

    Parameters

    • __namedParameters: { autoFocus: undefined | false | true; className: undefined | string; label: string; options: SelectMenuOption<T>[]; placeholder: undefined | string; props: props; required: undefined | false | true }
      • autoFocus: undefined | false | true
      • className: undefined | string
      • label: string
      • options: SelectMenuOption<T>[]
      • placeholder: undefined | string
      • props: props
      • required: undefined | false | true

    Returns Element

Const TextField

  • TextField(props: TextFieldProps & { children?: ReactNode | undefined }): Element
  • Constructs a TextField with the formik validation

    example
    <Field
      component={TextField}
      name='name'
      type='text'
      label='Example'
      placeholder='Example placeholder'
      variant='outlined'
      data-qa='exampleDataQA'
      required
    />

    Parameters

    • props: TextFieldProps & { children?: ReactNode | undefined }

      Props to pass to the Textield component

    Returns Element

Const renderIcons

Generated using TypeDoc