React進階篇(1) -- react-router4模塊化


本篇內容:

  • 單一的路由無嵌套
  • 多層嵌套路由
  • 獲取路徑中的參數
  • 按需加載

單一的路由無嵌套

routers.js

import Home from 'components/Home';
import News from 'components/News';
import User from 'components/User';
import My from 'components/My';

let routes=[
    {
        path:'/',
        component:Home ,
        exact:true
    },
    {
        path:'/news',
        component:News ,
    },
    {
        path:'/user',
        component:User 
    },
    {
        path:'/my',
        component:My 
    },
]
export default routes;

App.jsx

import React, { Component } from 'react';
import { HashRouter as Router, Switch, Route } from "react-router-dom";
import routes from '../routers/index';
class App extends Component {
  render() {
    return (
        <Router>
            <div>
                <Switch>
                    //主要邏輯在這里
                    {
                        routes.map((item, i) => {
                            if(item.exact){
                                return <Route exact path={item.path} component={item.component}  key={i}/>
                            }else{
                                return <Route path={item.path} component={item.component}  key={i}/>
                            }
                        }) 
                    }
                </Switch> 
            </div>
        </Router>
    );
  }
}

多層嵌套路由

let routes=[
    {
        path:'/hear',
        component:Hear,
        exact:true,
        description:"聽",
        subs:[
            {
                path:'/hear/',
                component:HearIndex,
                description:"聽-首頁" 
            },
            {
                path:'/hear/book',
                component:HearBook,
                description:"聽-課文" 
            },
        ]
    },
    {
        path:'/speak',
        component:Speak,
        exact:true,
        description:"說",
        subs:[
            {
                path:'/speak/',
                component:CN,
                description:"說-漢語" 
            },
            {
                path:'/speak/english',
                component:English,
                description:"說-英語" 
            },
        ]
    },
    {
        path:'/read',
        component:Read,
        exact:true,
        description:"讀",
        subs:[
            {
                path:'/read/',
                component:ReadBook,
                description:"讀-課文" 
            },
            {
                path:'/read/newspaper',
                component:ReadNews,
                description:"讀-報紙" 
            },
        ]
    },
    {
        path:'/writ',
        component:Writ,
        exact:true,
        description:"寫"
    }
]
export default routes;

App.jsx

{
    routes.map((item, i) => {
        if (item.exact) {
            //官方固定格式
            return <Route exact path={item.path} key={i} render={ props => (<item.component {...props} routes={item.subs}/>) />
        }
        else {
            return <Route path={item.path} key={i} render={ props => (<item.component {...props}  routes={item.subs}/>)} />
        }
    })
}

//step 2,在對應的組件中再次遍歷

{
    this.props.routes.map((item, i) => {
        return <Route exact path={item.path}
        component= {item.component}
        key={i}/>
    })
}

跳轉

this.props.history.push(`/about/type/${id}`)
this.props.history.replace(...)

注意:

不能在子組件中直接獲取,需要從父級傳入之后用props獲取;

跳轉時,如果還有事件未結束,則容易報錯!

如:

<LoginCom TIMEID={TIMEID} {...this.props}/>

獲取路徑參數

獲取對應的params

this.props.match.params.id

獲取?后面對應的值

const getQueryString = (str,name) => {
    let result = str.match(new RegExp("[\?\&]" + name + "=([^\&]+)", "i"));
    if (result == null || result.length < 1) {
        return "";
    }
    return decodeURI(result[1], "utf-8");
}

如:http://localhost:3000/#/textbook/bishun?val=看

console.log(getQueryString(this.props.location.search,'val'));

按需加載

感覺這種方式最簡單:

基於 webpack, babel-plugin-syntax-dynamic-import, 和 react-loadable;

主要是利用了react-loadable這個高級組件,他是專門用來異步加載(也可以預加載)組件的。

cnpm i -S react-loadable @babel/plugin-syntax-dynamic-import

.babelrc

{
   “ presets ”:[ “ @ babel / react ” ],
   “ plugins ”:[ “ @ babel / plugin-syntax-dynamic-import ” ]
}

routers.js變化

import Loadable from 'react-loadable';
import DelayLoading from './DelayLoading';

const Home= Loadable({loader: () => import('../components/Home'), loading : DelayLoading,delay:3000})
const Login= Loadable({loader: () => import('../components/Login'), loading : DelayLoading,delay:3000})

打包文件情況對比:

首屏加載情況對比:

參考文檔:

https://reacttraining.com/react-router/web/example/route-config

https://github.com/ReactTraining/react-router/blob/master/packages/react-router-dom/docs/guides/code-splitting.md

https://github.com/jamiebuilds/react-loadable

可參考其他文章:https://www.cnblogs.com/alan2kat/p/7754846.html


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM