How to center the search component in MUI AppBar? - reactjs

I've been struggling to center the search component in the AppBar of Material-UI. I wanted the search bar to remain in the center. Using this code from their website. I've played around margins and justify, but I can't seem to get the correct way of doing it and remain responsive.
const Search = styled('div')(({ theme }) => ({
position: 'relative',
borderRadius: theme.shape.borderRadius,
backgroundColor: alpha(theme.palette.common.white, 0.15),
'&:hover': {
backgroundColor: alpha(theme.palette.common.white, 0.25),
},
marginLeft: 0,
width: '100%',
[theme.breakpoints.up('sm')]: {
marginLeft: theme.spacing(1),
width: 'auto',
},
}));
const SearchIconWrapper = styled('div')(({ theme }) => ({
padding: theme.spacing(0, 2),
height: '100%',
position: 'absolute',
pointerEvents: 'none',
display: 'flex',
alignItems: 'center',
justifyContent: 'center',
}));
const StyledInputBase = styled(InputBase)(({ theme }) => ({
color: 'inherit',
'& .MuiInputBase-input': {
padding: theme.spacing(1, 1, 1, 0),
// vertical padding + font size from searchIcon
paddingLeft: `calc(1em + ${theme.spacing(4)})`,
transition: theme.transitions.create('width'),
width: '100%',
[theme.breakpoints.up('sm')]: {
width: '12ch',
'&:focus': {
width: '20ch',
},
},
},
}));
export default function SearchAppBar() {
return (
<Box sx={{ flexGrow: 1 }}>
<AppBar position="static">
<Toolbar>
<IconButton
size="large"
edge="start"
color="inherit"
aria-label="open drawer"
sx={{ mr: 2 }}
>
<MenuIcon />
</IconButton>
<Typography
variant="h6"
noWrap
component="div"
sx={{ flexGrow: 1, display: { xs: 'none', sm: 'block' } }}
>
MUI
</Typography>
<Search>
<SearchIconWrapper>
<SearchIcon />
</SearchIconWrapper>
<StyledInputBase
placeholder="Search…"
inputProps={{ 'aria-label': 'search' }}
/>
</Search>
</Toolbar>
</AppBar>
</Box>
);
}
How do I achieve something likes this?

Because Toolbar is a flex container, if you set its justify-content to space-between the element in the middle will be centered.
<AppBar position="static">
<Toolbar
sx={{
justifyContent: "space-between"
}}
>
{/* group IconButton and Typography in an element so there are */}
{/* only 3 children in the flex container */}
<Stack direction="row" alignItems="center">
<IconButton {...} />
<Typography {...} />
</Stack>
<Search {...} />
<IconButton {...} />
</Toolbar>
</AppBar>
Live Demo

Related

Specifying class for properties and styles for components and tags in React

I am pretty new to React. I was actually building an AppBar with a logo at center based on a suggestion in this post
<Box sx={{ display: "flex", alignItems: "center", flex: "1" }}>
<IconButton
color="inherit"
aria-label="open drawer"
onClick={onDrawerOpen}
edge="start"
sx={{ mr: 2, ...(open && { display: "none" }) }}
>
<MenuIcon />
</IconButton>
<Typography variant="h6" noWrap component="div">
TITLE
</Typography>
</Box>
But is there is any best way of specifying a single class or constant for these settings outside the definition like this
<IconButton class='settings'>
instead of all this
Tried the way #Dimitriy suggested and below my code
export default function AppBar({ open, onDrawerOpen }:any) {
const theme = useTheme();
const iconButtonOptions = {
color: "inherit",
ariaLabel: "open drawer",
onClick: onDrawerOpen,
edge: "start",
sx: {{ mr: 2, ...(open && { display: "none" }) }}
}
return (
<AppBar position="fixed" style={{ background: "#002a5e" }} open={open}>
<Toolbar>
<Box sx={{ display: "flex",flexDirection:"row", alignItems: "center", flex: "1" }}>
<IconButton {...iconButtonOptions} >
<MenuIcon />
</IconButton>
<Typography variant="h6" noWrap component="div">
TITLE
</Typography>
</Box>
<Box
component="img"
sx={{
height: 32,
}}
alt="MyLogo"
src={logo}
/>
<Box sx={{ flex: "1" }}></Box>
</Toolbar>
</AppBar>
);
}
But its saying
Cannot redeclare block-scoped variable '(Missing)'.ts(2451)
Yes, there's actually is the way for that.
First, you can make a new object variable that will hold all of your props.
Example:
const iconBtnProps = {
color: 'inherit',
aria-label: 'open drawer',
onClick: onDrawerOpen,
edge: 'start',
sx: { mr: 2, ...(open && { display: "none" }) }
};
// render the <IconButton /> component and spread the object
<IconButton {...iconBtnProps} />
I would advise you to check styled-components. It would really make things easier for styling components.
You can't define jsx component props through classes. But if you want to make your jsx more understandable, or avoid repetition, you can move all the props into an object.
const iconButtonOptions = {
color: "inherit",
ariaLabel: "open drawer",
onClick: onDrawerOpen,
edge: "start",
sx: { mr: 2, ...(open && { display: "none" }) }
}
return (
<IconButton {...iconButtonOptions}>
<MenuIcon />
</IconButton>
)

how to make 3 mui textfields under single border in react js

I want to add dimensions box. i created 3 mui textfields under formGroup and make border radius:0 and changed colour properties still it didn't work.
This what i want
I want to make 3 input fields in single border roof with attached autoComplete at the end. autoComplete want to look same as Mui textfield's width and height.
To remove the border of an input you should change it's border-width.
And for the cross signs you can use MUI icons.
So you will have a Box with flex display, that has 3 TextFields, 2 Icons and 1 Autocomplete inside.
This will be your final code:
import { TextField, Autocomplete, Box } from "#mui/material";
import CloseIcon from "#mui/icons-material/Close";
function Test() {
return (
<Box
sx={{
display: "flex",
justifyContent: "center",
alignItems: "center",
width: "240px",
border: "1px solid grey",
direction: "ltr",
}}
>
<TextField
size="small"
sx={{ width: "50px", "& fieldset": { borderWidth: 0 } }}
/>
<CloseIcon sx={{ fontSize: "10px" }} />
<TextField
size="small"
sx={{ width: "50px", "& fieldset": { borderWidth: 0 } }}
/>
<CloseIcon sx={{ fontSize: "10px" }} />
<TextField
size="small"
sx={{ width: "50px", "& fieldset": { borderWidth: 0 } }}
/>
<Autocomplete
disableClearable
size="small"
options={["cm", "inch"]}
renderInput={(params) => (
<TextField
{...params}
sx={{
backgroundColor: "#f5f5f5",
"& fieldset": { borderRadius: 0 },
}}
/>
)}
sx={{ width: "70px" }}
/>
</Box>
);
}
export default Test;

Material Ui Appbar Customization

I want to customize the Appbar for mobile devices but I don't know why I cant't. Somebody,please help me to do that.
here is the appbar for mobile devices. I want to change the background and width:
I have shared my full code here with inline styles. By the way I am using material using version 5.
import React from 'react';
import {
Button,
Menu,
MenuItem,
AppBar,
Box,
Toolbar,
IconButton,
Typography,
Container,
Fade,
} from '#mui/material';
import MenuIcon from '#mui/icons-material/Menu';
import Link from 'next/link';
import logo from '../../assets/main_logo.png';
import Image from 'next/image';
const Navbar = () = > {
const[anchorElNav, setAnchorElNav] = React.useState(null);
const handleOpenNavMenu = (event) = > {
setAnchorElNav(event.currentTarget);
};
const handleCloseNavMenu = () = > {
setAnchorElNav(null);
};
const[anchorEl, setAnchorEl] = React.useState(null);
const open = Boolean(anchorEl);
const handleClick = (event) = > {
setAnchorEl(event.currentTarget);
};
const handleClose = () = > {
setAnchorEl(null);
};
return ( < AppBar position = 'sticky'
sx = {
{
backgroundColor: '#000000',
opacity: '0.9'
}
} >
<Container maxWidth='xl'>
<Toolbar disableGutters>
<Typography
variant='h6'
noWrap
component='a'
href='/'
sx={{
mr: 2,
display: { xs: 'none', md: 'flex' },
fontFamily: 'monospace',
fontWeight: 700,
letterSpacing: '.3rem',
color: 'inherit',
textDecoration: 'none',
}}
>
<Image src={logo} alt='site_logo' height={40} width={210} />
</Typography>
<Box
sx={{
flexGrow: 1,
display: { xs: 'flex', md: 'none' },
}}
>
<IconButton
size='large'
aria-label='account of current user'
aria-controls='menu-appbar'
aria-haspopup='true'
onClick={handleOpenNavMenu}
color='primary'
>
<MenuIcon />
</IconButton>
<Menu
id='menu-appbar'
anchorEl={anchorElNav}
anchorOrigin={{
vertical: 'bottom',
horizontal: 'left',
}}
keepMounted
transformOrigin={{
vertical: 'top',
horizontal: 'left',
}}
open={Boolean(anchorElNav)}
onClose={handleCloseNavMenu}
>
<MenuItem onClick={handleCloseNavMenu}>
<Typography textAlign='center'>Home</Typography>
</MenuItem>
<Typography
onClick={handleClick}
onMouseEnter={handleClick}
onMouseLeave={handleClick}
textAlign='center'
>
Services
</Typography>
<MenuItem onClick={handleCloseNavMenu}>
<Typography textAlign='center'>Projects</Typography>
</MenuItem>
<MenuItem onClick={handleCloseNavMenu}>
<Typography textAlign='center'>Blog</Typography>
</MenuItem>
<MenuItem onClick={handleCloseNavMenu}>
<Typography textAlign='center'>Career</Typography>
</MenuItem>
<MenuItem onClick={handleCloseNavMenu}>
<Typography textAlign='center'>About</Typography>
</MenuItem>
</Menu>
</Box>
<Typography
variant='h5'
noWrap
component='a'
href='/'
sx={{
mr: 2,
display: { xs: 'flex', md: 'none' },
flexGrow: 1,
fontFamily: 'monospace',
fontWeight: 700,
letterSpacing: '.3rem',
color: 'inherit',
textDecoration: 'none',
}}
>
<Image src={logo} alt='site_logo' height={40} width={200} />
</Typography>
<Box
sx={{
flexGrow: 1,
display: { xs: 'none', md: 'flex' },
margin: '0 2rem',
}}
>
<Button
onClick={handleCloseNavMenu}
sx={{
my: 2,
color: 'white',
display: 'block',
textTransform: 'capitalize',
fontSize: '1rem',
padding: '0 1rem',
}}
>
Home
</Button>
<Button
onMouseOver={handleClick}
sx={{
my: 2,
color: 'white',
display: 'block',
textTransform: 'capitalize',
fontSize: '1rem',
padding: '0 1rem',
}}
>
Services
</Button>
<Menu
id='fade-menu'
MenuListProps={{
'aria-labelledby': 'fade-button',
}}
anchorEl={anchorEl}
open={open}
onClose={handleClose}
TransitionComponent={Fade}
sx={{
display: 'flex',
alignItems: 'center',
justifyContent: 'center',
position: 'absolute',
top: '15',
}}
>
<MenuItem onClick={handleClose}>Web Development</MenuItem>
<MenuItem onClick={handleClose}>E-Commerce Solution</MenuItem>
<MenuItem onClick={handleClose}>Digital Marketing</MenuItem>
<MenuItem onClick={handleClose}>Design & Editing</MenuItem>
</Menu>
<Button
onClick={handleCloseNavMenu}
sx={{
my: 2,
color: 'white',
display: 'block',
textTransform: 'capitalize',
fontSize: '1rem',
padding: '0 1rem',
}}
>
Projects
</Button>
<Button
onClick={handleCloseNavMenu}
sx={{
my: 2,
color: 'white',
display: 'block',
textTransform: 'capitalize',
fontSize: '1rem',
padding: '0 1rem',
}}
>
Blog
</Button>
<Button
onClick={handleCloseNavMenu}
sx={{
my: 2,
color: 'white',
display: 'block',
textTransform: 'capitalize',
fontSize: '1rem',
padding: '0 1rem',
}}
>
Career
</Button>
<Button
onClick={handleCloseNavMenu}
sx={{
my: 2,
color: 'white',
display: 'block',
textTransform: 'capitalize',
fontSize: '1rem',
padding: '0 1rem',
}}
>
About us
</Button>
</Box>
<Button
fontSize='1rem'
variant='outlined'
sx={{ textTransform: 'capitalize' }}
>
Contact us
</Button>
</Toolbar>
</Container> < /AppBar>
);`
};
export default Navbar;
You could use per-breakpoint styling on the AppBar itself.
<AppBar
sx={{
height: 100,
backgroundColor: { xs: 'green', sm: 'red' },
width: { xs: 300, sm: 500 }
}}
/>
Working example: https://codesandbox.io/s/appbar-change-width-and-color-on-mobile-mjgr30?file=/src/App.js

Toolbar container to observe minWidth

I'm new to react and material UI and I've been trying to design my navbar so that my logo, search bar and drawer are in the center. I was able to get help earlier to get space between the components and have my search bar centered, but now i'm struggling to have my logo and drawer to be in the center while observing a minimum width from my searchbar.
I already tried wrapping them into a container with a specified width but they lose their alignment in the center.
here's my code:
const Search = styled('div')(({ theme }) => ({
position: 'relative',
borderRadius: 30,
backgroundColor: alpha(theme.palette.common.white, 0.15),
'&:hover': {
backgroundColor: alpha(theme.palette.common.white, 0.25),
},
// marginLeft: 10,
width: 'auto'
}));
const SearchIconWrapper = styled('div')(({ theme }) => ({
padding: theme.spacing(0, 2),
height: '100%',
position: 'absolute',
pointerEvents: 'none',
display: 'flex',
alignItems: 'center',
justifyContent: 'center',
}));
const StyledInputBase = styled(InputBase)(({ theme }) => ({
color: 'inherit',
'& .MuiInputBase-input': {
padding: theme.spacing(1, 1, 1, 0),
// vertical padding + font size from searchIcon
paddingLeft: `calc(1em + ${theme.spacing(4)})`,
transition: theme.transitions.create('width'),
width: 'auto',
},
}));
export default function SearchAppBar({ search, setSearch }) {
return (
<Box sx={{ flexGrow: 1 }}>
<AppBar position="fixed" sx={{ backgroundColor: "#55597d" }}>
<Toolbar sx={{ justifyContent: "space-between" }}>
<Stack direction="row" alignItems="center">
<img
style={{ marginRight: "10px" }}
src={logo}
alt="logo"
className="logotext"
width="38"
height="38"
/>
</Stack>
<Search>
<SearchIconWrapper>
<SearchIcon />
</SearchIconWrapper>
<StyledInputBase
sx={{ width: "auto" }}
value={search}
onChange={(e) => {
setSearch(e.target.value);
}}
placeholder="Search All Games…"
inputProps={{ "aria-label": "search" }}
/>
</Search>
{/*</div>*/}
<IconButton
size="large"
edge="start"
color="inherit"
aria-label="open drawer"
sx={{ mr: 0, ml: 0 }}
>
<MenuIcon />
</IconButton>
</Toolbar>
</AppBar>
</Box>
);
}

Material UI: I want to make this component responsive

I have this project and it is in order to monitor employees and I have a component which is "create workspace"
and I have added elements to this interface and I want this interface to be responsive, how can I do that?
And what are the ways in which you can make this page responsive?
Within this component, I have added a group of elements.
const useStyles = makeStyles({
resize:{
fontSize:24
}
});
const Settings: FC = () => {
const classes = useStyles()
return (
<Card style={{backgroundColor: 'transparent' , maxWidth: 1500 , minWidth: 500}}>
<CardContent>
<Box
sx={{
maxWidth: 1500,
// minWidth: 300
}}
>
<Box
sx={{
display: 'flex',
justifyContent: 'start'
}}
>
<Avatar style={{width: '5rem', height: '5rem'}} alt="Remy Sharp"
src="/static/images/avatar/1.jpg"/>
<TextField
fullWidth
name="workspaceName"
placeholder="Workspace Name"
variant="standard"
style={{
paddingLeft: '1.4rem',
transition: ' all .2s cubic-bezier(.785,.135,.15,.86) 0s',
display: 'flex',
alignItems: 'center',
flexGrow: 1,
position: 'relative',
color: '#828588',
}}
InputProps={{
classes: {
input: classes.resize,
},
}}
defaultValue="nameeeee"
/>
</Box>
</Box>
<CardActions
style={{ paddingTop: '10rem'}}
>
<Button style={{
minWidth: '10rem',
fontSize: '1.5rem',
height: '44px',
fontWeight: 400,
textShadow: 'none',
color: '#fd71af',
border: 0,
background: 'none'
}}>Delete Workspace</Button>
<Button
color="primary"
component={RouterLink}
to="/dashboard/workspaces/1"
variant="contained"
style={{
minWidth: '13rem',
minHeight: '4.3rem',
fontSize: '1.4rem',
backgroundColor: '#7b68ee',
borderRadius: 6,
marginLeft:'60rem'
}}
>
Saved
</Button>
</CardActions>
</CardContent>
</Card>
);
}
export default Settings;
Use material UI grids where ever you want to make the layout responsive. Check its documentation here : Material UI Grid
You can add different layouts for different screen sizes. You should also wrap your component in the Container component provided by Material-UI, It makes your web page fluid.
Hope this answers your question.

Resources