I am building a website using reactjs. I have a js file which extract props from another file which is an array called sections with data like title and imageurl. I need to use the prop of imageuURL as a background for each element. I tried to use style but it doesn't work.
Here is the code of extracting :
import React from 'react'
const Menuitem = (props) => {
return(
<div>
<h1 className='title'>{props.title}</h1>
<span className='subtitle'>shop now</span>
</div>
)
}
I pass that code through array in app.js using the following function:
function extract(item) {
return <Menuitem title={item.title}/>
}
Then use map function to return result
function App() {
return (
<div className=''>
{sections.map(extract) }
</div>
);
}
The result I get is like the image. I need to get a background image for each section from the array file
( imageURl prop )
react js problem
If the imageURL is inside the props passed to the menu item you can just put it in inline
const Menuitem = (props) => {
return(
<div style={{ backgroundImage: `url(${props.imageUrl})` }}>
<h1 className='title'>{props.title}</h1>
<span className='subtitle'>shop now</span>
</div>
)
}
Related
I want to inject some css only for the child of the button, but since I am using this syntax to render a group of buttons, can be 1 or 2, I am not sure how to write this properly
this is my code below
const renderChildren = (children: React.ReactElement[]) => {
return children.map((child: React.ReactElement, index) => ({ ...child, key: index }));
};
const GenericPageComponent: React.FC<GenericPageProps> = ({
imageChildren,
headingChildren,
textChildren,
buttonChildren,
}) => {
return (
<div className={styles.main}>
<div className={styles.wrapper}>
<div className={styles.title}>{headingChildren}</div>
{textChildren && <div className={styles.paragraph}>{renderChildren(textChildren)}</div>}
<div className={styles.btn}>{renderChildren(buttonChildren)}</div>
</div>
what do I change here?
I am using SCSS modules for my components in React/Next.js but I can't figure out how to import kebab-case classes.
At the moment, I am just writing all my SCSS classes in camelCase but this isn't ideal as this means I cannot make use of SCSS cascading.
(I'm still learning React am I'm not so great at making dynamic components myself so I am sticking to React Strap for now.)
Essentially, I want to write
.company-logo
instead of:
.companyLogo
EDIT: className={styles['company-logo']} causes an unexpected token error
Here is my Component:
import styles from './styles/Navbar.module.scss'
const NavComponent = (props) => {
const [isOpen, setIsOpen] = useState(false);
const toggle = () => setIsOpen(!isOpen);
return (
<div>
<img src="../ss-logo.png" alt="Logo" className={styles.companyLogo}/>
</div>
);
}
export default NavComponent;
And my SCSS:
.companyLogo {
height: 3rem;
}
className={styles['company-logo']}
should be what you want.
You can use the object key [] syntax.
<img src="..." className={styles['company-logo']}`
<img src="../ss-logo.png" alt="Logo" className={`${style['company-logo']}`}/>
inline:
<img src="../ss-logo.png" alt="Logo" className={`${styles["company-logo"]}`}/>
variable:
var logo = classNames({
[`${styles["company-logo"]}`]: true,
});
return (
<div>
<img src="../ss-logo.png" alt="Logo" className={logo}/>
</div>
)
I'm working on a react with nextjs project.
I'm using Link to scroll to a specific section on the same page.
Here is one of the components that use Link:
import styles from './section1.module.scss';
import Image from 'next/image';
import Button from '#material-ui/core/Button';
import tought_process from '../../../public/thought_process.png';
import Link from 'next/link';
const Section1 = () => {
return (
<div className={styles.container}>
<div className={styles.left}>
<div className={styles.leftContainer}>
<Link href='#enews'>
<div className={styles.buttonContainer}>
<Button className={styles.buttonstyle1}>Get started</Button>
</div>
</Link>
</div>
</div>
<div className={styles.right}>
<Image
src={tought_process}
className={styles.imageStyle}
alt='how to think about organizing'
layout='responsive'
priority
/>
</div>
</div>
);
};
export default Section1;
And here i mark the element with the id:
<div {...handlers} className={styles.bigBody}>
<NavBar open={menuOpen} toggle={setMenuOpen} scrollY={scrollY} />
<SideMenu open={menuOpen} toggle={setMenuOpen} scrollY={scrollY} />
<div className={styles.sections}>
<Section1 />
<Section2 />
<Section3 id='enews' />
<Section4 />
</div>
Can't figure out what i'm doing wrong.
Multiple clickable elements are wrapping each other. Remove the button and add the anchor element.
<Link href="#enews">
<a>Get started</a>
</Link>
<Link href="#enews">
<a className={styles.buttonContainer}>
<span className={styles.buttonstyle1}>Get started</span>
</a>
</Link>
I'd recommend updating the styles so you can remove the inner span element.
I use a custom link component that does a few things (not shown); one is smooth scroll to hash routes if the browser supports smooth scrolling (not Safari).
import NextLink, { LinkProps } from "next/link";
import { HTMLProps, MouseEvent, FC } from "react";
export const Link: FC<LinkProps & HTMLProps<HTMLAnchorElement>> = ({ as, children, href, replace, scroll, shallow, passHref, ...rest}) => {
const onClick = (event: MouseEvent<HTMLAnchorElement>) => {
if (href.startsWith("#")) {
event.preventDefault();
const destination = document.getElementById(href.substring(1));
if (destination) destination.scrollIntoView({ behavior: "smooth" });
}
};
return (
<NextLink as={as} href={href} passHref={passHref} replace={replace} scroll={scroll} shallow={shallow}>
<a href={href} {...rest} onClick={onClick}>
{children}
</a>
</NextLink>
);
};
I removed new lines to condense the code block
If you went with the above approach, don't include the anchor tag since it's automatically included.
import { Link } from "./custom/path/link"
<Link href="#enews">Get started</Link>
Two points here:
As per the nextjs, passHref has to be used if a custom element is used as a child of Link tag instead of an anchor tag.
As per the same docs value of href should be '/#enews' not '#enews'
This is a simplified React component that uses helmet to update the link css on runtime:
function App() {
const [brand, setBrand] = useState('nike')
return (
<div className="App">
<Helmet>
<link rel="stylesheet" href={getBrandStyle(brand)} />
</Helmet>
<div>other contents here</div>
<!-- omitted the button components that change the brand state by calling setBrand -->
</div>
);
}
I have recently just used react-helmet as a declarative way to change the head tag's child and with the code I wrote above, when switching the css there is momentary lag when the page has no css stylings and then 1 second later the updated css shows up.
Even during the initial load of the page, if I use queryParameters (code above doesn't show the query parameter approach) such as
https://localhost:3000?brandQueryParam=nike
there is 1 second wherein there is no css styling before the brand css shows up.
Can you please let me know what I am missing and how to resolve this?
This is the solution that I came up with, not sure if setTimeout is the best solution so if anyone else knows a better way, please share it.
const brands = {
nike: 'nike2022',
adidas: 'adidas2017',
fila: 'fila2020'
};
function App() {
const [brand, setBrand] = useState('nike')
const [isLoading, setIsLoading] = useState(false)
const changeBrandStyleOnClick = (brand) => {
setBrand(brand)
setIsLoading(true)
}
return (
<div className="App">
<Helmet>
<link rel="stylesheet"
onChangeClientState={(newState, addedTags, removedTags) => setTimeout(() => setIsLoading(false), 1500)}
href={getBrandStyle(brand)} />
</Helmet>
{isLoading && (
<Overlay>
<Spinner/>
</Overlay>
)}
{!isLoading && (
<>
{Object.keys(brands).filter(b => b !== brand).map(b =>
(<Button onClick={() => changeBrandStyleOnClick (b)} value={b}>
<Logo
alt="default alt name"
appearance="default"
name={b}
size="small"/>
</Button>))
}
<div>other contents here</div>
</>
)}
</div>
);
}
I am new to nextjs and I have a question about CSS modules
I have a Product component that looks like this
import styles from "./Product.module.css"
function Product({className=""}) {
return (
<div class={`${styles.container} ${className}`}>
<p className={styles.title}>product</p>
</div>
)
}
Then I want to create another component that is called ProductCard which uses the Product component but needs to extend the p tag inside it
import styles from "./ProductCard.module.css"
function ProductCard() {
return (
<div class={styles.container}>
<Product className={styles.product}/>
</div>
)
}
How can I extend the p tag style in my Product component with a className given ProductCard
You need to add an additional custom prop and pass it to the p element. Using an object will allow you to pass any prop to the p element. See React's docs on props in JSX, MDN spread syntax, and nullish coalescing operator.
function Product({ className, titleProps, ...rest }) {
return (
<div className={`${styles.container} ${className ?? ''}`} {...rest}>
<p {...titleProps}>product</p>
</div>
);
}
function ProductCard() {
return (
<div className={styles.container}>
<Product
className={styles.product}
titleProps={{ className: styles.title }}
/>
</div>
);
}
import styles from "./Product.module.css"
function Product({className=""}) {
const classes = {
'product': `${styles.product}`
}
return (
<div class={`${styles.container} ${classes[className]}`}>
<p className={styles.title}>product</p>
</div>
)
}
import styles from "./ProductCard.module.css"
function ProductCard() {
return (
<div class={styles.container}>
<Product className='product' />
</div>
)
}