如何使用 gatsby-image 显示图像而不进行裁剪?
Posted
技术标签:
【中文标题】如何使用 gatsby-image 显示图像而不进行裁剪?【英文标题】:How to display images without cropping using gatsby-image? 【发布时间】:2019-12-23 19:42:43 【问题描述】:实时示例(图片可能加载缓慢):https://suhadolnik-photo.surge.sh/portreti
我正在使用 GatsbyJS 制作一个摄影网站,并使用以下模板作为我一直在更改的基础网站:https://github.com/LekoArts/gatsby-starter-portfolio-emilia
作为 graphql 的新手,在用户单击卡片以显示“肖像”子页面后,我遇到了显示图像的问题。这些图像都以我不想要的固定宽度和高度显示。我需要用它们的原生宽度和高度显示它们,只需调整大小以适应网格。
我尝试更改 project.js
文件中的 graphql 查询,在该文件中将 maxWidth: 1600
设置为无济于事,以及在查询的下方设置了 resize(width: 800)
。后来我发现通过开发工具更改gatsby-image-wrapper
上的margin
给了我预期的结果,但这需要更改核心gatsby-image
插件并且必须单独为每个图像手动更改margin
,这不是解决办法。
project.js
import React from 'react'
import Img from 'gatsby-image'
import PropTypes from 'prop-types'
import graphql from 'gatsby'
import styled from 'styled-components'
import Layout, ProjectHeader, ProjectPagination, SEO from '../components'
import config from '../../config/site'
const BG = styled.div`
background-color: $props => props.theme.colors.bg;
position: relative;
padding: 2rem 0 0 0;
`
const OuterWrapper = styled.div`
padding: 0 $props => props.theme.contentPadding;
margin: -10rem auto 0 auto;
`
const InnerWrapper = styled.div`
position: relative;
max-width: $props => `$props.theme.maxWidths.projectpx`;
margin: 0 auto;
`
const Grid = styled.div`
display: grid;
grid-template-columns: repeat($props => props.theme.gridColumnsProject, 1fr);
grid-gap: 20px;
@media (max-width: 768px)
grid-template-columns: 1fr;
`
const Project = ( pageContext: slug, prev, next , data: project: postNode, images ) =>
const project = postNode.frontmatter
return (
<Layout customSEO>
<SEO postPath=slug postNode=postNode postSEO />
<ProjectHeader
name=config.name
date=project.date
title=project.title
areas=project.areas
text=postNode.body
/>
<BG>
<OuterWrapper>
<InnerWrapper>
<Grid>
images.nodes.map(image => (
<Img
alt=image.name
key=image.childImageSharp.fluid.src
fluid=image.childImageSharp.fluid
style= margin: '2rem 0'
/>
))
</Grid>
</InnerWrapper>
<ProjectPagination next=next prev=prev />
</OuterWrapper>
</BG>
</Layout>
)
export default Project
Project.propTypes =
pageContext: PropTypes.shape(
slug: PropTypes.string.isRequired,
next: PropTypes.object,
prev: PropTypes.object,
),
data: PropTypes.shape(
project: PropTypes.object.isRequired,
images: PropTypes.object.isRequired,
).isRequired,
Project.defaultProps =
pageContext: PropTypes.shape(
next: null,
prev: null,
),
export const pageQuery = graphql`
query($slug: String!, $absolutePathRegex: String!)
images: allFile(
filter:
absolutePath: regex: $absolutePathRegex
extension: regex: "/(jpg)|(png)|(tif)|(tiff)|(webp)|(jpeg)/"
sort: fields: name, order: ASC
)
nodes
name
childImageSharp
fluid(maxWidth: 1600, quality: 90)
...GatsbyImageSharpFluid_withWebp
project: mdx(fields: slug: eq: $slug )
body
excerpt
parent
... on File
mtime
birthtime
frontmatter
cover
childImageSharp
resize(width: 800)
src
date(formatString: "DD.MM.YYYY")
title
areas
`
Card.js
父组件:
import React from 'react'
import styled from 'styled-components'
import PropTypes from 'prop-types'
import useSpring, animated, config from 'react-spring'
import rgba from 'polished'
import Img from 'gatsby-image'
import Link from 'gatsby'
const CardItem = styled(Link)`
min-height: 500px;
position: relative;
box-shadow: 0 20px 40px rgba(0, 0, 0, 0.3), 0 15px 12px rgba(0, 0, 0, 0.2);
display: flex;
flex-direction: column;
justify-content: flex-end;
color: $props => props.theme.colors.color;
transition: all 0.3s ease-in-out;
&:hover
color: white;
transform: translateY(-6px);
@media (max-width: $props => props.theme.breakpoints.s)
min-height: 300px;
`
const Cover = styled.div`
width: 100%;
height: 100%;
position: absolute;
`
const Content = styled.div`
padding: 1rem;
position: relative;
transition: all 0.6s cubic-bezier(0.68, -0.55, 0.265, 1.55);
opacity: 0;
background: $props => rgba(props.theme.colors.link, 0.65);
height: 0;
$CardItem:hover &
opacity: 1;
height: 120px;
`
const Bottom = styled.div`
margin-top: 0.5rem;
display: flex;
align-items: center;
font-size: 0.85rem;
div:first-child
margin-right: 1rem;
`
const Name = styled.h2`
margin-bottom: 0;
margin-top: 0;
`
const Card = ( path, cover, date, areas, title, delay ) =>
const springProps = useSpring(
config: config.slow,
delay: 200 * delay,
from: opacity: 0, transform: 'translate3d(0, 30px, 0)' ,
to: opacity: 1, transform: 'translate3d(0, 0, 0)' ,
)
return (
<animated.div style=springProps>
<CardItem to=path>
<Cover>
<Img fluid=cover />
</Cover>
<Content>
<Name>title</Name>
<Bottom>
<div>date</div>
<div>
areas.map((area, index) => (
<React.Fragment key=area>
index > 0 && ', '
area
</React.Fragment>
))
</div>
</Bottom>
</Content>
</CardItem>
</animated.div>
)
export default Card
Card.propTypes =
path: PropTypes.string.isRequired,
cover: PropTypes.object.isRequired,
date: PropTypes.string.isRequired,
areas: PropTypes.array.isRequired,
title: PropTypes.string.isRequired,
delay: PropTypes.number.isRequired,
我希望图像以其原始宽度和高度显示,但会调整大小以适应网格。在下面提供有关它现在的外观和预期结果的可视化表示。 Current result 和 expected result
干杯!
【问题讨论】:
你有一个可行的例子吗? 我能提供的最好的就是我使用过的模板的演示页面:emilia.lekoarts.de 你没有做一些改变吗? 我添加了一个现场演示:suhadolnik-photo.surge.sh/portreti 【参考方案1】:从主页上的封面组件中删除height:100%
和position:absolute
。
const Cover = styled.div`
width: 100%;
`
另外,如果您不知道,您可以将 style
和 imgStyle
属性传递给 Gatsby image to change it's css.
| style | object | Spread into the default styles of the wrapper element |
| imgStyle | object | Spread into the default styles of the actual img element |
| placeholderStyle | object | Spread into the default styles of the placeholder img element |
因此,在您的项目模板中,您可以像这样更改对象适合样式:
<Img
alt=image.name
key=image.childImageSharp.fluid.src
fluid=image.childImageSharp.fluid
imgStyle= objectFit: 'contain'
/>
【讨论】:
这仅修复了主页上的问题,而不是单个项目页面上的问题。 添加imgStyle= objectFit: 'contain'
解决了这个问题。另外我不知道图像可以采用样式,所以也谢谢你!
酷。是的,它就埋在文档的底部,所以通常不会有很多人知道gatsby-image
。以上是关于如何使用 gatsby-image 显示图像而不进行裁剪?的主要内容,如果未能解决你的问题,请参考以下文章
gatsby-image:如何将处理后的图像导入 css 并与 background-image 属性一起使用