From 239a5dc7ab3c87bdf6c913a7f48020828e657c2b Mon Sep 17 00:00:00 2001 From: CJ Cenizal Date: Fri, 11 Aug 2017 10:01:55 -0700 Subject: [PATCH] [UI Framework] Add functionality for hiding and showing the chrome when viewing Sandboxes (#13475) (#13478) * Update UI Framework doc site with functionality for hiding and showing the chrome when viewing Sandboxes. (#13437) * Fix formatting in generator-kui templates. (#13443) --- .../doc_site/src/actions/action_types.js | 4 ++ ui_framework/doc_site/src/actions/index.js | 5 ++ .../doc_site/src/actions/sandbox_actions.js | 9 +++ .../doc_site/src/components/guide/_guide.scss | 5 ++ .../src/components/guide_components.scss | 1 + .../src/components/guide_nav/_guide_nav.scss | 23 ++++++- .../src/components/guide_nav/guide_nav.js | 27 +++++++++ .../components/guide_sandbox/guide_sandbox.js | 60 +++++++++++++++++-- .../guide_section/_guide_section.scss | 6 ++ .../doc_site/src/store/configure_store.js | 2 + ui_framework/doc_site/src/store/index.js | 4 ++ .../src/store/reducers/sandbox_reducer.js | 26 ++++++++ .../doc_site/src/views/app_container.js | 4 ++ ui_framework/doc_site/src/views/app_view.js | 33 ++++++++++ .../component/templates/index.js | 4 +- .../generator-kui/component/templates/test.js | 2 +- 16 files changed, 206 insertions(+), 9 deletions(-) create mode 100644 ui_framework/doc_site/src/actions/sandbox_actions.js create mode 100644 ui_framework/doc_site/src/store/reducers/sandbox_reducer.js diff --git a/ui_framework/doc_site/src/actions/action_types.js b/ui_framework/doc_site/src/actions/action_types.js index b288e7b0edbed..66ef2b2afcd5f 100644 --- a/ui_framework/doc_site/src/actions/action_types.js +++ b/ui_framework/doc_site/src/actions/action_types.js @@ -7,6 +7,10 @@ export default keyMirror({ OPEN_CODE_VIEWER: null, CLOSE_CODE_VIEWER: null, + // Sandbox actions + OPEN_SANDBOX: null, + CLOSE_SANDBOX: null, + // Example nav actions REGISTER_SECTION: null, UNREGISTER_SECTION: null, diff --git a/ui_framework/doc_site/src/actions/index.js b/ui_framework/doc_site/src/actions/index.js index 310bc91f2755e..9517d850e4a2b 100644 --- a/ui_framework/doc_site/src/actions/index.js +++ b/ui_framework/doc_site/src/actions/index.js @@ -3,6 +3,11 @@ export { closeCodeViewer, } from './code_viewer_actions'; +export { + openSandbox, + closeSandbox, +} from './sandbox_actions'; + export { registerSection, unregisterSection, diff --git a/ui_framework/doc_site/src/actions/sandbox_actions.js b/ui_framework/doc_site/src/actions/sandbox_actions.js new file mode 100644 index 0000000000000..33b7e345f717d --- /dev/null +++ b/ui_framework/doc_site/src/actions/sandbox_actions.js @@ -0,0 +1,9 @@ +import ActionTypes from './action_types'; + +export const openSandbox = () => ({ + type: ActionTypes.OPEN_SANDBOX, +}); + +export const closeSandbox = () => ({ + type: ActionTypes.CLOSE_SANDBOX, +}); diff --git a/ui_framework/doc_site/src/components/guide/_guide.scss b/ui_framework/doc_site/src/components/guide/_guide.scss index fa35e61ca0a9a..3c292e01fedbd 100644 --- a/ui_framework/doc_site/src/components/guide/_guide.scss +++ b/ui_framework/doc_site/src/components/guide/_guide.scss @@ -25,6 +25,7 @@ html { padding-top: $guideNavHeight; background-color: $guideBaseBackgroundColor; transition: + padding-top $guideChromeTransition, padding-right $guideCodeViewerTransition, opacity $guideCodeViewerTransition; @@ -39,6 +40,10 @@ html { .is-guide-nav-open + & { opacity: 0.7; } + + &.is-chrome-hidden { + padding-top: 0; + } } @media only screen and (max-width: 1300px) { diff --git a/ui_framework/doc_site/src/components/guide_components.scss b/ui_framework/doc_site/src/components/guide_components.scss index 848ed12549e47..450e357978fca 100644 --- a/ui_framework/doc_site/src/components/guide_components.scss +++ b/ui_framework/doc_site/src/components/guide_components.scss @@ -6,6 +6,7 @@ $guideSideNavSmallWidth: 220px; $guideCodeViewerWidth: 660px; $guideCodeViewerSmallWidth: 520px; $guideCodeViewerTransition: 0.2s ease; +$guideChromeTransition: 0.3s ease; // Colors $guideBaseBackgroundColor: #f7f7f7; diff --git a/ui_framework/doc_site/src/components/guide_nav/_guide_nav.scss b/ui_framework/doc_site/src/components/guide_nav/_guide_nav.scss index f5723dc21364d..205961c15f43d 100644 --- a/ui_framework/doc_site/src/components/guide_nav/_guide_nav.scss +++ b/ui_framework/doc_site/src/components/guide_nav/_guide_nav.scss @@ -11,7 +11,10 @@ border-bottom: 1px solid #CCCCCC; color: $guideTextColor; background-color: $guidePanelBackgroundColor; - transition: height 0.3s ease, box-shadow 0.3s linear; + transition: + top $guideChromeTransition, + height 0.3s ease, + box-shadow 0.3s linear; overflow: hidden; box-shadow: 0 0 0 rgba(black, 0.3); @@ -19,8 +22,26 @@ height: 100%; box-shadow: 0 40px 200px rgba(black, 0.05); } + + &.is-chrome-hidden { + top: -$guideNavHeight; + } } + .guideNav__showButton { + position: fixed; + z-index: 9999; + top: 5px; + right: 5px; + font-size: 10px; + opacity: 0; + transition: opacity $guideChromeTransition; + + .is-chrome-hidden & { + opacity: 1; + } + } + .guideNav__header { position: relative; flex: 0 0 auto; diff --git a/ui_framework/doc_site/src/components/guide_nav/guide_nav.js b/ui_framework/doc_site/src/components/guide_nav/guide_nav.js index da8c0f7c56f35..512d0430d9fd3 100644 --- a/ui_framework/doc_site/src/components/guide_nav/guide_nav.js +++ b/ui_framework/doc_site/src/components/guide_nav/guide_nav.js @@ -78,8 +78,23 @@ export class GuideNav extends Component { ); + let hideChromeButton; + + if (this.props.isSandbox) { + hideChromeButton = ( + + ); + } + return (
+ {hideChromeButton} {previousButton} {nextButton}
@@ -89,6 +104,7 @@ export class GuideNav extends Component { render() { const classes = classNames('guideNav', { 'is-guide-nav-open': this.props.isNavOpen, + 'is-chrome-hidden': !this.props.isChromeVisible, }); const buttonClasses = classNames('guideNav__menu fa fa-bars', { @@ -185,14 +201,25 @@ export class GuideNav extends Component { { sandboxNavItems.length ? sandboxNavItems : this.renderNoItems('sandboxes') } + + ); } } GuideNav.propTypes = { + isChromeVisible: PropTypes.bool, isNavOpen: PropTypes.bool, + isSandbox: PropTypes.bool, onToggleNav: PropTypes.func, + onHideChrome: PropTypes.func, + onShowChrome: PropTypes.func, onClickNavItem: PropTypes.func, version: PropTypes.string, routes: PropTypes.array, diff --git a/ui_framework/doc_site/src/components/guide_sandbox/guide_sandbox.js b/ui_framework/doc_site/src/components/guide_sandbox/guide_sandbox.js index b1cfdc8276c7c..ec9501f6c5563 100644 --- a/ui_framework/doc_site/src/components/guide_sandbox/guide_sandbox.js +++ b/ui_framework/doc_site/src/components/guide_sandbox/guide_sandbox.js @@ -1,7 +1,55 @@ -import React from 'react'; +import React, { + Component, +} from 'react'; +import PropTypes from 'prop-types'; +import { bindActionCreators } from 'redux'; +import { connect } from 'react-redux'; -export const GuideSandbox = props => ( -
- {props.children} -
-); +import { + getIsSandbox, +} from '../../store'; + +import { + openSandbox, + closeSandbox, +} from '../../actions'; + +function mapStateToProps(state) { + return { + isSandbox: getIsSandbox(state), + }; +} + +function mapDispatchToProps(dispatch) { + const actions = { + openSandbox, + closeSandbox, + }; + + return bindActionCreators(actions, dispatch); +} + +class GuideSandboxComponent extends Component { + componentWillMount() { + this.props.openSandbox(); + } + + componentWillUnmount() { + this.props.closeSandbox(); + } + + render() { + return ( +
+ {this.props.children} +
+ ); + } +} + +GuideSandboxComponent.propTypes = { + openSandbox: PropTypes.func, + closeSandbox: PropTypes.func, +}; + +export const GuideSandbox = connect(mapStateToProps, mapDispatchToProps)(GuideSandboxComponent); diff --git a/ui_framework/doc_site/src/components/guide_section/_guide_section.scss b/ui_framework/doc_site/src/components/guide_section/_guide_section.scss index be596398381af..280b0026172e4 100644 --- a/ui_framework/doc_site/src/components/guide_section/_guide_section.scss +++ b/ui_framework/doc_site/src/components/guide_section/_guide_section.scss @@ -25,9 +25,15 @@ border: 1px solid $guideLinkHoverColor; border-radius: 3px; cursor: pointer; + transform: translateX(0); + transition: transform $guideChromeTransition; &:hover, &:active { background-color: #e6f7fc; } + + .is-chrome-hidden & { + transform: translateX(60px); + } } diff --git a/ui_framework/doc_site/src/store/configure_store.js b/ui_framework/doc_site/src/store/configure_store.js index 8f6de34b6733b..b7160220345bf 100644 --- a/ui_framework/doc_site/src/store/configure_store.js +++ b/ui_framework/doc_site/src/store/configure_store.js @@ -11,6 +11,7 @@ import { } from 'react-router-redux'; import codeViewerReducer from './reducers/code_viewer_reducer'; +import sandboxReducer from './reducers/sandbox_reducer'; import sectionsReducer from './reducers/sections_reducer'; /** @@ -22,6 +23,7 @@ export default function configureStore(initialState) { return { routing: routerReducer(state.routing, action), codeViewer: codeViewerReducer(state.codeViewer, action), + sandbox: sandboxReducer(state.sandbox, action), sections: sectionsReducer(state.sections, action), }; } diff --git a/ui_framework/doc_site/src/store/index.js b/ui_framework/doc_site/src/store/index.js index 0ab30476a2dbf..12be83f4b2374 100644 --- a/ui_framework/doc_site/src/store/index.js +++ b/ui_framework/doc_site/src/store/index.js @@ -2,6 +2,10 @@ export function getIsCodeViewerOpen(state) { return state.codeViewer.isOpen; } +export function getIsSandbox(state) { + return state.sandbox.isSandbox; +} + export function getSections(state) { return state.sections.sections; } diff --git a/ui_framework/doc_site/src/store/reducers/sandbox_reducer.js b/ui_framework/doc_site/src/store/reducers/sandbox_reducer.js new file mode 100644 index 0000000000000..6dd83497dc471 --- /dev/null +++ b/ui_framework/doc_site/src/store/reducers/sandbox_reducer.js @@ -0,0 +1,26 @@ +import ActionTypes from '../../actions/action_types'; + +const defaultState = { + isSandbox: false, +}; + +export default function sandboxReducer(state = defaultState, action) { + switch (action.type) { + case ActionTypes.OPEN_SANDBOX: { + return Object.assign({}, state, { + isSandbox: true, + }); + } + + case ActionTypes.CLOSE_SANDBOX: { + return Object.assign({}, state, { + isSandbox: false, + }); + } + + default: + break; + } + + return state; +} diff --git a/ui_framework/doc_site/src/views/app_container.js b/ui_framework/doc_site/src/views/app_container.js index 5289c137567c1..e54a3412302b1 100644 --- a/ui_framework/doc_site/src/views/app_container.js +++ b/ui_framework/doc_site/src/views/app_container.js @@ -3,11 +3,14 @@ import { connect } from 'react-redux'; import { getIsCodeViewerOpen, + getIsSandbox, getSections, getSource, getTitle, } from '../store'; + import { AppView } from './app_view'; + import { openCodeViewer, closeCodeViewer, @@ -19,6 +22,7 @@ function mapStateToProps(state, ownProps) { return { routes: ownProps.routes, isCodeViewerOpen: getIsCodeViewerOpen(state), + isSandbox: getIsSandbox(state), source: getSource(state), title: getTitle(state), sections: getSections(state), diff --git a/ui_framework/doc_site/src/views/app_view.js b/ui_framework/doc_site/src/views/app_view.js index 3829153e1efd1..24616e55b7763 100644 --- a/ui_framework/doc_site/src/views/app_view.js +++ b/ui_framework/doc_site/src/views/app_view.js @@ -23,11 +23,14 @@ export class AppView extends Component { this.state = { isNavOpen: false, + isChromeVisible: !props.isSandbox, }; this.onClickNavItem = this.onClickNavItem.bind(this); this.onToggleNav = this.onToggleNav.bind(this); this.onCloseCodeViewer = this.onCloseCodeViewer.bind(this); + this.onHideChrome = this.onHideChrome.bind(this); + this.onShowChrome = this.onShowChrome.bind(this); } onClickNavItem() { @@ -46,15 +49,44 @@ export class AppView extends Component { }); } + onHideChrome() { + this.setState({ + isChromeVisible: false, + isNavOpen: false, + }); + + this.props.closeCodeViewer(); + } + + onShowChrome() { + this.setState({ + isChromeVisible: true, + }); + } + + componentWillReceiveProps(nextProps) { + // Only force the chrome to be hidden if we're navigating from a non-sandbox to a sandbox. + if (!this.props.isSandbox && nextProps.isSandbox) { + this.setState({ + isChromeVisible: false, + }); + } + } + render() { const contentClasses = classNames('guideContent', { 'is-code-viewer-open': this.props.isCodeViewerOpen, + 'is-chrome-hidden': !this.state.isChromeVisible, }); return (
} from './<%= fileName %>'; +export { + <%= componentName %>, +} from './<%= fileName %>'; diff --git a/ui_framework/generator-kui/component/templates/test.js b/ui_framework/generator-kui/component/templates/test.js index aecd6497a73cb..4f384d6c2d3aa 100644 --- a/ui_framework/generator-kui/component/templates/test.js +++ b/ui_framework/generator-kui/component/templates/test.js @@ -7,7 +7,7 @@ import { <%= componentName %> } from './<%= fileName %>'; describe('<%= componentName %>', () => { test('is rendered', () => { const component = render( - <<%= componentName %> { ...requiredProps } /> + <<%= componentName %> {...requiredProps} /> ); expect(component)