reactjs - 如何让 Next Image 组件与 Storybook 一起工作

标签 reactjs next.js storybook

我正在尝试关注 this教程并遇到无法加载使用 NextJs Image 组件的 CatCard 组件的问题

import Image from 'next/image';
import styles from './CatCard.module.css';

export interface ICatCard {
  tag: string;
  title: string;
  body: string;
  author: string;
  time: string;
}

const CatCard: React.FC<ICatCard> = ({ tag, title, body, author, time }) => {
  return (
    <div className={styles.container}>
      <div className={styles.card}>
        <div className={styles.card__header}>
          <Image
            src="/time-cat.jpg"
            alt="card__image"
            className={styles.card__image}
            width="600"
            height="400"
          />
        </div>
        <div className={styles.card__body}>
          <span className={`${styles.tag} ${styles['tag-blue']}`}>{tag}</span>
          <h4>{title}</h4>
          <p>{body}</p>
        </div>
        <div className={styles.card__footer}>
          <div className={styles.user}>
            <Image
              src="https://i.pravatar.cc/40?img=3"
              alt="user__image"
              className={styles.user__image}
              width="40"
              height="40"
            />
            <div className={styles.user__info}>
              <h5>{author}</h5>
              <small>{time}</small>
            </div>
          </div>
        </div>
      </div>
    </div>
  );
};

export default CatCard;


在尝试运行此错误时,我已尝试按照建议更新 next.config.js 文件

Invalid src prop (https://i.pravatar.cc/40?img=3) on `next/image`, hostname "i.pravatar.cc" is not configured under images in your `next.config.js`
See more info:

https://nextjs.org/docs/messages/next-image-unconfigured-host

/** @type {import('next').NextConfig} */
const nextConfig = {
  reactStrictMode: true,
  images: {
    domains: ['i.pravatar.cc'],
  },
};

module.exports = nextConfig;

而且我已经尝试根据 this thread 为故事书添加 storybook-addon-next 插件

没有运气。

故事书的 preview.js

import * as NextImage from 'next/image';
import '../styles/globals.css';

const BREAKPOINTS_INT = {
  xs: 375,
  sm: 600,
  md: 900,
  lg: 1200,
  xl: 1536,
};

const customViewports = Object.fromEntries(
  Object.entries(BREAKPOINTS_INT).map(([key, val], idx) => {
    console.log(val);
    return [
      key,
      {
        name: key,
        styles: {
          width: `${val}px`,
          height: `${(idx + 5) * 10}vh`,
        },
      },
    ];
  })
);

// Allow Storybook to handle Next's <Image> component
const OriginalNextImage = NextImage.default;

Object.defineProperty(NextImage, 'default', {
  configurable: true,
  value: (props) => <OriginalNextImage {...props} unoptimized />,
});

export const parameters = {
  actions: { argTypesRegex: '^on[A-Z].*' },
  controls: {
    matchers: {
      color: /(background|color)$/i,
      date: /Date$/,
    },
  },
  viewport: { viewports: customViewports },
};

故事书的 main.js

module.exports = {
  stories: ['../**/*.stories.mdx', '../**/*.stories.@(js|jsx|ts|tsx)'],
  /** Expose public folder to storybook as static */
  staticDirs: ['../public'],
  addons: [
    '@storybook/addon-links',
    '@storybook/addon-essentials',
    '@storybook/addon-interactions',
    'storybook-addon-next',
  ],
  framework: '@storybook/react',
  core: {
    builder: '@storybook/builder-webpack5',
  },
};

最佳答案

创建一个 VARIABLE src 然后通过“加载器”传递它

import Image from 'next/image';
import styles from './CatCard.module.css';

export interface ICatCard {
  tag: string;
  title: string;
  body: string;
  author: string;
  time: string;
}
const CatCard: React.FC<ICatCard> = ({ tag, title, body, author, time }) => {
  const srcGuy = `https://i.pravatar.cc/40?img=3`;
  const srcCat = '/time-cat.jpg';
  return (
    <div className={styles.container}>
      <div className={styles.card}>
        <div className={styles.card__header}>
          <Image
            loader={() => srcCat}
            src={srcCat}
            width={600}
            height={400}
            alt="card__image"
          />
        </div>
        <div className={styles.card__body}>
          <span className={`${styles.tag} ${styles['tag-blue']}`}>{tag}</span>
          <h4>{title}</h4>
          <p>{body}</p>
        </div>
        <div className={styles.card__footer}>
          <div className={styles.user}>
            <Image
              loader={() => srcGuy}
              src={srcGuy}
              width={40}
              height={40}
              alt="user__image"
              className={styles.user__image}
            />
            <div className={styles.user__info}>
              <h5>{author}</h5>
              <small>{time}</small>
            </div>
          </div>
        </div>
      </div>
    </div>
  );
};

export default CatCard;

关于reactjs - 如何让 Next Image 组件与 Storybook 一起工作,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/72107329/

相关文章:

reactjs - 如何在 React 中使用 JWT token 实现私有(private)路由

javascript - 简单 react 错误 : Can't use @material-ui/picker library in Next. js

apollo MockedProvider + Storybook 不起作用

javascript - Storybook 中的 Vuex 存储未定义

reactjs - 什么时候应该在 Material-UI 中使用 Typography?

html - 表格嵌套在表格单元格内

javascript - 不确定是否调用了 d3.json 中的回调

css - 自定义 Next.js 服务器的 MIME 类型错误

javascript - React/Next.js 如何在按钮点击时获取其他 Element 事件目标值

vuejs3 - 为 Quasar v2 配置故事书