2017-02-22 3 views
1

페이지 매김을 구현하고 싶습니다. 따라서 사용자가 맨 아래로 스크롤하면 API 호출을하고 싶습니다. 나는 창문을 통해 본다. 스크롤 나는 스크롤의 위치를 ​​찾을 수 있고 그것을 얻을 수있다. 그러나 나는 certian 데이터를 얻기 위해 redux 상태에 액세스하려고합니다. 이 이벤트는 어떤 구성 요소에 의해서도 바인딩되지 않기 때문에 데이터를 전달할 수 없습니다. 이 시나리오에서 올바른 접근 방법은 무엇입니까? 간단한 기능을 통해 redux 상점에 액세스하려면 어떻게해야합니까? 그리고 스크롤에 대해서 어떻게 요청이 통과하는지 확인합니까?window.scroll에서 redux 상태 가져 오기

+0

내가 그것을 사용하지만, 아마도 [반응 - 무한 스크롤]하지 (https://github.com/CassetteRocks/react-infinite-scroller) 당신을 도울 수 . –

+0

@JoPeyper 감사합니다. 뭔가 https://github.com/brigade/react-waypoint가 흥미로운 것 같습니다. – scripter

답변

3

스크롤을 수행하는 구성 요소는 connect입니다. 또는 상점 정보가있는 구성 요소에 소품을 전달할 수 있습니다. 그것들은 귀하의 상점에 도착하는 두 가지 권장 방법입니다. 당신은 또한 컨텍스트를 볼 수 있다고 말했다.

class MyComponent extends React.Component { 
    someMethod() { 
    doSomethingWith(this.context.store); 
    } 
    render() { 
    ... 
    } 
} 

MyComponent.contextTypes = { 
    store: React.PropTypes.object.isRequired 
}; 

참고 : 컨텍스트는 옵트 인입니다. 구성 요소에 contextTypes을 지정해야합니다. 방금이 작업을 수행 할 수 있습니다 제공하는 명확성 코멘트 당

:이 향후 버전


편집에 사용되지 수 있기 때문에

React's Context doc 읽기 최대 그것은 완전한 솔루션을하지 않을 수 있습니다 .

import React, { Component } from 'react'; 
import ReactDOM = from 'react-dom'; 
import _ from 'lodash'; 

const defaultOffset = 300; 

var topOfElement = function(element) { 
    if (!element) { 
     return 0; 
    } 
    return element.offsetTop + topOfElement(element.offsetParent); 
}; 

class InfiniteScroll extends Component { 
    constructor(props) { 
     super(props); 
     this.listener = _.throttle(this.scrollListener, 200).bind(this); 
    } 

    componentDidMount() { 
     this.attachScrollListener(); 
    } 

    componentWillUnmount() { 
     this.detachScrollListener(); 
    } 

    scrollListener() { 
     var el = ReactDOM.findDOMNode(this); 
     var offset = this.props.offset || defaultOffset; 
     var scrollTop = (window.pageYOffset !== undefined) ? window.pageYOffset : (document.documentElement || document.body.parentNode || document.body).scrollTop; 
     if (topOfElement(el) + el.offsetHeight - scrollTop - window.innerHeight < offset) { 
      this.props.somethingHere; 
     } 
    } 

    attachScrollListener() { 
     window.addEventListener('scroll', this.listener); 
     window.addEventListener('resize', this.listener); 
     this.listener(); 
    } 

    detachScrollListener() { 
     window.removeEventListener('scroll', this.listener); 
     window.removeEventListener('resize', this.listener); 
    } 

    render() { 
     return (...) 
    } 
} 

export default connect(mapStateToProps, mapDispatchToProps)(InfiniteScroll); 

여기에 가져 오기에 lodash를 추가 했으므로 스크롤 수신기 기능을 제한 할 수 있습니다. 핸들러 함수를 초당 몇 번이나 호출해야하는지 아니면 청취자 함수가 얼마나 두꺼운 지에 따라 페이지를 뒤따를 수 있습니다.

+0

스크롤을 수행하는 구성 요소를 연결할 수 있습니까? 그 구성 요소는 무엇일까요? window.scroll을 호출하고 싶습니다. 나는 스크롤을위한 고정 컨테이너를 원하지 않는다. 당신이 새로운 데이터를 가져올 때 페이스 북과 같은 것을 원합니다. – scripter

+0

@scripter 저는'window.scroll' 리스너와 모든 것을 처리하는'InfiniteScroll' 컴포넌트를 만들 예정이라 가정합니다. 한 곳. 그 구성 요소 (또는 더 많은 데이터를 요청해야하는 구성 요소가 무한 스크롤 구성 요소를 만들지 않는다면)를 연결할 수 있다고 말하고있었습니다. –

+1

필요하지 않은 경우 저장소를 통해 직접 redux 저장소를 사용하면 안됩니다.이 경우 Components와 redux store를 연결하는 공식 모듈을 사용해야합니다 :'react-redux'; – floriangosse

0

구성 요소에서 응용 프로그램 상태에 액세스하는 올바른 방법은 react-redux 및 선택기 기능.

react-reduxconnect이라는 기능을 제공합니다. 이 함수를 사용하여 우리 상태의 값을 구성 요소의 소품에 매핑하여 사용할 수 있도록 정의해야합니다.

이 매핑에 필요한 기능은 mapStateToProps이며 구성 요소에 전달되어야하는 값을 가진 개체를 반환합니다.

또한 구성 요소에서 사용할 수 있도록해야 할 redux 동작을 정의 할 수 있습니다 (예 : 다음 페이지의로드를 트리거하는 경우). 이 함수의 이름은 mapDispatchToProps입니다. 여기

예 :

import React from 'react'; 
import { connect } from 'react-redux'; 

import { getUsersPage } from './selectors'; 
import { loadUsersPage } from './actions'; 

class MyComponent extends React.Component { 
    handleScroll() { 
     this.props.loadUsersPage({ page: lastPage + 1 }); 
    } 

    render() { 
     const users = this.props.users; 

     // ... 
    } 
} 

const mapStateToThis = (state) => { 
    return { 
     users: getUsers(state) 
    }; 
} 

const mapDispatchToProps = (dispatch) => { 
    return { 
     loadUsersPage: (payload) => { 
      dispatch (loadUsersPage(payload)); 
     } 
    } 
}; 

export default connect()(MyComponent);