#reactjs #typescript #material-ui #next.js
#reactjs #typescript #материал-пользовательский интерфейс #next.js
Вопрос:
Как я могу перейти post.mainImage
к backgroundImage
стилю.
Вот мой код;
import React from 'react';
import { Post } from '../interfaces';
import { makeStyles, createStyles, Theme } from '@material-ui/core/styles';
import Container from '@material-ui/core/Container';
type Props = {
post: Post;
}
const useStyles = makeStyles<Theme, Props>((theme: Theme) =>
createStyles({
root: {
maxWidth: '100%',
backgroundImage: ({ post }) => post.mainImage
},
date: {
margin: theme.spacing(1),
marginLeft: theme.spacing(2)
},
heroimage: {
maxWidth: '100%',
height: 'auto',
objectFit: 'cover'
}
})
);
export default function HeroPost({ post }: Props) {
const classes = useStyles({ post });
return (
<Container className={classes.root}>
<img alt={post.title} src={post.mainImage} className={classes.heroimage} />
</Container>
);
}
Приведенный ниже код прошел без проблем из linter. Но все еще не удается получить backgroundImage
значение спереди.
Комментарии:
1. Вы должны создать минимально воспроизводимый пример (предпочтительно на codesandbox )
Ответ №1:
Вы можете указать переменные типа для вызова makeStyles
(обратите внимание, что первая должна быть типом темы, а вторая — типом реквизита):
type Props = {
post: Post;
};
const useStyles = makeStyles<Theme, Props>(theme =>
createStyles({
root: {
maxWidth: '100%',
backgroundImage: ({ post }) => `url("${post.mainImage}")`
},
// ...
})
);
export default function HeroPost({ post }: Props) {
const classes = useStyles({ post });
return (
// ...
);
}
Комментарии:
1. Я знаю об этом взломе, но, как упоминал @Yatrix выше, можно передать с помощью JS, но не смог найти решение для TypeScript.
2. Изменен мой ответ — это должно устранить проблему с TS.
3. Это все еще не работает. Я использовал точку останова, чтобы проверить,
post
определена ли она наbackgroundImage: ({ post }) => post.mainImage
. К сожалению, это = undefined.5. Похоже, что Typescript теряет предполагаемый тип при указании двух первых универсальных типов. Мой способ — сначала объявить стили как отдельный const (
styles
), а затем установить третий общий дляmakeStyles
наkeyof typeof styles
.
Ответ №2:
Вам нужно передать реквизит с его типом непосредственно туда, где вы хотите получить к нему доступ. Это должно работать нормально.
type BgProps = {
mainImage: string;
}
const useStyles = makeStyles<Theme, Props>((theme: Theme) =>
createStyles({
root: {
maxWidth: '100%',
backgroundImage: (props: BgProps) => props.mainImage
},
date: {
margin: theme.spacing(1),
marginLeft: theme.spacing(2)
}
})
);
Ответ №3:
Попробуйте это: useStyles — это хук, который может принимать реквизит в параметрах и возвращать метод useStyles.
const useStyles = (props: Props) => {
const {post} = props;
return makeStyles(theme => ({
root: {
maxWidth: '100%',
backgroundImage: post.mainImage
},
}))
}
Ответ №4:
Вы получаете доступ к реквизитам следующим образом,
backgroundImage: props => props.backgroundImageProp
Комментарии:
1. Это не работает. Должно быть связано с TypeScript.
Ответ №5:
Попробуйте это с помощью Typescript :
const useStyles = makeStyles(theme => ({
root: ({mainImage}: {mainImage: string}) => ({
...
backgroundImage: mainImage
})
})
const component: React.FC => {
const classes = useStyles({mainImage})
return ...
}