add theme to preferences, add backbone of themes to scss

This commit is contained in:
catarak 2016-09-13 14:15:46 -04:00 committed by Cassie Tarakajian
parent f48b872500
commit 103ebd2014
10 changed files with 195 additions and 19 deletions

View file

@ -81,6 +81,7 @@ export const CLOSE_KEYBOARD_SHORTCUT_MODAL = 'CLOSE_KEYBOARD_SHORTCUT_MODAL';
export const SHOW_TOAST = 'SHOW_TOAST'; export const SHOW_TOAST = 'SHOW_TOAST';
export const HIDE_TOAST = 'HIDE_TOAST'; export const HIDE_TOAST = 'HIDE_TOAST';
export const SET_TOAST_TEXT = 'SET_TOAST_TEXT'; export const SET_TOAST_TEXT = 'SET_TOAST_TEXT';
export const SET_THEME = 'SET_THEME';
export const SET_UNSAVED_CHANGES = 'SET_UNSAVED_CHANGES'; export const SET_UNSAVED_CHANGES = 'SET_UNSAVED_CHANGES';

View file

@ -136,3 +136,11 @@ export function setTextOutput(value) {
} }
}; };
} }
export function setTheme(value) {
return {
type: ActionTypes.SET_THEME,
value
};
}

View file

@ -165,6 +165,33 @@ class Preferences extends React.Component {
<label htmlFor="autosave-off" className="preference__option">Off</label> <label htmlFor="autosave-off" className="preference__option">Off</label>
</div> </div>
</div> </div>
<div className="preference">
<h4 className="preference__title">Theme</h4>
<div className="preference__options">
<input
type="radio"
onChange={() => this.props.setTheme('light')}
aria-label="light theme on"
name="light theme"
id="light-theme-on"
className="preference__radio-button"
value="light"
checked={this.props.theme === 'light'}
/>
<label htmlFor="light-theme-on" className="preference__option">Light</label>
<input
type="radio"
onChange={() => this.props.setTheme('dark')}
aria-label="dark theme on"
name="dark theme"
id="dark-theme-on"
className="preference__radio-button"
value="dark"
checked={this.props.theme === 'dark'}
/>
<label htmlFor="dark-theme-on" className="preference__option">Dark</label>
</div>
</div>
<div className="preference"> <div className="preference">
<h4 className="preference__title">Lint Warning Sound</h4> <h4 className="preference__title">Lint Warning Sound</h4>
<div className="preference__options"> <div className="preference__options">
@ -249,7 +276,9 @@ Preferences.propTypes = {
textOutput: PropTypes.bool.isRequired, textOutput: PropTypes.bool.isRequired,
setTextOutput: PropTypes.func.isRequired, setTextOutput: PropTypes.func.isRequired,
lintWarning: PropTypes.bool.isRequired, lintWarning: PropTypes.bool.isRequired,
setLintWarning: PropTypes.func.isRequired setLintWarning: PropTypes.func.isRequired,
theme: PropTypes.string.isRequired,
setTheme: PropTypes.func.isRequired
}; };
export default Preferences; export default Preferences;

View file

@ -27,6 +27,7 @@ import SplitPane from 'react-split-pane';
import Overlay from '../../App/components/Overlay'; import Overlay from '../../App/components/Overlay';
import SketchList from '../components/SketchList'; import SketchList from '../components/SketchList';
import About from '../components/About'; import About from '../components/About';
import classNames from 'classnames';
class IDEView extends React.Component { class IDEView extends React.Component {
constructor(props) { constructor(props) {
@ -156,8 +157,13 @@ class IDEView extends React.Component {
} }
render() { render() {
let ideClass = classNames({
ide: true,
light: this.props.preferences.theme === 'light',
dark: this.props.preferences.theme === 'dark',
});
return ( return (
<div className="ide"> <div className={ideClass}>
{this.props.toast.isVisible && <Toast />} {this.props.toast.isVisible && <Toast />}
<Nav <Nav
user={this.props.user} user={this.props.user}
@ -203,6 +209,8 @@ class IDEView extends React.Component {
setLintWarning={this.props.setLintWarning} setLintWarning={this.props.setLintWarning}
textOutput={this.props.preferences.textOutput} textOutput={this.props.preferences.textOutput}
setTextOutput={this.props.setTextOutput} setTextOutput={this.props.setTextOutput}
theme={this.props.preferences.theme}
setTheme={this.props.setTheme}
/> />
<div className="editor-preview-container"> <div className="editor-preview-container">
<SplitPane <SplitPane
@ -432,7 +440,8 @@ IDEView.propTypes = {
isTabIndent: PropTypes.bool.isRequired, isTabIndent: PropTypes.bool.isRequired,
autosave: PropTypes.bool.isRequired, autosave: PropTypes.bool.isRequired,
lintWarning: PropTypes.bool.isRequired, lintWarning: PropTypes.bool.isRequired,
textOutput: PropTypes.bool.isRequired textOutput: PropTypes.bool.isRequired,
theme: PropTypes.string.isRequired
}).isRequired, }).isRequired,
closePreferences: PropTypes.func.isRequired, closePreferences: PropTypes.func.isRequired,
setFontSize: PropTypes.func.isRequired, setFontSize: PropTypes.func.isRequired,
@ -492,7 +501,8 @@ IDEView.propTypes = {
setRouteLeaveHook: PropTypes.func setRouteLeaveHook: PropTypes.func
}).isRequired, }).isRequired,
route: PropTypes.object.isRequired, route: PropTypes.object.isRequired,
setUnsavedChanges: PropTypes.func.isRequired setUnsavedChanges: PropTypes.func.isRequired,
setTheme: PropTypes.func.isRequired,
}; };
function mapStateToProps(state) { function mapStateToProps(state) {

View file

@ -6,7 +6,8 @@ const initialState = {
isTabIndent: true, isTabIndent: true,
autosave: true, autosave: true,
lintWarning: false, lintWarning: false,
textOutput: false textOutput: false,
theme: 'light'
}; };
const preferences = (state = initialState, action) => { const preferences = (state = initialState, action) => {
@ -31,6 +32,8 @@ const preferences = (state = initialState, action) => {
return Object.assign({}, state, { textOutput: action.value }); return Object.assign({}, state, { textOutput: action.value });
case ActionTypes.SET_PREFERENCES: case ActionTypes.SET_PREFERENCES:
return action.preferences; return action.preferences;
case ActionTypes.SET_THEME:
return Object.assign({}, state, { theme: action.value });
default: default:
return state; return state;
} }

View file

@ -0,0 +1,26 @@
@function map-fetch($map, $keys) {
$key: nth($keys, 1);
$length: length($keys);
$value: map-get($map, $key);
@if $value != null {
@if $length > 1 {
$rest: ();
@for $i from 2 through $length {
$rest: append($rest, nth($keys, $i))
}
@return map-fetch($value, $rest);
} @else {
@return $value;
}
} @else {
@return false;
}
}
@function getThemifyVariable($key) {
@return map-get($theme-map, $key);
}

View file

@ -0,0 +1,20 @@
@mixin themify ($themes: $themes) {
@each $theme, $map in $themes {
.#{$theme} & {
// Define theme color
$theme-map : (
color-alpha: blue
) !global;
@each $key, $submap in $map {
$value: map-fetch($themes, $theme '#{$key}');
$theme-map: map-merge($theme-map, ($key: $value)) !global;
}
@content;
// reset theme color to null
$theme-map: null !global;
}
}
}

View file

@ -5,6 +5,95 @@ $p5js-pink: #ed225d;
$white: #fff; $white: #fff;
$black: #000; $black: #000;
$themes: (
light: (
primary-text-color: #333,
secondary-text-color: #6b6b6b,
inactive-text-color: #b5b5b5,
background-color: #fdfdfd,
button-background-color: #f4f4f4,
button-color: $black,
button-border-color: #979797,
toolbar-button-color: $p5js-pink,
button-background-hover-color: $p5js-pink,
button-background-active-color: #f10046,
button-hover-color: $white,
button-active-color: $white,
modal-background-color: #f4f4f4,
modal-button-background-color: #e6e6e6,
modal-border-color: #B9D0E1,
icon-color: #8b8b8b,
icon-hover-color: #333,
shadow-color: rgba(0, 0, 0, 0.16),
console-background-color: #eee,
console-header-background-color: #d6d6d6,
ide-border-color: #f4f4f4,
),
dark: (
primary-text-color: $white,
secondary-text-color: #c2c2c2,
inactive-text-color: #7d7d7d,
background-color: #333,
button-background-color: $white,
button-color: $black,
button-border-color: #979797,
toolbar-button-color: $p5js-pink,
button-background-hover-color: $p5js-pink,
button-background-active-color: #f10046,
button-hover-color: $white,
button-active-color: $white,
modal-background-color: #444,
modal-button-background-color: #5f5f5f,
modal-border-color: #949494,
icon-color: #a9a9a9,
icon-hover-color: $white,
shadow-color: rgba(0, 0, 0, 0.16),
console-background-color: #4f4f4f,
console-header-background-color: #3f3f3f,
console-header-color: #b5b5b5,
ide-border-color: #949494,
)
);
$primary-text-color: #333;
$secondary-text-color: #6b6b6b;
$inactive-text-color: #b5b5b5;
$background-color: #fdfdfd;
$button-background-color: #f4f4f4;
$button-color: $black;
$button-border-color: #979797;
$toolbar-button-color: $p5js-pink;
$button-background-hover-color: $p5js-pink;
$button-background-active-color: #f10046;
$button-hover-color: $white;
$button-active-color: $white;
$modal-background-color: #f4f4f4;
$modal-button-background-color: #e6e6e6;
$modal-border-color: #B9D0E1;
$icon-color: #8b8b8b;
$icon-hover-color: #333;
$shadow-color: rgba(0, 0, 0, 0.16);
$console-background-color: #eee;
$console-header-background-color: #d6d6d6;
$ide-border-color: #f4f4f4;
// other variables i may or may not need later
$ide-border-color: #f4f4f4;
$editor-selected-line-color: #f3f3f3;
$input-border-color: #979797;
$console-light-background-color: #eee;
$console-header-background-color: #d6d6d6;
$console-header-color: #b1b1b1;
$console-warn-color: #ffbe05;
$console-error-color: #ff5f52;
$toast-background-color: #979797;
$toast-text-color: $white;
//light and dark colors
$light-primary-text-color: #333; $light-primary-text-color: #333;
$light-secondary-text-color: #6b6b6b; $light-secondary-text-color: #6b6b6b;
$light-inactive-text-color: #b5b5b5; $light-inactive-text-color: #b5b5b5;
@ -25,9 +114,6 @@ $light-icon-color: #8b8b8b;
$light-icon-hover-color: $light-primary-text-color; $light-icon-hover-color: $light-primary-text-color;
$light-shadow-color: rgba(0, 0, 0, 0.16); $light-shadow-color: rgba(0, 0, 0, 0.16);
$toast-background-color: #979797;
$toast-text-color: $white;
$dark-primary-text-color: $white; $dark-primary-text-color: $white;
$dark-secondary-text-color: #c2c2c2; $dark-secondary-text-color: #c2c2c2;
$dark-inactive-color: #7d7d7d; $dark-inactive-color: #7d7d7d;
@ -41,13 +127,3 @@ $dark-button-background-active-color: #f10046;
$dark-button-hover-color: $white; $dark-button-hover-color: $white;
$dark-button-active-color: $white; $dark-button-active-color: $white;
$ide-border-color: #f4f4f4;
$editor-selected-line-color: #f3f3f3;
$input-border-color: #979797;
$console-light-background-color: #eee;
$console-header-background-color: #d6d6d6;
$console-header-color: #b1b1b1;
$console-warn-color: #ffbe05;
$console-error-color: #ff5f52;

View file

@ -1,4 +1,6 @@
@import 'abstracts/variables'; @import 'abstracts/variables';
@import 'abstracts/functions';
@import 'abstracts/mixins';
@import 'abstracts/placeholders'; @import 'abstracts/placeholders';
@import 'base/reset'; @import 'base/reset';

View file

@ -15,7 +15,8 @@ const userSchema = new Schema({
isTabIndent: { type: Boolean, default: false }, isTabIndent: { type: Boolean, default: false },
autosave: { type: Boolean, default: true }, autosave: { type: Boolean, default: true },
lintWarning: { type: Boolean, default: false }, lintWarning: { type: Boolean, default: false },
textOutput: { type: Boolean, default: false } textOutput: { type: Boolean, default: false },
theme: { type: String, default: 'light' }
} }
}, { timestamps: true }); }, { timestamps: true });