21 项目实战:详情页面和登录功能开发(二)

异步获取数据

这一节,我们要把之前reducer写死的内容,放进模拟接口中,进行ajax请求。
1.先写一个模拟接口

//===>public/api/detail.js
{
    "success": true,
    "data": {
        "title": "【Android 音视频开发打怪升级:FFmpeg音视频编解码篇】五、Android FFmpeg+OpenGL ES播放视频",
        "content": "

特别说明一下这里,OpenGL 线程渲染的过程中,不是直接调用绘制器去渲染,而是通过一个代理来间接调用,这样 OpenGL 线程就不需要关心有多少个绘制器需要调用,统统交给代理去管理就好了。

特别说明一下这里,OpenGL 线程渲染的过程中,不是直接调用绘制器去渲染,而是通过一个代理来间接调用,这样 OpenGL 线程就不需要关心有多少个绘制器需要调用,统统交给代理去管理就好了。

特别说明一下这里,OpenGL 线程渲染的过程中,不是直接调用绘制器去渲染,而是通过一个代理来间接调用,这样 OpenGL 线程就不需要关心有多少个绘制器需要调用,统统交给代理去管理就好了。

特别说明一下这里,OpenGL 线程渲染的过程中,不是直接调用绘制器去渲染,而是通过一个代理来间接调用,这样 OpenGL 线程就不需要关心有多少个绘制器需要调用,统统交给代理去管理就好了。

" } }

2.在constants文件中添加获取到详情数据的action常量

//===>src/pages/detail/store/constants/js
export const CHANGE_DETAIL = 'detail/CHANGE_DETAIL'

3.编写异步获取数据的actionCreators

//===>src/pages/detail/store/actionCreators.js
import axios from 'axios'
import * as constants from './constants'

const changeDetail = (title, content) => ({
    type: constants.CHANGE_DETAIL,
    title,
    content
})

export const getDetail = () => {
    return (dispatch) => {
        axios.get('/api/detali.json').then((res) => {
            const result = res.data.data
            dispatch(changeDetail(result.title, result.content))
        })
    }
}

4.数据获取到之后,要用reducer去修改store的数据

//===>src/pages/detail/store/reducer.js
import { fromJS } from 'immutable'
import * as constants from './constants'

const defaultState = fromJS({
    title: '',
    content: ''
})

export default (state = defaultState, action) => {
    switch (action.type) {
        case constants.CHANGE_DETAIL:
            return state.merge({
                title: action.title,
                content: action.content
            })
        default:
            return state
    }
}

5.最后,我们来编写Detail页面的代码,在生命周期钩子函数中进行ajax请求

//===>src/pages/detail/index.js
import React, { Component } from 'react'
import { DetailWrapper, Header, Content } from './style'
import { connect } from 'react-redux'
import { actionCreators } from './store'
class Detail extends Component {
    render() {
        return (
            
                
{this.props.title}
) } componentDidMount() { this.props.getDetail(); } } const mapState = (state) => ({ title: state.getIn(['detail', 'title']), content: state.getIn(['detail', 'content']) }) const mapDispatch = (dispatch) => ({ getDetail() { dispatch(actionCreators.getDetail()) } }) export default connect(mapState, mapDispatch)(Detail)
效果不变

页面路由参数的传递

1.我们在List组件的item点击事件添加参数

//===>src/pages/home/components/List.js
...
class List extends PureComponent {
    render() {
        const { list, page, getMoreList } = this.props
        return (
            
{ list.map((item, index) => { return ( ... ) }) } getMoreList(page)}>更多文字
) } } ...

2.因为在App.js中,我们设置的是精准匹配,所以现在是不能访问/detail/id这个路径的,所以这里我们要改成动态路由的形式

//===>src/App.js
...
          
...

3.这样参数已经传到了detail页面了,我们来获取参数
我们通过this.props.match.params.id这种形式获取到了参数,在钩子函数中调用ajax请求的时候传参,这样actionCreators就可以接收到参数了。

//===>src/pages/detail/index.js
import React, { Component } from 'react'
import { DetailWrapper, Header, Content } from './style'
import { connect } from 'react-redux'
import { actionCreators } from './store'
class Detail extends Component {
    render() {
        return (
            
                
{this.props.title}
) } componentDidMount() { this.props.getDetail(this.props.match.params.id); } } const mapState = (state) => ({ title: state.getIn(['detail', 'title']), content: state.getIn(['detail', 'content']) }) const mapDispatch = (dispatch) => ({ getDetail(id) { dispatch(actionCreators.getDetail(id)) } }) ...

4.最后ajax发送请求并传参

//===>src/pages/detail/store/actionCreators.js
...
export const getDetail = (id) => {
    return (dispatch) => {
        axios.get('/api/detali.json?id=' + id).then((res) => {
            const result = res.data.data
            dispatch(changeDetail(result.title, result.content))
        })
    }
}
效果

你可能感兴趣的:(21 项目实战:详情页面和登录功能开发(二))