How to disable popover when hovered over another card in react js - reactjs

I'm trying to build course cards in which when hovered to any course card a popover should appear and popover is visible till when i hover on card and popover itself. And when I hover over to next card previous popover should be removed and current hovered card popover should appear.But when hover over another card previous pop over still exist.
Used package called react-tiny-popover react-tiny-popover
Below is the code snippet
<Popover
isOpen={isPopoverOpen}
positions={['right', 'left', 'top', 'bottom']}
padding={10}
align="center"
width={200}
onClickOutside={() => setIsPopoverOpen(false)}
reposition="true"
content={({ position, childRect, popoverRect }) => (
<ArrowContainer // if you'd like an arrow, you can import the ArrowContainer!
position={position}
childRect={childRect}
popoverRect={popoverRect}
arrowColor={'white'}
arrowSize={10}
arrowStyle={{ opacity: 0.7 }}
className='popover-arrow-container'
arrowClassName='popover-arrow'
>
<div
style={{ backgroundColor: 'white', color: '#170055', padding: '10px', borderRadius: '5px', width: '300px', height: '400px', lineHeight: '1.5' }}
onClick={() => setIsPopoverOpen(!isPopoverOpen)}
>
<div class="popover-text">
<h1 style={{ fontSize: '20px' }}>Lorem ipsum.</h1>
<h2 style={{ fontSize: '14px' }} class="course-instructor">Dr. Murthy</h2>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse vehicula rhoncus metus non condimentum. Int</p>
<ol>
<li>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse vehicula rhoncus metus non condimentum. Int</li>
<li>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse vehicula rhoncus metus non condimentum. Int</li>
</ol>
<button className="course-button">Add to Cart</button>
</div>
</div>
</ArrowContainer>
)}
>
<div class="tile" onMouseOver={() => setIsPopoverOpen(!isPopoverOpen)} >
<Link to={props.page}>
<img src='../../assets/images/courses-01.jpg' alt="ssd" />
<div class="text">
<h1>Lorem ipsum.</h1>
<h2 class="course-instructor">Dr. Murthy</h2>
<p className="course-price">Rs. 400</p>
</div>
</Link>
</div>
</Popover>

Try to add
onMouseLeave={() => setIsPopoverOpen(false)}
for div class="tile"

Related

How can I get a background image to show using Patternfly?

I was following this guide https://www.patternfly.org/v4/components/card/react-demos using their "Horizontal split" guide to try to get the desired effect but I am unable to get the background image to display properly even though the path to the image is correct.
I have tried to put the name of the image in curly brackets the way you do for normal images and also imported it but I am still unable to get the image to display. I am unsure of how to get the image to show up for this section.
Here is the code I have so far
import { Card, CardTitle, CardBody, CardFooter, Grid, GridItem, Button } from '#patternfly/react-core';
import dog from '../images/dog.jpg';
export default function adoptionReady() {
return (
<>
<h1>Pets Ready For Adoption</h1>
<div className="container">
<section>
<article>
<br></br>
<br></br>
<Card id="card-demo-horizontal-split-example" isFlat>
<Grid md={6}>
<GridItem
style={{
minHeight: '200px',
backgroundPosition: 'center',
backgroundSize: 'cover',
backgroundImage: 'url(../images/dog.jpg)'
} }
/>
<div class="col d-flex justify-content-center">
<Card id="card-demo-horizontal-split-example" isFlat>
<Grid md={6}>
<GridItem
style={{
minHeight: '200px',
backgroundPosition: 'center',
backgroundSize: 'cover',
backgroundImage: {dog}
}}
/>
<GridItem>
<CardTitle>Headline</CardTitle>
<CardBody>
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse arcu purus, lobortis nec euismod eu,
tristique ut sapien. Nullam turpis lectus, aliquet sit amet volutpat eu, semper eget quam. Maecenas in
tempus diam. Aenean interdum velit sed massa aliquet, sit amet malesuada nulla hendrerit. Aenean non
faucibus odio. Etiam non metus turpis. Praesent sollicitudin elit neque, id ullamcorper nibh faucibus eget.
</CardBody>
<CardFooter>
<Button variant="tertiary">Call to action</Button>
</CardFooter>
</GridItem>
</Grid>
</Card>
{/* <figure>
<figcaption></figcaption>
</figure> */}
</div>
</article>
</section>
</div>
<script src="https://cdn.jsdelivr.net/npm/#popperjs/core#2.11.6/dist/umd/popper.min.js" integrity="sha384-oBqDVmMz9ATKxIep9tiCxS/Z9fNfEXiDAYTujMAeBAsjFuCZSmKbSSUnQlmh/jp3" crossorigin="anonymous"></script>
<script src="https://cdn.jsdelivr.net/npm/bootstrap#5.2.2/dist/js/bootstrap.min.js" integrity="sha384-IDwe1+LCz02ROU9k972gdyvl+AESN10+x7tBKgc9I5HFtuNz0wWnPclzo6p9vxnk" crossorigin="anonymous"></script>
<>
</></>
);
}
Here is the example code I am trying to follow this url shows the end result that I am unable to duplicate https://www.patternfly.org/v4/components/card/react-demos/horizontal-split/
I was able to resolve the issue by inputting different code that split the content between it's containers, then all I had to just is just add a regular image like normal. Still not sure why the original code would not work though.
Leaving it here in case anyone needs it in the future when using pattern fly horizontal card tutorial.
import React from 'react';
import { Card, CardTitle, CardBody, CardFooter, Grid, GridItem, Button } from '#patternfly/react-core';
CardHorizontalSplitDemo = () => {
return (
<Card id="card-demo-horizontal-split-example" isFlat>
<Grid md={6}>
<Card id="card-demo-horizontal-split-example" isFlat>
<Grid md={6}>
<Split>
<SplitItem>
<img src={dog} alt=" " />
</SplitItem>
</Split>
<GridItem>
<CardTitle>Headline</CardTitle>
<CardBody>
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse arcu purus, lobortis nec euismod eu,
tristique ut sapien. Nullam turpis lectus, aliquet sit amet volutpat eu, semper eget quam. Maecenas in
tempus diam. Aenean interdum velit sed massa aliquet, sit amet malesuada nulla hendrerit. Aenean non
faucibus odio. Etiam non metus turpis. Praesent sollicitudin elit neque, id ullamcorper nibh faucibus eget.
</CardBody>
<CardFooter>
<Button variant="tertiary">Call to action</Button>
</CardFooter>
</GridItem>
</Grid>
</Card>
);
};
Example code maybe helpful
import React from 'react';
import { ImageBackground, StyleSheet } from 'react-native';
const BackgroundImage = ({ children }) => {
return (
<ImageBackground
source={require('path/to/your/image.jpg')}
style={styles.backgroundImage}
>
{children}
</ImageBackground>
);
};
const styles = StyleSheet.create({
backgroundImage: {
flex: 1,
resizeMode: 'cover',
justifyContent: 'center'
},
});
export default BackgroundImage;
You can then use this BackgroundImage component
import BackgroundImage from './BackgroundImage';
const YourComponent = () => {
return (
<BackgroundImage>
<!-- your content here -->
</BackgroundImage>
);
};
Solution was to add a split instead of a grid item for the image.
<Grid md={6}>
<Card id="card-demo-horizontal-split-example" isFlat>
<Grid md={6}>
<Split>
<SplitItem>
<img src={dog} alt=" " />
</SplitItem>
</Split>

how to dynamically fetch data in react while deploying?

Here's the thing, it all works fine if I run it with the npm run dev script, but images in testimonials.avatar don't render with npm run build.
const Testimonials = ({ testimonials }) => {
return (
<div id='testimonials' className='mt-20'>
<div className='text-center mb-8'>
<p className='text-xs uppercase mb-4 md:text-base'>Testimonials</p>
<h1 className='text-3xl md:text-5xl font-bold capitalize mb-10'>Read What Other<br />have to Say</h1>
</div>
<div className='flex flex-col gap-4 items-center md:flex-row'>
{testimonials.map(item =>
<div className='bg-light-gray rounded-3xl p-8 transition-transform duration-300 hover:-translate-y-2'>
<div className='w-32 h-32 mx-auto mb-4'>
<img src={item.avatar} alt="Person's avatar" className='rounded-full border' />
</div>
<p className='font-bold text-center'>{item.fullName}</p>
<p className='text-center mt-6'>{item.feedback}</p>
</div>
)}
</div>
</div>
)
}
Here I have a component which receives an array testimonials through props and then renders them in a div.
This is the array in App.jsx file.
const testimonials = [
{
avatar: '../src/images/avatars/avatar-1.png',
fullName: 'Andrew Rathore',
feedback: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nunc ullamcorper scelerisque mi, in malesuada felis malesuada vel. '
},
{
avatar: '../src/images/avatars/avatar-2.png',
fullName: 'Vera Duncan',
feedback: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nunc ullamcorper scelerisque mi, in malesuada felis malesuada vel. '
},
{
avatar: '../src/images/avatars/avatar-3.png',
fullName: 'Mark Smith',
feedback: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nunc ullamcorper scelerisque mi, in malesuada felis malesuada vel. '
}
];
I guess I know that the main reason why it does not work while deploying is because of a non-existent path since I will no longer have src/images/avatar during a deploy.
I also guess this is a dumb question because I am quite new to React and JavaScript in general, but would appreciate any answer regarding the problem.
You have to wrap the avatar path in require() like require('../src/images/avatars/avatar-1.png') I hope this works. thanks
Fixed this by creating an external file and then fetching it to the component like so.
data.js
import avatar1 from '../public/images/avatars/avatar-1.png';
import avatar2 from '../public/images/avatars/avatar-2.png';
import avatar3 from '../public/images/avatars/avatar-3.png';
export const testimonials = [
{
authorImg: avatar1,
authorName: 'Andrew Rathore',
authorText: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nunc ullamcorper scelerisque mi, in malesuada felis malesuada vel.'
},
{
authorImg: avatar2,
authorName: 'Vera Duncan',
authorText: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nunc ullamcorper scelerisque mi, in malesuada felis malesuada vel.'
},
{
authorImg: avatar3,
authorName: 'Mark Smith',
authorText: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nunc ullamcorper scelerisque mi, in malesuada felis malesuada vel.'
}
];
Testimonials.jsx
import React from 'react';
import { testimonials } from '../data/data';
const Testimonials = () => {
return (
<div className='flex flex-col gap-4 justify-between items-center md:flex-row'>
{testimonials.map((testimonial, index) =>
<div key={index} className='bg-light-gray rounded-3xl p-8 transition-transform duration-300 hover:-translate-y-2'>
<div className='w-32 h-32 mx-auto mb-4'>
<img src={testimonial.authorImg} alt="Person's avatar" className='rounded-full border' />
</div>
<p className='font-bold text-center'>{testimonial.authorName}</p>
<p className='text-center mt-6'>{testimonial.authorText}</p>
</div>
)}
</div>
)
}
export default Testimonials;
The main reason why it didn't work well in the first place was the fact that I specified path to the images in the object itself like so:
{
key: '../../../value.png'
}
That is why I ran into as error every time while deploying, 'cause it simply couldn't find that path due to its non-existence.

React object rendering to fontawesome

how do i render an object to a font awesome component. i have an object with different properties and i am rendering them dynamically into my cards component so i have many cards with different contents. below is my code.
import React from "react";
import "../Styles/card.css";
import "bootstrap/dist/css/bootstrap.css";
import { FontAwesomeIcon } from "#fortawesome/react-fontawesome";
import { faCar, faTruck, faHome } from "#fortawesome/free-solid-svg-icons";
const Card = () => {
const Cards = [
{
_uid: "BUY6Drn9e1",
Icon: "faHome",
head: "Free and Fast",
text: "Lorem ipsum dolor sit, amet consectetur adipisicing elit. Aliquam
tempora illum magni minima dolor id sequi quibusdam omnis.",
},
{
_uid: "BUY6Drn9e1",
Icon: "faTruck",
head: "Post Transportation",
text: "Lorem ipsum dolor sit, amet consectetur adipisicing elit. Aliquam tempora illum magni minima dolor id sequi quibusdam omnis.",
},
{
_uid: "BUY6Drn9e1",
Icon: "faCar",
head: "Free and Fast",
text: "Lorem ipsum dolor sit, amet consectetur adipisicing elit. Aliquam tempora illum magni minima dolor id sequi quibusdam omnis.",
},
];
const renderCard = (Card, index) => {
const shape = Card.Icon;
console.log(shape);
return (
<div className="card carded col mx-1 mb-2" key={index}>
<div className="flex">
<div className=" sameRow icon">
{/* <i class="bi bi-truck" style={{ fontSize: 35 }}></i> */}
</div>
<div className="sameRow body">
<FontAwesomeIcon
icon={faCar}
className="pic"
style={{ fontSize: 25, color: "#66b2e9" }}
/>
<h3 className="head">{Card.head}</h3>
<p className="text">{Card.text}</p>
</div>
</div>
</div>
);
};
return <div className="row mt-5 pt-5 px-5">{Cards.map(renderCard)}</div>;
};
export default Card;
i am trying to replace the faCar with {Card.Icon}
You have made a mistake,
Link the font awesome icon to each item using the import name, not as strings.
const Cards = [
{
_uid: "BUY6Drn9e1",
Icon: faHome,
head: "Free and Fast",
text:
"Lorem ipsum dolor sit, amet consectetur adipisicing elit. Aliquam tempora illum magni minima dolor id sequi quibusdam omnis."
},
{
_uid: "BUY6Drn9e1",
Icon: faTruck,
head: "Post Transportation",
text:
"Lorem ipsum dolor sit, amet consectetur adipisicing elit. Aliquam tempora illum magni minima dolor id sequi quibusdam omnis."
},
{
_uid: "BUY6Drn9e1",
Icon: faCar,
head: "Free and Fast",
text:
"Lorem ipsum dolor sit, amet consectetur adipisicing elit. Aliquam tempora illum magni minima dolor id sequi quibusdam omnis."
}
];
Access it when iterating as you have done for the text
...
<FontAwesomeIcon
icon={Card.Icon}
className="pic"
style={{ fontSize: 25, color: "#66b2e9" }}
/>
...

Problem fetching data in react using getStaticProps

I'm currently trying to fetch some data in my Next.js project using the getStaticProps() function and I continue to get this error:
TypeError: Cannot read property 'map' of undefined
My code looks like this:
export const getStaticProps = async () => {
const data = [
{
"id": 1,
"question": "Lorem ipsum dolor sit amet consectetur adipisicing elit.",
"answer": "Lorem ipsum dolor sit amet consectetur adipisicing elit. Iste magni at magnam placeat. Non, saepe?"
},
{
"id": 2,
"question": "Lorem ipsum dolor sit amet consectetur adipisicing elit.",
"answer": "Lorem ipsum dolor sit amet consectetur adipisicing elit. Iste magni at magnam placeat. Non, saepe?"
}
]
return {
props: {
questions: data
}
}
}
export default function FAQ({ questions }) {
return (
<div className="p-8 grid bg-blanco" >
<div className="grid place-content-center text-center mt-10 md:mt-0" >
<h1 className="text-2xl text-gun-rose-700 font-bold" >¿Tiene preguntas? Mira aquí</h1>
<h3 className="text-gun-rose-300 mt-4 max-w-2xl" >Lorem ipsum dolor sit amet consectetur adipisicing elit. Sunt, suscipit. Aliquid molestias eveniet ullam? Dolores, minus? Perspiciatis neque voluptates iste!</h3>
</div>
{questions.map(q => (
<div className="" key={q.id}>
<h3 className="">{q.question}</h3>
<p className="">{q.answer}</p>
</div>
))}
</div>
)
}
Any guidence will be appreciated, thanks in advance :)
It could be an async issue where questions is not immediately available. Try with a null check at the start of questions.
export default function FAQ({ questions }) {
return (
<div className="p-8 grid bg-blanco" >
<div className="grid place-content-center text-center mt-10 md:mt-0" >
<h1 className="text-2xl text-gun-rose-700 font-bold" >¿Tiene preguntas? Mira aquí</h1>
<h3 className="text-gun-rose-300 mt-4 max-w-2xl" >Lorem ipsum dolor sit amet consectetur adipisicing elit. Sunt, suscipit. Aliquid molestias eveniet ullam? Dolores, minus? Perspiciatis neque voluptates iste!</h3>
</div>
{questions && questions.map(q => (
<div className="" key={q.id}>
<h3 className="">{q.question}</h3>
<p className="">{q.answer}</p>
</div>
))}
</div>
)
}
Edit 1:
The getStaticProps method can only be used on the top level component of a page as stated in the caveats
The fix is to move the getStaticProps method to the top level page component. I've demo'ed this in a sandbox as folder structures are so important, link here.

Error while using Accordian in React-bootstrap

Every time when I copy-paste the code of accordion component from the react-bootstrap official docs. I am getting the following error. Attached below is both code and error screenshots.
import React, { useState } from 'react';
import { Navbar, Container, Nav, NavDropdown,Alert, Row, Col, Accordion} from 'react-bootstrap';
return (
<>
<div >
<div style={{border:'1px solid black'}} className="my-4">
<div className="my-3 mx-3" style={{fontSize:'160%', fontFamily:'Special Elite'}}>Chess Moves Notation</div>
<Row style={{padding:'5%',textAlign:'center'}}>
<Accordion defaultActiveKey="0" flush>
<Accordion.Item eventKey="0">
<Accordion.Header>Accordion Item #1</Accordion.Header>
<Accordion.Body>
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod
est laborum.
</Accordion.Body>
</Accordion.Item>
<Accordion.Item eventKey="1">
<Accordion.Header>Accordion Item #2</Accordion.Header>
<Accordion.Body>
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod
tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim
est laborum.
</Accordion.Body>
</Accordion.Item>
</Accordion>
</Row>
</div>
</div>
</>
)
}
export default PieceNotation;
Error
How can we fix this error?
It seems that you're using Accordion which the related method is used in bootstrap-5, but the bootstrap version which you've installed is bootstrap-4. So you need to use bootstrap-4 related method. You should use the Accordion component same as bellow:
<Accordion defaultActiveKey="0" flush>
<Card>
<Card.Header>
<Accordion.Toggle as={Button} variant="link" eventKey="0">
Accordion Item #1
</Accordion.Toggle>
</Card.Header>
<Accordion.Collapse eventKey="0">
<Card.Body>
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed
do eiusmod est laborum.
</Card.Body>
</Accordion.Collapse>
</Card>
</Accordion>
Please refer to this link for Accordion in bootstrap-4 : Accordion

Resources