目前正在尝试学习React。我有一个组件可以根据一些过滤器返回许多海报,我将如何读取渲染的海报数组的长度?
因此,我可以创建一个标题,例如“显示6/10个海报”
render() {
return (
<div className="App">
<Title />
<Posters
selectedGenre={this.state.genre}
selectedCategory={this.state.category}
titles={this.state.titles}
/>
</div>
);
}
我当时正在考虑将Posters函数嵌入render()中,因此我可以执行以下操作:const posters = this.state.titles.map(title=>...)
然后是const filteredPosters = posters.length
。但是试图找到一种分离逻辑的方法
感谢您的帮助。
答案 0 :(得分:0)
正如我在评论中所指出的那样,将标题设为<Posters />
组件的一部分,并使用props提供总数/已过滤的数字:
class Posters extends React.Component {
render() {
const { titles } = this.state;
const filteredTitles = this.filterTitles(titles);
return
<>
<Header totalSize={titles.length} displayedSize={filteredTitles.length} />
{filteredTitles.map(title => <Poster title={title} />)}
</>
}
}
答案 1 :(得分:0)
我知道这个问题已经回答了,但是对于将来的观众,我将发布另一种解决此问题的方法。下例显示了如何将数据从一个组件发送到另一个完全不相关的组件。 注意:搜索“杰克”或“史密斯” // HTML // JavaScript Page类扩展了React.Component {
constructor(props) {
super(props)
this.state = {
logo: '[logoImage]',
totalPosters: 0,
filteredPosters: 0,
activeFilter: ''
}
}
postersUpdated(event) {
this.state.totalPosters = event.totalPosters;
this.state.activeFilter = event.filter;
this.setState({
filteredPosters: event.filteredPosters,
totalPosters: event.totalPosters,
activeFilter: event.filter
});
}
render() {
return (
<div className='page'>
<span>{this.state.logo}</span>
<Header
totalPosters={this.state.totalPosters}
filteredPosters={this.state.filteredPosters}
activeFilter={this.state.activeFilter}
></Header>
<Posters ref={this.posters} onChange={this.postersUpdated.bind(this)}></Posters>
</div>
)
}
};
class Header extends React.Component {
constructor(props) {
super(props)
}
render() {
return (
<div>
Results for: "{this.props.activeFilter}":
{this.props.filteredPosters} /{this.props.totalPosters}
</div>)
}
};
class Posters extends React.Component {
constructor(props) {
super(props)
this.state = {
filter: '',
posters: [
{ name: "John Smith" },
{ name: "Mike" },
{ name: "Alice" },
{ name: "Jake" }
]
}
this.setFilter = this.setFilter.bind(this);
}
get filteredPosters() {
return this.state.posters.filter((poster) => {
if (!this.state.filter || !poster.name) { return; }
return poster.name.indexOf(this.state.filter) !== -1;
});
}
setFilter(event) {
this.setState({filter: event.target.value}, () => {
// send useful info to parent
// e.g page can show n out of x posters found
// active search word is "xxx" etc.
this.props.onChange({
filteredPosters: this.filteredPosters.length,
totalPosters: this.state.posters.length,
filter: this.state.filter
});
});
}
render() {
return (
<div>
<ol>
{this.filteredPosters.map(item => (
<li key={item.id}>
<label>
<span>{item.name}</span>
</label>
</li>
))}
</ol>
<input type="text" value={this.state.filter} onChange={this.setFilter} />
</div>
)
}
}
ReactDOM.render(<Page />, document.querySelector("#app"))
// CSS
body {
background: #20262E;
padding: 20px;
font-family: Helvetica;
}
#app {
background: #fff;
border-radius: 4px;
padding: 20px;
transition: all 0.2s;
}
li {
margin: 8px 0;
}
h2 {
font-weight: bold;
margin-bottom: 15px;
}
input {
margin-right: 5px;
}