Reputation: 537
I am relatively new to Reactjs so I might be missing something obvious:
I have a component (DisplayFlags.js) that displays country flags along with country names depending on a previously chosen continent. I have everything set up: all possible flag images exist locally, I also have a js object called 'myCountries' that maps each continent to its countries, and each country to its name + local flag image name. Here is a part of it:
const myCountries ={
"north-america": {
"US": {
"name": "United States",
"picPath": "flag-of-United-States.png"
},
"UM": {
"name": "United States Minor Outlying Islands",
"picPath": "flag-of-United-States-Minor-Outlying-Islands.png"
},
"CA": {
"name": "Canada",
"picPath": "flag-of-Canada.png"
},
"MX": {
"name": "Mexico",
"picPath": "flag-of-Mexico.png"
},
//etc
},
"south-america":{
"AR": {
"name": "Argentina",
"picPath": "flag-of-Argentina.png"
},
"BO": {
"name": "Bolivia",
"picPath": "flag-of-Bolivia.png"
},
//etc
}
}
What I am planning to do: loop through all the countries of a previously selected continent, and pass the "name" and "picPath" as props to another component, SingleCountry.js, who in turn displays them. My problem is with importing: I usually just write (example):
import randomImage from '../../img/icons/some-image-name.png'
And then use randomImage as the src of an img element in my component. In this case, is there a way to import an image from a path that is passed in props? Something like:
import flagImage from "../../img/flags/" + this.props.picPath
I understand that the above doesn't work because imports work outside of a component, and they don't have access to any kind of props. Can I import inside a component? Or should I totally drop this and import images in bulk in DisplayFlag.js then pass images one by one into SingleCountry.js?
Upvotes: 4
Views: 8045
Reputation: 6036
You can try with:
Using import
for browser and nodejs
const picture = (await import(`../path/to/file/${this.props.picPath}`)); // this is async
Using require
for browser and nodejs
const picture = require(`../path/to/file/${this.props.picPath}`); // this is sync
Using readFileSync
from fs
only for nodejs
const fs = require('fs')
// or: import fs from 'fs'
const file = fs.readFileSync(`../path/to/file/${this.props.picPath}`).toString()
Using readFile
from fs
only for nodejs
const fs = require('fs')
// or: import fs from 'fs'
const file = (await fs.readFile(`../path/to/file/${this.props.picPath}`)).toString()
Tip #1:
When you using require, it only can handle json and js files, but when you using import, it can handle svg, and other stuff. But you can apply some trick like:
// in tsconfig.json
"include": [
"./declarations.d.ts",
],
// in declaration.d.ts
declare module '*.png';
Tip #2:
When you wanna import images like png
, you should be define how it work with this:
declare module "*.png" {
const value: any;
export default value;
}
Tip #3
In javascript you can use Template Literals using ``
and ${}
.
const name = "John"
console.log(`Hello ${name}`);
Upvotes: 3
Reputation: 1728
You could have a file import all the images like
//images/index.js
import image1 from './image1.png'
import image2 from './image2.png'
.
.
export default {
image1,
image2,
.
.
}
you can access images dynamically from the object exported from here
import images from './images/index.js'
images['image1']
// or dynamically
let name = 'image2'
images[name]
Upvotes: 5
Reputation: 66
What first coming to my head is to create stateless component which will take your flag object and show tag with specific path. It won't import as react suggest but it will do the job :) Instead if u really want use react approches you could use require instead of import, checkout below question, I think it will satisfying you:
react native use variable for image file
Upvotes: 1