I'm a beginner developer and I work with Reactjs.
I'm doing a project where there will be a gallery of photos that I brought
from a flickr api service.
Each image will have two buttons:
1.Clone: clicking the clone button should duplicate the image.
2.Expand: clicking an image should display this image in a larger view
How do I clone the image in a different way than I did? (more effective)
How do I large the image without using the 'react-modal'?
I have two components- One of the gallery and the other of the pictures.
my Gallery.js:
handleClone = image => {
this.state.images.push(image);
this.setState({ images: this.state.images });
};
render() {
return (
<div className="gallery-root">
{this.state.images.map((dto, index) => {
return <Image key={'image-' + index} dto={dto} galleryWidth=
{this.state.galleryWidth}
handleClone={image => this.handleClone(image)}
/>;
})}
</div>
);
}
my Image.js:
handleClone() {
this.props.handleClone(this.props.dto); // send to the Gallery component
the image to clone.
}
render() {
return (
<div>
<FontAwesome className="image-icon" name="clone" title="clone"
onClick={()=> this.handleClone()}/>
<FontAwesome className="image-icon" name="filter" title="filter"
onClick={()=> this.filterChange()}/>
<FontAwesome className="image-icon" name="expand" title="expand" />
</div>
</div>
);
}
Thanks :)
For the clone purposes.
handleClone = image => {
const imagesCopy = [...this.state.images]; //creates a copy of the images array which is stored in your component.
imagesCopy.push(image);
//this.state.images.push(image); this way will mutate the state directly which is a mistake.
this.setState({ images: imagesCopy });
};
About the react-modal thing, I don't see anything related to that in the question post, can you please share out the related code?
Related
I am trying display a carousel of images on my page, but it is not displaying the images at all. when I console logged the image url, it is there, but no image at all.
also one more question, what would I use for the key here? I used the image url here as the key
import galleryStyles from "../styles/Gallery.module.css";
import Carousel from "react-bootstrap/Carousel";
const BigGallery = ({ images }) => {
return (
<>
<div>hi </div>
<Carousel interval={4000} className={galleryStyles.Carousel}>
{images.map((image) => {
console.log(image.url); // This logged the correct url
<Carousel.Item key={image.url}>
<img src={image.url} className={galleryStyles.image} />
</Carousel.Item>;
})}
</Carousel>
</>
);
};
export default BigGallery;
https://res.cloudinary.com/catify/image/upload/v1588704903/hcnqjp7okfykkb3az2v3.jpg
Hello im trying to create a proyect of a guessing game, i have multiple components of letters as show in the image, some letters are needed for the answer and some are not, i need a button that when i click it it removes or hides the components that are not needed for the answer, how can i do this with react or react native?
Im saving the letters in a array and then rendering them using Map with a custom component that is styled to look like the photo, im doing it in react native but i think it should be the same in react, any help is welcome, thanks.
return (
<Animated.View style={{flex: 1}}>
{Letters.forEach(element => {
<LetterCard letter={element} />;
})}
<Button
title="eliminar"
onPress={() => {
eliminar;
}}
/>
</Animated.View>
);
You probably need a list in state or somewhere that holds which letters are needed and which aren't, as well as a boolean to determine if you are showing all letters or just your needed letters.
Your button which toggles to show/hide the unneeded letters would simply toggle the neededOnly state.
this.state={
neededLetters = [], //array of needed letters
neededOnly = false,
}
{neededOnly ?
neededLetters.forEach(element => {
<LetterCard letter={element} />;
}) :
Letters.forEach(element => {
<LetterCard letter={element} />;
})}
<Button
title="eliminate"
onPress={() => {
this.setState(prevState => ({
neededOnly: !prevState.neededOnly
}));
/>
I am building a boat visualizer using AISHub and the external database Contentful.
All the vessels I am interested are injected into a table. When I click on the table I locate the marker (vessel) on the map and the image of that vessel pops up on a sidebar on the right of the map as shown below:
The problem I have is that I should also visualize the image of the vessel, but unfortunately I only visualize a weird icon as shown below:
Below the code:
class Sidebar extends React.Component {
state = {
ships: []
};
async componentDidMount() {
let response = await Client.getEntries({
content_type: 'cashmanCards'
});
const ships = response.items.map((item) => {
const { name, slug, type, company, description, images, companylogo } = item.fields;
return {
name,
slug,
type,
company,
description,
images,
companylogo
};
});
this.setState({
ships
});
}
getFilteredShips = () => {
if (!this.props.activeShip) {
return this.state.ships;
}
return this.state.ships.filter((ship) => this.props.activeShip.name.toLowerCase() === ship.name.toLowerCase());
};
render() {
return (
<div className="map-sidebar">
{this.props.activeShipTypes}
<pre>
{this.getFilteredShips().map((ship) => {
console.log(ship);
return (
<Card className="mb-2">
<CardImg />
<CardBody>
<div className="row">
{/* <div className="column"> */}
<img className="image-sizing-primary" src={ship.companylogo} alt="shipImage" />
</div>
<div>
<img className="image-sizing-secondary" src={ship.images} alt="shipImage" />
</div>
<CardTitle>
<h3 className="thick">{ship.name}</h3>
</CardTitle>
<CardSubtitle>{ship.type}</CardSubtitle>
<CardText>
<br />
<h6>Project Details</h6>
<p>For a description of the project view the specification included</p>
</CardText>
<div class="btn-toolbar">
<SpecsButton />
<Link to="/vessels/Atchafalaya" className="btn btn-primary">
Go to vessel
</Link>
</div>
</CardBody>
</Card>
);
})}
</pre>
</div>
);
}
}
export default Sidebar;
What I have done so far:
1) I console.log() the problem that could be the cause of that weird icon and the result (the value) of the command was a strange path. I can confirm that the command is correct. Also I should say that those images are currently held by an external container called Contentful. Below the path after console log:
Am I missing something from the path?
I am not sure how to move on as all other checks seems correct and this one is the only one that is ringing some bells to me.
Thanks for pointing in the right direction for solving this issue.
#Emanuele , could you please try this instead ?
src = {ship.images.fields.file.url}
I'm trying to build a custom modal off this react carousel library
Basically, I'm at the point where the modal is implemented correctly, but I can't seem to find out how to wire the featured image on the modal to always be the same like the one which is currently also being featured in the carousel.
const Modal = ({ modal, items, handleModalFalse, currentIndex, featured }) => {
return (
<div className={modal ? "modal" : "hide"} onClick={handleModalFalse}>
{/* this only features the first image */}
{/* <img src={featured} /> */}
{/* shows every image on modal*/}
{items.map((item, i) => (
<div key={i} className="wrapper">
<img src={item} />
</div>
))}
</div>
);
};
These are all the handlers that power the Carousel.
I'm struggling to wire the featured image correctly (perhaps inside componentDidMount() ?)
class Gallery2 extends React.Component {
state = {
currentIndex: 0,
items: [
"https://homepages.cae.wisc.edu/~ece533/images/airplane.png",
"https://homepages.cae.wisc.edu/~ece533/images/baboon.png",
"https://homepages.cae.wisc.edu/~ece533/images/cat.png",
"https://homepages.cae.wisc.edu/~ece533/images/boat.png"
],
modal: false,
featured: undefined
};
// what should go here instead??
componentDidMount() {
this.setState({ featured: this.state.items[0] });
}
slideTo = i => console.log("clicked") || this.setState({ currentIndex: i });
onSlideChanged = e => this.setState({ currentIndex: e.item });
slideNext = () =>
this.setState({ currentIndex: this.state.currentIndex + 1 });
slidePrev = () =>
this.setState({ currentIndex: this.state.currentIndex - 1 });
handleEnlargeClick = () => {
this.setState({ modal: true });
};
handleModalFalse = () => {
this.setState({ modal: false });
};
render() {
return (
<>
<h3>React Alice Carousel</h3>
{/* MODAL */}
<Modal
modal={this.state.modal}
items={this.state.items}
handleModalFalse={this.handleModalFalse}
currentIndex={this.state.currentIndex}
featured={this.state.featured}
/>
<RenderGallery
items={this.state.items}
responsive={this.responsive}
onSlideChanged={this.onSlideChanged}
currentIndex={this.state.currentIndex}
/>
<button onClick={() => this.handleEnlargeClick()}>
click to enlarge
</button>
<RenderThumbs
items={this.state.items}
slideNext={this.slideNext}
slidePrev={this.slidePrev}
slideTo={this.slideTo}
responsive={this.responsive}
/>
</>
);
}
}
*******
You can see the full Carousel implementation and bug in action here on this code sandbox. Please feel free to fork it.
Right now my Modal only either shows the first image or all of them...
I understand why I currently only get either the first or all of the images, I just can't figure a solution for my issue.
How can I make the featured image on the Modal to be the same as the one currently on the carousel?
The issue in your code is that your modal is looping over all of the items, and displaying them when you click the "enlarge" button. To fix this, you just need to use the selectedIndex with your items variable to get the currently selected item.
Sandbox example: https://codesandbox.io/s/21p19wmpyy
Modal Code:
const Modal = ({ modal, items, handleModalFalse, currentIndex, featured }) => {
return (
<div className={modal ? "modal" : "hide"} onClick={handleModalFalse}>
{/* this only features the first image */}
{/* <img src={featured} /> */}
{/* shows every image on modal*/}
<div className="wrapper">
<img src={items[currentIndex]} />
</div>
</div>
);
};
I'm sure nothing is wrong with react-dropzone works great and when I drop a file, array shows in my console:
getInitialState() {
return{files: []}
},
onDrop(files) {
this.setState({files: files});
console.log(files);
},
render(){
var attachedFiles = this.state.files;
return(
{attachedFiles.map((file, idx) =>
<img key={idx} src={file.preview} />
)}
)
}
When two files are dropped, in console it shows as
>[File]
>[File]
But only the last file is shown. Am I not iterating correctly?
Edited:
I have noticed that my files state only shows one array no matter if I dropped more than one file.
As suggested in the comments, I think you'll need a return statement in your map function. Your render function also needs to return your data wrapped in a single parent node, something like:
render(){
var attachedFiles = this.state.files;
var imagesNodes = attachedFiles.map((file, idx) => {
return <img key={idx} src={file.preview} />;
});
return (
<div className="imagesList">
{imagesNodes}
</div>
);
}