diff options
23 files changed, 210 insertions, 153 deletions
diff --git a/public/index.html b/public/index.html index b9560c37..065185d3 100644 --- a/public/index.html +++ b/public/index.html @@ -7,10 +7,21 @@ <meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no"> <meta name="theme-color" content="#000000"> + <!-- Standard meta tags --> <meta name="description" content="Collaborative Datacenter Simulation and Exploration for Everybody"> <meta name="author" content="Alexandru Iosup, Leon Overweel, Georgios Andreadis, Matthijs Bijman"> <meta name="keywords" content="OpenDC, Datacenter, Simulation, Simulator, Collaborative, Distributed, Cluster"> + <!-- OpenGraph meta tags --> + <meta property="og:title" content="OpenDC: Collaborative Datacenter Simulation and Exploration for Everybody"> + <meta property="og:type" content="website"> + <meta property="og:image" content="/img/logo.png"> + <meta property="og:url" content="/"> + <meta property="og:description" + content="OpenDC provides collaborative online datacenter modeling, diverse and effective datacenter + simulation, and exploratory datacenter performance feedback."> + <meta property="og:locale" content="en_US"> + <link rel="manifest" href="/manifest.json"> <link rel="shortcut icon" href="/favicon.ico"> diff --git a/src/components/home/ContactSection.js b/src/components/home/ContactSection.js new file mode 100644 index 00000000..8e6aed1a --- /dev/null +++ b/src/components/home/ContactSection.js @@ -0,0 +1,33 @@ +import React from "react"; +import ContentSection from "./ContentSection"; +import "./ContentSection.css"; + +const ContactSection = () => ( + <ContentSection name="contact"> + <h1>Contact</h1> + <div className="row"> + <img src="img/tudelfticon.png" className="col-lg-2 col-md-2 col-sm-3 col-xs-6 + col-lg-offset-4 col-md-offset-4 col-sm-offset-3 col-xs-offset-3 tudelft-icon" alt="TU Delft Logo"/> + <div className="col-lg-4 col-md-5 col-sm-6 col-xs-10 + col-lg-offset-0 col-md-offset-0 col-sm-offset-0 col-xs-offset-1 text-left"> + <div className="row vcenter"> + <img src="img/email-icon.png" className="col-lg-2 col-md-2 col-sm-2 col-xs-2" alt="Email Icon"/> + <div className="info-points col-lg-10 col-md-10 col-sm-10 col-xs-10"> + <a href="mailto:opendc@atlarge-research.com">opendc@atlarge-research.com</a> + </div> + </div> + <div className="row vcenter"> + <img src="img/github-icon.png" className="col-lg-2 col-md-2 col-sm-2 col-xs-2" alt="Github Icon"/> + <div className="info-points col-lg-10 col-md-10 col-sm-10 col-xs-10"> + <a href="https://github.com/atlarge-research/opendc">atlarge-research/opendc</a> + </div> + </div> + </div> + </div> + <div className="atlarge-footer row"> + A project by the <a href="http://atlarge-research.com"><strong>@Large Research Group</strong></a>. + </div> + </ContentSection> +); + +export default ContactSection; diff --git a/src/components/home/ContentSection.js b/src/components/home/ContentSection.js new file mode 100644 index 00000000..126c5e4b --- /dev/null +++ b/src/components/home/ContentSection.js @@ -0,0 +1,20 @@ +import classNames from "classnames"; +import PropTypes from "prop-types"; +import React from "react"; +import "./ContentSection.css"; + +const ContentSection = ({name, children}) => ( + <div id={name} className={classNames(name + "-section", "content-section")}> + <div className="container"> + <div className="row"> + {children} + </div> + </div> + </div> +); + +ContentSection.propTypes = { + name: PropTypes.string.isRequired, +}; + +export default ContentSection; diff --git a/src/components/home/ContentSection.sass b/src/components/home/ContentSection.sass new file mode 100644 index 00000000..c84f26db --- /dev/null +++ b/src/components/home/ContentSection.sass @@ -0,0 +1,27 @@ +@import ../../style-globals/_variables.sass + +.content-section + padding-top: 50px + padding-bottom: 150px + text-align: center + +@media screen and (min-width: $screen-sm) and (max-width: $screen-md) + .content-section h1 + font-size: 2em + margin-bottom: 40px + + .content-section h3 + font-size: 1.5em + +@media screen and (min-width: $screen-md) and (max-width: $screen-lg) + .content-section h1 + font-size: 3em + margin-bottom: 40px + + .content-section h3 + font-size: 1.8em + +@media screen and (min-width: $screen-lg) + .content-section h1 + font-size: 3em + margin-bottom: 40px diff --git a/src/components/navigation/LogoutButton.js b/src/components/navigation/LogoutButton.js index e2da7751..d58776dc 100644 --- a/src/components/navigation/LogoutButton.js +++ b/src/components/navigation/LogoutButton.js @@ -1,11 +1,11 @@ import PropTypes from "prop-types"; import React from "react"; +import FontAwesome from "react-fontawesome"; import {Link} from "react-router-dom"; -import "./LogoutButton.css"; const LogoutButton = ({onLogout}) => ( - <Link className="logout" title="Sign out" to="#" onClick={onLogout}> - <span className="fa fa-lg fa-power-off"/> + <Link className="logout nav-link" title="Sign out" to="#" onClick={onLogout}> + <FontAwesome name="power-off" size="lg"/> </Link> ); diff --git a/src/components/navigation/LogoutButton.sass b/src/components/navigation/LogoutButton.sass deleted file mode 100644 index b63494ab..00000000 --- a/src/components/navigation/LogoutButton.sass +++ /dev/null @@ -1,17 +0,0 @@ -@import ../../style-globals/_mixins.sass -@import ../../style-globals/_variables.sass - -.logout - float: right - margin-top: -1px - width: $navbar-height - - font-size: 14pt - - +clickable - - &:hover - background: #e3474d - - &:active - background: #a73438 diff --git a/src/components/navigation/Navbar.js b/src/components/navigation/Navbar.js index ce020fef..5a4cd29e 100644 --- a/src/components/navigation/Navbar.js +++ b/src/components/navigation/Navbar.js @@ -1,37 +1,66 @@ -import React, {Component} from 'react'; -import FontAwesome from "react-fontawesome"; +import classNames from "classnames"; +import React from 'react'; import Mailto from "react-mailto"; -import {Link} from "react-router-dom"; +import {Link, withRouter} from "react-router-dom"; +import {userIsLoggedIn} from "../../auth/index"; +import Login from "../../containers/auth/Login"; import Logout from "../../containers/auth/Logout"; import ProfileName from "../../containers/auth/ProfileName"; import "./Navbar.css"; -class Navbar extends Component { - render() { - return ( - <div className="opendc-navbar"> - <Link className="opendc-brand" to="/"> - <img src="/img/logo.png" alt="OpenDC Logo"/> - <div className="opendc-title"> - Open<strong>DC</strong> - </div> - </Link> - <div className="navigation navbar-button-group"> - <Link className="simulations" title="Simulations" to="/simulations">Simulations</Link> - </div> - <div className="user-controls navbar-button-group"> - <Mailto className="support" title="Support" email="opendc.tudelft@gmail.com" - headers={{subject: "OpenDC Support"}}> - <FontAwesome name="question-circle" size="lg"/> - </Mailto> - <Link className="username" title="My Profile" to="/profile"> - <ProfileName/> - </Link> - <Logout/> - </div> +const NavItem = withRouter(props => <NavItemWithoutRoute {...props}/>); + +const NavItemWithoutRoute = ({route, location, children}) => ( + <li className={classNames("nav-item", location.pathname === route ? "active" : undefined)}> + {children} + </li> +); + +const Navbar = () => ( + <nav className="navbar fixed-top navbar-toggleable-md navbar-light bg-faded"> + <div className="container"> + <button className="navbar-toggler navbar-toggler-right" type="button" data-toggle="collapse" + data-target="#navbarSupportedContent" aria-controls="navbarSupportedContent" + aria-expanded="false" aria-label="Toggle navigation"> + <span className="navbar-toggler-icon"/> + </button> + <Link className="navbar-brand opendc-brand" to="/"> + <img src="/img/logo.png" alt="OpenDC Logo"/> + </Link> + + <div className="collapse navbar-collapse" id="navbarSupportedContent"> + <ul className="navbar-nav mr-auto"> + <NavItem route="/simulations"> + <Link className="nav-link simulations" title="Simulations" + to="/simulations">Simulations</Link> + </NavItem> + <NavItem route="email"> + <Mailto className="nav-link support" title="Support" email="opendc.tudelft@gmail.com" + headers={{subject: "OpenDC Support"}}> + Support + </Mailto> + </NavItem> + </ul> + <ul className="navbar-nav"> + {userIsLoggedIn() ? + [ + <NavItem route="/profile"> + <Link className="username nav-link" title="My Profile" to="/profile"> + <ProfileName/> + </Link> + </NavItem>, + <NavItem route="logout"> + <Logout/> + </NavItem> + ] : + <NavItem route="login"> + <Login visible={true}/> + </NavItem> + } + </ul> </div> - ); - } -} + </div> + </nav> +); export default Navbar; diff --git a/src/components/navigation/Navbar.sass b/src/components/navigation/Navbar.sass index e9a83301..80346660 100644 --- a/src/components/navigation/Navbar.sass +++ b/src/components/navigation/Navbar.sass @@ -1,59 +1,30 @@ @import ../../style-globals/_mixins.sass @import ../../style-globals/_variables.sass -.opendc-navbar - position: relative - display: block - width: 100% - height: $navbar-height - - color: #eee - background: #343434 - - z-index: 100 - - -webkit-box-shadow: -10px 8px 3px 12px #000 - -moz-box-shadow: -10px 8px 3px 12px #000 - box-shadow: -10px -10px 3px 12px #000 +.navbar + border-top: $blue 3px solid + border-bottom: $gray-semi-dark 1px solid + color: $gray-very-dark + background: #fafafb .opendc-brand display: inline-block - float: left - margin-left: $global-padding + //float: left + //margin-left: $global-padding - padding: 0 10px + //padding: 0 10px - cursor: pointer - color: #eee - height: 100% + //cursor: pointer + color: $gray-very-dark + //height: 100% +transition(background, $transition-length) - &:hover - color: #fff - img + position: relative + bottom: 3px display: inline-block - float: left - margin: $navbar-padding 0 - - width: $navbar-height - $navbar-padding * 2 - height: $navbar-height - $navbar-padding * 2 - vertical-align: middle - - .opendc-title - display: inline-block - float: right - margin-left: 20px - - font-size: 16pt - line-height: $navbar-height - -.opendc-brand:hover - background: $blue - -.opendc-brand:active - background: $blue-dark + width: 30px .navbar-button-group display: inline-block @@ -63,18 +34,16 @@ display: inline-block line-height: $navbar-height text-align: center - color: #eee - - border-left: 1px solid #464646 + color: $gray-very-dark +clickable +transition(background, $transition-length) - a:last-of-type - border-right: 1px solid #464646 + a:hover + color: $gray-dark .navigation - margin-left: 30px + margin-left: 10px .simulations float: left @@ -82,12 +51,6 @@ font-size: 12pt - .simulations:hover - background: #606060 - - .simulations:active - background: #161616 - .user-controls float: right margin-right: $global-padding @@ -100,20 +63,8 @@ font-size: 14pt - .support:hover - background: #41a0cd - - .support:active - background: #307798 - .username float: left padding: 0 20px font-size: 12pt - - .username:hover - background: #4eae44 - - .username:active - background: #2d6527 diff --git a/src/components/simulations/FilterButton.sass b/src/components/simulations/FilterButton.sass index 60f6faca..698bc9a4 100644 --- a/src/components/simulations/FilterButton.sass +++ b/src/components/simulations/FilterButton.sass @@ -4,18 +4,13 @@ .simulation-filter-button display: inline-block width: 33.3% - //margin-right: -4px padding: 10px $global-padding font-size: 12pt - border-right: 1px solid #06326b +clickable +transition(background, $transition-length) -.simulation-filter-button:last-of-type - border: 0 - .simulation-filter-button:hover background: #0c60bf diff --git a/src/components/simulations/FilterPanel.js b/src/components/simulations/FilterPanel.js index b43139c1..811da005 100644 --- a/src/components/simulations/FilterPanel.js +++ b/src/components/simulations/FilterPanel.js @@ -7,7 +7,7 @@ const FilterPanel = () => ( <div className="simulation-filters"> <FilterLink filter="SHOW_ALL">All Simulations</FilterLink> <FilterLink filter="SHOW_OWN">My Simulations</FilterLink> - <FilterLink filter="SHOW_SHARED">Simulations shared with me</FilterLink> + <FilterLink filter="SHOW_SHARED">Shared with me</FilterLink> </div> </div> ); diff --git a/src/components/simulations/FilterPanel.sass b/src/components/simulations/FilterPanel.sass index a59ffdfd..70401dcb 100644 --- a/src/components/simulations/FilterPanel.sass +++ b/src/components/simulations/FilterPanel.sass @@ -5,12 +5,11 @@ display: block background: #0761b1 - border: 1px solid #06326b color: #eee text-align: center - +border-radius($standard-border-radius) + +border-radius(25px) overflow: hidden margin-bottom: 20px diff --git a/src/components/simulations/SimulationActionButtons.js b/src/components/simulations/SimulationActionButtons.js index 1731b9be..29872fcb 100644 --- a/src/components/simulations/SimulationActionButtons.js +++ b/src/components/simulations/SimulationActionButtons.js @@ -7,7 +7,7 @@ const SimulationActionButtons = ({simulationId, onViewUsers, onDelete}) => ( <Link to={"/simulations/" + simulationId} className="open" title="Open this simulation"> <span className="fa fa-play"/> </Link> - <div className="users" title="View and edit collaborators on this simulation" + <div className="users" title="View and edit collaborators" onClick={() => onViewUsers(simulationId)}> <span className="fa fa-users"/> </div> diff --git a/src/components/simulations/SimulationAuthList.sass b/src/components/simulations/SimulationAuthList.sass index 58683446..cb1fe4cc 100644 --- a/src/components/simulations/SimulationAuthList.sass +++ b/src/components/simulations/SimulationAuthList.sass @@ -54,8 +54,9 @@ .simulation-list .list-head > div:not(:first-of-type) padding-left: 5px !important -.simulation-row .simulation-icons +.simulation-icons text-align: right + padding-right: 0 !important .simulation-row .simulation-icons div, .simulation-row .simulation-icons a display: inline-block @@ -75,9 +76,10 @@ top: -4px left: -1px + background-color: $blue-dark + &.open - $icon-color: #0c60bf - background: $icon-color + $icon-color: #0a00bf span left: 1px @@ -91,23 +93,21 @@ &.users font-size: 10pt $icon-color: #17bf55 - background: $icon-color span left: -2px &:hover - background: lighten($icon-color, 10%) + background: $icon-color &:active background: darken($icon-color, 10%) &.delete $icon-color: #e3474d - background: $icon-color &:hover - background: lighten($icon-color, 10%) + background: $icon-color &:active background: darken($icon-color, 10%) diff --git a/src/containers/auth/Login.js b/src/containers/auth/Login.js index f1deb33c..3bc36a17 100644 --- a/src/containers/auth/Login.js +++ b/src/containers/auth/Login.js @@ -30,7 +30,10 @@ class LoginContainer extends React.Component { <GoogleLogin clientId="311799954046-jv2inpg9nu7m0avcg6gulvkuvfgbtgb4.apps.googleusercontent.com" onSuccess={this.onAuthResponse.bind(this)} - onFailure={this.onAuthResponse.bind(this)}> + onFailure={this.onAuthResponse.bind(this)} + style={{height: "40px"}} + className="btn btn-secondary" + > <span className='fa fa-google'/> {' '} <span>Login with Google</span> diff --git a/src/index.sass b/src/index.sass index 80c72a77..dcf3f0ee 100644 --- a/src/index.sass +++ b/src/index.sass @@ -11,5 +11,11 @@ html, body, #root .full-height height: 100% +.page-container + padding-top: 60px + +.text-page-container + padding-top: 80px + a, a:hover text-decoration: none diff --git a/src/pages/App.js b/src/pages/App.js index f34c03cd..ce6556fb 100644 --- a/src/pages/App.js +++ b/src/pages/App.js @@ -5,7 +5,6 @@ import {openSimulationSucceeded} from "../actions/simulations"; import {fetchLatestDatacenter} from "../actions/topology"; import MapStage from "../components/map/MapStage"; import Navbar from "../components/navigation/Navbar"; -import Login from "../containers/auth/Login"; class AppContainer extends React.Component { static propTypes = { @@ -19,12 +18,11 @@ class AppContainer extends React.Component { render() { return ( - <div className="full-height"> + <div className="page-container full-height"> <Navbar/> <div className="full-height"> <MapStage/> </div> - <Login visible={false}/> </div> ); } diff --git a/src/pages/Home.js b/src/pages/Home.js index bd32d0d9..dd5fd492 100644 --- a/src/pages/Home.js +++ b/src/pages/Home.js @@ -1,8 +1,11 @@ import React from 'react'; -import Login from "../containers/auth/Login"; +import Navbar from "../components/navigation/Navbar"; +import "./Home.css"; -const Index = () => ( - <Login visible={true}/> +const Home = () => ( + <div className="body-wrapper"> + <Navbar/> + </div> ); -export default Index; +export default Home; diff --git a/src/pages/Home.sass b/src/pages/Home.sass new file mode 100644 index 00000000..58fbf6b2 --- /dev/null +++ b/src/pages/Home.sass @@ -0,0 +1,4 @@ +// Fix for the white space appearing otherwise on the right of the page, on mobile +.body-wrapper + overflow-x: hidden + overflow-y: hidden diff --git a/src/pages/Profile.js b/src/pages/Profile.js index 3c3b0899..d4594c9e 100644 --- a/src/pages/Profile.js +++ b/src/pages/Profile.js @@ -2,15 +2,12 @@ import React from 'react'; import {connect} from "react-redux"; import {openDeleteProfileModal} from "../actions/profile"; import Navbar from "../components/navigation/Navbar"; -import Login from "../containers/auth/Login"; import DeleteProfileModal from "../containers/profile/DeleteProfileModal"; -import "./Profile.css"; const ProfileContainer = ({onDelete}) => ( <div className="full-height"> <Navbar/> - <div className="container profile-page-container full-height"> - <h2>Profile Settings</h2> + <div className="container text-page-container full-height"> <button className="btn btn-danger" onClick={onDelete}>Delete my account on OpenDC</button> <p> This does not delete your Google account, it simply disconnects it from the OpenDC app and deletes any @@ -19,7 +16,6 @@ const ProfileContainer = ({onDelete}) => ( </p> </div> <DeleteProfileModal/> - <Login visible={false}/> </div> ); diff --git a/src/pages/Profile.sass b/src/pages/Profile.sass deleted file mode 100644 index 9bb0a7e4..00000000 --- a/src/pages/Profile.sass +++ /dev/null @@ -1,2 +0,0 @@ -.profile-page-container - padding-top: 2rem diff --git a/src/pages/Simulations.js b/src/pages/Simulations.js index 8218b1a4..6c40516d 100644 --- a/src/pages/Simulations.js +++ b/src/pages/Simulations.js @@ -5,10 +5,8 @@ import {fetchAuthorizationsOfCurrentUser} from "../actions/users"; import Navbar from "../components/navigation/Navbar"; import SimulationFilterPanel from "../components/simulations/FilterPanel"; import NewSimulationButton from "../components/simulations/NewSimulationButton"; -import Login from "../containers/auth/Login"; import NewSimulationModal from "../containers/simulations/NewSimulationModal"; import VisibleSimulationList from "../containers/simulations/VisibleSimulationAuthList"; -import "./Simulations.css"; class SimulationsContainer extends React.Component { componentDidMount() { @@ -19,13 +17,12 @@ class SimulationsContainer extends React.Component { return ( <div className="full-height"> <Navbar/> - <div className="container simulation-page-container full-height"> + <div className="container text-page-container full-height"> <SimulationFilterPanel/> <VisibleSimulationList/> <NewSimulationButton onClick={() => {this.props.openNewSimulationModal()}}/> </div> <NewSimulationModal/> - <Login visible={false}/> </div> ); } diff --git a/src/pages/Simulations.sass b/src/pages/Simulations.sass deleted file mode 100644 index d639ba83..00000000 --- a/src/pages/Simulations.sass +++ /dev/null @@ -1,2 +0,0 @@ -.simulation-page-container - padding-top: 2rem diff --git a/src/style-globals/_variables.sass b/src/style-globals/_variables.sass index 4386059d..00c2b479 100644 --- a/src/style-globals/_variables.sass +++ b/src/style-globals/_variables.sass @@ -14,6 +14,7 @@ $navbar-padding: 10px $transition-length: 150ms // Colors +$gray-very-dark: #5c5c5c $gray-dark: #aaa $gray-semi-dark: #bbb $gray-semi-light: #ccc @@ -23,3 +24,8 @@ $blue: #00A6D6 $blue-dark: #0087b5 $blue-very-dark: #006182 $blue-light: #deebf7 + +// Media queries +$screen-sm: 768px +$screen-md: 992px +$screen-lg: 1200px |
