【问题标题】:Gatsby: set an image background through frontmatter, GraphQl and Styled-componentsGatsby:通过frontmatter、GraphQl和Styled-components设置图片背景
【发布时间】:2019-07-11 07:10:49
【问题描述】:

我知道这个问题听起来有点复杂,但事实并非如此。
我尽量用简单的方式解释一下:

  • 我正在为我的 Gatsby 网站的主页制作博客文章列表。
  • 列表由“框”组成,链接到帖子的每个框都有一个背景图像。

  • 我将此背景图像传递给样式组件,它从我插入主 元素中的 prop 值获取图像(您将找到示例下)。

  • 它工作正常,直到我尝试使用 src 下本地文件夹中的图像(而不是使用我简单放在 frontmatter 上的在线链接)。


这是我过去所做的工作:
我把图片的url放在markdown文件的frontmatter上:

---
slug: "/post/my-post"
 [...]
imghero: "https:/path/to/image-online.jpg" 
---

然后用graphql查询:

const LISTING_QUERY = graphql`
        query BlogPostListing {
            allMarkdownRemark(limit: 10, sort: {
                order: DESC,
                fields: [frontmatter___date]
            }) {
            edges {
                node {
                excerpt
                frontmatter {
                    title
                    slug
                    date(formatString: "MMMM DD, YYYY")
                    imghero
                }
                }
            }
            }
        }
`

之后我将 {node.frontmatter.imghero} 插入到主 div 的一个道具上:

const Listing = () => (
    <StaticQuery 
        query={LISTING_QUERY} 
        render={({allMarkdownRemark}) => ( 
            allMarkdownRemark.edges.map(({node}) => (
                <Article img_background={node.frontmatter.imghero} key={node.frontmatter.slug}>
                [... etc ...]
                </Article>
            ))
        )}
    />
)

export default Listing

最后我在 styled-component 中调用了 img_background 属性:

const Article = styled.article`
    background-image: url(${props => props.img_background};);
    [... etc ...]
`

此方法有效。


现在我想从我的“图像”文件夹中获取图像,而不是从随机 url。

  • 我安装了 gatsby-remark-images
  • 在 gatsby-config.js 上设置它,并将一些图像的路径放在 frontmatter 上。
  • 使用http://localhost:8000/___graphql 测试所有内容(并且有效)
  • 通过graphql插入附加查询:

    [...]
    frontmatter {
    date(formatString: "DD MMMM, YYYY")
    title
    imghero
    hero {
        childImageSharp{
            fluid(maxWidth: 630) {
                ...GatsbyImageSharpFluid
            }
        }
    }
    [...]
    
  • 我用新路径修改了组件上的节点:

    <Article img_background={node.frontmatter.hero.childImageSharp.fluid} [...]> 
        [...] 
    </Article>
    
  • Gatsby Develop 编译正常。

但是我的主页完全是白色的。
浏览器控制台显示 node.frontmatter.hero 为“null”。 我不知道还能做什么。

感谢您的帮助。

【问题讨论】:

    标签: graphql markdown gatsby styled-components yaml-front-matter


    【解决方案1】:

    我认为需要更多信息来解决您的问题,您列出的所有内容本身都没有错误。然而,很多人都被 gatsby 中的图像处理绊倒了,我正在写一个检查清单。应该是通用的,但我认为 5、8、9、12 号可能会帮助您找到问题所在。


    使用图像与gatsby-transformer-remark + gatsby-transformer-sharp 故障排除

    设置

    1. 是否有任何错误?有时尽管出现问题,gatsby 仍会成功编译。检查控制台是否有任何...红色的东西。
    2. 您是否重新启动gatsby,即重新打开和关闭?如果您怀疑它们有问题,请尝试删除缓存和公用文件夹(.cachepublic)。
    3. 您是否在gatsby-source-filesystem 中列出了您的图像文件夹或其任何父文件夹?
    4. 在您的frontmatter 中,图像的路径relative 是否与markdown 文件本身有关?即路径以点 ./relative/path/to/image.png 开头
    5. 是否所有降价在 frontmatter 中都有 hero 字段?如果文件没有 hero 字段,则为 null
    6. 如果 frontmatter 中的图片路径不是相对路径或未链接到文件,则会将其视为常规字符串。

    查询和片段

    1. 您的查询有效吗?在http://localhost:8000/___graphql 中测试您的查询。确保图像字段显示为文件节点。尝试一些简单的事情,例如
    query {
      allMarkdownRemark {
        frontmatter {
          title
          hero {
            id
            name  <-- just enough to know the file exists
          }
        }
      }
    }
    

    如果您的hero 显示为字符串,则说明有问题,请再次检查设置。

    1. 您使用的是片段吗?目前无法在 graphiql 工具中测试片段,因此您可能需要找到该片段的定义并手动对其进行测试。这是the default ones that come with gatsby-transformer-sharp 及其定义的列表。

    2. 如果您使用的是自定义片段,请确保在某处定义并导出它。

    用法

    1. 如果图像未显示在浏览器中,请检查并尝试查找代替图像显示的内容。
    2. 你在使用gatsby-image吗?如果是这样,请确保您传递了可以使用的东西。
    3. 确保您的图像组件接收到应有的内容。如果您的组件需要路径,请不要传入对象,例如片段的结果。

    一些旁注

    • gatsby-remark-images 只处理 markdown 图像和 html &lt;img&gt; 中的相对链接,因此如果您的图像位于 frontmatter 中,它不会做任何事情。

    【讨论】:

    • 非常感谢您的回答!我解决了这个问题,它是不。 5!确实,浏览器上的控制台谈到了“空”问题。你知道有没有什么方法可以告诉 gatsby,如果 frontmatter 中没有英雄,就不要放任何图片吗?
    • 很高兴它有帮助!当然,您至少可以在 2 个地方这样做:(1)​​您的样式组件:background: ${({ img }) =&gt; img || 'fallbackImage.png'}; (b) 您的模板:&lt;div&gt;{ node.frontmatter.img &amp;&amp; &lt;ImageComponent img={...}&gt; }&lt;div&gt;。你也可以修改gatsby-node.js或者传入一个自定义的frontmatter解析器,但这可能太多了
    • 所以可以在样式组件上使用后备图像吗? background-image: url(${props =&gt; props.img_background} || 'fallbackImage.png');应该不错吧?我会尝试两者,因为我认为问题不在于样式组件。确实,使用第一种方法(在 frontmatter 上放置一个简单的图像链接)没有问题并且有效。当我开始查询一些 childImageSharp { ... } 时出现问题。 PS:gatsby-node.js的方式应该如何?
    • 我尝试了您建议的两种方法,但不幸的是控制台一直告诉我这是我尝试的第一个方法:background-image: url(${props =&gt; props.img_background || 'some-random-image-online.jpg'}); 并且页面以某种方式呈现,但框的所有内容都是白色的。这是第二种方法:&lt;Article {node.frontmatter.hero.childImageSharp &amp;&amp; img_background=node.frontmatter.hero.childImageSharp.fluid.src } 在启动 gatsby 开发时,这也会在编译时给我带来错误。我将尝试获取gatsby-node.js 选项的一些信息。
    • 嘿@圣地亚哥!抱歉,我以为您的意思是使用后备图片,这有点不同(当天有点晚了,我需要更多的咖啡)。您需要检查 node.frontmatter.hero 是否为 null - 如果该字段丢失,尝试访问 childImageSharp 将引发错误。另外,看起来你的 jsx 语法有点错误——你必须在元素标签之间做空检查,比如&lt;div&gt;{ node.frontmatter.hero &amp;&amp; &lt;Article {img_background=...}&gt; }&lt;/div&gt;。随意提出一个新问题,我相信很多人超过react.js标签可以帮助你!
    猜你喜欢
    • 1970-01-01
    • 2020-09-05
    • 2018-06-09
    • 2019-09-25
    • 2021-04-04
    • 2020-05-29
    • 1970-01-01
    • 2023-03-25
    • 2013-12-02
    相关资源
    最近更新 更多