1

The image I'm using in React Native uses a require statement for the source of the image. I want to change the source of the image so it is kind of of like switching out frames in an animation.

var module1 = './hello';
var module2 = './goodbye';

state = {
  module: module1 // will later be changed to module2
}

require(this.state.module);
sdfsdf
  • 5,052
  • 9
  • 42
  • 75
  • why would you want to change a required module? do they implement the same functions? then get rid of one of the modules and introduce a flag to the functions to change their behavior dynamically. – Simon Hänisch Jul 05 '16 at 15:49
  • I have an image that I want to replace the source of to animate by switching out the 'frames' – sdfsdf Jul 05 '16 at 18:14

3 Answers3

0

Require both and then use the correct one where you need it:

var hello = require('./hello');
var goodbye = require('./goodbye');

hello.myFunction();

// later:

goodbye.anotherFunction()
TimoStaudinger
  • 41,396
  • 16
  • 88
  • 94
0

I dont think it is a good programming style but it is possible. For example the modules look like this

exports.name = () => {
  console.log('modul1')
}

And the main file like this, it will work like expected

const modul1 = './modul1'
const modul2 = './modul2'

var modul = require(modul1)
modul.name() // -> modul1
modul = require(modul2)
modul.name() // -> modul2
Julian
  • 2,724
  • 1
  • 15
  • 21
0

I ended up just creating an object like this:

var frames = { '1': require('./assets/phase1.png'), '2': require('./assets/phase2.png'), '3': require('./assets/phase3.png'), '4': require('./assets/phase4.png'), }

and in my Image tag, I set the source attribute to this.state.frame and setState with a new key from frames like frames[imageIndex]. Luckily I didn't have too many images, but this isn't the most ideal solution.

EDIT: Another solution (which is more elegant and less verbose) is to create a drawable folder in android>app>src>main>res and drop all the images in the that folder. On iOS, you can drop all your images in ios>Appname>Images.xcassets.

From there, you can set the source of your images to {uri: this.state.imageFile} where this.state.imageFile is a string without the file extension and you can change them dynamically without having to require() each file.

sdfsdf
  • 5,052
  • 9
  • 42
  • 75
  • why do you require all images? why not create an array `frames = ['./assets/phase1.png', './assets/phase2.png', './assets/phase3.png', ...]` and then just `require(frames[this.state.frame])`? or if your image naming is like this, even easier: `require('./assets/phase' + this.state.frame + '.png')` – Simon Hänisch Jul 06 '16 at 12:38
  • Because that didn't work for some reason. I was not able to require() – sdfsdf Jul 06 '16 at 14:32
  • Just tried this in node.js and it worked: `var module = 'fs';` and `var fs = require(module);` I don't know what react does when requiring an image though... – Simon Hänisch Jul 06 '16 at 14:52
  • Probably because when you require an image file, there is no module.exports, or export default. I'll change the question title to be Image centric. – sdfsdf Jul 06 '16 at 17:02
  • That shouldn't have anything to do with how the string is passed to the `require()`. It is valid Javascript. Anyway it's a good idea to make it clear it's about requiring images. – Simon Hänisch Jul 06 '16 at 19:18
  • 1
    "Note that in order for this to work, the image name in require has to be known statically." Facebook confirms my instinct. https://facebook.github.io/react-native/docs/images.html#static-image-resources – sdfsdf Jul 07 '16 at 21:52
  • found an explanation here: http://stackoverflow.com/a/33917557/2897426 ... react creates a bundle of your scripts & assets, so require statements are resolved at bundle time and you can't use variable expressions as arguments. – Simon Hänisch Jul 08 '16 at 10:17
  • Just edited my answer so that you can just use the file name instead of having to require each image. – sdfsdf Jul 08 '16 at 17:24