How to use conditional rendering using class name in React? [duplicate] - reactjs

This question already has answers here:
React Js conditionally applying class attributes
(24 answers)
Closed 1 year ago.
import { display } from '#mui/system';
import React from 'react';
import "../user_config/user_page.css"
export default function FileUploadButton({showBtn, setShowBtn,value,...rest}) {
const handelClick = () => {
setShowBtn(false);
};
return (
<div style={{ position: 'relative', display: 'inline-block' ,marginTop:'10px'}} className="big-size-file">
<button style={{ padding: '1px 12px', border: ' 1px solid #989797', borderRadius: '4px', color: '#727171',cursor:"pointer !important" }}>
{value && showBtn ? 'Replace file' : 'Choose file'}
</button>
{value && showBtn?<span title={value} style={{fontSize: '9px', color: 'blue', marginLeft:'10px' }}>{value}<button type="button" onClick={handelClick} className="float-right rounded-md text-blue-500 hover:text-gray-500 focus:outline-none " className={"big-size-file"?'marginTop:-17px':'margTop:11px'}>
<svg
xmlns="http://www.w3.org/2000/svg"
className="h-3 w-3 z-100"
viewBox="0 0 20 20"
fill="currentColor"
>
<path
fillRule="evenodd"
d="M4.293 4.293a1 1 0 011.414 0L10 8.586l4.293-4.293a1 1 0 111.414 1.414L11.414 10l4.293 4.293a1 1 0 01-1.414 1.414L10 11.414l-4.293 4.293a1 1 0 01-1.414-1.414L8.586 10 4.293 5.707a1 1 0 010-1.414z"
clipRule="evenodd"
/>
</svg>
</button></span>:<span>No file chosen</span>}
<input type='file' {...rest} className="fileStyle" style={{ position: 'absolute', zIndex: 2, opacity: 0, height: '100%', top: 0, bottom: 0, left: 0, right: 0 }} />
</div>
)
}
also big-size-file CSS property
.big-size-file {
max-width: 190px;
white-space: nowrap;
text-overflow: ellipsis;
overflow: hidden;
display: block;
}
How can I use that classname in conditional rendering that if classname is "big-size-file" then button marginTop is -17px or else marginTop 11px?

you can use state for storing your inital default value.
make two css classes with different styling
const [sty,setSty]=useState("default css class name here")
if you have some event then change it state set classname of your css.Now for your else part just change the state or make another state for storing name of diffeent css class
{value && showBtn?<span title={value} className={sty}>{value}<button type="button" onClick={handelClick} className="float-right rounded-md text-blue-500 hover:text-gray-500 focus:outline-none " className={"big-size-file"?'marginTop:-17px':'margTop:11px'}>
<svg
xmlns="http://www.w3.org/2000/svg"
className="h-3 w-3 z-100"
viewBox="0 0 20 20"
fill="currentColor"
>
<path
fillRule="evenodd"
d="M4.293 4.293a1 1 0 011.414 0L10 8.586l4.293-4.293a1 1 0 111.414 1.414L11.414 10l4.293 4.293a1 1 0 01-1.414 1.414L10 11.414l-4.293 4.293a1 1 0 01-1.414-1.414L8.586 10 4.293 5.707a1 1 0 010-1.414z"
clipRule="evenodd"
/>
</svg>
</button></span>:<span>No file chosen</span>}

Related

What's the best way go about animating this SVG?

I've been scrolling through looking various dev pages, many many answers but I think I'm missing the entire concept. It gets very technical and I'm at a loss for understanding. Most the pages I've read turn up things on the burger icon itself - which is what it is just broken down; so really I'm just at a lost for how to clone that. Strokes and Stroke-disarrays... The following is the SVG component (Open Icon):
export default function OpenIcon() {
return (
<svg
width="24"
height="20"
viewBox="0 0 24 20"
fill="none"
xmlns="http://www.w3.org/2000/svg"
>
<path
fillRule="evenodd"
clipRule="evenodd"
d="M0.800049 1.9999C0.800049 1.11625 1.51639 0.399902 2.40005 0.399902H21.6C22.4837 0.399902 23.2001 1.11625 23.2001 1.9999C23.2001 2.88356 22.4837 3.5999 21.6 3.5999H2.40005C1.51639 3.5999 0.800049 2.88356 0.800049 1.9999Z"
fill="#c91249"
/>
<path
fillRule="evenodd"
clipRule="evenodd"
d="M0.800049 9.9999C0.800049 9.11625 1.51639 8.3999 2.40005 8.3999H21.6C22.4837 8.3999 23.2001 9.11625 23.2001 9.9999C23.2001 10.8836 22.4837 11.5999 21.6 11.5999H2.40005C1.51639 11.5999 0.800049 10.8836 0.800049 9.9999Z"
fill="#c91249"
/>
<path
fillRule="evenodd"
clipRule="evenodd"
d="M0.800049 17.9999C0.800049 17.1162 1.51639 16.3999 2.40005 16.3999H21.6C22.4837 16.3999 23.2001 17.1162 23.2001 17.9999C23.2001 18.8836 22.4837 19.5999 21.6 19.5999H2.40005C1.51639 19.5999 0.800049 18.8836 0.800049 17.9999Z"
fill="#c91249"
/>
</svg>
);
}
Standard. Non-descript (intense descriptions lol). It is called under <OpenFocusTrap> on a MobileNavagation.jsx to operate as an App. It is then likewise displayed on a normal Header.jsx (see following):
MobileNavagation.jsx
<OpenFocusTrap>
<button
type="button"
className="flex justify-center items-center w-7 h-full"
onClick={() => setIsOpen((previousIsOpen) => !previousIsOpen)}
>
<span className="sr-only">{isOpen ? 'Close' : 'Open'} Menu</span>
{isOpen ? <CloseIcon /> : <OpenIcon />}
</button>.........
/* Additionally */
function CloseIcon() {
return (
<svg
width="18"
height="18"
viewBox="0 0 18 18"
fill="none"
xmlns="http://www.w3.org/2000/svg"
>
<path
d="M1 17L17 1M1 1L17 17"
stroke="#c91249"
strokeWidth="2"
strokeLinecap="round"
strokeLinejoin="round"
/>
</svg>
);
}
and...
Header.jsx
<Headroom>
<header className="h-14 lg:h-15" role="banner">
<div
className={`fixed z-20 h-14 lg:h-15 w-full bg-realative px-3 md:px-4 md:py-2 lg:pt-2 lg:pb-0 mx-auto ${
isMobileNavOpen ? '' : 'bg-opacity-95'
}`}
> ...........
They're cut short, didn't think the full pages necessary. If anyone have any solid sources for animating the paths? And/or a barney style explanation as to how...
Thanks for the assistance.
PS. Current "index.css" for <header> is as follows:
header {
position: sticky;
transition-property: all;
transition-timing-function: cubic-bezier(0.4, 0, 0.2, 1);
transition-duration: 500ms;
background-color: #191c1b;
top: 0;
left: 0;
height: 80px;
width: 100%;
margin-bottom: 10px;
z-index: 1;
font-family: 'Times New Roman', Times, serif;
}
#layer header {
.logo {
letter-spacing: -.16em;
}
.shadow {
box-shadow: 0 9px 9px -9px rgba(0, 0, 0, 0.13);
}
.hidden {
transform: translateY(-110%);
}
Note: Some details that might matter...
I'm using VSCode, WSL as a workspace for Ubuntu.
"Prettier" and "Tailwind" are included within.
"Hydrogen" is the app.
Yarn and github are used primary for repository downloads (npm gives me lip)

How to change cart icon state using React Hooks

I have two components, one will contain a button that will trigger the cart icon change when clicked, while the second component will contain the cart icon to be changed. I have tried but i have not been able to achieve this.Here is an image to explain better
Component A
import React,{useState} from 'react'
const Cart = () => {
const [itemCount, setItemCount] = useState('');
return (
<div>
<button
style={{width: '10%', height: '10%', padding:'20px'}}
onClick={() => {
setItemCount(itemCount + 1);
}}
>
{" "}
</button>
</div>
)
}
export default Cart
Component B
import React from 'react'
import Cart from './Cart'
const CartShow = (props) => {
return (
<div style={{border: '2px solid red', background: 'black', width: '30%', margin: '100px',
padding: '30px'}}>
<svg width="24" height="24" viewBox="0 0 24 24" fill="none"
xmlns="http://www.w3.org/2000/svg">
<path d="M9 22C9.55228 22 10 21.5523 10 21C10 20.4477 9.55228 20 9 20C8.44772 20 8 20.4477
8 21C8 21.5523 8.44772 22 9 22Z" stroke="white" stroke-width="2" stroke-linecap="round"
stroke-linejoin="round"/>
<path d="M20 22C20.5523 22 21 21.5523 21 21C21 20.4477 20.5523 20 20 20C19.4477 20 19
20.4477 19 21C19 21.5523 19.4477 22 20 22Z" stroke="white" stroke-width="2" stroke-
linecap="round" stroke-linejoin="round"/>
<path d="M1 1H5L7.68 14.39C7.77144 14.8504 8.02191 15.264 8.38755 15.5583C8.75318 15.8526
9.2107 16.009 9.68 16H19.4C19.8693 16.009 20.3268 15.8526 20.6925 15.5583C21.0581 15.264
21.3086 14.8504 21.4 14.39L23 6H6" stroke="white" stroke-width="2" stroke-linecap="round"
stroke-linejoin="round"/>
{props.itemCount}</svg>
<Cart/>
</div>
)
}
export default CartShow
Assuming your code works except the state change. following should work(not tested):
Component A
const Cart = (props) =>
<div>
<button
style={{width: '10%', height: '10%', padding:'20px'}}
onClick={() => props.setItemCount(props.itemCount + 1)}
>
{" "}
</button>
</div>
export default Cart
Component B
import React,{useState} from 'react'
import Cart from './Cart'
const CartShow = () => {
const [itemCount, setItemCount] = useState(0);
return (
<div style={{border: '2px solid red', background: 'black', width: '30%', margin: '100px',
padding: '30px'}}>
<svg width="24" height="24" viewBox="0 0 24 24" fill="none"
xmlns="http://www.w3.org/2000/svg">
<path d="M9 22C9.55228 22 10 21.5523 10 21C10 20.4477 9.55228 20 9 20C8.44772 20 8 20.4477
8 21C8 21.5523 8.44772 22 9 22Z" stroke="white" stroke-width="2" stroke-linecap="round"
stroke-linejoin="round"/>
<path d="M20 22C20.5523 22 21 21.5523 21 21C21 20.4477 20.5523 20 20 20C19.4477 20 19
20.4477 19 21C19 21.5523 19.4477 22 20 22Z" stroke="white" stroke-width="2" stroke-
linecap="round" stroke-linejoin="round"/>
<path d="M1 1H5L7.68 14.39C7.77144 14.8504 8.02191 15.264 8.38755 15.5583C8.75318 15.8526
9.2107 16.009 9.68 16H19.4C19.8693 16.009 20.3268 15.8526 20.6925 15.5583C21.0581 15.264
21.3086 14.8504 21.4 14.39L23 6H6" stroke="white" stroke-width="2" stroke-linecap="round"
stroke-linejoin="round"/>
{itemCount}</svg>
<Cart itemCount={itemCount} setItemCount={setItemCount} />
</div>
)
}
export default CartShow
Edit: to show the numbers on on the cart, check this link: How to put the number at top right corner of cart icon?
Since Cart is a child of CartShow you should move the state to CartShow ( or have a different parent component that contains both of them ). Then pass a func down to Cart to update itemCount

How to make a line break in svg

I have the following SVG of dynamically rendered pie chart using react-minimal-pie-chart :-
<svg viewBox="0 0 100 100" width="100%" height="100%"><path d="M 75 50 A 25 25 0 0 1 54.34120444167326 74.6201938253052" fill="none" stroke-width="50" stroke="#8dcd81"><title>Excellent</title></path><path d="M 54.34120444167326 74.6201938253052 A 25 25 0 0 1 26.507684480352285 41.449496416858295" fill="none" stroke-width="50" stroke="#eefa6b"><title>Good</title></path><path d="M 26.507684480352285 41.449496416858295 A 25 25 0 0 1 75 49.99999999999999" fill="none" stroke-width="50" stroke="#FF6382"><title>Weak</title></path><text dominant-baseline="central" x="50" y="50" dx="19.151111077974452" dy="16.06969024216348" text-anchor="middle" style="font-size: 5px;">22 %Excellent</text><text dominant-baseline="central" x="50" y="50" dx="-19.15111107797445" dy="16.069690242163485" text-anchor="middle" style="font-size: 5px;">33 %Good</text><text dominant-baseline="central" x="50" y="50" dx="4.341204441673249" dy="-24.620193825305204" text-anchor="middle" style="font-size: 5px;">44 %Weak</text></svg>
This is my Reactjs code:-
const Element = (props) => {
return (
<text
dominant-baseline="central"
x={props.x}
y={props.y}
dx={props.dx}
dy={props.dy}
text-anchor="middle"
style={{ fontSize: "5px" }}
>
{`${Math.round(props.dataEntry.percentage)} %`}
{props.dataEntry.title}
</text>
);
};
This is codesandbox full Reactjs example:-
https://codesandbox.io/s/throbbing-moon-ejs67?file=/src/App.js
How can i line break between the texts (excellent - good ..) and their percentage .
As Danny says - just stick in a tspan. These settings seem to work ok:
const Element = (props) => {
return (
<text
dominant-baseline="central"
x={props.x}
y={props.y}
dx={props.dx}
dy={props.dy}
text-anchor="middle"
style={{ fontSize: "5px" }}
>
{`${Math.round(props.dataEntry.percentage)} %`}
<tspan dx="-12" dy="5">
{props.dataEntry.title}
</tspan>
</text>
);
};

React-Spring — Parallax Issue incorporating a nav and footer due to height constraints

I am using Parallax from react-spring to create a parallax effect. I understand that the can use the height of its parent to set its area. This solution, however, is causing a strange behaviour when scrolling by keeping the and visible on the screen. I have a few questions here:
How can I setup this layout in a way where it will behave normally?
Do I need to place the and inside the ParallaxComp with fixed heights (I am hoping there is a better solution)?
Is there a way to make the assume its height based on the contents inside rather than use the prop factor?
Thank you in advance.
Codesandbox
App.js
import React from "react";
import ParallaxComp from "./ParallaxComp";
import "./styles.css";
export default function App() {
return (
<div className="App">
<nav style={{ height: "5rem", background: "purple", color: "white" }}>
Nav
</nav>
{/* <main style={{ height: "100%" }}> */}
<main style={{ height: "100vh" }}>
<ParallaxComp />
</main>
<footer style={{ height: "5rem", background: "blue", color: "white" }}>
Footer
</footer>
</div>
);
}
ParallaxComp.js
import React from "react";
import { Parallax, ParallaxLayer } from "react-spring/renderprops-addons";
let parallax;
const ParallaxComp = () => {
return (
<Parallax pages={2} scrolling={true} vertical ref={ref => (parallax = ref)}>
<ParallaxLayer
offset={0}
speed={0.1}
style={{
fontSize: "23.47222vw",
textAlign: "right",
textTransform: "uppercase"
}}
>
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 948.26 1122.2">
<path
d="M887 0c0 224.45-182.22 406.4-407 406.4S73 224.45 73 0h814z"
fill-rule="evenodd"
clip-rule="evenodd"
fill="#fec70e"
/>
</svg>
</ParallaxLayer>
<ParallaxLayer
offset={0}
speed={-0.4}
style={{
fontSize: "23.47222vw",
textAlign: "right",
textTransform: "uppercase"
}}
>
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 948.26 1122.2">
<path
d="M216 105.2c0 59.65-48.35 108-108 108S0 164.84 0 105.2h216z"
fill-rule="evenodd"
clip-rule="evenodd"
fill="#037e36"
/>
</svg>
</ParallaxLayer>
</Parallax>
);
};
export default ParallaxComp;

How to pass style in svg tag in React?

I am trying to pass
<svg class="svg-abs svg-f-btm" xmlns="http://www.w3.org/2000/svg" xmlnsXlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 1920 140" style="margin-bottom: -9px; backgroundImage:new 0 0 1920 140;" xmlSpace="preserve">
<path class="svg-gray" d="M960,92.9C811.4,93.3,662.8,89.4,515.3,79c-138.6-9.8-277.1-26.2-409-53.3C97.8,24,0,6.5,0,0c0,0,0,140,0,140
l960-1.2l960,1.2c0,0,0-140,0-140c0,2.7-42.1,11.3-45.8,12.2c-45.1,11-91.5,20.1-138.4,28.1c-176.2,30.1-359.9,43.8-542.9,48.9
C1115.4,91.4,1037.7,92.7,960,92.9z"></path>
</svg>
This thing in React component but getting error at
style="margin-bottom: -9px; backgroundImage:new 0 0 1920 140;"
How can I correct it?
you need to do like this
style={{marginBottom: “-9px”, backgroundImage: “new 0 0 1920 140”}}
in react you pass it like this: style={{ marginBottom: -9px; backgroundImage: new 0 0 1920 140 }}, for the property remove '-' and use camelCase

Resources