Merge pull request #9 from MathuraMG/pref
Add indentation to preferences
This commit is contained in:
commit
13aeed8092
11 changed files with 216 additions and 30 deletions
|
@ -8,6 +8,12 @@ export const OPEN_PREFERENCES = 'OPEN_PREFERENCES';
|
||||||
export const CLOSE_PREFERENCES = 'CLOSE_PREFERENCES';
|
export const CLOSE_PREFERENCES = 'CLOSE_PREFERENCES';
|
||||||
export const INCREASE_FONTSIZE = 'INCREASE_FONTSIZE';
|
export const INCREASE_FONTSIZE = 'INCREASE_FONTSIZE';
|
||||||
export const DECREASE_FONTSIZE = 'DECREASE_FONTSIZE';
|
export const DECREASE_FONTSIZE = 'DECREASE_FONTSIZE';
|
||||||
|
export const UPDATE_FONTSIZE = 'UPDATE_FONTSIZE';
|
||||||
|
export const INCREASE_INDENTATION = 'INCREASE_INDENTATION';
|
||||||
|
export const DECREASE_INDENTATION = 'DECREASE_INDENTATION';
|
||||||
|
export const UPDATE_INDENTATION = 'UPDATE_INDENTATION';
|
||||||
|
export const INDENT_WITH_SPACE = 'INDENT_WITH_SPACE';
|
||||||
|
export const INDENT_WITH_TAB = 'INDENT_WITH_TAB';
|
||||||
|
|
||||||
export const AUTH_USER = 'AUTH_USER';
|
export const AUTH_USER = 'AUTH_USER';
|
||||||
export const UNAUTH_USER = 'UNAUTH_USER';
|
export const UNAUTH_USER = 'UNAUTH_USER';
|
||||||
|
|
|
@ -23,3 +23,43 @@ export function decreaseFont() {
|
||||||
type: ActionTypes.DECREASE_FONTSIZE
|
type: ActionTypes.DECREASE_FONTSIZE
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export function updateFont(event) {
|
||||||
|
const value = event.target.value;
|
||||||
|
return {
|
||||||
|
type: ActionTypes.UPDATE_FONTSIZE,
|
||||||
|
value
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
export function increaseIndentation() {
|
||||||
|
return {
|
||||||
|
type: ActionTypes.INCREASE_INDENTATION
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
export function decreaseIndentation() {
|
||||||
|
return {
|
||||||
|
type: ActionTypes.DECREASE_INDENTATION
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
export function updateIndentation() {
|
||||||
|
const value = event.target.value;
|
||||||
|
return {
|
||||||
|
type: ActionTypes.UPDATE_INDENTATION,
|
||||||
|
value
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
export function indentWithTab() {
|
||||||
|
return {
|
||||||
|
type: ActionTypes.INDENT_WITH_TAB
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
export function indentWithSpace() {
|
||||||
|
return {
|
||||||
|
type: ActionTypes.INDENT_WITH_SPACE
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
|
@ -18,6 +18,8 @@ class Editor extends React.Component {
|
||||||
this.props.updateFileContent(this.props.file.name, this._cm.getValue());
|
this.props.updateFileContent(this.props.file.name, this._cm.getValue());
|
||||||
});
|
});
|
||||||
this._cm.getWrapperElement().style['font-size'] = `${this.props.fontSize}px`;
|
this._cm.getWrapperElement().style['font-size'] = `${this.props.fontSize}px`;
|
||||||
|
this._cm.setOption('indentWithTabs', this.props.isTabIndent);
|
||||||
|
this._cm.setOption('tabSize', this.props.indentationAmount);
|
||||||
}
|
}
|
||||||
|
|
||||||
componentDidUpdate(prevProps) {
|
componentDidUpdate(prevProps) {
|
||||||
|
@ -28,6 +30,12 @@ class Editor extends React.Component {
|
||||||
if (this.props.fontSize !== prevProps.fontSize) {
|
if (this.props.fontSize !== prevProps.fontSize) {
|
||||||
this._cm.getWrapperElement().style['font-size'] = `${this.props.fontSize}px`;
|
this._cm.getWrapperElement().style['font-size'] = `${this.props.fontSize}px`;
|
||||||
}
|
}
|
||||||
|
if (this.props.indentationAmount !== prevProps.indentationAmount) {
|
||||||
|
this._cm.setOption('tabSize', this.props.indentationAmount);
|
||||||
|
}
|
||||||
|
if (this.props.isTabIndent !== prevProps.isTabIndent) {
|
||||||
|
this._cm.setOption('indentWithTabs', this.props.isTabIndent);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
componentWillUnmount() {
|
componentWillUnmount() {
|
||||||
|
@ -42,12 +50,14 @@ class Editor extends React.Component {
|
||||||
}
|
}
|
||||||
|
|
||||||
Editor.propTypes = {
|
Editor.propTypes = {
|
||||||
|
indentationAmount: PropTypes.number.isRequired,
|
||||||
|
isTabIndent: PropTypes.bool.isRequired,
|
||||||
|
updateFileContent: PropTypes.func.isRequired,
|
||||||
|
fontSize: PropTypes.number.isRequired,
|
||||||
file: PropTypes.shape({
|
file: PropTypes.shape({
|
||||||
name: PropTypes.string.isRequired,
|
name: PropTypes.string.isRequired,
|
||||||
content: PropTypes.string.isRequired
|
content: PropTypes.string.isRequired
|
||||||
}),
|
})
|
||||||
updateFileContent: PropTypes.func.isRequired,
|
|
||||||
fontSize: PropTypes.number.isRequired
|
|
||||||
};
|
};
|
||||||
|
|
||||||
export default Editor;
|
export default Editor;
|
||||||
|
|
|
@ -11,6 +11,14 @@ function Preferences(props) {
|
||||||
preferences: true,
|
preferences: true,
|
||||||
'preferences--selected': props.isVisible
|
'preferences--selected': props.isVisible
|
||||||
});
|
});
|
||||||
|
let preferencesTabOptionClass = classNames({
|
||||||
|
preference__option: true,
|
||||||
|
'preference__option--selected': props.isTabIndent
|
||||||
|
});
|
||||||
|
let preferencesSpaceOptionClass = classNames({
|
||||||
|
preference__option: true,
|
||||||
|
'preference__option--selected': !props.isTabIndent
|
||||||
|
});
|
||||||
return (
|
return (
|
||||||
<div className={preferencesContainerClass} tabIndex="0">
|
<div className={preferencesContainerClass} tabIndex="0">
|
||||||
<div className="preferences__heading">
|
<div className="preferences__heading">
|
||||||
|
@ -19,16 +27,37 @@ function Preferences(props) {
|
||||||
<Isvg src={exitUrl} alt="Exit Preferences" />
|
<Isvg src={exitUrl} alt="Exit Preferences" />
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div className="preference">
|
<div className="preference">
|
||||||
<h3 className="preference__title">Text Size</h3>
|
<h4 className="preference__title">Text Size</h4>
|
||||||
<button className="preference__plus-button" onClick={props.decreaseFont}>
|
<button className="preference__plus-button" onClick={props.decreaseFont}>
|
||||||
<Isvg src={minusUrl} alt="Decrease Font Size" />
|
<Isvg src={minusUrl} alt="Decrease Font Size" />
|
||||||
|
<h6 className="preference__label">Decrease</h6>
|
||||||
</button>
|
</button>
|
||||||
<p className="preference__value">{props.fontSize}</p>
|
|
||||||
|
<input className="preference__value" value={props.fontSize} onChange={props.updateFont}></input>
|
||||||
<button className="preference__minus-button" onClick={props.increaseFont}>
|
<button className="preference__minus-button" onClick={props.increaseFont}>
|
||||||
<Isvg src={plusUrl} alt="Increase Font Size" />
|
<Isvg src={plusUrl} alt="Increase Font Size" />
|
||||||
|
<h6 className="preference__label">Increase</h6>
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div className="preference">
|
||||||
|
<h4 className="preference__title">Indentation Amount</h4>
|
||||||
|
<button className="preference__plus-button" onClick={props.decreaseIndentation}>
|
||||||
|
<Isvg src={minusUrl} alt="DecreaseIndentation Amount" />
|
||||||
|
<h6 className="preference__label">Decrease</h6>
|
||||||
|
</button>
|
||||||
|
<input className="preference__value" value={props.indentationAmount} onChange={props.updateIndentation}></input>
|
||||||
|
<button className="preference__minus-button" onClick={props.increaseIndentation}>
|
||||||
|
<Isvg src={plusUrl} alt="IncreaseIndentation Amount" />
|
||||||
|
<h6 className="preference__label">Increase</h6>
|
||||||
|
</button>
|
||||||
|
<div className="preference__vertical-list">
|
||||||
|
<button className={preferencesSpaceOptionClass} onClick={props.indentWithSpace}>Spaces</button>
|
||||||
|
<button className={preferencesTabOptionClass} onClick={props.indentWithTab}>Tabs</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -37,8 +66,16 @@ Preferences.propTypes = {
|
||||||
isVisible: PropTypes.bool.isRequired,
|
isVisible: PropTypes.bool.isRequired,
|
||||||
closePreferences: PropTypes.func.isRequired,
|
closePreferences: PropTypes.func.isRequired,
|
||||||
decreaseFont: PropTypes.func.isRequired,
|
decreaseFont: PropTypes.func.isRequired,
|
||||||
|
updateFont: PropTypes.func.isRequired,
|
||||||
fontSize: PropTypes.number.isRequired,
|
fontSize: PropTypes.number.isRequired,
|
||||||
increaseFont: PropTypes.func.isRequired
|
increaseFont: PropTypes.func.isRequired,
|
||||||
|
indentationAmount: PropTypes.number.isRequired,
|
||||||
|
decreaseIndentation: PropTypes.func.isRequired,
|
||||||
|
increaseIndentation: PropTypes.func.isRequired,
|
||||||
|
updateIndentation: PropTypes.func.isRequired,
|
||||||
|
indentWithSpace: PropTypes.func.isRequired,
|
||||||
|
indentWithTab: PropTypes.func.isRequired,
|
||||||
|
isTabIndent: PropTypes.bool.isRequired
|
||||||
};
|
};
|
||||||
|
|
||||||
export default Preferences;
|
export default Preferences;
|
||||||
|
|
|
@ -44,7 +44,15 @@ class IDEView extends React.Component {
|
||||||
closePreferences={this.props.closePreferences}
|
closePreferences={this.props.closePreferences}
|
||||||
increaseFont={this.props.increaseFont}
|
increaseFont={this.props.increaseFont}
|
||||||
decreaseFont={this.props.decreaseFont}
|
decreaseFont={this.props.decreaseFont}
|
||||||
|
updateFont={this.props.updateFont}
|
||||||
fontSize={this.props.preferences.fontSize}
|
fontSize={this.props.preferences.fontSize}
|
||||||
|
increaseIndentation={this.props.increaseIndentation}
|
||||||
|
decreaseIndentation={this.props.decreaseIndentation}
|
||||||
|
updateIndentation={this.props.updateIndentation}
|
||||||
|
indentationAmount={this.props.preferences.indentationAmount}
|
||||||
|
isTabIndent={this.props.preferences.isTabIndent}
|
||||||
|
indentWithSpace={this.props.indentWithSpace}
|
||||||
|
indentWithTab={this.props.indentWithTab}
|
||||||
/>
|
/>
|
||||||
<Sidebar
|
<Sidebar
|
||||||
files={this.props.files}
|
files={this.props.files}
|
||||||
|
@ -55,6 +63,8 @@ class IDEView extends React.Component {
|
||||||
file={this.props.selectedFile}
|
file={this.props.selectedFile}
|
||||||
updateFileContent={this.props.updateFileContent}
|
updateFileContent={this.props.updateFileContent}
|
||||||
fontSize={this.props.preferences.fontSize}
|
fontSize={this.props.preferences.fontSize}
|
||||||
|
indentationAmount={this.props.preferences.indentationAmount}
|
||||||
|
isTabIndent={this.props.preferences.isTabIndent}
|
||||||
files={this.props.files}
|
files={this.props.files}
|
||||||
/>
|
/>
|
||||||
<PreviewFrame
|
<PreviewFrame
|
||||||
|
@ -93,11 +103,19 @@ IDEView.propTypes = {
|
||||||
openPreferences: PropTypes.func.isRequired,
|
openPreferences: PropTypes.func.isRequired,
|
||||||
preferences: PropTypes.shape({
|
preferences: PropTypes.shape({
|
||||||
isVisible: PropTypes.bool.isRequired,
|
isVisible: PropTypes.bool.isRequired,
|
||||||
fontSize: PropTypes.number.isRequired
|
fontSize: PropTypes.number.isRequired,
|
||||||
|
indentationAmount: PropTypes.number.isRequired,
|
||||||
|
isTabIndent: PropTypes.bool.isRequired
|
||||||
}).isRequired,
|
}).isRequired,
|
||||||
closePreferences: PropTypes.func.isRequired,
|
closePreferences: PropTypes.func.isRequired,
|
||||||
increaseFont: PropTypes.func.isRequired,
|
increaseFont: PropTypes.func.isRequired,
|
||||||
decreaseFont: PropTypes.func.isRequired,
|
decreaseFont: PropTypes.func.isRequired,
|
||||||
|
updateFont: PropTypes.func.isRequired,
|
||||||
|
increaseIndentation: PropTypes.func.isRequired,
|
||||||
|
decreaseIndentation: PropTypes.func.isRequired,
|
||||||
|
updateIndentation: PropTypes.func.isRequired,
|
||||||
|
indentWithSpace: PropTypes.func.isRequired,
|
||||||
|
indentWithTab: PropTypes.func.isRequired,
|
||||||
files: PropTypes.array.isRequired,
|
files: PropTypes.array.isRequired,
|
||||||
updateFileContent: PropTypes.func.isRequired,
|
updateFileContent: PropTypes.func.isRequired,
|
||||||
selectedFile: PropTypes.shape({
|
selectedFile: PropTypes.shape({
|
||||||
|
|
|
@ -2,31 +2,53 @@ import * as ActionTypes from '../../../constants';
|
||||||
|
|
||||||
const initialState = {
|
const initialState = {
|
||||||
isVisible: false,
|
isVisible: false,
|
||||||
fontSize: 18
|
fontSize: 18,
|
||||||
|
indentationAmount: 2,
|
||||||
|
isTabIndent: true
|
||||||
};
|
};
|
||||||
|
|
||||||
const preferences = (state = initialState, action) => {
|
const preferences = (state = initialState, action) => {
|
||||||
switch (action.type) {
|
switch (action.type) {
|
||||||
case ActionTypes.OPEN_PREFERENCES:
|
case ActionTypes.OPEN_PREFERENCES:
|
||||||
return {
|
return Object.assign({}, state, {
|
||||||
isVisible: true,
|
isVisible: true
|
||||||
fontSize: state.fontSize
|
});
|
||||||
};
|
|
||||||
case ActionTypes.CLOSE_PREFERENCES:
|
case ActionTypes.CLOSE_PREFERENCES:
|
||||||
return {
|
return Object.assign({}, state, {
|
||||||
isVisible: false,
|
isVisible: false
|
||||||
fontSize: state.fontSize
|
});
|
||||||
};
|
|
||||||
case ActionTypes.INCREASE_FONTSIZE:
|
case ActionTypes.INCREASE_FONTSIZE:
|
||||||
return {
|
return Object.assign({}, state, {
|
||||||
isVisible: state.isVisible,
|
|
||||||
fontSize: state.fontSize + 2
|
fontSize: state.fontSize + 2
|
||||||
};
|
});
|
||||||
case ActionTypes.DECREASE_FONTSIZE:
|
case ActionTypes.DECREASE_FONTSIZE:
|
||||||
return {
|
return Object.assign({}, state, {
|
||||||
isVisible: state.isVisible,
|
|
||||||
fontSize: state.fontSize - 2
|
fontSize: state.fontSize - 2
|
||||||
};
|
});
|
||||||
|
case ActionTypes.UPDATE_FONTSIZE:
|
||||||
|
return Object.assign({}, state, {
|
||||||
|
fontSize: action.value
|
||||||
|
});
|
||||||
|
case ActionTypes.INCREASE_INDENTATION:
|
||||||
|
return Object.assign({}, state, {
|
||||||
|
indentationAmount: state.indentationAmount + 2
|
||||||
|
});
|
||||||
|
case ActionTypes.DECREASE_INDENTATION:
|
||||||
|
return Object.assign({}, state, {
|
||||||
|
indentationAmount: state.indentationAmount - 2
|
||||||
|
});
|
||||||
|
case ActionTypes.UPDATE_INDENTATION:
|
||||||
|
return Object.assign({}, state, {
|
||||||
|
indentationAmount: action.value
|
||||||
|
});
|
||||||
|
case ActionTypes.INDENT_WITH_TAB:
|
||||||
|
return Object.assign({}, state, {
|
||||||
|
isTabIndent: true
|
||||||
|
});
|
||||||
|
case ActionTypes.INDENT_WITH_SPACE:
|
||||||
|
return Object.assign({}, state, {
|
||||||
|
isTabIndent: false
|
||||||
|
});
|
||||||
default:
|
default:
|
||||||
return state;
|
return state;
|
||||||
}
|
}
|
||||||
|
|
|
@ -69,6 +69,8 @@
|
||||||
@extend %toolbar-button;
|
@extend %toolbar-button;
|
||||||
color: $light-primary-text-color;
|
color: $light-primary-text-color;
|
||||||
background-color: $light-modal-button-background-color;
|
background-color: $light-modal-button-background-color;
|
||||||
|
padding: 0;
|
||||||
|
line-height: #{48 / $base-font-size}rem;
|
||||||
& g {
|
& g {
|
||||||
fill: $light-primary-text-color;
|
fill: $light-primary-text-color;
|
||||||
}
|
}
|
||||||
|
@ -88,3 +90,19 @@
|
||||||
color: $light-primary-text-color;
|
color: $light-primary-text-color;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
%preference-option {
|
||||||
|
background-color: $light-button-background-color;
|
||||||
|
color: $light-inactive-text-color;
|
||||||
|
font-size: #{14 / $base-font-size}rem;
|
||||||
|
cursor: pointer;
|
||||||
|
text-align: left;
|
||||||
|
margin-bottom: #{5 / $base-font-size}rem;
|
||||||
|
border: 0px;
|
||||||
|
&:hover {
|
||||||
|
color: $light-primary-text-color;
|
||||||
|
}
|
||||||
|
&--selected {
|
||||||
|
color: $light-primary-text-color;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -13,6 +13,7 @@ $light-background-color: #fdfdfd;
|
||||||
$light-button-background-color: #f4f4f4;
|
$light-button-background-color: #f4f4f4;
|
||||||
$light-button-color: $black;
|
$light-button-color: $black;
|
||||||
$light-button-border-color: #979797;
|
$light-button-border-color: #979797;
|
||||||
|
$light-value-border-color: #e6e6e6;
|
||||||
$light-toolbar-button-color: $p5js-pink;
|
$light-toolbar-button-color: $p5js-pink;
|
||||||
$light-button-background-hover-color: $p5js-pink;
|
$light-button-background-hover-color: $p5js-pink;
|
||||||
$light-button-background-active-color: #f10046;
|
$light-button-background-active-color: #f10046;
|
||||||
|
|
|
@ -46,7 +46,12 @@ h2 {
|
||||||
h3 {
|
h3 {
|
||||||
font-weight: normal;
|
font-weight: normal;
|
||||||
}
|
}
|
||||||
|
h4 {
|
||||||
|
font-weight: normal;
|
||||||
|
}
|
||||||
|
h6 {
|
||||||
|
font-weight: normal;
|
||||||
|
}
|
||||||
thead {
|
thead {
|
||||||
text-align: left;
|
text-align: left;
|
||||||
}
|
}
|
|
@ -2,7 +2,7 @@
|
||||||
position: absolute;
|
position: absolute;
|
||||||
top: #{66 / $base-font-size}rem;
|
top: #{66 / $base-font-size}rem;
|
||||||
right: #{40 / $base-font-size}rem;
|
right: #{40 / $base-font-size}rem;
|
||||||
width: #{276 / $base-font-size}rem;
|
width: #{332 / $base-font-size}rem;
|
||||||
background-color: $light-button-background-color;
|
background-color: $light-button-background-color;
|
||||||
display: none;
|
display: none;
|
||||||
padding: #{16 / $base-font-size}rem #{26 / $base-font-size}rem;
|
padding: #{16 / $base-font-size}rem #{26 / $base-font-size}rem;
|
||||||
|
@ -35,7 +35,10 @@
|
||||||
.preference {
|
.preference {
|
||||||
display: flex;
|
display: flex;
|
||||||
flex-wrap: wrap;
|
flex-wrap: wrap;
|
||||||
justify-content: space-between;
|
padding-bottom: #{40 / $base-font-size}rem;
|
||||||
|
& + & {
|
||||||
|
border-top: 2px dashed $light-button-border-color;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.preference__title {
|
.preference__title {
|
||||||
|
@ -44,8 +47,35 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
.preference__value {
|
.preference__value {
|
||||||
border: 1px solid $light-button-border-color;
|
border: 2px solid $light-value-border-color;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
line-height: #{48 / $base-font-size}rem;
|
border-radius: 0%;
|
||||||
width: #{48 / $base-font-size}rem;
|
width: #{48 / $base-font-size}rem;
|
||||||
|
height: #{44 / $base-font-size}rem;
|
||||||
|
margin: 0 #{28 / $base-font-size}rem;
|
||||||
|
padding: 0;
|
||||||
|
background-color: $light-button-background-color;
|
||||||
|
}
|
||||||
|
|
||||||
|
.preference__label {
|
||||||
|
margin: 0;
|
||||||
|
line-height: #{20 / $base-font-size}rem;
|
||||||
|
color: $light-inactive-text-color;
|
||||||
|
&:hover {
|
||||||
|
color: $light-inactive-text-color;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.preference__vertical-list {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
}
|
||||||
|
|
||||||
|
.preference__option {
|
||||||
|
@extend %preference-option;
|
||||||
|
list-style-type: none;
|
||||||
|
padding-left: #{28 / $base-font-size}rem;
|
||||||
|
&--selected {
|
||||||
|
@extend %preference-option--selected;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -83,4 +83,3 @@ app.listen(serverConfig.port, (error) => {
|
||||||
});
|
});
|
||||||
|
|
||||||
export default app;
|
export default app;
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue