@mui/material#MenuItem TypeScript Examples

The following examples show how to use @mui/material#MenuItem. You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example #1
Source File: Select.tsx    From Cromwell with MIT License 6 votes vote down vote up
/** @internal */
export function Select(props: TSelectProps & MuiSelectProps<string | number>) {
  const { className, style, variant = 'filled' } = props;
  return (
    <FormControl
      fullWidth={props.fullWidth}
      style={props.style}
      className={props.className}
    >
      {props.label && (
        <InputLabel style={{
          marginTop: '8px',
        }}>{props.label}</InputLabel>
      )}
      <MuiSelect
        {...props}
        variant={variant}
        className={className}
        style={style}
      >
        {props.options?.map((option) => {
          const label = typeof option === 'object' ? option.label : option;
          const value = typeof option === 'object' ? option.value : option;
          return (
            <MenuItem value={value} key={value + ''}>{label}</MenuItem>
          )
        })}
      </MuiSelect>
    </FormControl>
  )
}
Example #2
Source File: Mobile.tsx    From GTAV-NativeDB with MIT License 6 votes vote down vote up
function AppBarAction({ text, mobileIcon, buttonProps: { href, target, onClick, ...buttonProps } }: AppBarActionProps) {
  const history = useHistory()

  const handleClick = useCallback(() => {
    if (href) {
      if (href.includes('://') || target) {
        window.open(href, target)
      }
      else {
        history.push(href)
      }
    }

    onClick && onClick()
  }, [href, target, onClick, history])

  return (
    <MenuItem onClick={handleClick}>
      {mobileIcon && <ListItemIcon>
        {React.createElement(mobileIcon)}
      </ListItemIcon>}
      {text}
    </MenuItem>
  )
}
Example #3
Source File: DarkModeSwitch.tsx    From your_spotify with GNU General Public License v3.0 6 votes vote down vote up
export default function DarkModeSwitch() {
  const dispatch = useAppDispatch();
  const dark = useSelector(selectDarkMode);

  const changeDarkMode = useCallback(
    (mode: DarkModeType) => {
      dispatch(setDarkMode(mode));
    },
    [dispatch],
  );

  return (
    <Select
      variant="standard"
      value={dark}
      onChange={(ev) => changeDarkMode(ev.target.value as DarkModeType)}>
      <MenuItem value="follow">Follow system theme</MenuItem>
      <MenuItem value="dark">Use dark theme</MenuItem>
      <MenuItem value="light">Use light theme</MenuItem>
    </Select>
  );
}
Example #4
Source File: ArtifactRarityDropdown.tsx    From genshin-optimizer with MIT License 6 votes vote down vote up
export default function ArtifactRarityDropdown({ rarity, onChange, filter, ...props }: props) {
  const { t } = useTranslation("artifact")
  return <DropdownButton
    {...props}
    title={rarity ? <Stars stars={rarity} /> : t`editor.rarity`}
    color={rarity ? "success" : "primary"}
  >
    {([5, 4, 3] as ArtifactRarity[]).map(rarity =>
      <MenuItem key={rarity} disabled={!filter(rarity)} onClick={() => onChange(rarity)}>
        <Stars stars={rarity} />
      </MenuItem>)}
  </DropdownButton>
}
Example #5
Source File: ThemeEditor.tsx    From mui-toolpad with MIT License 6 votes vote down vote up
function PaletteColorPicker({ name, value, onChange }: PaletteColorPickerProps) {
  return (
    <TextField
      select
      fullWidth
      value={value}
      label={name}
      onChange={(event) => onChange(event.target.value)}
    >
      {THEME_COLORS.map((color) => (
        <MenuItem key={color} value={color}>
          {color}
        </MenuItem>
      ))}
    </TextField>
  );
}
Example #6
Source File: App.tsx    From NekoMaid with MIT License 6 votes vote down vote up
LanguageSwitch: React.FC = React.memo(() => {
  const [anchorEl, setAnchorEl] = React.useState<HTMLElement | undefined>()
  return <>
    <IconButton onClick={e => setAnchorEl(e.currentTarget)} color='inherit'><Translate /></IconButton>
    <MenuComponent anchorEl={anchorEl} open={!!anchorEl} onClose={() => setAnchorEl(undefined)}>
      {Object.entries(languages).map(([key, value]) => <MenuItem
        key={key}
        selected={currentLanguage === key}
        onClick={() => {
          setAnchorEl(undefined)
          if (currentLanguage !== key) {
            localStorage.setItem('NekoMaid:language', key)
            location.reload()
          }
        }}
      >{value.minecraft['language.name']}</MenuItem>)}
    </MenuComponent>
  </>
})
Example #7
Source File: CampaignTypeSelect.tsx    From frontend with MIT License 6 votes vote down vote up
export default function CampaignTypeSelect({ name = 'campaignTypeId' }) {
  const { t } = useTranslation()
  const { data } = useCampaignTypesList()
  const [field, meta] = useField(name)

  const helperText = meta.touched ? translateError(meta.error as TranslatableField, t) : ''
  return (
    <FormControl
      fullWidth
      size="small"
      variant="outlined"
      error={Boolean(meta.error) && Boolean(meta.touched)}>
      <InputLabel>{t('campaigns:campaign.type')}</InputLabel>
      <Select fullWidth defaultValue="" label={t('campaigns:campaign.type')} {...field}>
        <MenuItem value="" disabled>
          {t('campaigns:campaign.type')}
        </MenuItem>
        {data?.map((campaignType, index) => (
          <MenuItem key={index} value={campaignType.id}>
            {campaignType.name}
          </MenuItem>
        ))}
      </Select>
      {helperText && <FormHelperText error>{helperText}</FormHelperText>}
    </FormControl>
  )
}
Example #8
Source File: ethereum-deploy-form.tsx    From sdk with MIT License 6 votes vote down vote up
export function EthereumDeployForm({ form }: IEthereumDeployFormProps) {
	return (
		<>
			<Stack spacing={2}>
				<FormSelect
					form={form}
					defaultValue={"ERC721"}
					name="contract"
					label="Contract Type"
				>
					<MenuItem value={"ERC721"}>{"ERC721"}</MenuItem>
					<MenuItem value={"ERC1155"}>{"ERC1155"}</MenuItem>
				</FormSelect>
				<FormTextInput form={form} name="name" label="Name"/>
				<FormTextInput form={form} name="symbol" label="Symbol"/>
				<FormTextInput form={form} name="baseURI" label="Base URI"/>
				<FormTextInput form={form} name="contractURI" label="Contract URI"/>
				<FormCheckbox form={form} name="private" label="Private Collection"/>
			</Stack>
		</>
	)
}
Example #9
Source File: AppNavbar.tsx    From sapio-studio with Mozilla Public License 2.0 6 votes vote down vote up
function Simulator() {
    const dispatch = useDispatch();
    const simulateRef = React.useRef<HTMLLIElement>(null);
    const [sim_open, setSimOpen] = React.useState(false);
    return (
        <div>
            <ListItem
                disableGutters
                button={false}
                key={'Simulate'}
                onClick={() => setSimOpen(true)}
                ref={simulateRef}
            >
                <ListItemIcon></ListItemIcon>
                <ListItemText primary={'Simulate'} />
            </ListItem>
            <Menu
                anchorEl={simulateRef.current}
                anchorOrigin={{
                    vertical: 'center',
                    horizontal: 'right',
                }}
                keepMounted
                open={sim_open}
                onClose={() => setSimOpen(false)}
            >
                <MenuItem
                    onClick={() => {
                        setSimOpen(false);
                        dispatch(toggle_showing());
                    }}
                >
                    Timing
                </MenuItem>
            </Menu>
        </div>
    );
}
Example #10
Source File: SettingsPage.tsx    From Cromwell with MIT License 5 votes vote down vote up
export function SettingsPage(props: TPluginSettingsProps<TMainMenuSettings>) {
    const classes = useStyles();
    const forceUpdate = useForceUpdate();
    const [canReorder, setCanReorder] = useState(false);

    const onSave = () => {
        getRestApiClient().purgeRendererEntireCache();
    }

    return (
        <PluginSettingsLayout<TMainMenuSettings> {...props} onSave={onSave}>
            {({ pluginSettings, changeSetting }) => {
                const items = pluginSettings?.items;

                if (items) {
                    for (const item of items) {
                        if (!item.id) item.id = getRandStr(12);
                    }
                }

                const updateItems = (items: TMainMenuItem[]) => {
                    if (pluginSettings) pluginSettings.items = items;
                }

                return (
                    <>
                        <div onClick={() => setCanReorder(!canReorder)}
                            style={{ display: 'flex', alignItems: 'center' }}>
                            {canReorder ? (
                                <Tooltip title="Apply order">
                                    <IconButton><DoneIcon /></IconButton>
                                </Tooltip>
                            ) : (
                                <Tooltip title="Edit order">
                                    <IconButton><ReorderIcon /></IconButton>
                                </Tooltip>
                            )}
                        </div>
                        <div className={classes.itemList}>
                            {canReorder && items?.length && (
                                <DraggableList data={items}
                                    component={Item}
                                    onChange={updateItems}
                                    itemProps={{
                                        items,
                                        canReorder,
                                        refreshList: forceUpdate,
                                    }}
                                />
                            )}
                            {!canReorder && items?.map((data) => {
                                return <Item data={data}
                                    key={data.id}
                                    itemProps={{
                                        items,
                                        canReorder,
                                        refreshList: forceUpdate,
                                    }} />
                            })}
                        </div>
                        <div style={{ padding: '5px 10px' }}>
                            <div className={`${classes.card} PluginMainMenu-paper`}>
                                <MenuItem
                                    className={classes.addBtn}
                                    onClick={() => changeSetting('items',
                                        [...(items ?? []), {
                                            title: '',
                                            id: getRandStr(12),
                                        }]
                                    )}>
                                    <AddIcon />
                                </MenuItem>
                            </div>
                        </div>
                    </>
                )
            }}
        </PluginSettingsLayout>
    )
}
Example #11
Source File: CategorySelect.tsx    From mojito_pdm with Creative Commons Attribution Share Alike 4.0 International 5 votes vote down vote up
CategorySelect: React.FC = () => {
    const theme = useTheme()
    const [category, setCategory] = useRecoilState(CarState.categorySearch)

    const handleChange = (event: SelectChangeEvent) => {
        setCategory(event.target.value)
    };

    return (
        <>
            <div>
                <FormControl variant="outlined" sx={{margin: theme.spacing(1), minWidth: 240}} color="error">
                    <InputLabel sx={{color: "white"}}>Category</InputLabel>
                    <Select sx={{color: "white"}}
                            labelId="demo-simple-select-outlined-label"
                            id="demo-simple-select-outlined"
                            value={category}
                            onChange={handleChange}
                            label="Category"
                    >
                        <MenuItem value="">
                            <em>All</em>
                        </MenuItem>
                        <MenuItem value={"Sports"}>Sports</MenuItem>
                        <MenuItem value={"Compacts"}>Compacts</MenuItem>
                        <MenuItem value={"Muscle"}>Muscle</MenuItem>
                        <MenuItem value={"Sedan"}>Sedan</MenuItem>
                        <MenuItem value={"Coupe"}>Coupé</MenuItem>
                        <MenuItem value={"Super"}>Super</MenuItem>
                        <MenuItem value={"SUV"}>SUV</MenuItem>
                        <MenuItem value={"Vans"}>Vans</MenuItem>
                        <MenuItem value={"Offroad"}>Offroad</MenuItem>
                        <MenuItem value={"Sports Classics"}>Sports Classics</MenuItem>
                        <MenuItem value={"Motorcycles"}>Motorcycles</MenuItem>
                    </Select>
                </FormControl>
            </div>
        </>
    )
}
Example #12
Source File: BestOfHour.tsx    From your_spotify with GNU General Public License v3.0 5 votes vote down vote up
export default function BestOfHour({ className }: BestOfHourProps) {
  const { interval } = useSelector(selectRawIntervalDetail);
  const [element, setElement] = useState<Element>(Element.ARTIST);
  const result = useAPI(elementToCall[element], interval.start, interval.end);

  const data = useMemo(() => {
    if (!result) {
      return [];
    }
    return Array.from(Array(24).keys()).map((index) => getElementData(result, index));
  }, [result]);

  const labelFormatter = useCallback(
    (label: string) => {
      return `20 most listened ${element} at ${label}:00`;
    },
    [element],
  );

  const valueFormatter = useCallback(
    (value: number, elementId: string, { payload }: any) => {
      const foundIndex = result?.findIndex((r) => r._id === payload.x);
      if (result && foundIndex !== undefined && foundIndex !== -1) {
        const found = result[foundIndex];
        return [`${value}% of ${getElementName(found, elementId)}`];
      }
      return [];
    },
    [result],
  );

  if (!result) {
    return (
      <LoadingImplementedChart title={`Best ${element} for hour of day`} className={className} />
    );
  }

  return (
    <ChartCard
      title={`Best ${element} for hour of day`}
      right={
        <Select
          value={element}
          onChange={(ev) => setElement(ev.target.value as Element)}
          variant="standard">
          {Object.values(Element).map((elem) => (
            <MenuItem key={elem} value={elem}>
              {elem}
            </MenuItem>
          ))}
        </Select>
      }
      className={className}>
      <StackedBar
        data={data}
        xFormat={formatX}
        tooltipLabelFormatter={labelFormatter}
        tooltipValueFormatter={valueFormatter}
        tooltipItemSorter={itemSorter as any}
      />
    </ChartCard>
  );
}
Example #13
Source File: PlayBar.tsx    From rewind with MIT License 5 votes vote down vote up
function MoreMenu() {
  const [anchorEl, setAnchorEl] = useState(null);
  const open = Boolean(anchorEl);
  const handleClick = (event: any) => {
    setAnchorEl(event.currentTarget);
  };
  const handleClose = () => {
    setAnchorEl(null);
  };

  const analyzer = useAnalysisApp();
  const handleTakeScreenshot = () => {
    analyzer.screenshotTaker.takeScreenshot();
    handleClose();
  };

  const [helpOpen, setHelpOpen] = useState(false);

  const handleOpenHelp = () => {
    setHelpOpen(true);
    handleClose();
  };

  return (
    <>
      <HelpModalDialog isOpen={helpOpen} onClose={() => setHelpOpen(false)} />
      <IconButton
        aria-label="more"
        id="long-button"
        aria-controls="long-menu"
        // aria-expanded={open ? "true" : undefined}
        aria-haspopup="true"
        onClick={handleClick}
        onFocus={ignoreFocus}
      >
        <MoreVert />
      </IconButton>
      <Menu
        open={open}
        onClose={handleClose}
        anchorEl={anchorEl}
        anchorOrigin={{
          vertical: "top",
          horizontal: "center",
        }}
        transformOrigin={{
          vertical: "bottom",
          horizontal: "center",
        }}
      >
        <MenuItem onClick={handleTakeScreenshot}>
          <ListItemIcon>
            <PhotoCamera />
          </ListItemIcon>
          <ListItemText>Take Screenshot</ListItemText>
        </MenuItem>
        <MenuItem onClick={handleOpenHelp}>
          <ListItemIcon>
            <Help />
          </ListItemIcon>
          <ListItemText>Help</ListItemText>
        </MenuItem>
      </Menu>
    </>
  );
}
Example #14
Source File: MultiSelect.tsx    From multi-downloader-nx with MIT License 5 votes vote down vote up
MultiSelect: React.FC<MultiSelectProps> = (props) => {
  const theme = useTheme();

  return <div>
    <FormControl sx={{ m: 1, width: 300 }}>
      <InputLabel id="multi-select-label">{props.title}</InputLabel>
      <Select
        labelId="multi-select-label"
        id="multi-select"
        multiple
        value={(props.selected ?? [])}
        onChange={e => {
          const val = typeof e.target.value === "string" ? e.target.value.split(",") : e.target.value;
          if (props.allOption && val.includes('all')) {
            if (props.values.length === val.length - 1)
              props.onChange([]);
            else 
              props.onChange(props.values);
          } else {
            props.onChange(val);
          }
        }}
        input={<OutlinedInput id="select-multiple-chip" label={props.title} />}
        renderValue={(selected) => (
          selected.join(', ')
        )}
        MenuProps={MenuProps}
      >
        {props.values.concat(props.allOption ? 'all' : []).map((name) => (
          <MenuItem
            key={`${props.title}_${name}`}
            value={name}
            style={getStyles(name, props.selected, theme)}
          >
            {name}
          </MenuItem>
        ))}
      </Select>
    </FormControl>
  </div>
}
Example #15
Source File: Sort.tsx    From cli with Apache License 2.0 5 votes vote down vote up
SortRenderer: FunctionComponent<SortProps> = (props) => {
  const {controller, criteria} = props;
  const [state, setState] = React.useState(controller.state);

  useEffect(
    () => controller.subscribe(() => setState(controller.state)),
    [controller]
  );

  const getCurrentCriterion = () =>
    criteria.find(
      ([, criterion]) =>
        state.sortCriteria === buildCriterionExpression(criterion)
    )!;

  const getCriterionFromName = (name: string) =>
    criteria.find(([criterionName]) => criterionName === name)!;

  return (
    <Box>
      <FormControl>
        <InputLabel id="sort-by-label">Sort by</InputLabel>
        <Select
          labelId="sort-by-label"
          label="Sort by"
          id="sort-by"
          onChange={(e) =>
            controller.sortBy(getCriterionFromName(e.target.value as string)[1])
          }
          defaultValue={getCurrentCriterion()[0]}
        >
          {criteria.map(([criterionName]) => (
            <MenuItem key={criterionName} value={criterionName}>
              {criterionName}
            </MenuItem>
          ))}
        </Select>
      </FormControl>
    </Box>
  );
}
Example #16
Source File: Footer.tsx    From website with Apache License 2.0 5 votes vote down vote up
StyledMenuItem = styled(MenuItem)`
  display: flex;
  align-items: center;
`
Example #17
Source File: SelectElement.tsx    From react-hook-form-mui with MIT License 5 votes vote down vote up
export default function SelectElement({
  name,
  required,
  valueKey = 'id',
  labelKey = 'title',
  options = [],
  parseError,
  type,
  objectOnChange,
  validation = {},
  control,
  ...rest
}: SelectElementProps): JSX.Element {
  const isNativeSelect = !!rest.SelectProps?.native
  const ChildComponent = isNativeSelect ? 'option' : MenuItem
  if (required) {
    validation.required = 'This field is required'
  }
  return (
    <Controller
      name={name}
      rules={validation}
      control={control}
      render={({ field: { onBlur, onChange, value }, fieldState: { invalid, error } }) => {
        // handle shrink on number input fields
        if (type === 'number' && typeof value !== 'undefined') {
          rest.InputLabelProps = rest.InputLabelProps || {}
          rest.InputLabelProps.shrink = true
        }
        if (typeof value === 'object') {
          value = value[valueKey] // if value is object get key
        }
        return <TextField
          {...rest}
          name={name}
          value={value ?? ''}
          onBlur={onBlur}
          onChange={(event) => {
            let item: number | string = event.target.value
            if (type === 'number') {
              item = Number(item)
            }
            onChange(item)
            if (typeof rest.onChange === 'function') {
              if (objectOnChange) {
                item = options.find(i => i[valueKey] === item)
              }
              rest.onChange(item)
            }
          }}
          select
          required={required}
          error={invalid}
          helperText={error ? (typeof parseError === 'function' ? parseError(error) : error.message) : rest.helperText}
        >{isNativeSelect && <option />}
          {options.map((item: any) =>
            createElement(
              ChildComponent,
              {
                key: `${name}_${item[valueKey]}`,
                value: item[valueKey]
              },
              item[labelKey]
            )
          )}
        </TextField>
      }}
    />
  )
}
Example #18
Source File: ArtifactSetPicker.tsx    From genshin-optimizer with MIT License 5 votes vote down vote up
export default function ArtifactSetPicker({ index, setFilters, onChange, disabled = false }: PickerProps) {
  const { key: setKey, num: setNum } = setFilters[index]
  const { t } = useTranslation("page_character")
  const artifactSheets = usePromise(ArtifactSheet.getAll, [])
  const artifactSets = useMemo(() => {
    if (!artifactSheets) return undefined
    return allArtifactSets.filter(set => {
      const setsNumArr = set ? Object.keys(artifactSheets[set].setEffects) : []
      const artsAccountedOther = setFilters.reduce((accu, cur, ind) => (cur.key && ind !== index) ? accu + cur.num : accu, 0)
      if (setsNumArr.every((num: any) => parseInt(num) + artsAccountedOther > 5)) return false
      return true
    })
  }, [artifactSheets, setFilters, index])

  if (!artifactSets) return null

  const artsAccounted = setFilters.reduce((accu, cur) => cur.key ? accu + cur.num : accu, 0)

  return <CardLight>
    <ButtonGroup sx={{ width: "100%" }}>
      {/* Artifact set */}
      {artifactSheets && <ArtifactSetSingleAutocomplete
        flattenCorners
        showDefault
        size="small"
        artSetKey={setKey}
        setArtSetKey={setKey => onChange(index, setKey as ArtifactSetKey, parseInt(Object.keys(artifactSheets[setKey]?.setEffects ?? {})[0] as string) ?? 0)}
        allArtSetKeys={artifactSets}
        label={t("forceSet")}
        disabled={disabled}
        sx={{ flexGrow: 1 }}
        disable={(setKey) => setFilters.some(setFilter => setFilter.key === setKey)}
        defaultText={t("none")}
      />}
      {/* set number */}
      <DropdownButton title={`${setNum}-set`}
        disabled={disabled || !setKey || artsAccounted >= 5}
        sx={{ borderRadius: 0 }}
      >
        {Object.keys(artifactSheets?.[setKey]?.setEffects ?? {}).map((num: any) => {
          let artsAccountedOther = setFilters.reduce((accu, cur) => (cur.key && cur.key !== setKey) ? accu + cur.num : accu, 0)
          return (parseInt(num) + artsAccountedOther <= 5) &&
            (<MenuItem key={num} onClick={() => onChange(index, setFilters[index].key, parseInt(num) ?? 0)} >
              {`${num}-set`}
            </MenuItem>)
        })}
      </DropdownButton>
    </ButtonGroup>
    {!!setKey && <Divider />}
    {!!setKey && <CardContent sx={{ display: "flex", flexDirection: "column", gap: 2 }}>
      {Object.keys(artifactSheets?.[setKey].setEffects ?? {}).map(setNKey => parseInt(setNKey as string) as SetNum).filter(setNkey => setNkey <= setNum).map(setNumKey =>
        <SetEffectDisplay key={setKey + setNumKey} setKey={setKey} setNumKey={setNumKey} />)}
    </CardContent>}
  </CardLight>
}
Example #19
Source File: InputUnitMenu.tsx    From console with GNU Affero General Public License v3.0 5 votes vote down vote up
InputUnitMenu = ({
  classes,
  id,
  unitSelected,
  unitsList,
  disabled = false,
  onUnitChange,
}: IInputUnitBox) => {
  const [anchorEl, setAnchorEl] = React.useState<null | HTMLElement>(null);
  const open = Boolean(anchorEl);
  const handleClick = (event: React.MouseEvent<HTMLElement>) => {
    setAnchorEl(event.currentTarget);
  };
  const handleClose = (newUnit: string) => {
    setAnchorEl(null);
    if (newUnit !== "" && onUnitChange) {
      onUnitChange(newUnit);
    }
  };

  return (
    <Fragment>
      <button
        id={`${id}-button`}
        aria-controls={`${id}-menu`}
        aria-haspopup="true"
        aria-expanded={open ? "true" : undefined}
        onClick={handleClick}
        className={classes.buttonTrigger}
        disabled={disabled}
        type={"button"}
      >
        {unitSelected}
      </button>
      <Menu
        id={`${id}-menu`}
        aria-labelledby={`${id}-button`}
        anchorEl={anchorEl}
        open={open}
        onClose={() => {
          handleClose("");
        }}
        anchorOrigin={{
          vertical: "bottom",
          horizontal: "center",
        }}
        transformOrigin={{
          vertical: "top",
          horizontal: "center",
        }}
      >
        {unitsList.map((unit) => (
          <MenuItem
            onClick={() => handleClose(unit.value)}
            key={`itemUnit-${unit.value}-${unit.label}`}
          >
            {unit.label}
          </MenuItem>
        ))}
      </Menu>
    </Fragment>
  );
}
Example #20
Source File: CreateApiNodeDialog.tsx    From mui-toolpad with MIT License 5 votes vote down vote up
export function ConnectionSelect({ dataSource, value, onChange }: ConnectionSelectProps) {
  const dom = useDom();

  const app = appDom.getApp(dom);
  const { connections = [] } = appDom.getChildNodes(dom, app);

  const filtered = React.useMemo(() => {
    return dataSource
      ? connections.filter((connection) => connection.attributes.dataSource.value === dataSource)
      : connections;
  }, [connections, dataSource]);

  const handleSelectionChange = React.useCallback(
    (event: React.ChangeEvent<HTMLInputElement>) => {
      onChange((event.target.value as NodeId) || null);
    },
    [onChange],
  );

  return (
    <TextField
      select
      fullWidth
      value={value || ''}
      label="Connection"
      onChange={handleSelectionChange}
    >
      {filtered.map((connection) => (
        <MenuItem key={connection.id} value={connection.id}>
          {connection.name} | {connection.attributes.dataSource.value}
        </MenuItem>
      ))}
    </TextField>
  );
}
Example #21
Source File: CampaignSelect.tsx    From frontend with MIT License 5 votes vote down vote up
export default function CampaignSelect({ label, name, campaigns, ...textFieldProps }: Props) {
  const { t } = useTranslation('transfer')

  const [field, meta] = useField(name)
  const { setFieldValue } = useFormikContext()

  const helperText = meta.touched ? translateError(meta.error as TranslatableField, t) : ''

  const handleChange = (event: React.ChangeEvent<{ value: unknown }>) => {
    setFieldValue(name, event.target.value)
  }

  return (
    <TextField
      {...textFieldProps}
      {...field}
      select
      variant="outlined"
      fullWidth
      onChange={handleChange}
      label={t(label)}
      error={Boolean(meta.error) && Boolean(meta.touched)}
      helperText={helperText}>
      {[{ id: '', title: '' }, ...(campaigns || [])].map((p) => {
        return (
          <MenuItem key={p.id} value={p.id}>
            {p.title}
          </MenuItem>
        )
      })}
    </TextField>
  )
}
Example #22
Source File: deploy-page.tsx    From example with MIT License 5 votes vote down vote up
export function DeployPage() {
	const connection = useContext(ConnectorContext)
	const form = useForm()
	const { handleSubmit } = form
	const { result, setComplete, setError } = useRequestResult()
	const blockchain = connection.sdk?.wallet?.blockchain

	return (
		<Page header="Deploy Collection">
			{
				!validateConditions(blockchain) && <CommentedBlock sx={{ my: 2 }}>
                    <UnsupportedBlockchainWarning blockchain={blockchain}/>
                </CommentedBlock>
			}
			<CommentedBlock sx={{ my: 2 }} comment={<CollectionDeployComment/>}>
				<form onSubmit={handleSubmit(async (formData) => {
					try {
						setComplete(await connection.sdk?.nft.deploy(getDeployRequest(formData)))
					} catch (e) {
						setError(e)
					}
				})}
				>
					<Stack spacing={2}>
						<FormSelect
							form={form}
							defaultValue={blockchain ?? Blockchain.ETHEREUM}
							name="blockchain"
							label="Blockchain"
						>
							<MenuItem value={Blockchain.ETHEREUM}>{Blockchain.ETHEREUM}</MenuItem>
							<MenuItem value={Blockchain.POLYGON}>{Blockchain.POLYGON}</MenuItem>
							<MenuItem value={Blockchain.TEZOS}>{Blockchain.TEZOS}</MenuItem>
							<MenuItem value={Blockchain.FLOW}>{Blockchain.FLOW}</MenuItem>
						</FormSelect>
						<FormTextInput form={form} name="name" label="Name"/>
						<FormTextInput form={form} name="symbol" label="Symbol"/>
						<FormTextInput form={form} name="baseURI" label="Base URI"/>
						<FormTextInput form={form} name="contractURI" label="Contract URI"/>
						<FormCheckbox form={form} name="private" label="Private Collection"/>
						<Box>
							<FormSubmit
								form={form}
								label="Deploy"
								state={resultToState(result.type)}
								disabled={!validateConditions(blockchain)}
							/>
						</Box>
					</Stack>
				</form>
			</CommentedBlock>

			<CommentedBlock sx={{ my: 2 }} comment={result.type === "complete" ? <CollectionResultComment/> : null}>
				<RequestResult
					result={result}
					completeRender={(data) =>
						<>
							<Box sx={{ my: 2 }}>
								<Typography variant="overline">Collection Address:</Typography>
								<div>
									<InlineCode>{data?.address}</InlineCode> <CopyToClipboard value={data?.address}/>
								</div>
							</Box>
							<Box sx={{ my: 2 }}>
								<TransactionInfo transaction={data?.tx}/>
							</Box>
						</>
					}
				/>
			</CommentedBlock>
		</Page>
	)
}
Example #23
Source File: deploy-page.tsx    From sdk with MIT License 5 votes vote down vote up
export function DeployPage() {
	const connection = useContext(ConnectorContext)
	const form = useForm()
	const { handleSubmit } = form
	const { result, setComplete, setError } = useRequestResult()
	const blockchain = connection.sdk?.wallet?.blockchain

	return (
		<Page header="Deploy Collection">
			{
				!validateConditions(blockchain) && (
					<CommentedBlock sx={{ my: 2 }}>
						<UnsupportedBlockchainWarning blockchain={blockchain}/>
					</CommentedBlock>
				)
			}
			<CommentedBlock sx={{ my: 2 }} comment={<CollectionDeployComment/>}>
				<form
					onSubmit={handleSubmit(async (formData) => {
						try {
							setComplete(await connection.sdk?.nft.deploy(getDeployRequest(formData)))
						} catch (e) {
							setError(e)
						}
					})}
				>
					<Stack spacing={2}>
						{
							blockchain &&
							<FormSelect
								form={form}
								defaultValue={blockchain}
								name="blockchain"
								label="Blockchain"
							>
								<MenuItem value={BlockchainGroup.ETHEREUM}>
									{Blockchain.ETHEREUM} / {Blockchain.POLYGON}
								</MenuItem>
								<MenuItem value={BlockchainGroup.TEZOS}>{BlockchainGroup.TEZOS}</MenuItem>
								<MenuItem value={Blockchain.SOLANA}>{Blockchain.SOLANA}</MenuItem>
								{ /*<MenuItem value={Blockchain.FLOW}>{Blockchain.FLOW}</MenuItem>*/ }
							</FormSelect>
						}
						<DeployForm form={form}/>
						<Box>
							<FormSubmit
								form={form}
								label="Deploy"
								state={resultToState(result.type)}
								disabled={!validateConditions(blockchain)}
							/>
						</Box>
					</Stack>
				</form>
			</CommentedBlock>

			<CommentedBlock sx={{ my: 2 }} comment={result.type === "complete" ? <CollectionResultComment/> : null}>
				<RequestResult
					result={result}
					completeRender={(data) =>
						<>
							<Box sx={{ my: 2 }}>
								<Typography variant="overline">Collection Address:</Typography>
								<div>
									<InlineCode>{data?.address}</InlineCode> <CopyToClipboard value={data?.address}/>
								</div>
							</Box>
							<Box sx={{ my: 2 }}>
								<TransactionInfo transaction={data?.tx}/>
							</Box>
						</>
					}
				/>
			</CommentedBlock>
		</Page>
	)
}
Example #24
Source File: AppNavbar.tsx    From sapio-studio with Mozilla Public License 2.0 5 votes vote down vote up
function NodeMenu(props: { bitcoin_node_manager: BitcoinNodeManager }) {
    const dispatch = useDispatch();
    const nodeRef = React.useRef<HTMLLIElement>(null);
    const [node_open, setNodeOpen] = React.useState(false);
    const close = () => setNodeOpen(false);

    return (
        <>
            <ListItem
                disableGutters
                button={false}
                key={'Bitcoin Node'}
                onClick={() => setNodeOpen(true)}
                ref={nodeRef}
            >
                <ListItemIcon></ListItemIcon>
                <ListItemText primary={'Bitcoin Node'} />
            </ListItem>
            <Menu
                anchorEl={nodeRef.current}
                anchorOrigin={{
                    vertical: 'center',
                    horizontal: 'right',
                }}
                keepMounted
                open={node_open}
                onClose={close}
            >
                <MenuItem
                    onClick={async () => {
                        close();
                        const addr =
                            await props.bitcoin_node_manager.get_new_address();
                        window.electron.write_clipboard(addr);
                    }}
                >
                    Get New Address to Clipboard
                </MenuItem>
                <MenuItem
                    onClick={() => {
                        close();
                        props.bitcoin_node_manager
                            .generate_blocks(10)
                            .catch((err) => console.error(err));
                    }}
                >
                    Generate 10 Blocks
                </MenuItem>
                <Divider />
                <MenuItem
                    onClick={() => {
                        close();
                        dispatch(toggle_status_bar());
                    }}
                >
                    Toggle Status
                </MenuItem>
            </Menu>
        </>
    );
}
Example #25
Source File: WalletMultiButton.tsx    From wallet-adapter with Apache License 2.0 5 votes vote down vote up
WalletActionMenuItem = styled(MenuItem)(({ theme }: { theme: Theme }) => ({
    padding: theme.spacing(1, 2),
    boxShadow: 'inset 0 1px 0 0 ' + 'rgba(255, 255, 255, 0.1)',

    '&:hover': {
        boxShadow: 'inset 0 1px 0 0 ' + 'rgba(255, 255, 255, 0.1)' + ', 0 1px 0 0 ' + 'rgba(255, 255, 255, 0.05)',
    },
}))
Example #26
Source File: CollectionRowActions.tsx    From firecms with MIT License 4 votes vote down vote up
/**
 *
 * @param entity
 * @param isSelected
 * @param selectionEnabled
 * @param size
 * @param toggleEntitySelection
 * @param onCopyClicked
 * @param onEditClicked
 * @param onDeleteClicked
 * @constructor
 *
 * @category Collection components
 */
export function CollectionRowActions<M extends { [Key: string]: any }>({
                                                                           entity,
                                                                           isSelected,
                                                                           selectionEnabled,
                                                                           size,
                                                                           toggleEntitySelection,
                                                                           onCopyClicked,
                                                                           onEditClicked,
                                                                           onDeleteClicked
                                                                       }:
                                                                           {
                                                                               entity: Entity<M>,
                                                                               size: CollectionSize,
                                                                               isSelected?: boolean,
                                                                               selectionEnabled?: boolean,
                                                                               toggleEntitySelection?: (selectedEntity: Entity<M>) => void
                                                                               onEditClicked?: (selectedEntity: Entity<M>) => void,
                                                                               onCopyClicked?: (selectedEntity: Entity<M>) => void,
                                                                               onDeleteClicked?: (selectedEntity: Entity<M>) => void,
                                                                           }) {

    const editEnabled = Boolean(onEditClicked);
    const copyEnabled = Boolean(onCopyClicked);
    const deleteEnabled = Boolean(onDeleteClicked);

    const classes = useTableStyles();

    const [anchorEl, setAnchorEl] = React.useState<any | null>(null);

    const openMenu = useCallback((event: React.MouseEvent) => {
        setAnchorEl(event.currentTarget);
        event.stopPropagation();
    }, [setAnchorEl]);

    const closeMenu = useCallback(() => {
        setAnchorEl(null);
    }, [setAnchorEl]);

    const onCheckboxChange = (event: React.ChangeEvent) => {
        if (toggleEntitySelection)
            toggleEntitySelection(entity);
        event.stopPropagation();
    };

    const onDeleteClick = useCallback((event: MouseEvent) => {
        event.stopPropagation();
        if (onDeleteClicked)
            onDeleteClicked(entity);
        setAnchorEl(null);
    }, [entity, onDeleteClicked, setAnchorEl]);

    const onCopyClick = useCallback((event: MouseEvent) => {
        event.stopPropagation();
        if (onCopyClicked)
            onCopyClicked(entity);
        setAnchorEl(null);
    }, [entity, onCopyClicked, setAnchorEl]);

    return (
        <div className={classes.cellButtonsWrap}>

            {(editEnabled || deleteEnabled || selectionEnabled) &&
            <div className={classes.cellButtons}
            >
                {editEnabled &&
                <Tooltip title={`Edit ${entity.id}`}>
                    <IconButton
                        onClick={(event: MouseEvent) => {
                            event.stopPropagation();
                            if (onEditClicked)
                                onEditClicked(entity);
                        }}
                        size="large">
                        <KeyboardTab/>
                    </IconButton>
                </Tooltip>
                }

                {selectionEnabled &&
                <Tooltip title={`Select ${entity.id}`}>
                    <Checkbox
                        checked={isSelected}
                        onChange={onCheckboxChange}
                    />
                </Tooltip>}

                {(copyEnabled || deleteEnabled) &&
                <IconButton onClick={openMenu} size="large">
                    <MoreVert/>
                </IconButton>
                }

                {(copyEnabled || deleteEnabled) && <Menu
                    anchorEl={anchorEl}
                    open={Boolean(anchorEl)}
                    onClose={closeMenu}
                    elevation={2}
                >
                    {deleteEnabled && <MenuItem onClick={onDeleteClick}>
                        <ListItemIcon>
                            <Delete/>
                        </ListItemIcon>
                        <ListItemText primary={"Delete"}/>
                    </MenuItem>}

                    {copyEnabled && <MenuItem onClick={onCopyClick}>
                        <ListItemIcon>
                            <FileCopy/>
                        </ListItemIcon>
                        <ListItemText primary="Copy"/>
                    </MenuItem>}

                </Menu>}


            </div>}

            {size !== "xs" && (
                <div className={classes.cellButtonsId}>

                    {entity
                        ? <Typography
                            className={"mono"}
                            variant={"caption"}
                            color={"textSecondary"}> {entity.id} </Typography>
                        : <Skeleton variant="text"/>
                    }
                </div>
            )}

        </div>
    );

}
Example #27
Source File: MenuItem.tsx    From Cromwell with MIT License 4 votes vote down vote up
Item = (props: {
    data: TMainMenuItem;
    itemProps?: {
        items: TMainMenuItem[];
        canReorder: boolean;
        refreshList: () => void;
    }
}) => {
    const { refreshList, items, canReorder } = props.itemProps ?? {};
    const item = props.data;

    const forceUpdate = useForceUpdate();
    const classes = useStyles();
    const [_expanded, setExpanded] = React.useState(false);
    const expanded = _expanded && !canReorder;

    if (!item) return null;

    const handleExpandClick = () => {
        if (canReorder) return;
        setExpanded(!_expanded);
    };

    const handleChange = (prop: keyof TMainMenuItem, val: string) => {
        (item as any)[prop] = val;
        forceUpdate();
    }

    const handleRemove = (event) => {
        event.stopPropagation();
        if (items) {
            items.splice(items.indexOf(item), 1);
            refreshList?.();
        }
    }

    return (
        <div className={`${classes.card} PluginMainMenu-paper`}>
            <CardActionArea
                className={classes.cardHeader}
                onClick={handleExpandClick}
            >
                <p className={classes.cardTitle}>{item.title}</p>
                <CardActions disableSpacing className={classes.cardActions}>
                    {!canReorder && (
                        <IconButton
                            className={clsx(classes.expand, {
                                [classes.expandOpen]: expanded,
                            })}
                            aria-expanded={expanded}
                            aria-label="show more"
                        >
                            <ExpandMoreIcon />
                        </IconButton>
                    )}
                    <IconButton onClick={handleRemove}>
                        <HighlightOffIcon />
                    </IconButton>
                </CardActions>
            </CardActionArea>
            <Collapse in={expanded} timeout="auto" unmountOnExit>
                <div className={classes.cardContent}>
                    <TextField label="Title" variant="outlined"
                        value={item.title}
                        className={classes.field}
                        onChange={(e) => { handleChange('title', e.target.value) }}
                    />
                    <TextField label="Link" variant="outlined"
                        value={item.href}
                        className={classes.field}
                        onChange={(e) => { handleChange('href', e.target.value) }}
                    />
                    <TextField label="Columns" variant="outlined"
                        value={item.sublinkCols}
                        className={classes.field}
                        onChange={(e) => { handleChange('sublinkCols', e.target.value) }}
                    />
                    <TextField label="Width in px" variant="outlined"
                        value={item.width}
                        className={classes.field}
                        onChange={(e) => { handleChange('width', e.target.value) }}
                    />
                    <TextField
                        value={item.html}
                        label="Custom HTML"
                        multiline
                        rows={4}
                        variant="outlined"
                        className={classes.field}
                        onChange={(e) => { handleChange('html', e.target.value) }}
                    />
                    <div className={classes.sublinksList}>
                        <h3 className={classes.sublinksTitle}>Sublinks</h3>
                        {item.sublinks && item.sublinks.map((sl, slIndex) => {
                            return (
                                <div className={`${classes.sublinkItem} PluginMainMenu-paper`} >
                                    <TextField label="Sublink title" variant="outlined"
                                        value={sl.title}
                                        className={classes.subField}
                                        onChange={(e) => { if (item.sublinks) item.sublinks[slIndex].title = e.target.value; forceUpdate(); }}
                                    />
                                    <TextField label="Sublink href" variant="outlined"
                                        value={sl.href}
                                        className={classes.subField}
                                        onChange={(e) => { if (item.sublinks) item.sublinks[slIndex].href = e.target.value; forceUpdate(); }}
                                    />
                                    <IconButton onClick={(e) => {
                                        e.stopPropagation();
                                        if (item.sublinks) item.sublinks.splice(slIndex, 1);
                                        refreshList?.();
                                    }}>
                                        <HighlightOffIcon />
                                    </IconButton>
                                </div>
                            )
                        })}
                        <div className={`PluginMainMenu-paper ${classes.card}`}>
                            <MenuItem
                                className={classes.addBtn}
                                onClick={() => {
                                    if (!item.sublinks) item.sublinks = [];
                                    item.sublinks.push({});
                                    forceUpdate();
                                }}>
                                <AddIcon />
                            </MenuItem>
                        </div>
                    </div>
                </div>
            </Collapse>
        </div>
    )
}
Example #28
Source File: Language.tsx    From GTAV-NativeDB with MIT License 4 votes vote down vote up
export function CodeGenOptionComponent<TSettings>(props:CodeGenOptionComponentProps<TSettings>) {
  const { type, label, prop, value, onChange } = props

  switch (type) {
    case 'boolean':
      return (
        <FormControlLabel
          control={
            <Checkbox
              name={prop}
              checked={value}
              onChange={onChange}
            />
          }
          sx={{ userSelect: 'none' }}
          label={label}
        />
      )
    case 'combo':
      const options = props.options
      return (
        <FormControl fullWidth>
          <InputLabel id={`${prop}-label`}>{label}</InputLabel>
          <Select
            id={`${prop}-select`}
            labelId={`${prop}-label`}
            name={prop}
            value={value}
            onChange={onChange}
            label={label}
          >
            {options.map(({ label, value }) => (
              <MenuItem key={value} value={value}>
                {label}
              </MenuItem>
            ))}
          </Select>
        </FormControl>
      )
    case 'string':
      return (
        <TextField
          label={label}
          name={prop}
          onChange={(onChange as unknown as ChangeEventHandler<HTMLInputElement | HTMLTextAreaElement>)}
          value={value}
        />
      )
  }
}
Example #29
Source File: Layout.tsx    From abrechnung with GNU Affero General Public License v3.0 4 votes vote down vote up
export default function Layout({ group = null, children, ...props }) {
    const authenticated = useRecoilValue(isAuthenticated);
    const [anchorEl, setAnchorEl] = useState(null);
    const theme: Theme = useTheme();
    const dotsMenuOpen = Boolean(anchorEl);
    const cfg = useRecoilValue(config);
    const location = useLocation();

    const [mobileOpen, setMobileOpen] = useState(true);

    const { window } = props;

    const handleProfileMenuOpen = (event) => {
        setAnchorEl(event.currentTarget);
    };

    const handleDotsMenuClose = (event) => {
        setAnchorEl(null);
    };

    const handleDrawerToggle = () => {
        setMobileOpen(!mobileOpen);
    };

    const drawer = (
        <div style={{ height: "100%" }}>
            <Toolbar />
            <Divider />
            {group != null && (
                <List sx={{ pb: 0 }}>
                    <ListItemLink
                        to={`/groups/${group.id}/`}
                        selected={
                            location.pathname === `/groups/${group.id}/` || location.pathname === `/groups/${group.id}`
                        }
                    >
                        <ListItemIcon>
                            <Paid />
                        </ListItemIcon>
                        <ListItemText primary="Transactions" />
                    </ListItemLink>
                    <ListItemLink
                        to={`/groups/${group.id}/balances`}
                        selected={location.pathname.startsWith(`/groups/${group.id}/balances`)}
                    >
                        <ListItemIcon>
                            <BarChart />
                        </ListItemIcon>
                        <ListItemText primary="Balances" />
                    </ListItemLink>
                    <ListItemLink
                        to={`/groups/${group.id}/accounts`}
                        selected={location.pathname.startsWith(`/groups/${group.id}/accounts`)}
                    >
                        <ListItemIcon>
                            <AccountBalance />
                        </ListItemIcon>
                        <ListItemText primary="Accounts" />
                    </ListItemLink>
                    <ListItemLink
                        to={`/groups/${group.id}/detail`}
                        selected={location.pathname.startsWith(`/groups/${group.id}/detail`)}
                    >
                        <ListItemIcon>
                            <AdminPanelSettings />
                        </ListItemIcon>
                        <ListItemText primary="Group Settings" />
                    </ListItemLink>
                    <ListItemLink
                        to={`/groups/${group.id}/members`}
                        selected={location.pathname.startsWith(`/groups/${group.id}/members`)}
                    >
                        <ListItemIcon>
                            <People />
                        </ListItemIcon>
                        <ListItemText primary="Group Members" />
                    </ListItemLink>
                    <ListItemLink
                        to={`/groups/${group.id}/invites`}
                        selected={location.pathname.startsWith(`/groups/${group.id}/invites`)}
                    >
                        <ListItemIcon>
                            <Mail />
                        </ListItemIcon>
                        <ListItemText primary="Group Invites" />
                    </ListItemLink>
                    <ListItemLink
                        to={`/groups/${group.id}/log`}
                        selected={location.pathname.startsWith(`/groups/${group.id}/log`)}
                    >
                        <ListItemIcon>
                            <Message />
                        </ListItemIcon>
                        <ListItemText primary="Group Log" />
                    </ListItemLink>
                    <Divider />
                </List>
            )}
            <SidebarGroupList group={group} />

            <Box
                sx={{
                    display: "flex",
                    position: "absolute",
                    width: "100%",
                    justifyContent: "center",
                    bottom: 0,
                    padding: 1,
                    borderTop: 1,
                    borderColor: theme.palette.divider,
                }}
            >
                {cfg.imprintURL && (
                    <Link href={cfg.imprintURL} target="_blank" sx={{ mr: 2 }}>
                        imprint
                    </Link>
                )}
                <Tooltip title="Source Code">
                    <Link sx={{ ml: 1 }} target="_blank" href={cfg.sourceCodeURL}>
                        <GitHub />
                    </Link>
                </Tooltip>
                {cfg.issueTrackerURL && (
                    <Tooltip title="Bug reports">
                        <Link sx={{ ml: 1 }} target="_blank" href={cfg.issueTrackerURL}>
                            <BugReport />
                        </Link>
                    </Tooltip>
                )}
            </Box>
        </div>
    );

    const container = window !== undefined ? () => window().document.body : undefined;

    return (
        <Box sx={{ display: "flex" }}>
            <CssBaseline />
            <AppBar
                position="fixed"
                sx={{
                    // width: {sm: `calc(100% - ${drawerWidth}px)`},
                    // ml: {sm: `${drawerWidth}px`},
                    zIndex: (theme) => theme.zIndex.drawer + 1,
                }}
            >
                <Toolbar>
                    <IconButton
                        color="inherit"
                        aria-label="open drawer"
                        onClick={handleDrawerToggle}
                        edge="start"
                        sx={{ mr: 2, display: { sm: "none" } }}
                    >
                        <MenuIcon />
                    </IconButton>
                    <Typography variant="h6" component="div" sx={{ flexGrow: 1 }}>
                        Abrechnung
                    </Typography>
                    {authenticated ? (
                        <div>
                            <IconButton
                                aria-label="account of current user"
                                aria-controls="menu-appbar"
                                aria-haspopup="true"
                                onClick={handleProfileMenuOpen}
                                color="inherit"
                            >
                                <AccountCircleIcon />
                            </IconButton>
                            <Menu
                                id="menu-appbar"
                                open={dotsMenuOpen}
                                anchorOrigin={{
                                    vertical: "top",
                                    horizontal: "right",
                                }}
                                keepMounted
                                anchorEl={anchorEl}
                                transformOrigin={{
                                    vertical: "top",
                                    horizontal: "right",
                                }}
                                onClose={handleDotsMenuClose}
                            >
                                <MenuItem component={RouterLink} to="/profile">
                                    Profile
                                </MenuItem>
                                <MenuItem component={RouterLink} to="/profile/settings">
                                    Settings
                                </MenuItem>
                                <MenuItem component={RouterLink} to="/profile/sessions">
                                    Sessions
                                </MenuItem>
                                <MenuItem component={RouterLink} to="/profile/change-email">
                                    Change E-Mail
                                </MenuItem>
                                <MenuItem component={RouterLink} to="/profile/change-password">
                                    Change Password
                                </MenuItem>
                                <Divider />
                                <MenuItem component={RouterLink} to="/logout">
                                    <ListItemIcon>
                                        <Logout fontSize="small" />
                                    </ListItemIcon>
                                    <ListItemText>Sign out</ListItemText>
                                </MenuItem>
                            </Menu>
                        </div>
                    ) : (
                        <Button component={RouterLink} color="inherit" to="/login">
                            Login
                        </Button>
                    )}
                </Toolbar>
            </AppBar>

            {authenticated ? (
                <Box component="nav" sx={{ width: { sm: drawerWidth }, flexShrink: { sm: 0 } }}>
                    <Drawer
                        container={container}
                        variant="temporary"
                        open={mobileOpen}
                        onClose={handleDrawerToggle}
                        ModalProps={{
                            keepMounted: true, // Better open performance on mobile.
                        }}
                        sx={{
                            display: { xs: "block", sm: "none" },
                            "& .MuiDrawer-paper": {
                                boxSizing: "border-box",
                                width: drawerWidth,
                            },
                        }}
                    >
                        {drawer}
                    </Drawer>
                    <Drawer
                        variant="permanent"
                        sx={{
                            flexShrink: 0,
                            display: { xs: "none", sm: "block" },
                            "& .MuiDrawer-paper": {
                                boxSizing: "border-box",
                                width: drawerWidth,
                            },
                        }}
                        open
                    >
                        {drawer}
                    </Drawer>
                </Box>
            ) : null}
            <Box
                component="main"
                sx={{
                    flexGrow: 1,
                    width: { sm: `calc(100% - ${drawerWidth}px)` },
                }}
            >
                <Toolbar />
                <Banner />
                <Container maxWidth="lg" sx={{ padding: { xs: 0, md: 1, lg: 3 } }}>
                    {children}
                </Container>
            </Box>
        </Box>
    );
}