Load images based on dynamic path in ReactJs
Asked Answered
S

5

22

I'm trying to display images in a shopping cart i'm making but its not showing up. Do i have to import each image? I know my paths are fine because it worked before.I think there might be something wrong in my product.js file but I can't figure it out.

Here is my Product.js

import React, { Component, PropTypes } from 'react';

class Product extends Component {
    handleClick = () => {
        const { id, addToCart, removeFromCart, isInCart } = this.props;

        if (isInCart) {
            removeFromCart(id);
        } else {
            addToCart(id);
        }
    }

    render() {
        const { name, price, currency, image, url, isInCart } = this.props;

        return (
            <div className="product thumbnail">
                <img src={image} alt="product" />
                <div className="caption">
                    <h3>
                        <a href={url}>{name}</a>
                    </h3>
                    <div className="product__price">{price} {currency}</div>
                    <div className="product__button-wrap">
                        <button
                            className={isInCart ? 'btn btn-danger' : 'btn btn-primary'}
                            onClick={this.handleClick}>
                            {isInCart ? 'Remove' : 'Add to cart'}
                        </button>
                    </div>
                </div>
            </div>
        );
    }
}

Product.propTypes = {
    id: PropTypes.number.isRequired,
    name: PropTypes.string.isRequired,
    price: PropTypes.number,
    currency: PropTypes.string,
    image: PropTypes.string,
    url: PropTypes.string,
    isInCart: PropTypes.bool.isRequired,
    addToCart: PropTypes.func.isRequired,
    removeFromCart: PropTypes.func.isRequired,
}

export default Product;

The data comes from this product.js

const data = [
    {
        id: 1,
        name: 'Reggae Blaster',
        price: 10,
        currency: 'GOLD',
        image: '../assets/blaster_1.png'
    },
    {
        id: 2,
        name: 'Juicy Blaster',
        price: 10,
        currency: 'GOLD',
        image: 'images/02.jpg'
    },
    {
        id: 4,
        name: 'Full Body Reggae Armor',
        price: 20,
        currency: 'GOLD',
        image: 'images/04.jpg'
    },
    {
        id: 6,
        name: 'Reggae Spikes Left',
        price: 5,
        currency: 'GOLD',
        image: 'images/06.jpg'
    },
    {
        id: 5,
        name: 'Reggae Spikes Right',
        price: 5,
        currency: 'GOLD',
        image: 'images/05.jpg'
    },
    {
        id: 3,
        name: 'Black Full Body Reggae Armor',
        price: 20,
        currency: 'GOLD',
        image: 'images/03.jpg'
    }
];

export default data;

I am pulling all the data except the images just don't show up

Shaynashayne answered 26/7, 2017 at 18:30 Comment(0)
N
34

Assuming that you are using webpack, you need to import the image in order to display it like

<img src={require('images/06.jpg')} alt="product" />

Now that your image data is dynamic, directly specifying the import path like

<img src={require(image)} alt="product" />

doesn't work.

However you can import the image by making use of template literals like

<img src={require(`${image}`)} alt="product" />

So your code will look like

render() {
    const { name, price, currency, image, url, isInCart } = this.props;

    return (
        <div className="product thumbnail">
            <img src={require(`${image}`)} alt="product" />
            <div className="caption">
                <h3>
                    <a href={url}>{name}</a>
                </h3>
                <div className="product__price">{price} {currency}</div>
                <div className="product__button-wrap">
                    <button
                        className={isInCart ? 'btn btn-danger' : 'btn btn-primary'}
                        onClick={this.handleClick}>
                        {isInCart ? 'Remove' : 'Add to cart'}
                    </button>
                </div>
            </div>
        </div>
    );
}

P.S. Also make sure that your image path is relative to the file you are importing them in.

Nonmetallic answered 26/7, 2017 at 18:36 Comment(5)
Hi Shubham Khatri, This approach solved my problem but I get next warning adding images dynamically: WARNING in ./index.html Module parse failed: Unexpected token (1:0) You may need an appropriate loader to handle this file type. | <!DOCTYPE html> | <html lang="en">Friend
@JuanReinaPascual, I guess you might have already solved this problem by now, but just to share, you need to configure your webpack config to load jpeg, svg file typesNonmetallic
Great stuff... This doesn't work: img src={require(filePath)}. This does works img src={require(`${filePath}`)}Cut
After searching for almost 2hrs, found this perfect answer. Using backtick is the key here - require(${image})Triboluminescent
@Shubham Khatri how do you deal with this if you are using a build tool like webpack in where the images are put to public directory directly? I get a browser error saying that the corresponding image is not found in that directory which is relative to the server..?Fenner
T
2

img src={require(${filePath})} -- working you also need to add default to get exact URL

img src={require(`${filePath}.default`)}
Tamatave answered 3/6, 2021 at 8:36 Comment(0)
S
1

I adding this comment so that future guys can benefit.

So the problem I faced was I had an array of people, and I needed to display the profile picture of each person

Solution

2 files :

  • data.js which contains an exported JSON object

  • main.js which has my react component

Step#1 : data.js

in data.js import all your local image asset files that you need. ex.

import ProfilePicN from "./ProfilePicN.jpg";

export default [
  {
    "name": "PersonN",
    "image": ProfilePicN 
  }
]

*important: no quotes around the import, quotes on everything else as they are all literals

Step#2:


      import data from "./data.
    
      .
      .
      .
    /*inside the react component*/
     {
       data.map((dataItem,key)=> {
          <img src={dataItem.image}>
       })
     }

Schlock answered 22/12, 2021 at 17:44 Comment(0)
N
0

You have to put those images in folder where your bundled application lives.

Neurogram answered 26/7, 2017 at 18:36 Comment(1)
how do you deal with this if you are using a build tool like webpack in where the images are put to public directory directly?Fenner
A
0

What helped me was that I immediately imported the pictures to an array of objects and entered a variable into the image link.

cakeData.js

import gallery1 from '../../images/cakes/gallery1.jpg';
import gallery2 from '../../images/cakes/gallery2.jpg';
import gallery3 from '../../images/cakes/gallery3.jpg';
import gallery4 from '../../images/cakes/gallery4.jpg';

export const Cakes = [
    {
        id: 1,
        name: 'cheesecake',
        description:'',
        link: gallery1,
    },
    {
        id: 2,
        name: 'honeycake',
        description:'',
        link: gallery2,
    },
    {
        id: 3,
        name: 'applecake',
        description:'',
        link: gallery3,
    },
    {
        id: 4,
        name: 'cupcake',
        description:'',
        link: gallery4,
    },
]`

Cards.js

import React from 'react';
import './Card.css';

function Card(card) {
     return (
        <figure className='card'>
            <img
                className='card__image'
                src={card.link}
                alt={card.name}
                title={card.name}
                
            />
        </figure>
    );
}

export default Card;
Aglitter answered 5/4 at 5:16 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.