I'm using v1.1.0 of material-ui in React 16.3.2. I'm trying to create a landing page similar to Showcase - Local Insights
where the dialog has opacity (Find foreclosures). I'm trying to use PaperProps for Dialog component described here Dialog doc
Here's a component I've created to try to do this.
import React from 'react';
import PropTypes from 'prop-types';
import { withStyles } from '#material-ui/core/styles';
import Button from '#material-ui/core/Button';
import Dialog from '#material-ui/core/Dialog';
import DialogActions from '#material-ui/core/DialogActions';
import DialogContent from '#material-ui/core/DialogContent';
import DialogTitle from '#material-ui/core/DialogTitle';
import ForwardIcon from '#material-ui/icons/Forward';
import Input from '#material-ui/core/Input';
import FormControl from '#material-ui/core/FormControl';
import Slide from '#material-ui/core/Slide';
const styles = theme => ({
dialogPaper: {
opacity: 0.5,
border: '#FF0000 1px solid',
},
button: {
margin: '30px'
}
});
function Transition(props) {
return <Slide direction="up" {...props} />;
}
class SignInDialog extends React.Component {
state = {
open: false,
username: ''
};
handleClickOpen = () => {
this.setState({ open: true });
};
handleClose = () => {
this.setState({ open: false });
};
handleChange = name => event => {
this.setState({
[name]: event.target.value,
});
};
render() {
const { classes } = this.props;
return (
<div>
<Button variant="fab" color="primary" aria-label="add" className={classes.button} onClick={this.handleClickOpen}>
<ForwardIcon />
</Button>
<Dialog
PaperProps={styles.dialogPaper}
open={this.state.open}
TransitionComponent={Transition}
onClose={this.handleClose}
aria-labelledby="form-dialog-title"
>
<DialogTitle id="form-dialog-title">WELCOME</DialogTitle>
<DialogContent>
<p>SIGN IN</p>
<FormControl className={classes.formControl}>
<Input
value={this.state.searchString}
onChange={this.handleChange('search')}
id="siginin-input"
placeholder="Enter your username"
/>
</FormControl>
</DialogContent>
<DialogActions>
<Button onClick={this.handleClose} color="primary">
Cancel
</Button>
<Button onClick={this.handleClose} color="primary">
Continue
</Button>
</DialogActions>
</Dialog>
</div>
);
}
}
SignInDialog.propTypes = {
classes: PropTypes.object.isRequired,
};
export default withStyles(styles)(SignInDialog);
I haven't been able to figure out how to get the Dialog to take the styles. What is needed to get PaperProps to work?
If you want to use PaperProps you have to specify the props of the Paperfor which you are applying style.
<Dialog
PaperProps={{ classes: {root: classes.dialogPaper } }}
/>
You can also use classes property and override the style
<Dialog
classes={{paper:classes.dialogPaper}}
/>
The correct way to overide paper props is by using classNames
<Dialog
PaperProps={{ className: classNames(classes.dialogPaper) }}/>
<Dialog
PaperProps={{ classes: {root: classes.dialogPaper } }}
/>
Related
I am new to REACT and the MERN Stack and try to understand everything. But sometimes, it seems that the simplest things do not want to get into my head.
I hope that, one day, I will understand it all. Until then it still seems a long way away. Anyway. I am starting with a simple MERN app. All users should be displayed on the start page. On a separate "page" there should be a create users form. For now, the users are displayed on the home screen but when I switch back from the "create users page" they dissappeared. Furthermore the input form do not work (validation error). When checking get and posts requests from my backend with Thunder Client everthing works, so I suppose, this might be something to do with the frontend. Sorry for my wording. I am a programming newbie.
I hope it is somewhat understandable. What am I doing wrong? I would be so happy, if anyone could help. Thank you!
client/src/App.js
import React from "react";
import { Routes, Route } from "react-router-dom";
import AllUsers from "./pages/AllUsers";
import Navigation from "./components/Navigation";
import CreateUser from "./pages/CreateUser";
import "./App.css";
function App() {
return (
<div className="App">
<Navigation />
<Routes>
<Route path="/" element={<AllUsers />} />
<Route path="create-User" element={<CreateUser />} />
</Routes>
</div>
);
}
export default App;
client/src/components/Navigation.js
import React from "react";
import { Link } from "react-router-dom";
const Navigation = () => {
return (
<header className="bg-background border-t-0 shadow-none">
<nav className="bg-navigation bg-opacity-40 rounded-t-xs flex justify-around h-12 p-3 ">
<Link to="/create-user">Create User</Link>
<Link to="/">
<img id="workshop-icon" src="../assets/home.svg" alt="home button" />
</Link>
</nav>
</header>
);
};
export default Navigation;
client/src/AllUsers.js
import React from "react";
import { useState, useEffect } from "react";
import Axios from "axios";
const AllUsers = () => {
const [listOfUsers, setListOfUsers] = useState([]);
useEffect(() => {
Axios.get("http://localhost:3001/getUsers").then((response) => {
setListOfUsers(response.data);
});
}, []);
return (
<div className="App">
<div className="usersDisplay">
{listOfUsers.map((user) => {
return (
<div key={user._id}>
<h1>Name: {user.name}</h1>
<h1>Age: {user.age}</h1>
<h1>Username: {user.username}</h1>
</div>
);
})}
</div>
</div>
);
};
export default AllUsers;
client/src/createUser.js
import React from "react";
import { useState } from "react";
import Axios from "axios";
const CreateUser = () => {
const [listOfUsers, setListOfUsers] = useState([]);
const [name, setName] = useState("");
const [age, setAge] = useState(0);
const [username, setUsername] = useState("");
Axios.post("http://localhost:3001/createUser", {
name,
age,
username,
}).then((response) => {
setListOfUsers([
...listOfUsers,
{
name,
age,
username,
},
]);
});
return (
<div className="input">
<div>
<input
type="text"
placeholder="Name..."
onChange={(event) => {
setName(event.target.value);
}}
/>
<input
type="number"
placeholder="Age..."
onChange={(event) => {
setAge(event.target.value);
}}
/>
<input
type="text"
placeholder="Username..."
onChange={(event) => {
setUsername(event.target.value);
}}
/>
<button onClick={CreateUser}> Create User </button>
</div>
</div>
);
};
export default CreateUser;
I am trying to implement tailwindcss styles into Formik to style forms. But the styles declared through className are not being applied?
I think Formik is using classname to define input type and tailwind uses the same method to declare styles?
my form page:
import React from "react";
import * as yup from "yup"
import { Formik, Form } from 'formik'
import { MyTextInput } from "../components/FormParts";
let mainFormSchema = yup.object().shape({
name: yup.string().trim().required()
})
const tryMainForm = () => {
const initValues = {
name: ''
}
return (
<div>
<h1>Any place in your app!</h1>
<Formik
initialValues={initValues}
validationSchema={mainFormSchema}
onSubmit={(values, { setSubmitting }) => {
setTimeout(() => {
alert(JSON.stringify(values, null, 2));
setSubmitting(false);
}, 400);
}}
>
{({ isSubmitting }) => (
<Form>
<MyTextInput
label="name"
name="name"
type="text"
placeholder="name"
/>
<button type="submit" disabled={isSubmitting}>
Submit
</button>
</Form>
)}
</Formik>
</div>
)
}
export default tryMainForm
formpart component:
import { useField } from "formik";
export const MyTextInput = ({ label, ...props }) => {
const [field, meta] = useField(props)
return (
<>
<label htmlFor={props.id || props.name} className="block text-sm font-medium text-gray-700">{label}</label>
<input className="shadow-sm focus:ring-indigo-500 focus:border-indigo-500 block w-full sm:text-sm border-gray-300 rounded-md" {...field} {...props} />
{meta.touched && meta.error ? (
<div className="error">{meta.error}</div>
) : null}
</>
)
}
can you suggest a way to deal with this?
tailwind applies styles properly to label but doesn't with input?
By default the helperText "Some important text" is not aligned to the far left. How can it be done?
You can use makeStyles for your css and then apply your generated styles to the className prop inside of the FormHelperTextProps prop from TextField.
import React from "react";
import { TextField } from "#material-ui/core";
import { makeStyles } from "#material-ui/core/styles";
const useStyles = makeStyles((theme) => ({
helperText: {
marginLeft: 0
}
}));
export default function App() {
const classes = useStyles();
return (
<div className="App">
<TextField
FormHelperTextProps={{
className: classes.helperText
}}
label="Test"
helperText="Helper text..."
variant="outlined"
/>
</div>
);
}
Live demo:
I have to implement a form with a bit less than 30 different fields.
So I decided to split them in 2 differents container component with two tabs to navigate between them.
I use redux-form to handle the data binding.
For on component I can get the value from handleSubimit of one component. But the final validation must be in the last tab only. From here I only have access to the value of the second tab. Like the data from the store where wipe out.
How can I access the store where my previous data should be ?
TabNavigationBar.js
import React from 'react';
import TabNavigationItem from './TabNavigationItem';
const TabNavigationBar = ({ onTabChange, activeTab }) => {
const tabList = [
{ hasIcon: 'fas fa-user-circle', hastext: 'Information Utilisateur' },
{ hasIcon: 'fas fa-file-alt', hastext: 'Informations contrat' }
];
const clickOnTab = tabNumer => {
onTabChange(tabNumer);
};
return (
<div className="columns">
<div className="column is-offset-one-quarter-desktop is-offset-one-thirds-tablet is-half-desktop is-one-thirds-tablet">
<div className="tabs is-toggle is-fullwidth">
<ul>
{tabList.map((tab, i) => (
<TabNavigationItem
key={i}
tabSelected={() => clickOnTab(i)}
hasClass={activeTab === i ? 'is-active' : ''}
hasIcon={tab.hasIcon}
hasText={tab.hastext}
/>
))}
</ul>
</div>
</div>
</div>
);
};
export default TabNavigationBar;
UserForm.js
import React from 'react';
import { reduxForm } from 'redux-form';
import CiviliteRadioButton from './CiviliteRadioButton';
import NameInputs from './NameInputs';
import AddressInputs from './AddressInputs';
import MailAndDOB from './MailAndDOB';
import TelephoneInputs from './TelephoneInputs';
let UserForm = ({ handleSubmit }) => {
return (
<div>
<CiviliteRadioButton />
<NameInputs />
<AddressInputs />
<MailAndDOB />
<TelephoneInputs />
</div>
);
};
UserForm = reduxForm({
form: 'form1',
initialValues: {
user: {
adresse: {
country: 'France'
},
civilite: 'Madame'
}
}
})(UserForm);
export default UserForm;
ContractForm.js
import React from 'react';
import { reduxForm } from 'redux-form';
import InputItem from '../InputItem';
import ContratInputsList from './contratInputList';
let ContratForm = ({ handleSubmit }) => {
const submit = values => {
console.log(values);
};
return (
<div>
<div className="columns is-multiline ">
{ContratInputsList.map((item, i) => {
return (
<div className="column is-half" key={i}>
<InputItem spec={item.spec} />
</div>
);
})}
</div>
<div className="columns">
<div className="column">
<div className="field is-grouped is-grouped-right">
<input
className="button is-primary"
onClick={handleSubmit(submit)}
type="submit"
value="Envoyer"
/>
</div>
</div>
</div>
</div>
);
};
ContratForm = reduxForm({
form: 'form2'
})(ContratForm);
export default ContratForm;
EDIT
When I click on my tabs, redux-form/DESTROY is called and erase form1's data.
Try setting destroyOnUnmount flag to false in reduxForm(options).
Currently for pre 1.0.0 releases Material-UI does not allow text selection on RadioButton and Checkbox control labels.
How can I override this behavior? Apparently passing labelStyle={{ userSelect: 'all' }} to the component doesn't help.
What I'm trying to achieve is being able to highlight the text in the option label as per this screenshot:
You need to override the CSS class that prevents selection of the labels.
The labels are made with components of type FormControlLabel. At the bottom of the doc page for that component, you can see that the CSS label class is available to override.
So, you need to override the label class on each FormControlLabel like this:
// Define the overriding style
const styles = () => ({
selectableLabel: {
userSelect: 'all',
},
});
// Override the label CSS that prevents selection
<FormControlLabel classes={{ label: classes.selectableLabel }} value="male" control={<Radio />} label="Male" />
Here's full code for a group of selectable radio buttons (derived from the Radio buttons example in the docs:
import React from 'react';
import PropTypes from 'prop-types';
import { withStyles } from 'material-ui/styles';
import Radio, { RadioGroup } from 'material-ui/Radio';
import { FormLabel, FormControl, FormControlLabel } from 'material-ui/Form';
const styles = theme => ({
root: {
display: 'flex',
},
formControl: {
margin: theme.spacing.unit * 3,
},
group: {
margin: `${theme.spacing.unit}px 0`,
},
selectableLabel: {
userSelect: 'all',
},
});
class RadioButtonsGroup extends React.Component {
state = {
value: '',
};
handleChange = (event, value) => {
this.setState({ value });
};
render() {
const { classes } = this.props;
return (
<div className={classes.root}>
<FormControl component="fieldset" required className={classes.formControl}>
<FormLabel component="legend">Gender</FormLabel>
<RadioGroup
aria-label="gender"
name="gender1"
className={classes.group}
value={this.state.value}
onChange={this.handleChange}
>
<FormControlLabel classes={{ label: classes.selectableLabel }} value="male" control={<Radio />} label="Male" />
<FormControlLabel classes={{ label: classes.selectableLabel }} value="female" control={<Radio />} label="Female" />
<FormControlLabel classes={{ label: classes.selectableLabel }} value="other" control={<Radio />} label="Other" />
<FormControlLabel classes={{ label: classes.selectableLabel }} value="disabled" disabled control={<Radio />} label="Disabled" />
</RadioGroup>
</FormControl>
</div>
);
}
}
RadioButtonsGroup.propTypes = {
classes: PropTypes.object.isRequired,
};
export default withStyles(styles)(RadioButtonsGroup);
And here's the full code for the Checkbox buttons (derived from the Checkboxes example in the doc):
import React from 'react';
import PropTypes from 'prop-types';
import { withStyles } from 'material-ui/styles';
import { FormControl, FormGroup, FormControlLabel } from 'material-ui/Form';
import Checkbox from 'material-ui/Checkbox';
const styles = {
selectableLabel: {
userSelect: 'all',
},
};
class CheckboxesGroup extends React.Component {
state = {
gilad: true,
jason: false,
antoine: true,
};
handleChange = name => (event, checked) => {
this.setState({ [name]: checked });
};
render() {
const { classes } = this.props;
return (
<FormControl component="fieldset">
<FormGroup>
<FormControlLabel
classes={{ label: classes.selectableLabel }}
control={
<Checkbox
checked={this.state.gilad}
onChange={this.handleChange('gilad')}
value="gilad"
/>
}
label="Gilad Gray"
/>
<FormControlLabel
classes={{ label: classes.selectableLabel }}
control={
<Checkbox
checked={this.state.jason}
onChange={this.handleChange('jason')}
value="jason"
/>
}
label="Jason Killian"
/>
</FormGroup>
</FormControl>
);
}
}
CheckboxesGroup.propTypes = {
classes: PropTypes.object.isRequired,
};
export default withStyles(styles)(CheckboxesGroup);