Просмотр исходного кода

WIP: reconstruct layouts

* on-edit configuration-dropdown
Yuki Takei 8 лет назад
Родитель
Сommit
7023ce3227
2 измененных файлов с 88 добавлено и 31 удалено
  1. 75 21
      resource/js/components/PageEditor/OptionsSelector.js
  2. 13 10
      resource/styles/scss/_on-edit.scss

+ 75 - 21
resource/js/components/PageEditor/OptionsSelector.js

@@ -6,6 +6,9 @@ import FormControl from 'react-bootstrap/es/FormControl';
 import ControlLabel from 'react-bootstrap/es/ControlLabel';
 import ControlLabel from 'react-bootstrap/es/ControlLabel';
 import Button from 'react-bootstrap/es/Button';
 import Button from 'react-bootstrap/es/Button';
 
 
+import Dropdown from 'react-bootstrap/es/Dropdown';
+import MenuItem from 'react-bootstrap/es/MenuItem';
+
 import OverlayTrigger  from 'react-bootstrap/es/OverlayTrigger';
 import OverlayTrigger  from 'react-bootstrap/es/OverlayTrigger';
 import Tooltip from 'react-bootstrap/es/Tooltip';
 import Tooltip from 'react-bootstrap/es/Tooltip';
 
 
@@ -20,6 +23,7 @@ export default class OptionsSelector extends React.Component {
     this.state = {
     this.state = {
       editorOptions: this.props.editorOptions || new EditorOptions(),
       editorOptions: this.props.editorOptions || new EditorOptions(),
       previewOptions: this.props.previewOptions || new PreviewOptions(),
       previewOptions: this.props.previewOptions || new PreviewOptions(),
+      isCddMenuOpened: false,
       isMathJaxEnabled,
       isMathJaxEnabled,
     }
     }
 
 
@@ -30,6 +34,7 @@ export default class OptionsSelector extends React.Component {
     this.onChangeTheme = this.onChangeTheme.bind(this);
     this.onChangeTheme = this.onChangeTheme.bind(this);
     this.onClickStyleActiveLine = this.onClickStyleActiveLine.bind(this);
     this.onClickStyleActiveLine = this.onClickStyleActiveLine.bind(this);
     this.onClickRenderMathJaxInRealtime = this.onClickRenderMathJaxInRealtime.bind(this);
     this.onClickRenderMathJaxInRealtime = this.onClickRenderMathJaxInRealtime.bind(this);
+    this.onToggleConfigurationDropdown = this.onToggleConfigurationDropdown.bind(this);
   }
   }
 
 
   componentDidMount() {
   componentDidMount() {
@@ -50,6 +55,9 @@ export default class OptionsSelector extends React.Component {
   }
   }
 
 
   onClickStyleActiveLine(event) {
   onClickStyleActiveLine(event) {
+    // keep dropdown opened
+    this._cddForceOpen = true;
+
     const newValue = !this.state.editorOptions.styleActiveLine;
     const newValue = !this.state.editorOptions.styleActiveLine;
     const newOpts = Object.assign(this.state.editorOptions, {styleActiveLine: newValue});
     const newOpts = Object.assign(this.state.editorOptions, {styleActiveLine: newValue});
     this.setState({editorOptions: newOpts});
     this.setState({editorOptions: newOpts});
@@ -59,6 +67,9 @@ export default class OptionsSelector extends React.Component {
   }
   }
 
 
   onClickRenderMathJaxInRealtime(event) {
   onClickRenderMathJaxInRealtime(event) {
+    // keep dropdown opened
+    this._cddForceOpen = true;
+
     const newValue = !this.state.previewOptions.renderMathJaxInRealtime;
     const newValue = !this.state.previewOptions.renderMathJaxInRealtime;
     const newOpts = Object.assign(this.state.previewOptions, {renderMathJaxInRealtime: newValue});
     const newOpts = Object.assign(this.state.previewOptions, {renderMathJaxInRealtime: newValue});
     this.setState({previewOptions: newOpts});
     this.setState({previewOptions: newOpts});
@@ -67,6 +78,19 @@ export default class OptionsSelector extends React.Component {
     this.dispatchOnChange();
     this.dispatchOnChange();
   }
   }
 
 
+  /*
+   * see: https://github.com/react-bootstrap/react-bootstrap/issues/1490#issuecomment-207445759
+   */
+  onToggleConfigurationDropdown(newValue) {
+    if (this._cddForceOpen) {
+      this.setState({ isCddMenuOpened: true });
+      this._cddForceOpen = false;
+    }
+    else {
+      this.setState({ isCddMenuOpened: newValue });
+    }
+  }
+
   /**
   /**
    * dispatch onChange event
    * dispatch onChange event
    */
    */
@@ -86,7 +110,7 @@ export default class OptionsSelector extends React.Component {
     return (
     return (
       <FormGroup controlId="formControlsSelect">
       <FormGroup controlId="formControlsSelect">
         <ControlLabel>Theme:</ControlLabel>
         <ControlLabel>Theme:</ControlLabel>
-        <FormControl componentClass="select" placeholder="select" bgSize="sm" bsClass={bsClassName} className="btn-group-sm selectpicker"
+        <FormControl componentClass="select" placeholder="select" bsClass={bsClassName} className="btn-group-sm selectpicker"
             onChange={this.onChangeTheme}
             onChange={this.onChangeTheme}
             inputRef={ el => this.themeSelectorInputEl=el }>
             inputRef={ el => this.themeSelectorInputEl=el }>
 
 
@@ -97,44 +121,74 @@ export default class OptionsSelector extends React.Component {
     )
     )
   }
   }
 
 
-  renderStyleActiveLineSelector() {
-    const bool = this.state.editorOptions.styleActiveLine;
+  renderConfigurationDropdown() {
     return (
     return (
       <FormGroup controlId="formControlsSelect">
       <FormGroup controlId="formControlsSelect">
-        <Button active={bool} className="btn-sm btn-style-active-line"
-            onClick={this.onClickStyleActiveLine}>
-          Active Line
-        </Button>
+
+        <Dropdown dropup id="configurationDropdown" className="configuration-dropdown"
+            open={this.state.isCddMenuOpened} onToggle={this.onToggleConfigurationDropdown}>
+
+          <Dropdown.Toggle bsSize="sm">
+            <i className="icon-settings"></i>
+          </Dropdown.Toggle>
+
+          <Dropdown.Menu>
+            {this.renderActiveLineMenuItem()}
+            {this.renderRealtimeMathJaxMenuItem()}
+            {/* <MenuItem divider /> */}
+          </Dropdown.Menu>
+
+        </Dropdown>
+
       </FormGroup>
       </FormGroup>
     )
     )
   }
   }
 
 
-  renderRealtimeMathJaxSelector() {
+  renderActiveLineMenuItem() {
     if (!this.state.isMathJaxEnabled) {
     if (!this.state.isMathJaxEnabled) {
       return;
       return;
     }
     }
 
 
-    // tooltip
-    const tooltip = (
-      <Tooltip id="tooltip-realtime-mathjax-rendering">Realtime MathJax Rendering</Tooltip>
-    );
+    const isActive = this.state.editorOptions.styleActiveLine;
+
+    const iconClasses = ['text-info']
+    if (isActive) {
+      iconClasses.push('ti-check')
+    }
+    const iconClassName = iconClasses.join(' ');
+
+    return (
+      <MenuItem onClick={this.onClickStyleActiveLine}>
+        <span className="icon-container"><i className={iconClassName}></i></span>
+        Show active line
+      </MenuItem>
+    )
+  }
+
+  renderRealtimeMathJaxMenuItem() {
+    if (!this.state.isMathJaxEnabled) {
+      return;
+    }
 
 
     const isEnabled = this.state.isMathJaxEnabled;
     const isEnabled = this.state.isMathJaxEnabled;
     const isActive = isEnabled && this.state.previewOptions.renderMathJaxInRealtime;
     const isActive = isEnabled && this.state.previewOptions.renderMathJaxInRealtime;
+
+    const iconClasses = ['text-info']
+    if (isActive) {
+      iconClasses.push('ti-check')
+    }
+    const iconClassName = iconClasses.join(' ');
+
     return (
     return (
-      <FormGroup controlId="formControlsSelect">
-        <OverlayTrigger placement="top" overlay={tooltip}>
-          <Button active={isActive} className="btn-sm btn-render-mathjax-in-realtime"
-              onClick={this.onClickRenderMathJaxInRealtime}>
-            <i className="fa fa-superscript" aria-hidden="true"></i>
-          </Button>
-        </OverlayTrigger>
-      </FormGroup>
+      <MenuItem onClick={this.onClickRenderMathJaxInRealtime}>
+        <span className="icon-container"><i className={iconClassName}></i></span>
+        MathJax Rendering
+      </MenuItem>
     )
     )
   }
   }
 
 
   render() {
   render() {
-    return <span>{this.renderThemeSelector()} {this.renderStyleActiveLineSelector()} {this.renderRealtimeMathJaxSelector()}</span>
+    return <span>{this.renderThemeSelector()} {this.renderConfigurationDropdown()}</span>
   }
   }
 }
 }
 
 

+ 13 - 10
resource/styles/scss/_on-edit.scss

@@ -86,14 +86,15 @@ body.on-edit {
         padding: 4px;
         padding: 4px;
         min-height: 39px;
         min-height: 39px;
         border-top: solid 1px transparent;
         border-top: solid 1px transparent;
+      }
 
 
-        .input-group-slack {
-          .input-group-addon {
-            padding: 2px 8px;
-            line-height: 1em;
-            img, input {
-              vertical-align: middle;
-            }
+      // slack
+      .input-group-slack {
+        .input-group-addon {
+          padding: 2px 8px;
+          line-height: 1em;
+          img, input {
+            vertical-align: middle;
           }
           }
         }
         }
       }
       }
@@ -265,9 +266,11 @@ body.on-edit {
       margin-right: 0.5em;
       margin-right: 0.5em;
     }
     }
 
 
-    .btn-style-active-line, .btn-render-mathjax-in-realtime {
-      &:hover:not(.active), &:focus:not(.active) {
-        background-color: inherit;
+    // configuration dropdown
+    .configuration-dropdown {
+      .icon-container {
+        display: inline-block;
+        width: 20px;
       }
       }
     }
     }