Elroy Toscano
Elroy Toscano

Reputation: 541

Material-UI Swipeable Drawer Does not translate smoothly


import { ThemeProvider } from '@material-ui/core/styles'

import React, { useState } from 'react'
import { Link } from 'react-router-dom'

import AppBar from '@material-ui/core/AppBar'
import Toolbar from '@material-ui/core/Toolbar'
import Tabs from '@material-ui/core/Tabs'
import Tab from '@material-ui/core/Tab'
import IconButton from '@material-ui/core/IconButton'
import MenuIcon from '@material-ui/icons/Menu'
import SwipeableDrawer from '@material-ui/core/SwipeableDrawer'
import { useMediaQuery, makeStyles } from '@material-ui/core'
import { useTheme } from '@material-ui/core/styles'
import { ListItem, ListItemText } from '@material-ui/core'

import logo from './logo.png'

const linksData = [
  {
    id: 1,
    name: 'home',
    path: '/',
  },
  {
    id: 2,
    name: 'portfolio',
    path: '/portfolio',
  },
  {
    id: 3,
    name: 'services',
    path: '/services',
  },
  {
    id: 4,
    name: 'about',
    path: '/about',
  },
]

const useStyles = makeStyles((theme) => ({
  root: {
    flexGrow: '1',
  },
  contentItems: {
    width: '100%',
    height: '100%',
    display: 'flex',
    justifyContent: 'space-between',
    alignItems: 'center',
    padding: '0.5rem',
  },
  logo: {
    width: '100%',
    height: '4rem',
    objectFit: 'cover',
  },
  logoContainer: {
    flexBasis: '1',
    display: 'flex',
    alignItems: 'center',
  },
  linksContainer: {
    flexBasis: '3',
  },
  link: {
    textDecoration: 'none',
    minWidth: 10,
  },
}))

function App() {
  const theme = useTheme()
  const webView = useMediaQuery(theme.breakpoints.down('md'))

  const classes = useStyles()

  const [value, setValue] = useState(1)
  const [openDrawer, setOpenDrawer] = useState(false)

  const handleChange = (e, value) => setValue(value)

  const iOS = process.browser && /iPad|iPhone|iPod/.test(navigator.userAgent)

  return (
    <>
      <Router>
        <ThemeProvider theme={theme}>
          <Switch>
            <Route path='/'>
              <div className={classes.root}>
                <AppBar>
                  <Toolbar>
                    <nav className={classes.contentItems}>
                      <div className={classes.logoContainer}>
                        <img src={logo} alt='logo' className={classes.logo} />
                      </div>
                      <Tabs value={value} onChange={handleChange}>
                        {linksData.map(({ path, name, id }) => {
                          console.log(path)
                          return (
                            <Tab
                              key={id}
                              value={id}
                              component={Link}
                              to={path.toString()}
                              className={classes.link}
                              label={name}
                            ></Tab>
                          )
                        })}
                      </Tabs>
                      {webView && (
                        <IconButton onClick={() => setOpenDrawer(true)}>
                          <MenuIcon />
                        </IconButton>
                      )}
                      {openDrawer && (
                        <SwipeableDrawer
                          disableBackdropTransition={!iOS}
                          disableDiscovery={iOS}
                          open={openDrawer}
                          onOpen={() => setOpenDrawer(true)}
                          onClose={() => setOpenDrawer(false)}
                        >
                          <ListItem>
                            <ListItemText>hello</ListItemText>
                            <br />
                            <ListItemText>hello</ListItemText>
                          </ListItem>
                        </SwipeableDrawer>
                      )}
                    </nav>
                  </Toolbar>
                </AppBar>
              </div>
            </Route>
          </Switch>
        </ThemeProvider>
      </Router>
    </>
  )
}

export default App

I'm trying to implement a Swipeable Drawer, the drawer is visible, the fade out transition is smooth as well, however, the drawer does not translate smoothly, The drawer slides in and out without any transition style applied to it( which should be applied). One interesting case is that in case the "openDrawer" state is set to 'true', during initialization, the drawer translates smoothly, but beyond that, the transitions of the drawer are not smooth.

Here's a CodeSandBox link: https://codesandbox.io/s/xenodochial-ritchie-owen9

Upvotes: 3

Views: 1680

Answers (1)

Drew Reese
Drew Reese

Reputation: 202605

At first when I ran your sandbox and from what I can see it's running fine... I don't notice any jankiness when toggling the sidebar open/close.

BUT

As I was suspecting with the conditional rendering, when I took it out the sidebar transition is butter smooth and not nearly so "instant".

{openDrawer && (
  <SwipeableDrawer
    disableBackdropTransition={!iOS}
    disableDiscovery={iOS}
    open={openDrawer}
    onOpen={() => setOpenDrawer(true)}
    onClose={() => setOpenDrawer(false)}
  >
    <ListItem>
      <ListItemText>hello</ListItemText>
      <br />
      <ListItemText>hello</ListItemText>
    </ListItem>
  </SwipeableDrawer>
)}

Remove the conditional rendering.

<SwipeableDrawer
  disableBackdropTransition={!iOS}
  disableDiscovery={iOS}
  open={openDrawer}
  onOpen={() => setOpenDrawer(true)}
  onClose={() => setOpenDrawer(false)}
>
  <ListItem>
    <ListItemText>hello</ListItemText>
    <br />
    <ListItemText>hello</ListItemText>
  </ListItem>
</SwipeableDrawer>

Edit material-ui-swipeable-drawer-does-not-translate-smoothly

Upvotes: 3

Related Questions