因此,我正在为自己的简历创建自己的网站,遇到了我不确定如何解决的问题。我正在使用React和Redux,出现的问题是,我想要使用集成了适当的redux的react使用轮播类型格式显示小的小项目。目前我的文件结构如下:
src/
actions/
index.js
components/
App.js
NavBar.js
Projects.js
projects/
Project1/
Project2/
containers/
Main.js
reducers/
index.js
projects.js
我不确定要如何实现自己想要的目标,我一直在寻找一个好的解决方案,但还没有真正遇到任何问题。我还是比较陌生的。我不想显示一个项目,向下滚动显示下一个项目,再滚动更多...我尝试过的是:
let components = [{TicTacToe}, {}];
let index = 0;
export default class Projects extends React.Component {
constructor(props) {
super(props);
this.state = {
component: components[0]
};
}
renderProject(i)
{
this.setState({component: components[i]});
}
backRotate()
{
index--;
if(index < 0)
{
index = components.length - 1;
}
this.renderProject(index);
}
forwardRotate()
{
index++;
if(index >= components.length)
{
index = 0;
}
this.renderProject(index);
}
render() {
return(
<div>
<button onClick='backRotate'>Back</button>
<div class='carousel-container'>
<this.state.component />
</div>
<button onClick='forwardRotate'>Next</button>
</div>
) }
}
我本来以为这可以用,但是确实坏了。我目前正在我的组件文件夹中通过App.js运行,添加了NavBar组件,然后添加了Main.js容器。之所以使用此容器,是因为我需要一个后退和前进按钮来旋转每个项目,就像图像轮播一样。我曾考虑过添加所有组件,然后只是隐藏和显示,但这似乎是不必要的资源浪费,应该有一种更好的方法来实现这一目标。
是否可以通过单击按钮来替换组件?完全删除原始组件并在其中添加新组件?如果是这样,我还如何使用redux完成此操作?目前,我的项目减速器只是一个占位符。
答案 0 :(得分:0)
首先,它中断了,因为components
数组包含对象,而React无法拥有对象。
有效的React元素可以是节点(HTMLElement,React Component,文本或数字)或节点数组。
如果您只想将React组件保留在一个集合中并能够选择要显示的组件,则首先必须删除components
数组中的括号,如下所示:
let components = [TicTacToe, AnotherComponent];
您还需要修复backRotate
和forwardRotate
处理程序。它们不能像html中那样是字符串(请注意大括号而不是引号):
<button onClick={this.backRotate}>Back</button>
<button onClick={this.forwardRotate}>Next</button>
...并且必须绑定到您的组件实例。绑定它们的一种方法是使用Function.prototype.bind方法。应该在构造函数中完成:
constructor(props) {
super(props);
this.backRotate = this.backRotate.bind(this);
this.forwardRotate= this.forwardRotate.bind(this);
}
没有绑定this
不会引用您的组件实例,并且在处理程序中调用它肯定会失败。
TicTacToe
和AnotherComponent
必须是扩展React.Component
或React.PureComponent
的类,或者必须是道具的纯功能组件。
更清晰,可能会更支持声明包含组件的大写变量:
render() {
const Comp = this.state.component;
return (
<div>
<button onClick={this.backRotate}>Back</button>
<div class='carousel-container'>
<Comp />
</div>
<button onClick={this.forwardRotate}>Next</button>
</div>
);
}
最后,您应该使index
成为组件的状态(随组件的控件而改变),并使components
成为道具(其在组件内不会改变)。
您将设置当前组件索引,而不是将当前组件设置为状态:
import React from 'react':
import PropTypes from 'prop-types';
import { TicTacToe, AnotherComponent } from 'path/to/named/imports/TicTacToeAndAnotherComponent';
export default class Projects extends React.Component {
static propTypes = {
components: PropTypes.any,
}
static defaultProps = {
components: [TicTacToe, AnotherComponent],
}
constructor(props) {
super(props);
this.state = {
index: 0,
};
this.backRotate = this.backRotate.bind(this);
this.forwardRotate= this.forwardRotate.bind(this);
}
backRotate() {
const { components } = this.props;
const { index } = this.state;
if(index - 1 < 0) {
this.setState(() => ({ index: components.length - 1 }));
} else {
this.setState(() => ({ index: index - 1 }));
}
}
forwardRotate() {
const { components } = this.props;
const { index } = this.state;
if(index >= components.length) {
this.setState(() => ({ index: 0 }));
} else {
this.setState(() => ({ index: index + 1 }));
}
}
render() {
const Comp = this.props.components[this.state.index];
return (
<div>
<button onClick={this.backRotate}>Back</button>
<div class='carousel-container'>
<Comp />
</div>
<button onClick={this.forwardRotate}>Next</button>
</div>
);
}
}
无论哪种方式,Redux都无法帮助您。
Redux的目的主要是提供单一数据源(单一事实源),提供操作和简化程序以对该数据进行突变,并通知注册的组件以监听存储更新。您是否将轮播与商店连接都与解决iisue无关。