【问题标题】:React Native - Dynamic Image SourceReact Native - 动态图像源
【发布时间】:2017-05-16 21:40:00
【问题描述】:

我正在尝试使用 map 方法遍历 SOURCE 数组,但我不断收到此错误:

Unknown named module: '../images/one.jpeg'

有人知道为什么会这样吗? require中的文件路径肯定是正确的。

var SECTIONS = [
  {
    title: 'One',
    fileName: 'one.jpeg',
  },
  {
    title: 'Two',
    fileName: 'two.jpeg',
  },
  {
    title: 'Three',
    fileName: 'three.jpeg',
  },
  {
    title: 'Four',
    fileName: 'four.jpeg',
  },
];


{SECTIONS.map((section, i) => (
   <CategoryCard
     key={i}
     source={require(`../images/${section.fileName}`)}
     title={section.title}
   />
))}

【问题讨论】:

  • 我认为你可能给出了错误的路径。

标签: javascript arrays react-native


【解决方案1】:

我认为这是不可能的,因为 react native 需要提前知道要捆绑什么 (AFAIK)。但是,您可以require 数组中的所有文件:

var SECTIONS = [
  {
    title: 'One',
    file: require('../images/one.jpeg'),
  },
  {
    title: 'Two',
    file: require('../images/two.jpeg'),
  },
  {
    title: 'Three',
    file: require('../images/three.jpeg'),
  },
  {
    title: 'Four',
    file: require('../images/four.jpeg'),
  },
];


{SECTIONS.map((section, i) => (
   <CategoryCard
     key={i}
     source={section.file}
     title={section.title}
   />
))}

【讨论】:

  • 是的,这是我能想到的唯一其他解决方案。似乎不是最佳选择,但它现在可以工作。谢谢!
  • 当使用这个我得到:&lt;?&gt;PNG ... unexpected character &lt;?&gt;。它包括图像并尝试将图像作为文件读取。 &lt;?&gt; 是一个无法识别的字符,而不是实际的三个字符 .
【解决方案2】:

尝试使用类似的直接 URL 在单独的浏览器中打开文件

http:///images/one.jpg

你也可以这样做:

使用 react 显示动态图像的一个工作示例:

Example Click Here

【讨论】:

  • 这会在原生反应中起作用吗?该示例在网络浏览器中,这是一种非常不同的动物。
【解决方案3】:

有一个可行的解决方案,虽然不推荐用于大图像,但非常适合(很多)小图像。

步骤:

  1. 将图标转换为 base64 字符串。
  2. 创建一个 JSON 文件,其中文件名作为键,base64 字符串作为值。 (您也可以将它们存储到本地数据库中)

例如 图像数据.json

{

"icon1": "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAFAAAABQ.......==",
"icon2": "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAFAAAABQ.......=="

}

3.将json文件动态导入到需要图片的地方。

例如

const imageData = require("./images/ImageData.json")

4:在运行时获取/生成密钥/文件名。并获取图片来源。

例如

const imageSrc = imageData[keyname]

5:运行时动态生成图片。

例如

<Image style={{ width: 70, height: 70, resizeMode: Image.resizeMode.contain }} source={ uri: imageSrc } />

完成..

额外.. 编写了一个辅助 python 脚本来自动创建 json 文件。

import base64
import os

directory = os.fsencode('.')

with open('ImagesData.json', 'wb') as jsonFile:
    jsonFile.write(bytes('{', 'utf-8'))

    written = False

    for file in os.listdir(directory):
        filename = os.fsdecode(file)

        if filename.endswith('.png'):
            with open(filename, "rb") as image_file:
                if written:
                    jsonFile.write(bytes(',\n','utf-8'))
                encoded_string = base64.b64encode(image_file.read())
                jsonFile.write(bytes(('"' +filename+ '":'), 'utf-8'))
                jsonFile.write(bytes('"data:image/png;base64,', 'utf-8') + encoded_string + bytes('"', 'utf-8'))
                written = True

    jsonFile.write(bytes('}', 'utf-8'))
  1. 将脚本复制到镜像文件夹并运行脚本(需要python 3.6)。
  2. 将创建一个 json 文件,其中图像名称为键,base64 字符串为值。
  3. 将文件复制到项目中并使用(之后您可以删除图像)。
  4. 使用上面提到的json文件。

【讨论】:

    【解决方案4】:

    您不能使用动态链接。我发现解决这个问题的最好方法是:

    var SECTIONS = {
      One: {
        title: 'One',
        file: require('../images/one.jpeg'),
      },
      Two: {
        title: 'Two',
        file: require('../images/two.jpeg'),
      },
      Three: {
        title: 'Three',
        file: require('../images/three.jpeg'),
      },
      Four: {
        title: 'Four',
        file: require('../images/four.jpeg'),
      },
    };
    
    
    {SECTIONS.map((section, i) => (
       <CategoryCard
         key={i}
         source={section.file}
         title={section.title}
       />
    ))}
    

    这样,你可以只使用文件,如果你有某种动态图像选择,你可以使用这样的东西

    <Image source={SECTIONS[image.type]} />
    

    【讨论】:

      【解决方案5】:

      我有同样的问题,但我的情况有点不同。我有一系列需要动态图像的不同对象。我已经在映射数组,但我需要根据名称将图像与该数组匹配。这有点hacky,但这就是我的做法。

      首先,在我的父组件中,我创建了一个函数来为我的对象数组呈现一个组件。我将对象数据传递给一个名为“对象”的道具。

      在我的例子中,我知道我的数据是什么,我需要将相应的图像与从我从中获取数据的外部 api 中提取的对象相匹配。

      renderObjects() {
      return this.state.objects.map(object => (
        <ObjectListDetail
          key={object.id}
          next
          props={this.props}
          object={object}
        />
      ));
      }
      

      在我的 ObjectListDetail 组件中,我创建了一个名为 icons 的变量,它是另一个对象数组。这一次,我创建了一个 name 属性,该属性将匹配从父级传递给组件的对象,然后有一个名为 source 的第二个键,我在其中提供了图像的路径。事情是这样的。

      var icons = [
      { name: "BTC", source: Images.btc },
      { name: "ETH", source: Images.eth },
      { name: "ETC", source: Images.etc },
      { name: "ZRX", source: Images.zrx },
      { name: "USDC", source: Images.usdc },
      { name: "LTC", source: Images.ltc },
      { name: "BCH", source: Images.bch },
      { name: "USD", source: Images.usd }
      ];
      

      注意 *** 我已经为整个应用程序将所有图像放入一个单独的文件中,并将它们导入顶部。

      然后我创建了一个名为 imgSrc 的变量并过滤结果以匹配我传递给子组件的对象的名称。

      var imgSrc = icons.filter(
      icon => icon.name === props.wallet.name
      )
      

      然后我创建了一个 Image 组件,并在源需求中调用了过滤器的结果并将其指向源。

        <Image source={imgSrc[0].source} />
      

      这就是我在应用程序中实现动态图像渲染的方式。

      这可能不是最好的做事方式,我对此还是有点陌生​​,但我喜欢任何批评

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2021-11-15
        • 2017-04-03
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2019-05-02
        • 2016-06-22
        相关资源
        最近更新 更多