基于React實現(xiàn)下拉刷新效果
簡介
本文基于react實現(xiàn)下拉刷新效果,在下拉的時候會進入loading狀態(tài)。
實現(xiàn)效果
效果如上圖所示,在下拉到底部時候,會出現(xiàn)loading條,在處理完成后loading條消失。
具體代碼
布局 & 邏輯
import {useRef, useState} from "react"; export const ScrollView = ({loadingComponent, contentComponent}) => { const LoadingComponent = loadingComponent; const ContentComponent = contentComponent; /** * 加載狀態(tài) */ const [loading, setLoading] = useState(false); /** * 滾動容器引用 */ const scrollRef = useRef(null); let contentStyle = {height: '30px', width:'100%', textAlign:'center', display:'none'}; if (loading){ // 加載中顯示 contentStyle = {height: '30px', width:'100%', textAlign:'center'}; scrollRef.current.scrollTop = 0; // 滾到頭部 } const handleScroll = ()=>{ const {scrollTop} = scrollRef.current; if (scrollTop > 50 && !loading){ setLoading(true); // 設置為加載中狀態(tài) // 模擬數(shù)據(jù)加載 setTimeout(()=>{ setLoading(false); // 加載完成 }, 3000) } } return ( <div style={{height: '200px', overflow:'auto', width:'40%'}} ref={scrollRef} onScroll={handleScroll}> <div style={contentStyle}> <LoadingComponent/> </div> <div style={{height:'300px', width:'100%'}}> <ContentComponent/> </div> </div> ) }
使用demo
import {ScrollView} from "./component/scroll-view/ScrollView"; const App = ()=> { return ( <ScrollView loadingComponent={Loading} contentComponent={Content}> </ScrollView> ) } const Loading = ()=>{ return <div>loading</div> } const Content = ()=>{ return <div> hello, world</div> } export default App;
番外:上拉加載實現(xiàn)
1、下載react-pullload
npm i react-pullload
2、在組件中去引用
import ReactPullLoad,{ STATS } from "react-pullload";
3、css樣式
①引用插件內(nèi)的樣式
import "node_modules/react-pullload/dist/ReactPullLoad.css";
②或者直接引入使用下列代碼:
.pull-load { position: relative; overflow-y: scroll; -webkit-overflow-scrolling: touch; } .pull-load-head { position: absolute; transform: translate3d(0px, -100%, 0px); width: 100%; } .state-refreshing .pull-load-head, .state-refreshed .pull-load-head { position: relative; transform: none; } .pull-load-body { position: relative; } .state-refreshing .pull-load-body { transition: transform 0.2s; } .state-reset .pull-load-body { transition: transform 0.2s; } .pull-load-head-default { text-align: center; font-size: 12px; line-height: 0.8rem; color: #7676a1; } .state-pulling .pull-load-head-default:after { content: '下拉刷新'; } .state-pulling.enough .pull-load-head-default:after { content: '松開刷新'; } .state-refreshing .pull-load-head-default:after { content: '正在刷新...'; } .state-refreshed .pull-load-head-default:after { content: '刷新成功'; } .state-pulling .pull-load-head-default { opacity: 1; } .state-pulling .pull-load-head-default i { display: inline-block; font-size: 0.3rem; margin-right: .6em; margin-top: -3px; vertical-align: middle; height: 0.3rem; border-left: 1px solid; position: relative; transition: transform .3s ease; } .state-pulling .pull-load-head-default i:before, .state-pulling .pull-load-head-default i:after { content: ''; position: absolute; font-size: .5em; width: 1em; bottom: 0px; border-top: 1px solid; } .state-pulling .pull-load-head-default i:before { right: 1px; transform: rotate(50deg); transform-origin: right; } .state-pulling .pull-load-head-default i:after { left: 0px; transform: rotate(-50deg); transform-origin: left; } .state-pulling.enough .pull-load-head-default i { transform: rotate(180deg); } .state-refreshing .pull-load-head-default i { margin-right: 10px; margin-top: -3px; display: inline-block; vertical-align: middle; font-size: 0.3rem; width: 0.3rem; height: 0.3rem; border: 2px solid #9494b6; border-top-color: #fff; border-radius: 100%; animation: circle .8s infinite linear; } .state-refreshed .pull-load-head-default { opacity: 1; transition: opacity 1s; } .state-refreshed .pull-load-head-default i { display: inline-block; box-sizing: content-box; vertical-align: middle; margin-right: 10px; margin-top: -3px; font-size: 14px; height: 1em; width: 1em; border: 2px solid; border-radius: 100%; position: relative; } .state-refreshed .pull-load-head-default i:before { content: ''; position: absolute; top: -2px; left: 4px; height: 11px; width: 5px; border: solid; border-width: 0 2px 2px 0; transform: rotate(40deg); } .pull-load-footer-default { text-align: center; font-size: 12px; line-height: 0.8rem; color: #7676a1; } .state-loading .pull-load-footer-default:after { content: '加載更多'; } .pull-load-footer-default.nomore:after { content: '沒有更多'; } .state-loading .pull-load-footer-default i { margin-right: 10px; margin-top: -3px; display: inline-block; vertical-align: middle; font-size: 0.3rem; width: 0.3rem; height: 0.3rem; border: 2px solid #9494b6; border-top-color: #fff; border-radius: 100%; animation: circle .8s infinite linear; } @keyframes circle { 100% { transform: rotate(360deg); } }
4、pullLoad標簽包裹
<ReactPullLoad downEnough={150} ref="reactpullload" className="block" *加上下面注釋的屬性會出問題 // isBlockContainer={true} action={this.state.action} handleAction={this.handleAction} hasMore={this.state.hasMore} style={{paddingTop: 132}} distanceBottom={1000}> ..... this is list </ReactPullLoad>
5、scroll函數(shù)
constructor(props) { super(props); this.state = { // scroll 相關 hasMore: true, action: STATS.init, } } // 滾動條 handleAction = (action) => { if(action === this.state.action || action === STATS.refreshing && this.state.action === STATS.loading || action === STATS.loading && this.state.action === STATS.refreshing){ return false } if(action === STATS.refreshing){//刷新 setTimeout(()=>{ //refreshing complete 下拉刷新 }, 1000) } else if(action === STATS.loading){//加載更多 this.setState({ hasMore: true }); setTimeout(()=>{ if(this.state.index === this.state.curPage){ this.setState({ action: STATS.reset, hasMore: false }); } else{ 上拉加載.... } }, 1000) } this.setState({ action: action }) }
到此這篇關于基于React實現(xiàn)下拉刷新效果的文章就介紹到這了,更多相關React下拉刷新內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關文章希望大家以后多多支持腳本之家!
相關文章
解決React報錯Property does not exist on 
這篇文章主要為大家介紹了React報錯Property does not exist on type 'JSX.IntrinsicElements'解決方法,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪2022-12-12React中setState/useState的使用方法詳細介紹
這篇文章主要介紹了React中setState/useState的使用方法,useState 和 setState 在React開發(fā)過程中 使用很頻繁,但很多人都停留在簡單的使用階段,并沒有正在了解它們的執(zhí)行機制2023-04-04React如何使用refresh_token實現(xiàn)無感刷新頁面
本文主要介紹了React如何使用refresh_token實現(xiàn)無感刷新頁面,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧2022-04-04React?Native中原生實現(xiàn)動態(tài)導入的示例詳解
在React?Native社區(qū)中,原生動態(tài)導入一直是期待已久的功能,在這篇文章中,我們將比較靜態(tài)和動態(tài)導入,學習如何原生地處理動態(tài)導入,以及有效實施的最佳實踐,希望對大家有所幫助2024-02-02React中的useState和setState的執(zhí)行機制詳解
這篇文章主要介紹了React中的useState和setState的執(zhí)行機制,具有很好的參考價值,希望對大家有所幫助,如有錯誤或未考慮完全的地方,望不吝賜教2024-03-03react循環(huán)數(shù)據(jù)(列表)的實現(xiàn)
這篇文章主要介紹了react循環(huán)數(shù)據(jù)的實現(xiàn),文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧2021-04-04