Я работаю с Docusaurus, который предоставляет siteConfig.js в качестве реквизита для конфигурации. Таким образом, я должен использовать этот реквизит для создания компонентов моего сайта. Рабочий код отформатирован так:

const React = require("react");

class SamplePage extends React.Component {
  render() {
    const siteConfig = this.props.config;
    return <div>{siteConfig.title}</div>;
  }
}

module.exports = SamplePage;

У меня есть другой сегмент рабочего кода, показанный в этом вопрос, но он использует другую настройку, где const {useState} = React; используется вместо const React = require("react"); и <div id="root"> с ReactDOM.render(<SamplePage/>, document.getElementById("root")); на месте из module.exports = SamplePage;. Я понимаю, что это позволяет запускать фрагменты кода на SE, но не показывает мне, как должны работать импорт и экспорт в контексте этого проекта Docusaurus. Я хочу включить сегмент кода в React.Component или иным образом создать этот компонент, чтобы использовать ловушку useState с настройками конфигурации, чтобы утверждать или отклонять атрибут isOpen в 3 detail теги, используя 2 button (s) для управления ловушкой:

const {useState} = React;

const SamplePage = () => {
    const [isOpen, setIsOpen] = React.useState(false); 

    return (
        <div>
            <details open={isOpen}>
                <summary>
                    First text detail.
                </summary>
                <p>testing</p>
            </details>
            <details open={isOpen}>
                <summary>
                    Second text detail.
                </summary>
                <p>testing</p>
            </details>
            <details open={isOpen}>
                <summary>
                    Third text detail.
                </summary>
                <p>testing</p>
            </details>

            <button onClick={() => setIsOpen(false)}>Open All Details.</button>
            <button onClick={() => setIsOpen(true)}>Close All Details.</button>
        </div>
    );
  }

ReactDOM.render(<SamplePage/>, document.getElementById("root"));

Для фрагмента кода:

<div id="root"></div>

<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.9.0/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.9.0/umd/react-dom.production.min.js"></script>

Мой вопрос заключается в том, как объединить эти сегменты кода. Я пытался сконструировать этот компонент разными способами, но я не могу заставить button (s) запустить эффект onClick(). Например, я попробовал:

const React = require("react");

const SamplePage, {useState} = () => {
  const [isOpen, setIsOpen] = React.useState(false); 
  const siteConfig = this.props.config;

  return (
      <div>
          <details open={isOpen}>
              <summary>
                  First text detail.
              </summary>
              <p>testing</p>
          </details>
          <details open={isOpen}>
              <summary>
                  Second text detail.
              </summary>
              <p>testing</p>
          </details>
          <details open={isOpen}>
              <summary>
                  Third text detail.
              </summary>
              <p>testing</p>
          </details>

          <button onClick={() => setIsOpen(false)}>Open All Details.</button>
          <button onClick={() => setIsOpen(true)}>Close All Details.</button>
      </div>
  );
}

module.exports = SamplePage;

Конечно, это вызывает «недопустимый вызов ловушки», поскольку я не могу фактически использовать ловушку useState в моей текущей установке. Я получаю неожиданные токены и ошибки ссылок во всех других моих конструкциях.

0
Lichtung 28 Окт 2019 в 23:32

2 ответа

Лучший ответ

Вы должны перевернуть, что вы правы / ложны в ваших кликах (открыть должно быть верно)

Имейте в виду, что ваш 'open' onClick прекрасно открывает раскрывающиеся списки, но 'close' onClick закрывает раскрывающиеся списки только в том случае, если для 'open' onClick устанавливается состояние true первый

Если вам нужно экспортировать это вместо рендеринга в DOM (и вы не можете / не хотите переходить на операторы импорта ES6 в другом месте), тогда измените ReactDom.render() на:

module.exports = SamplePage;

Полный пример:

const React = require('react')
const {useState} = React;

const SamplePage = (props) => {
    const [isOpen, setIsOpen] = useState(false); 
    const siteConfig = props.config

    return (
        <div>
            <details open={isOpen}>
                <summary>
                    First text detail.
                </summary>
                <p>testing</p>
            </details>
            <details open={isOpen}>
                <summary>
                    Second text detail.
                </summary>
                <p>testing</p>
            </details>
            <details open={isOpen}>
                <summary>
                    Third text detail.
                </summary>
                <p>testing</p>
            </details>

            <button onClick={() => setIsOpen(true)}>Open All Details.</button>
            <button onClick={() => setIsOpen(false)}>Close All Details.</button>
        </div>
    );
  }

module.exports = SamplePage;

Запускаемый фрагмент:

// const React = require('react')
const {useState} = React; //refer to above note

const SamplePage = (props) => {
    const [isOpen, setIsOpen] = useState(false);
    const siteConfig = props.config

    return (
        <div>
            <details open={isOpen}>
                <summary>
                    First text detail.
                </summary>
                <p>testing</p>
            </details>
            <details open={isOpen}>
                <summary>
                    Second text detail.
                </summary>
                <p>testing</p>
            </details>
            <details open={isOpen}>
                <summary>
                    Third text detail.
                </summary>
                <p>testing</p>
            </details>

            <button onClick={() => setIsOpen(true)}>Open All Details.</button>
            <button onClick={() => setIsOpen(false)}>Close All Details.</button>
        </div>
    );
  }

ReactDOM.render(<SamplePage/>, document.getElementById("root"));
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.8.4/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.8.4/umd/react-dom.production.min.js"></script>

<div id="root"></div>
1
Willman.Codes 30 Окт 2019 в 16:02

Я думаю, что вы смешиваете разрушение объектов с импортом. Вот разбивка того, что вы должны делать:

// this line imports the react library, which we need in order to
// export a JSX component
const React = require("react");

// this line pulls the useState function out of the React library
// using object destructuring
const { useState } = React;
// it is the same as const useState = React.useState

// we dont need to pass useState in as a prop because its already
// imported in the same file
const SamplePage = props => {
  // and here we don't need to call React.useState because it has been
  // separated into its own variable
  const [isOpen, setIsOpen] = useState(false); 
  const siteConfig = props.config; // functional components don't use this

  return (
      <div>
          <details open={isOpen}>
              <summary>
                  First text detail.
              </summary>
              <p>testing</p>
          </details>
          <details open={isOpen}>
              <summary>
                  Second text detail.
              </summary>
              <p>testing</p>
          </details>
          <details open={isOpen}>
              <summary>
                  Third text detail.
              </summary>
              <p>testing</p>
          </details>

          <button onClick={() => setIsOpen(false)}>Open All Details.</button>
          <button onClick={() => setIsOpen(true)}>Close All Details.</button>
      </div>
  );
}

module.exports = SamplePage;

Позвольте мне знать, если у вас есть какие-либо другие вопросы.

< Сильный > ИЗМЕНИТЬ

Я добавил в функцию параметр props и случайно пропустил это. Кроме того, при использовании функциональных компонентов вы не используете ключевое слово this при доступе к реквизиту, просто вызывайте его самостоятельно.

1
Chris Sandvik 28 Окт 2019 в 20:55
58598000