Об элементах React, Suspense, lazyLoad и предварительной загрузке / рендеринге - PullRequest
1 голос
/ 06 июня 2019

Я изучаю концепции <Suspense> и React.lazy() и хотел бы лучше понять, что происходит, чтобы добавить некоторую логику в существующее приложение.

Давайте начнем с определений:

Функция React.lazy позволяет визуализировать динамический импорт как обычный компонент.

( визуализация выделена мной)

и

Если модуль, содержащий OtherComponent, еще не загружен к моменту рендеринга MyComponent, мы должны показать некоторый запасной контент, пока ожидаемчтобы загрузить [...]

( загружено выделено мной)

Теперь в определении Suspense используется термин load , lazy() использует рендер .

Давайте добавим немного кода в концепцию.

const ComponentOne = React.lazy(() => import("./ComponentOne"));
const ComponentTwo = React.lazy(() => import("./ComponentTwo"));

function BigBang() {
    return (
        <Suspense fallback={<SplashScreen/>}>
            <section>
                <ComponentOne/>
                <ComponentTwo/>
            </section>
        </Suspense>
    );
}

Fine.Идея в том, что мы лениво загружаем ComponentOne и ComponentTwo.Пока этот процесс не закончен, мы отобразим SplashScreen.

ВОПРОС Теперь давайте предположим, что у меня есть некоторые импортные данные для некоторых локальных изображений в ComponentOne и ComponentTwo (я добавлю только коддля одного, давайте предположим, что есть что-то похожее для другого):

import avatar from "../../img/avatar.svg";
import logo from "../../img/logo.svg";

export default class ComponentOne extends React.Component {
    componentDidMount() {
        console.log("ComponentOne@componentDidMount");
    }

    render() {
        console.log("ComponentOne@render");
        return (
            <div style={{display: 'none'}}>
                <img src={avatar}/>
                <img src={logo}/>
            </div>
        );
    }
}

Теперь должно быть ясно, что я хотел бы спросить:

Исчезает ли SplashScreen, когда ВСЕ импортируетзагружены?Другими словами, когда исчезает SplashScreen, могу ли я предположить, что все изображения в ComponentOne и ComponentTwo уже загружены?

Это основной вопрос.

Вторичный вопрос (который кажется связаннымдля меня, но если это не так, я могу открыть другую ветку): если ответ на предыдущий вопрос «НЕТ», какова лучшая стратегия, чтобы быть уверенным, что images / fonts / «api response» / ​​«other resources»загружаются перед рендерингом, возможно, поддерживая логику из-за уже существующего потока?Прямой fetch() к ресурсам в настоящее время не поддерживается.

1 Ответ

0 голосов
/ 06 июня 2019

Suspense ожидает получения динамически импортированного файла компонента (скажем, 0.js).Теперь, когда 0.js загружен и начинает синтаксический анализ, Suspense перестает отображать SplashScreen и делегаты управляют вашим компонентом.Что бы ни случилось дальше, это не ленивая загрузка.Это было бы так, как если бы вы сделали статический импорт.

В вашем случае два изображения будут загружены только после того, как SplashScreen исчезнет.Теперь, если вы хотите предварительно / лениво загрузить изображения, есть несколько способов сделать это.

1) Если вы используете веб-пакет, вы можете использовать url-loader, чтобы встроить изображения как data-uri.Но учтите, что это может увеличить размер вашего пакета, а также вы потеряете при кэшировании в браузере изображений, которые обычно статичны.

2) Для svgs вы можете использовать плагин inline-react-svg babel, который преобразует svg в реагирующий компонент так, чтобы он входил в ваш пакет (0.js).Но он также имеет тот же компромисс, упомянутый выше.

Следовательно, предварительная загрузка изображений имеет свои собственные компромиссы.Могут быть и лучшие альтернативы, такие как отложенная загрузка, которую можно легко выполнить, а также React HOC можно получить из нескольких сторонних библиотек.

...