Javascript 为反应组件设置默认道具
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/38004703/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Set default props for a react Component
提问by Mithril
I want my app component has a default props , and use that props in mapStateToProps
.
我希望我的应用程序组件有一个默认的 props ,并在 mapStateToProps
.
containers/App.js
容器/App.js
import React, { Component, PropTypes } from 'react';
import { bindActionCreators } from 'redux';
import { connect } from 'react-redux';
import Footer from '../components/Footer';
import TreeNode from '../containers/TreeNode';
import Home from '../containers/Home';
import * as NodeActions from '../actions/NodeActions'
export default class App extends Component {
constructor(props, context) {
super(props, context)
this.props = {
info:{
path:'/'
}
}
}
componentWillMount() {
// this will update the nodes on state
this.props.actions.openNode('/');
}
render() {
const { node , actions} = this.props
console.log(this.props)
return (
<div className="main-app-container">
<Home />
<div className="main-app-nav">Simple Redux Boilerplate</div>
{node.childNodes &&
<div>{node.childNodes.map(node => <TreeNode key={info.path} info={node} tree={tree} actions={actions} />)}</div>
}
{!node.childNodes &&
<div>no children</div>
}
{/*<Footer />*/}
</div>
);
}
}
App.defaultProps = {
info:{
path:'/'
}
};
function mapStateToProps(state, ownProps) {
console.log('state')
console.log(state)
console.log('ownProps')
console.log(ownProps)
return {
node: ownProps.info.path? state.TreeNodeReducer.tree[ownProps.info.path] : {}
};
}
function mapDispatchToProps(dispatch) {
return {
actions: bindActionCreators(NodeActions, dispatch)
};
}
export default connect(
mapStateToProps,
mapDispatchToProps
)(App);
reducers/TreeNodeReducer.js
减速器/TreeNodeReducer.js
import { OPEN_NODE, CLOSE_NODE, GET_NODES } from '../constants/NodeActionTypes';
import UUID from "node-uuid"
const initialState = {
open: false,
info: {}
}
class NodeModel {
constructor(path, type, right) {
this.name = path;
this.path = path;
this.type = type;
this.right = right;
}
}
let lastId = 0;
function getFileList() {
var testNodes = []
for (var i=0; i< 3; i++) {
testNodes.push(new NodeModel(lastId,'d', i.toString()))
lastId++;
}
return testNodes
}
const getNodes = (state, action) => {
var { path } = action
var tree = state.tree ? state.tree : {}
tree[path] = getFileList(path)
return {
...state,
tree:tree
};
};
export default function (state = initialState, action) {
switch (action.type) {
case OPEN_NODE:
return { ...getNodes(state, action), open:true };
case GET_NODES:
return getNodes(state, action);
case CLOSE_NODE:
return {
...state,
open:false
};
default:
return state;
}
}
I have tried :
我试过了 :
1: constructor
1:构造函数
constructor(props, context) {
super(props, context)
this.props = {
info:{
path:'/'
}
}
}
2: defaultProps:
2:默认道具:
App.defaultProps = {
info:{
path:'/'
}
};
but none of them work... log always is:
但他们都没有工作......日志总是:
state
has the correct default value, but ownProps
is empty...
state
具有正确的默认值,但ownProps
为空...
PS:Project is here .
PS:项目在这里。
采纳答案by mrlew
1) two "export default"
1)两个“出口默认”
you're doing two export default
into App.js
.
你做了两export default
成App.js
。
Try changing:
尝试改变:
export default class App extends Component
export default class App extends Component
to
到
const App = class App extends Component
.
const App = class App extends Component
.
And then:
进而:
...
App.defaultProps = {
info:{
path:'/'
}
};
...
export default connect(
mapStateToProps,
mapDispatchToProps
)(App);
2) "defaultProps" and "ownProps":
2)“defaultProps”和“ownProps”:
As mapStateToProps
is being called before the component construction (when defaultProps are defined), the ownProps
is empty. You can try two options:
作为mapStateToProps
在部件施工前被调用(defaultProps被定义时),则ownProps
是空的。您可以尝试两种选择:
1) this workaround:
1)这个解决方法:
App.defaultProps = {
info: {
path:'/'
}
}
function mapStateToProps(state, ownProps) {
console.log('state')
console.log(state)
console.log('ownProps')
console.log(ownProps)
const path = ownProps.info && ownProps.info.path ? ownProps.info.path : App.defaultProps.info.path;
return {
node: path ? state.TreeNodeReducer.tree[path] : {}
};
}
2) apparently, ownProps
first call is feeded with the inline defined props. So, you can call <App />
this way in the index.js
:
2)显然,ownProps
第一个调用是用内联定义的道具提供的。所以,你可以调用<App />
这样的index.js
:
<App info={{ path:'/' }} />
Anyway, after solving this, another error is thrown (Cannot read property '/' of undefined
) when trying to read tree
from the reducer (doesn't exist there).
无论如何,解决此问题后,Cannot read property '/' of undefined
尝试tree
从减速器读取时会引发另一个错误 ( ) (那里不存在)。
回答by Mithril
I found a better way to set defaultProps,
我找到了一个更好的方法来设置 defaultProps,
Because connect()
returns a new component. If you'd like defaultProps to be present on it, you need to put defaultProps on it:
因为connect()
返回一个新组件。如果您希望 defaultProps 出现在其上,则需要将 defaultProps 放在其上:
App = connect(
mapStateToProps,
mapDispatchToProps
)(App);
App.defaultProps = {
path:'/'
};
export default App
This would work!
这行得通!