【发布时间】:2017-04-12 11:47:33
【问题描述】:
我正在制作一个分页组件,但我遇到了传递给这个分页组件的道具的问题。元素道具会自动更新,所以我不能使用 componentWillReceiveProps 来更新我的组件。
这是我的父组件对 Paginate 组件的渲染和回调:
class AlarmManagement extends React.Component{
constructor(props){
super(props)
this.state = {
alarms: undefined,
nameIsOrdered: false,
codeIsOrdered: true,
priorityIsOrdered: false,
alarmsPaginate: undefined,
}
this.orderByName = this.orderByName.bind(this)
this.orderByCode = this.orderByCode.bind(this)
this.orderByPriority = this.orderByPriority.bind(this)
this.getAlarms = this.getAlarms.bind(this)
this.getAlarmsPaginate = this.getAlarmsPaginate.bind(this)
}
componentWillMount(){
this.getAlarms()
}
getAlarms(){
$.ajax({
type: 'GET',
url: '/api/alarm-event-types/',
headers: { 'Authorization': "Token " + localStorage.token },
success: (alarms) => {
this.setState({
alarms: alarms.sort((a, b) => a.code - b.code)
})
},
error: (fail) => console.log(fail)
})
}
getAlarmsPaginate(page, amount) {
const newAlarms = this.state.alarms
this.setState({ alarmsPaginate: newAlarms.slice(page, amount) });
}
componentWillReceiveProps({emergency}){
if(emergency !== undefined && emergency !== null){
let updateList = [],
shouldUpdate = false
emergency.forEach((el, index) => {
if(el.update){
updateList.push(index)
}
if(el.update == "alarm"){
shouldUpdate = true
}
})
if(shouldUpdate){
this.getAlarms()
}
updateList.forEach((el) => {
if(this.props.clearList){
this.props.clearList(el)
}
})
}
}
orderByName(){
let alarms = this.state.alarms
if(this.state.nameIsOrdered === true){
this.setState({
alarms: alarms.sort((a, b) => {
let nameA = `${a.name.toUpperCase()}`,
nameB = `${b.name.toUpperCase()}`
if (nameA > nameB) {
return 1;
}
if (nameA < nameB) {
return -1;
}
return 0;
}),
nameIsOrdered: false,
codeIsOrdered: false,
priorityIsOrdered: false
})
}
else{
this.setState({
alarms: alarms.sort((a, b) => {
let nameA = `${a.name.toUpperCase()}`,
nameB = `${b.name.toUpperCase()}`
if (nameB > nameA) {
return 1;
}
if (nameB < nameA) {
return -1;
}
return 0;
}),
nameIsOrdered: true,
codeIsOrdered: false,
priorityIsOrdered: false
})
}
}
orderByCode(){
let alarms = this.state.alarms
if(this.state.codeIsOrdered === true){
this.setState({
alarms: alarms.sort((a, b) => b.code - a.code),
codeIsOrdered: false,
nameIsOrdered: false,
priorityIsOrdered: false
})
}
else{
this.setState({
alarms: alarms.sort((a, b) => a.code - b.code),
codeIsOrdered: true,
nameIsOrdered: false,
priorityIsOrdered: false
})
}
}
orderByPriority(){
let alarms = this.state.alarms
if(this.state.priorityIsOrdered === true){
this.setState({
alarms: alarms.sort((a, b) => b.priority - a.priority),
nameIsOrdered: false,
codeIsOrdered: false
})
}
else{
this.setState({
alarms: alarms.sort((a, b) => a.priority - b.priority),
nameIsOrdered: false,
codeIsOrdered: false
})
}
this.setState(prevState => ({
priorityIsOrdered: !prevState.priorityIsOrdered,
}))
}
render(){
const alarms = this.state.alarms,
alarmsPaginate = this.state.alarmsPaginate;
return(
this.props.user.groups == 1 ? (
<div className="contactto-middle-content">
<ManagementMenu/>
<div className="management-content">
<div className="list-management-subtitle">ALARMES</div>
<button type="button" className="btn btn--save-attend-or-add-someone btn--color-tecno" onClick={() => browserHistory.push('/app/alarms/form/add')}>
<div><span className="btn--bold">+ ADICIONAR</span> ALARME</div>
</button>
{alarms &&
<div className="list-table">
<Paginate outerClass="paginate-wrapper" filterElements={this.getAlarmsPaginate} maxElements={5} elements={alarms} />
<div className="list-table-header">
<div className="left list-table--200"><span className="icons-order clickable" onClick={this.orderByName}>Nome<Order width="15" height="10"/></span></div>
<div className="left list-table--200"><span className="icons-order clickable" onClick={this.orderByCode}>Código<Order width="15" height="10"/></span></div>
<div className="left list-table--200"><span className="icons-order clickable" onClick={this.orderByPriority}>Prioridade<Order width="15" height="10"/></span></div>
<div className="list-table-body-column--action--2icons"></div>
</div>
<div className="list-table-body scroll">
{alarmsPaginate && alarmsPaginate.map((alarm) =>
<AlarmRow key={alarm.code} alarm={alarm} getAlarms={this.getAlarms} channelId={this.props.channelId} iconDetail={this.refs["iconDetail"]}/>
)}
</div>
</div>
}
</div>
</div>
):
<div className="error">Página não pode ser acessada, pois você não é um administrador</div>
)
}
}
export default AlarmManagement
这是我的分页组件:
export default class Paginate extends React.Component{
constructor(props){
super(props)
this.state = {
pagesNumber: undefined,
elements: undefined,
elementsNumber: undefined,
startNumber: undefined,
endNumber: undefined,
pos: undefined,
}
this.nextList = this.nextList.bind(this)
this.previousList = this.previousList.bind(this)
}
previousList(){
if(this.state.pos > 1){
let pos = this.state.pos - 1
this.changePage(pos)
}
}
nextList(){
if(this.state.pos < this.state.pagesNumber){
let pos = this.state.pos + 1
this.changePage(pos)
}
}
changePage(pos){
const newStartNumber = pos === 1 ? 0 : this.props.maxElements * (pos - 1);
const newEndNumber = this.props.maxElements * pos > this.state.elementsNumber ? this.state.elementsNumber : this.props.maxElements * pos;
this.props.filterElements(newStartNumber, newEndNumber);
this.setState({
pos: pos,
startNumber: newStartNumber,
endNumber: newEndNumber,
});
}
componentWillReceiveProps(nextProps){
console.log(nextProps.elements != this.props.elements ? 'different' : 'equal')
}
componentWillMount(){
this.setState((prevState, props) => ({
pagesNumber: props.elements ? Math.ceil(props.elements.length / props.maxElements) : 0,
elements: props.elements,
elementsNumber: props.elements.length,
startNumber: 1,
endNumber: props.maxElements,
pos: 1,
}));
if(this.props.filterElements){
this.props.filterElements(0, this.props.maxElements)
}
}
render(){
const elementsNumber = this.state.elementsNumber,
startNumber = this.state.startNumber,
endNumber = this.state.endNumber;
return(
<div className={this.props.outerClass}>
{elementsNumber > this.props.maxElements &&
<div className="left contactto-100">
{elementsNumber && <span className="left">{`${startNumber === 0 ? 1 : startNumber}-${endNumber} de ${elementsNumber}`}</span>}
<span className="paginate-arrow paginate-arrow-left" onClick={this.previousList}></span>
<span className="paginate-arrow paginate-arrow-right" onClick={this.nextList}></span>
</div>
}
</div>
)
}
}
Paginate.defaultProps = {
outerClass: 'paginate-wrapper'
}
Paginate.propTypes = {
outerClass: React.PropTypes.string,
filterElements: React.PropTypes.func.isRequired,
maxElements: React.PropTypes.number.isRequired,
elements: React.PropTypes.arrayOf(React.PropTypes.object).isRequired,
}
componentWillReceive props 中记录的元素是一样的。
根据帖子建议更新了代码,但是: 组件WillReceiveProps(nextProps){ console.log(nextProps.elements != this.props.elements ? 'different' : 'equal') // 仍然相等 }
怎么了?
提前致谢。
【问题讨论】:
标签: reactjs pagination