【发布时间】:2018-03-25 21:06:40
【问题描述】:
我有一个使用参数调用的应用程序。现在,我的菜单总是加载到默认的 MainMenu。我希望能够将状态传递给 Menu.js 并从打开的不同菜单开始,而不是默认的 MainMenu。
我认为 componentWillMount() 可以让我将状态设置为我选择的菜单状态,但无论出于何种原因,它都不会更新呈现的内容。当我调用它时,this.state.Selected 成为我想要呈现的正确菜单名称......但它实际上并没有呈现 - 它最终呈现默认菜单。
所以我必须在 componentWillMount() 之后调用其他东西才能让它真正呈现?
Landing.js - 调用 Menu.js。我想先渲染菜单“FileOptions”。但是,它当前正在渲染 MainMenu。
import React, { Component } from 'react'
import sass from '../scss/application.scss'
import PropTypes from 'prop-types'
import Header from './Header'
import Menu from './Menu'
import HelpFile from './HelpFile'
class Landing extends Component {
constructor(props) {
super(props);
this.state = {
helpFileName: 'Mainmenu',
menuName: 'FileOptions',
}
}
handleHelpChange(helpFileName) {
this.setState( {helpFileName} );
}
handleMenuClick(menuName) {
this.setState( {menuName} );
}
componentWillMount() {
let hlpString = require('electron').remote.getGlobal('sharedObject').hlpOne;
if (hlpString != null && hlpString != '.')
{
this.setState({
helpFileName: hlpString
});ss
}
}
render() {
return (
<div>
<div>
<Header />
</div>
<br /><br />
<div className="mainMenuDiv">
<Menu handleHelpChange={this.handleHelpChange.bind(this)} menuName={this.state.menuName}/>
</div>
<div className="mainContainerDiv">
<HelpFile name={this.state.helpFileName}/>
</div>
</div>
)
}
}
export default Landing;
菜单.js
import React, { Component } from 'react'
import sass from '../scss/application.scss'
import PropTypes from 'prop-types'
class Menu extends Component {
constructor(props) {
super(props);
this.state = {
Selected: props.menuName, // reads FileOptions, but still renders MainMenu
name: ''
}
}
handleChange(name) {
this.setState({
name: name
});
}
handleClick(e, num) {
this.setState({
name: num
}, () => {
let helpFileName = num;
helpFileName = helpFileName.toLowerCase().trim();
//Cap the first letter in the name and add the rest of the name
helpFileName = helpFileName.charAt(0).toUpperCase() + helpFileName.substr(1);
this.props.handleHelpChange(helpFileName);
});
}
handleMenuClick(e, num, opt) {
this.setState({
name: num,
Selected: opt
}, () => {
let helpFileName = num;
helpFileName = helpFileName.toLowerCase().trim();
//Cap the first letter in the name and add the rest of the name
helpFileName = helpFileName.charAt(0).toUpperCase() + helpFileName.substr(1);
this.props.handleHelpChange(helpFileName);
});
}
render() {
const MainMenu = () => (
<div>
<button
label="File Options"
//onClick={() => this.setState({ Selected: FileOptions })}
onClick={(e) => this.handleMenuClick(e, 'Fileopt', FileOptions)}
className="aMenuButton"
>FILE OPTIONS</button>
<button
label="Setup Options"
onClick={(e) => this.handleMenuClick(e, 'Setupopt', SetUpOptions)}
className="aMenuButton"
>SETUP OPTIONS</button>
<button
label="Lumber Options"
onClick={(e) => this.handleMenuClick(e, 'Lumberopt', MoreOptions)}
className="aMenuButton"
>MORE OPTIONS</button>
<button
label="Main Menu"
onClick={(e) => this.handleClick(e, 'Mainmenu')}
className="aPrevButton"
>MAIN MENU</button>
</div>
);
const FileOptions = () => (
<div>
<button
label="Option One"
onClick={(e) => this.handleClick(e, 'Option One')}
className="aMenuButton"
>Option One</button>
<button
label="Option Two"
onClick={(e) => this.handleClick(e, 'Option Two')}
className="aMenuButton"
>Option Two</button>
<button
label="Option Three"
onClick={(e) => this.handleClick(e, 'Option Three')}
className="aMenuButton"
>Option Three</button>
<button
label="Option Four"
onClick={(e) => this.handleClick(e, 'Option Four')}
className="aMenuButton"
>Option Four</button>
<button
label="Previous Menu"
onClick={() => this.setState({ Selected: MainMenu })}
className="aPrevButton"
>PREVIOUS MENU</button>
</div>
);
const SetUpOptions = () => (
<div>
<button
label="Option One"
onClick={(e) => this.handleClick(e, 'Option One')}
className="aMenuButton"
>Option One</button>
<button
label="Option Two"
onClick={(e) => this.handleClick(e, 'Option Two')}
className="aMenuButton"
>Option Two</button>
<button
label="Option Three"
onClick={(e) => this.handleClick(e, 'Option Three')}
className="aMenuButton"
>Option Three</button>
<button
label="Previous Menu"
onClick={() => this.setState({ Selected: MainMenu })}
className="aPrevButton"
>PREVIOUS MENU</button>
</div>
);
const MoreOptions = () => (
<div>
<button
label="Option One"
onClick={(e) => this.handleClick(e, 'Option One')}
className="aMenuButton"
>Option One</button>
<button
label="Option Two"
onClick={(e) => this.handleClick(e, 'Option Two')}
className="aMenuButton"
>Option Two</button>
<button
label="Option Three"
onClick={(e) => this.handleClick(e, 'Option Three')}
className="aMenuButton"
>Option Three</button>
<button
label="Option Four"
onClick={(e) => this.handleClick(e, 'Option Four')}
className="aMenuButton"
>Option Four</button>
<button
label="Previous Menu"
onClick={() => this.setState({ Selected: MainMenu })}
className="aPrevButton"
>PREVIOUS MENU</button>
</div>
);
const { Selected } = this.state;
return (
<div>
<div className="menuButtons">
{Selected === 'MainMenu' ? <MainMenu /> : <Selected /> }
</div>
</div>
)
}
}
Menu.propTypes = {
handleHelpChange: PropTypes.func,
name: PropTypes.string,
menuName: PropTypes.string
}
export default Menu;
【问题讨论】:
-
我认为菜单中的渲染功能存在错误。您不能只将字符串更改为 React 组件。如果 Selected = "FileOptions",则不能执行
并期望它是 。我不确定它为什么会呈现 MainMenu,您可能想检查从 require('electron').remote.getGlobal('sharedObject').hlpOne返回的内容@ -
sharedObject 呈现页面内容并且不会弄乱菜单。现在
渲染 MainMenu 或 FileOptions 因为 const { Selected } = this.state。当一个菜单项被点击时,状态被更新并且一个函数被调用导致组件重新渲染。整个菜单系统运行良好,它总是必须从 MainMenu 开始。希望找到一种方法从不同的菜单点开始,例如 FileOptions
标签: reactjs components render lifecycle