skeleton在心意web上的實踐

經過手動編寫skeleton,在fetch數據時顯示skeleton loading,數據拉取成功隱藏skeletonreact

先看下效果圖web

在component下建立頁面對應的skeleton,而後經過在index.js中export輸出,在須要使用skeleton的頁面中引入。redux

代碼結構

charity-web
       |--- components
                |---Skeleton
 |---HomeProject.js    home頁項目列表
 |---index.js    導出全部skeleton
 |---ProjectCard.js    項目列表item
 |---HomeListing.js   項目列表頁
       |--- pages
                |---index.js
                |---listing.js
       |--- redux
                |---app
                |---project
                |---index.js
                |---rootSaga.js

skeleton部分代碼

  • skeleton/index.js文件
import HomeProjectSkeleton from './HomeProject'
import ProjectListingSkeleton from './ProjectListing'
import PromotionItemSkeleton from './PromotionItem'

export { PromotionItemSkeleton, HomeProjectSkeleton, ProjectListingSkeleton }
  • skeleton/homeproject.js文件
import { Col, Row } from 'antd'
import React, { Component } from 'react'
import styled from 'styled-components'

import mediaQuery from '../../utils/mediaQuery'
import ProjectCard from './ProjectCard'
const Container = styled.div`
  .projects {
    padding-top: 32px;
    ${mediaQuery.tablet} {
      padding-top: 24px;
    }
    ${mediaQuery.mobile} {
      padding-top: 24px;
    }
  }
  .projectWrapper {
    padding-bottom: 24px;
  }
`

class HomeProject extends Component {
  render() {
    const items = [0, 1, 2, 3, 4]
    return (
      <Container>
        <div className='projects'>
          <div className='max-width'>
            <Row type='flex' justify='start' gutter={24}>
              {items.map(i => {
                return (
                  <Col
                    xs={24}
                    md={12}
                    xl={8}
                    className='projectWrapper'
                    key={`p_${i}`}
                  >
                    <ProjectCard />
                  </Col>
                )
              })}
            </Row>
          </div>
        </div>
      </Container>
    )
  }
}

export default HomeProject
  • skeleton/projectlisting.js文件
import { Col, Row } from 'antd'
import React, { Component } from 'react'

import ProjectCard from './ProjectCard'

class ProjectListing extends Component {
  render() {
    const items = [0, 1, 2, 3, 4]
    return (
      <Row type='flex' justify='start' gutter={24}>
        {items.map(i => {
          return (
            <Col
              xs={24}
              md={24}
              xl={24}
              className='projectWrapper'
              key={`p_${i}`}
            >
              <ProjectCard listStyle />
            </Col>
          )
        })}
      </Row>
    )
  }
}

export default ProjectListing
  • skeleton/promotionitem.js文件
import React, { Component } from 'react'
import styled from 'styled-components'

import mediaQuery from '../../utils/mediaQuery'
const Container = styled.div`
  width: 100vw;
  height: 37.5vw;
  background-color: #f4f4f4;
  ${mediaQuery.mobile} {
    height: 56.25vw;
  }
`

class PromotionItem extends Component {
  render() {
    return <Container />
  }
}

export default PromotionItem

在頁面中應用skeleton

一、首先引入skeletonantd

import {
  HomeProjectSkeleton,
  PromotionItemSkeleton
} from '../components/Skeleton/index'

二、在render函數中,經過 this.props.isFetching判斷是否顯示skeletonapp

{process.env.usePromoItem ? (
          this.props.isFetching ? (
            <PromotionItemSkeleton />
          ) : (
            <Swiper slides={this.props.promoItems} />
          )
        ) : (
          this.renderHeroProject()
        )}
        {this.props.isFetching ? (
          <HomeProjectSkeleton />
        ) : (
          (this.renderHighlightedProjects(), this.renderOtherProjects())
        )}

三、在reduces.js中,當getHomePageDataRequest拉取數據的時候,設置isFetching爲true,getHomePageDataSucceeded獲取成功後,將isFetching修改成falseide

import {
  getHomePageDataRequest,
  getHomePageDataSucceeded,
} from './actions'

export const projectInitialState = {
  fetching: {
    getHomepageData: false,
    getSearchListingPageData: false
  }
}

const projectReducer = handleActions(
  {
    [getHomePageDataRequest]: state => {
      return {
        ...state,
        fetching: {
          getHomepageData: true
        }
      }
    },
    [getHomePageDataSucceeded]: (state, action) => {
      return {
        ...state,
        fetching: {
          getHomepageData: false
        }
      }
    },
  }
  projectInitialState
)
export default projectReducer

四、這樣,在頁面中mapStateToProps中咱們能夠拿到isFetching的狀態,從而在數據獲取成功以前顯示skeleton函數

const mapStateToProps = ({ appState, projectState, paymentState }, props) => ({
  isFetching: projectState.fetching.getHomepageData
})

總結

以上,就是對skeleton在項目中的應用,固然經過以上這種方式實現的skeleton,有一個很差的地方是,若是頁面結構變化,咱們同時也須要更新sekleton的結構,這是比較麻煩的地方。fetch

相關文章
相關標籤/搜索