第七色在线视频,2021少妇久久久久久久久久,亚洲欧洲精品成人久久av18,亚洲国产精品特色大片观看完整版,孙宇晨将参加特朗普的晚宴

為了賬號(hào)安全,請(qǐng)及時(shí)綁定郵箱和手機(jī)立即綁定
已解決430363個(gè)問(wèn)題,去搜搜看,總會(huì)有你想問(wèn)的

React:你如何從 API 響應(yīng)中延遲加載圖像?

React:你如何從 API 響應(yīng)中延遲加載圖像?

慕少森 2023-01-06 15:48:54
我的網(wǎng)站太重了,因?yàn)樗趶姆?wù)器(Google 的 Firebase Firestore)獲取數(shù)據(jù)后下載了 200-400 張圖像。我想出了兩個(gè)解決方案,我希望有人回答其中一個(gè):我想將每個(gè) img 設(shè)置為具有加載狀態(tài),并使訪問(wèn)者能夠在加載之前看到占位符圖像。因?yàn)槲也恢缽姆?wù)器獲取數(shù)據(jù)之前我得到了多少圖像,所以我發(fā)現(xiàn)很難通過(guò) useState 初始化圖像加載狀態(tài)。這可能嗎?那么,怎么辦?如何延遲加載圖像?圖像使用占位符進(jìn)行初始化。當(dāng)滾動(dòng)條靠近圖像時(shí),圖像開(kāi)始下載并替換占位符。function sample() {}{  const [items, setItems] = useState([])  const [imgLoading, setImgLoading] = useState(true)  // imgLoading might have to be boolean[]  useEffect(() => {    axios.get(url).    .then(response => setItems(response.data))  }, [])  return (    items.map(item => <img src={item.imageUrl} onLoad={setImgLoading(false)} />)  )}
查看完整描述

3 回答

?
斯蒂芬大帝

TA貢獻(xiàn)1827條經(jīng)驗(yàn) 獲得超8個(gè)贊

我會(huì)創(chuàng)建一個(gè)Image組件來(lái)處理它自己的相關(guān)狀態(tài)。然后在這個(gè)組件內(nèi),我會(huì)使用IntersectionObserverAPI 來(lái)判斷圖像的容器在用戶瀏覽器上是否可見(jiàn)。


我會(huì)isLoading和isInview狀態(tài),isLoading將永遠(yuǎn)true直到isInview更新到true.


而當(dāng)isLoadingis時(shí)true,我會(huì)使用nullas 作為src圖像并顯示占位符。


src僅在容器在用戶瀏覽器上可見(jiàn)時(shí)加載。


function Image({ src }) {

  const [isLoading, setIsLoading] = useState(true);

  const [isInView, setIsInView] = useState(false);

  const root = useRef(); // the container


  useEffect(() => {

    // sets `isInView` to true until root is visible on users browser


    const observer = new IntersectionObserver(onIntersection, { threshold: 0 });

    observer.observe(root.current);


    function onIntersection(entries) {

      const { isIntersecting } = entries[0];


      if (isIntersecting) { // is in view

        observer.disconnect();

      }


      setIsInView(isIntersecting);

    }

  }, []);


  function onLoad() {

    setIsLoading((prev) => !prev);

  }


  return (

    <div

      ref={root}

      className={`imgWrapper` + (isLoading ? " imgWrapper--isLoading" : "")}

    >

      <div className="imgLoader" />

      <img className="img" src={isInView ? src : null} alt="" onLoad={onLoad} />

    </div>

  );

}

我還會(huì)有 CSS 樣式來(lái)切換占位符和圖像的display屬性。


.App {

  --image-height: 150px;

  --image-width: var(--image-height);

}


.imgWrapper {

  margin-bottom: 10px;

}


.img {

  height: var(--image-height);

  width: var(--image-width);

}


.imgLoader {

  height: 150px;

  width: 150px;

  background-color: red;

}


/* container is loading, hide the img */

.imgWrapper--isLoading .img {

  display: none;

}


/* container not loading, display img */

.imgWrapper:not(.imgWrapper--isLoading) .img {

  display: block;

}


/* container not loading, hide placeholder */

.imgWrapper:not(.imgWrapper--isLoading) .imgLoader {

  display: none;

}

現(xiàn)在我的父組件將執(zhí)行對(duì)所有圖像 url 的請(qǐng)求。它也有自己的isLoading狀態(tài),當(dāng)設(shè)置時(shí)true會(huì)顯示自己的占位符。當(dāng)圖像 url 的請(qǐng)求得到解決時(shí),我將映射到每個(gè) url 以呈現(xiàn)我的Image組件。


export default function App() {

  const [imageUrls, setImageUrls] = useState([]);

  const [isLoading, setIsLoading] = useState(true);


  useEffect(() => {

    fetchImages().then((response) => {

      setImageUrls(response);

      setIsLoading((prev) => !prev);

    });

  }, []);


  const images = imageUrls.map((url, index) => <Image key={index} src={url} />);


  return <div className="App">{isLoading ? "Please wait..." : images}</div>;

}


查看完整回答
反對(duì) 回復(fù) 2023-01-06
?
慕碼人2483693

TA貢獻(xiàn)1860條經(jīng)驗(yàn) 獲得超9個(gè)贊

有用于此的庫(kù),但如果您想推出自己的庫(kù),則可以使用IntersectionObserver,如下所示:

const { useState, useRef, useEffect } = React;


const LazyImage = (imageProps) => {

  const [shouldLoad, setShouldLoad] = useState(false);

  const placeholderRef = useRef(null);


  useEffect(() => {

    if (!shouldLoad && placeholderRef.current) {

      const observer = new IntersectionObserver(([{ intersectionRatio }]) => {

        if (intersectionRatio > 0) {

          setShouldLoad(true);

        }

      });

      observer.observe(placeholderRef.current);

      return () => observer.disconnect();

    }

  }, [shouldLoad, placeholderRef]);


  return (shouldLoad 

    ? <img {...imageProps}/> 

    : <div className="img-placeholder" ref={placeholderRef}/>

  );

};


ReactDOM.render(

  <div className="scroll-list">

    <LazyImage src='https://i.insider.com/536a52d9ecad042e1fb1a778?width=1100&format=jpeg&auto=webp'/>

    <LazyImage src='https://www.denofgeek.com/wp-content/uploads/2019/12/power-rangers-beast-morphers-season-2-scaled.jpg?fit=2560%2C1440'/>

    <LazyImage src='https://i1.wp.com/www.theilluminerdi.com/wp-content/uploads/2020/02/mighty-morphin-power-rangers-reunion.jpg?resize=1200%2C640&ssl=1'/>

    <LazyImage src='https://m.media-amazon.com/images/M/MV5BNTFiODY1NDItODc1Zi00MjE2LTk0MzQtNjExY2I1NTU3MzdiXkEyXkFqcGdeQXVyNzU1NzE3NTg@._V1_CR0,45,480,270_AL_UX477_CR0,0,477,268_AL_.jpg'/>

  </div>,

  document.getElementById('app')

);

.scroll-list > * {

  margin-top: 400px;

}


.img-placeholder {

  content: 'Placeholder!';

  width: 400px;

  height: 300px;

  border: 1px solid black;

  background-color: silver;

}

<div id="app"></div>


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

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


此代碼讓它們?cè)谄聊簧巷@示占位符后立即加載,但如果您想要更大的檢測(cè)余量,則可以調(diào)整 的rootMargin選項(xiàng),IntersectionObserver以便它在仍然略微離開(kāi)屏幕的情況下開(kāi)始加載。



查看完整回答
反對(duì) 回復(fù) 2023-01-06
?
呼如林

TA貢獻(xiàn)1798條經(jīng)驗(yàn) 獲得超3個(gè)贊

將響應(yīng)數(shù)據(jù)映射到“isLoading”布爾值數(shù)組,并更新回調(diào)以獲取索引并更新特定的“isLoading”布爾值。


function Sample() {

  const [items, setItems] = useState([]);

  const [imgLoading, setImgLoading] = useState([]);


  useEffect(() => {

    axios.get(url).then((response) => {

      const { data } = response;

      setItems(data);

      setImgLoading(data.map(() => true));

    });

  }, []);


  return items.map((item, index) => (

    <img

      src={item.imageUrl}

      onLoad={() =>

        setImgLoading((loading) =>

          loading.map((el, i) => (i === index ? false : el))

        )

      }

    />

  ));

}


查看完整回答
反對(duì) 回復(fù) 2023-01-06
  • 3 回答
  • 0 關(guān)注
  • 194 瀏覽
慕課專(zhuān)欄
更多

添加回答

舉報(bào)

0/150
提交
取消
微信客服

購(gòu)課補(bǔ)貼
聯(lián)系客服咨詢(xún)優(yōu)惠詳情

幫助反饋 APP下載

慕課網(wǎng)APP
您的移動(dòng)學(xué)習(xí)伙伴

公眾號(hào)

掃描二維碼
關(guān)注慕課網(wǎng)微信公眾號(hào)