Change the style of a modal using react-modal - javascript

I have this object, with the styles I want for the modal:
const customStyles = {
content: {
top: '35%',
left: '50%',
right: 'auto',
bottom: 'auto',
marginRight: '-50%',
width: '60%',
transform: 'translate(-40%, -10%)',
},
};
Then I pass that styles to the modal like this:
<Modal
isOpen={this.state.modalIsOpen}
onRequestClose={this.closeModal}
style={customStyles}
>
And it works fine but I want to pass a class, not create a customStyle object inside the component.
I try something like this, first creating the modal class:
.modal {
top: '35%';
left: '50%';
right: 'auto';
bottom: 'auto';
marginRight: '-50%';
width: '60%';
transform: 'translate(-40%, -10%)';
}
and then:
<Modal
isOpen={this.state.modalIsOpen}
onRequestClose={this.closeModal}
className="modal"
>
But it didn't work. What am I doing wrong?

It should be portalClassName:
<Modal
isOpen={this.state.modalIsOpen}
onRequestClose={this.closeModal}
portalClassName="modal"
>

I think there might be a billion ways to do this, here is just one that uses CSS Modules. If you put your styles into a separate .css.js file you can import it in your module:
/// modal.css.js ///
export default {
modal: {
top: '35%',
left: '50%',
right: 'auto',
bottom: 'auto',
marginRight: '-50%',
width: '60%',
transform: 'translate(-40%, -10%)'
},
greenText: {
color: 'rgb(0,255,100)'
},
style3: {
marginRight: '-25%'
}
}
You can then assign your styles by accessing them as you would with any object and apply them to your component on the style attribute
import styles from './modal.css.js'
...
<Modal
isOpen={this.state.modalIsOpen}
onRequestClose={this.closeModal}
style={styles.modal}
>
if you want to apply multiple styles to your component you give the style attribute an array. This would allow you to apply styles from multiple imported style objects.
<Modal
isOpen={this.state.modalIsOpen}
onRequestClose={this.closeModal}
style={[styles.modal, styles.greenText]}
>

<ReactModal id={this.state.dialogId}
isOpen={showDialog}
onRequestClose={this.onCancel.bind(this)}
className={`shadow p-4`}
style={{
overlay: {
position: 'fixed',
zIndex: 1020,
top: 0,
left: 0,
width: '100vw',
height: '100vh',
background: 'rgba(255, 255, 255, 0.75)',
display: 'flex',
alignItems: 'center',
justifyContent: 'center',
},
content: {
background: 'white',
width: '45rem',
maxWidth: 'calc(100vw - 2rem)',
maxHeight: 'calc(100vh - 2rem)',
overflowY: 'auto',
position: 'relative',
border: '1px solid #ccc',
borderRadius: '0.3rem',
}}}
appElement={document.getElementById('root') as HTMLElement}> ... </ReactModal>

i tried this way and it works fine with me i added a simple class to the react modal tag
<Modal
size="sm"
aria-labelledby="contained-modal-title-vcenter"
className='modalStyle'
centered
show={prescriptionPreview}
onHide={() => setPrescriptionPreview(false)}
>
then i went to app.css and selected like this way
.modalStyle .modal-dialog
and style it whatever you want

Just in case you also need to handle different env file depending on your environment, e.g: .env.prod and .env.dev, then follow this:
Make sure that .env.prod and .env.dev are in the root directory of your project.
Load Environment Variables in next.config.js like that:
const dotenv = require('dotenv');
const environment = process.env.NODE_ENV || 'development';
if (environment === 'development') {
dotenv.config({ path: '.env.dev' });
} else {
dotenv.config({ path: '.env.prod' });
}
module.exports = withBundleAnalyzer({
// ...
env: {
VALUE_1: process.env.VALUE_1,
VALUE_2: process.env.VALUE_2,
VALUE_3: process.env.VALUE_3,
},
});

Related

MUI: Pseudo element being cut-off outside of Paper

I am having trouble with a red arrow '::before' pseudo element being partly cut-off outside of its '.MuiPaper-root' container. I would like for it to still be visible, any suggestions?
Below I have provided the relevant code and screenshots:
const useStyles = makeStyles(theme => ({
root: {
left: '5rem !important',
'& .MuiPaper-root': {
'&::before': {
position: 'absolute',
left: '4rem',
display: 'inline-block',
top: '-3.9rem',
fontSize: '5rem',
fontFamily: 'Material Icons',
content: '"arrow_drop_up"',
color: 'red',
zIndex: '5 !important',
},
},
},
}));
<S.Item style={{ alignSelf: 'stretch' }}>
<S.ItemGrid>
<S.Title>Guest rating</S.Title>
<S.Rating>
<FormControl style={{ width: '10rem' }}>
<S.StyledSelect
defaultValue={3.5}
value={rating.currency}
onChange={changeRating('currency')}
renderValue={option => option.value}
MenuProps={{
classes: { root: classes.root },
}}
>
{ratings.map(option => (
<S.StyledMenuItem key={option.value} value={option}>
<div>{option.value}</div>
<div>{option.label}</div>
</S.StyledMenuItem>
))}
</S.StyledSelect>
</FormControl>
</S.Rating>
</S.ItemGrid>
</S.Item>
Add overflow: 'visible' in your Paper style to prevent the content from being clipped even if it's outside the parent:
overflow: "visible",
"&::before": {
// ...
}

My Card's Background and Image are flickering when I move over it (while hovering), it works fine when I just hover over it and stop moving my cursor

import React from 'react';
import { makeStyles, Typography, Grid } from '#material-ui/core';
import Card from '#material-ui/core/Card';
const styles = makeStyles((theme) => ({
card: {
background: 'black',
width: '140px',
margin: '0px 10px',
},
root: {
width: '142px',
height: '196px',
overflow: 'hidden',
position: 'relative',
transition: 'all 0.5s ease-out',
},
image: {
position: 'absolute',
width: '100%',
height: '100%',
objectFit: 'cover',
transition: 'all 0.5s ease-out',
zIndex: 10,
'&:hover': {
zIndex: -1,
},
},
textPositioning: {
width: '140px',
height: '40px',
overflow: 'hidden',
marginTop: '10px',
},
text: {
display: 'flex',
justifyContent: 'center',
alignItems: 'center',
fontFamily: 'Comfortaa',
},
genresContainer: {
backgroundColor: theme.palette.primary.main,
width: '100%',
height: '100%',
position: 'relative',
transition: 'all 0.5s ease-out',
zIndex: 2,
},
genreList: {
width: '100%',
height: '100%',
},
}));
interface AnimeData {
image_url: string;
title: string;
genres: Array<any>;
}
interface DisplayAnimeCardProps {
data: AnimeData;
}
const DisplayAnimeCard: React.FC<DisplayAnimeCardProps> = (
props: DisplayAnimeCardProps
) => {
const classes = styles();
const { data } = props;
console.log(typeof data, data.genres);
return (
<Card className={classes.card}>
<div className={classes.root}>
<img
className={classes.image}
alt='anime'
src={data.image_url}
/>
<div className={classes.genresContainer}>
<Grid
className={classes.genreList}
container
direction='column'
justifyContent='center'
alignItems='center'
>
{data.genres.map((genre) => (
<Typography
className={classes.text}
variant='body1'
>
{genre.name}
</Typography>
))}
</Grid>
</div>
</div>
<div className={classes.textPositioning}>
<Typography className={classes.text} variant='body1'>
{data.title}
</Typography>
</div>
</Card>
);
};
export default DisplayAnimeCard;
The Hovering effect show a div a top the image with some text. It works fine when I simply hover over the Card and do not move the cursor again. But If I move my cursor(during hovering) a top the card, the hover effect breaks and causes flickering between the textPositioningdiv and the image. I want to stop this flickering and just show the textPositioning div whenever I hover over the card and move my cursor

In material ui using makeStyles, is it possible to write a css rule that applies only if the element has both classes?

I know that I can do this in CSS.
.makeStyles-mainNavWrapper-67.sticky{
position: fixed;
top: 0px;
opacity: 1;
transition: opacity 1s ease;
padding: 10px;
}
I want to know if I can do this in Material-UI so that I do not have to have two separate stylesheets so to speak (one for the MaterialUI ReactApp and one that is linked in the HTML tag.
const Header = (props) => {
const useStyles = makeStyles(theme => ({
mainNav: {
zIndex: '3',
color: 'white',
textAlign: 'right',
marginRight: '10%'
},
mainNavWrapper: {
paddingTop: '2%',
background: 'rgba(0,0,0,0.8)'
},
mainNavWrapper.sticky: {
I know this does not work. Is it possible?
},
I tried to just string together two classes in MaterialUI and I get errors.
I found the answer. I had to import the react-jss package and follow their documentation. I can now use the jssNested syntax and access nested elements and write rules that only apply if there are two classes attached to the element.
here it is:
import React from 'react'
import { render } from 'react-dom'
// Import React-JSS
import injectSheet from 'react-jss'
// Create your Styles. Remember, since React-JSS uses the default preset,
// most plugins are available without further configuration needed.
const styles = {
mainNav: {
zIndex: '3',
color: 'white',
textAlign: 'right',
marginRight: '10%',
'& ul': {
zIndex: '2',
textAlign: 'right',
listStyleType: 'none',
margin: '0px',
}
},
li: {
'& a': {
color: 'white'
}
},
mainNavWrapper: {
paddingTop: '2%',
background: 'rgba(0,0,0,0.8)',
width: '100%',
opacity: '1',
transition: 'width 2s ease',
padding: '10px',
'&.sticky': {
// jss-nested applies this to a child span
fontWeight: 'bold' // jss-camel-case turns this into 'font-weight'
},
'&.scrolling': {
opacity: '0',
position: 'absolute',
transition: 'opacity 1s ease'
}
},
myLabel: {
fontStyle: 'italic'
}
}
// Define the component using these styles and pass it the 'classes' prop.
// Use this to assign scoped class names.
const Button = ({ classes, children }) => (
<div className={classes.mainNavWrapper}>
<nav className={classes.mainNav}>
<ul className={classes.ul}>
<li className={classes.li} ><a href="#" >home</a></li>
<li className={classes.li}>about us</li>
<li className={classes.li}>packages</li>
<li className={classes.li}>reviews</li>
<li className={classes.li}><a href="#" className={classes.current}>contact us</a></li>
</ul>
</nav>
</div>
)
// Finally, inject the stylesheet into the component.
const Test = injectSheet(styles)(Button)
export default Test;
I think I may have found it (extensive rubberducking)
https://github.com/cssinjs/jss-nested
const styles = {
container: {
padding: 20,
'&:hover': {
background: 'blue'
},
// Add a global .clear class to the container.
'&.clear': {
clear: 'both'
},
// Reference a global .button scoped to the container.
'& .button': {
background: 'red'
},
// Use multiple container refs in one selector
'&.selected, &.active': {
border: '1px solid red'
}
}
}
complies to:
.container-3775999496 {
padding: 20px;
}
.container-3775999496:hover {
background: blue;
}
.container-3775999496.clear {
clear: both;
}
.container-3775999496 .button {
background: red;
}
.container-3775999496.selected, .container-3775999496.active {
border: 1px solid red;
}
Some of my other code is broken so it will take some time to verify this.
I left the other answer because it shows how to solve this issue using react-jss. This you can do the same thing with makeStyles in MaterialUI. I must have had syntax error somewhere which was causing none of my css rules to go into effect.
Here's the makeStyles way, there's also some breakpoint code here to boot:
import { makeStyles } from '#material-ui/core/styles';
const Header = () => {
const useStyles = makeStyles(theme => ({
root: {
padding: theme.spacing(1),
[theme.breakpoints.down('sm')]: {
backgroundColor: 'red',
},
[theme.breakpoints.up('md')]: {
backgroundColor: 'blue',
},
[theme.breakpoints.up('lg')]: {
backgroundColor: 'green',
},
},
mainNav: {
zIndex: '3',
color: 'white',
textAlign: 'right',
marginRight: '10%',
'& ul': {
zIndex: '2',
textAlign: 'right',
listStyleType: 'none',
margin: '0px',
}
},
li: {
display: 'inline-block',
marginLeft: '3%',
'& a': {
color: 'white',
textDecoration: 'none',
marginRight: '10px',
padding: '10px',
'&:hover': {
background: '#3498db'
}
}
},
mainNavWrapper: {
background: 'rgba(0,0,0,1)',
width: '100%',
opacity: '1',
transition: 'width 2s ease',
padding: '10px',
position: 'fixed',
zIndex: 1,
'&.sticky': {
position: 'fixed',
top: '0px',
opacity: '1',
transition: 'opacity 2s ease',
padding: '10px',
zIndex: 1
},
'&.scrolling': {
opacity: '0',
position: 'fixed',
transition: 'opacity 30ms ease'
}
},
...
in the functional component's return ():
<div className={classes.root}>
<div className={classes.mainNavWrapper}>
<nav className={classes.mainNav}>
<ul className={classes.ul}>
<li className={classes.li}><a href="#" >home</a></li>
<li className={classes.li}>about us</li>
<li className={classes.li}>packages</li>
<li className={classes.li}>reviews</li>
<li className={classes.li}><a href="#" className={classes.current}>contact us</a></li>
</ul>
</nav>
</div>
</div>

Popover component - onExited callback doesn't work , material ui

<Popover
key={element.name}
classes={{
paper: classes.paper
}}
open={open}
anchorEl={this.myRef.current}
anchorOrigin={{
vertical: 'bottom',
horizontal: 'left'
}}
transformOrigin={{
vertical: 'top',
horizontal: 'left'
}}
BackdropProps={
{
classes: { root: classes.backdrop }
}
}
onExited={this.handlePopoverClose}
>
onExited callback doesn't work , onClose work well , pls help me find out why does it happens , is it issue on material ui , or in my code ?? I also have tried to use onMouseLeave and it is also doesn't work
paper: {
display: 'grid',
justifyContent: 'center',
backgroundColor: palette.common.black,
flexFlow: 'wrap',
width: 1128,
height: 432,
borderRadius: '0 0 8px 8px',
padding: '56px 40px 66px 40px',
overflow: 'hidden',
gridTemplateColumns: 'auto auto auto auto',
position: 'absolute',
zIndex: 20
},
backdrop: {
background: 'transparent',
zIndex: 20
},
Above you can find css styles which I assign for this Popover
The onExited event is fired when the Popover has successfully closed. In order to do this you need to first call a function that closes the Popover.
<Popover
key={element.name}
open={open}
anchorEl={this.myRef.current}
onClose={this.handlePopoverClose}
onExited={() => console.log("The Popup closed")}
>
...
</Popover>

React Native can you puts views, with other elements inside, inside a ScrollView

I am trying to create an application using React-Native the page i am working on takes data it is given from a web server to populate a list. i am trying to display 20 entries, this includes an image and a name. i would like to create 20 views that contain this information in a scroll-able view. When i put a view inside of the scroll view it disappears. I am having trouble figuring out how scroll views work exactly, could someone please explain how this is done?
Code:
<View style={commonStyle.container}>
{/* Scrollable View */}
<ScrollView style={toysListStyle.MainContent}>
<View style={toysListStyle.ToyEntry}>
<Image resizeMode="contain" style={toysListStyle.ToyPicture}
source={{uri: 'http://icons.iconarchive.com/icons/paomedia/small-n-flat/1024/sign-check-icon.png'}}></Image>
<View style={toysListStyle.ToyNameView}>
<Text>Name</Text>
</View>
</View>
</ScrollView>
</View>
const toysListStyle = StyleSheet.create({
MainContent: {
position: "absolute",
left: "0%",
top: "33.5%",
width: "100%",
height: "60.5%",
backgroundColor: "rgba(0,0,0,0.05)",
flex: 1
},
ToyEntry: {
position: "absolute",
width: "100%",
height: "25%",
backgroundColor: "red",
flex: 1
},
ToyPicture: {
position: "absolute",
top: "5%",
left: "5%",
height: "90%",
width: "60%"
},
ToyNameView: {
position: "absolute",
top: "
right: "
height: "100%",
width: "
justifyContent: '
alignItems: 'center'
}
});
const commonStyle = StyleSheet.create({
container: {
position: "absolute",
bottom: 0,
left: 0,
height: windowHeight,
width: "100%",
backgroundColor: "white",
justifyContent: 'center',
alignItems: 'center',
},
I left out the information of the entire page because there is a lot but this is where i am having the problem. If i Change the ScrollView to a View then the View inside shows up, but in a ScrollView It doesn't appear. What am i missing?
You did all things right but...
ToyEntry: {
position: "absolute",
width: "100%",
height: "25%",// This will work if parent contain fixed height like device height or in points and it will divide those value in that ratio...
backgroundColor: "red",
flex: 1
}
So you can add fixed height to ToyEntry or you can add fixed height to
its parent...
I was able to view the content inside ScrollView with a bit change in ToyEntry style, just add height to absolute value instead of %
ToyEntry: {
position: "absolute",
width: "100%",
height: 250,
backgroundColor: "red",
flex: 1
}
Also, the image that you have shared, for some reason is not showing so I changed the image link also to see the result
<Image resizeMode="contain" style={styles.ToyPicture}
source={{uri: 'https://unsplash.it/400/400?image=1'}}
/>

Categories

Resources