Search code examples
reactjstypescriptdatetimepickermui-x-date-picker

muix-datepicker Customization: Labeling Hours and Minutes Selection


I am using this muix-datepicker and I want to add a label on the hours and minutes column. Unfortunately, the API doesn't provide this functionality.

Need help.

enter image description here


Solution

  • Unless you are willing to create your own multiSectionDigitalClock menu items, the closest you can get is to customize the PickersLayout to add an additional grid row for the labels.

    However, the problem with this approach is that you won't be able to align these labels with the multiSectionDigitalClock without some hard-coded width for its columns, as the calendar and the clock are wrapped together as a single grid cell. Here, I use width=3.5rem for each column.

    Optionally, you could add some negative top margin to the ContentWrapper and add a background (perhaps inherit) and z-index on the labels to hide the numbers that scrolls over it.

    Sandbox Demo

    const CHILD_WIDTH = "3.5rem";
    
    function MyCustomLayout(props) {
      const { toolbar, tabs, content, actionBar } = usePickerLayout(props);
      return (
        <PickersLayoutRoot className={pickersLayoutClasses.root} ownerState={props}>
          {toolbar}
          <Box
            sx={{
              gridColumn: 2,
              display: props.wrapperVariant === "desktop" ? "flex" : "none",
              justifyContent: "end",
              textAlign: "center"
            }}
          >
            <Typography sx={{ width: CHILD_WIDTH }}>Hour</Typography>
            <Typography sx={{ width: CHILD_WIDTH }}>Min</Typography>
            <Typography sx={{ width: CHILD_WIDTH }}></Typography>
          </Box>
          <PickersLayoutContentWrapper
            sx={{
              ".MuiMultiSectionDigitalClock-root": {
                ul: {
                  width: CHILD_WIDTH,
                  boxSizing: "border-box"
                }
              }
            }}
          >
            {tabs}
            {content}
          </PickersLayoutContentWrapper>
          {actionBar}
        </PickersLayoutRoot>
      );
    }
    
    <LocalizationProvider dateAdapter={AdapterDayjs}>
      <DateTimePicker label="Basic date time picker"
        slots={{
          layout: MyCustomLayout
        }}
      />
    </LocalizationProvider>