redesign base component (#232)
* redesign base component * rebrand base component * redesign base component * rewrite & optimize base component * redesign base component * address feedback Co-authored-by: Waheed Ahmed <waheed.ahmed@arbisoft.com>
This commit is contained in:
committed by
Waheed Ahmed
parent
f3721b5db2
commit
eaf3f1eba5
19
package-lock.json
generated
19
package-lock.json
generated
@@ -3877,6 +3877,19 @@
|
||||
"babel-polyfill": "6.26.0",
|
||||
"react-responsive": "8.0.3",
|
||||
"react-transition-group": "4.3.0"
|
||||
},
|
||||
"dependencies": {
|
||||
"react-responsive": {
|
||||
"version": "8.0.3",
|
||||
"resolved": "https://registry.npmjs.org/react-responsive/-/react-responsive-8.0.3.tgz",
|
||||
"integrity": "sha512-F9VXyLao7O8XHXbLjQbIr4+mC6Zr0RDTwNjd7ixTmYEAyKyNanBkLkFchNaMZgszoSK6PgSs/3m/QDWw33/gpg==",
|
||||
"requires": {
|
||||
"hyphenate-style-name": "^1.0.0",
|
||||
"matchmediaquery": "^0.3.0",
|
||||
"prop-types": "^15.6.1",
|
||||
"shallow-equal": "^1.1.0"
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"@edx/frontend-platform": {
|
||||
@@ -21058,9 +21071,9 @@
|
||||
}
|
||||
},
|
||||
"react-responsive": {
|
||||
"version": "8.0.3",
|
||||
"resolved": "https://registry.npmjs.org/react-responsive/-/react-responsive-8.0.3.tgz",
|
||||
"integrity": "sha512-F9VXyLao7O8XHXbLjQbIr4+mC6Zr0RDTwNjd7ixTmYEAyKyNanBkLkFchNaMZgszoSK6PgSs/3m/QDWw33/gpg==",
|
||||
"version": "8.2.0",
|
||||
"resolved": "https://registry.npmjs.org/react-responsive/-/react-responsive-8.2.0.tgz",
|
||||
"integrity": "sha512-iagCqVrw4QSjhxKp3I/YK6+ODkWY6G+YPElvdYKiUUbywwh9Ds0M7r26Fj2/7dWFFbOpcGnJE6uE7aMck8j5Qg==",
|
||||
"requires": {
|
||||
"hyphenate-style-name": "^1.0.0",
|
||||
"matchmediaquery": "^0.3.0",
|
||||
|
||||
@@ -58,6 +58,7 @@
|
||||
"react-helmet": "6.1.0",
|
||||
"react-loading-skeleton": "2.2.0",
|
||||
"react-redux": "7.2.3",
|
||||
"react-responsive": "8.2.0",
|
||||
"react-router": "5.2.0",
|
||||
"react-router-dom": "5.2.0",
|
||||
"redux": "4.0.5",
|
||||
|
||||
@@ -13,6 +13,7 @@ $microsoft-black: #2f2f2f;
|
||||
$microsoft-focus-black: #000;
|
||||
$apple-black: #000000;
|
||||
$apple-focus-black: $apple-black;
|
||||
$accent-a-light: #c9f2f5;
|
||||
|
||||
.sr-only {
|
||||
position: absolute;
|
||||
@@ -282,6 +283,10 @@ $apple-focus-black: $apple-black;
|
||||
margin-top: 10px;
|
||||
}
|
||||
|
||||
.mt-7 {
|
||||
margin-top: 7rem;
|
||||
}
|
||||
|
||||
.pt-10 {
|
||||
padding-top: 10px;
|
||||
}
|
||||
@@ -323,6 +328,92 @@ $apple-focus-black: $apple-black;
|
||||
}
|
||||
}
|
||||
|
||||
.custom-select-size {
|
||||
background-size: 8px 10px;
|
||||
.large-screen-container {
|
||||
background-color: $white;
|
||||
background-image: linear-gradient(102.02deg, $primary 45%, $white 45%);
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.medium-screen-header {
|
||||
background-color: $white;
|
||||
background-image: linear-gradient(102.02deg, $primary 93%, $white 7%);
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.large-screen-top-stripe {
|
||||
height: 0.5rem;
|
||||
background-image: linear-gradient(
|
||||
102.02deg,
|
||||
$brand-700,
|
||||
$brand-700 10%,
|
||||
$brand 10%,
|
||||
$brand 40%,
|
||||
$primary-700 40%,
|
||||
$primary-700 50%,
|
||||
$accent-a 50%,
|
||||
$accent-a 72%,
|
||||
$accent-a-light 72%,
|
||||
);
|
||||
background-repeat: no-repeat;
|
||||
}
|
||||
|
||||
.medium-screen-top-stripe {
|
||||
height: 0.5rem;
|
||||
background-image: linear-gradient(
|
||||
102.02deg,
|
||||
$brand-700,
|
||||
$brand-700 10%,
|
||||
$brand 10%,
|
||||
$brand 90%,
|
||||
$primary-700 90%,
|
||||
$primary-700 100%,
|
||||
);
|
||||
background-repeat: no-repeat;
|
||||
}
|
||||
|
||||
.small-screen-top-stripe {
|
||||
height: 0.5rem;
|
||||
background-image: linear-gradient(
|
||||
102.02deg,
|
||||
$brand-700,
|
||||
$brand-700 20%,
|
||||
$brand 20%,
|
||||
);
|
||||
background-repeat: no-repeat;
|
||||
}
|
||||
|
||||
.svg-line {
|
||||
padding-top: 0.5rem;
|
||||
stroke: $accent-b;
|
||||
stroke-width: 0.5rem;
|
||||
width: 7em;
|
||||
}
|
||||
|
||||
.small-screen-svg-line {
|
||||
padding-top: 0.5rem;
|
||||
stroke: $accent-b;
|
||||
stroke-width: 0.25rem;
|
||||
width: 4em;
|
||||
height: 72px;
|
||||
}
|
||||
|
||||
.large-heading {
|
||||
padding-left: 1rem;
|
||||
color: $white;
|
||||
max-width: 24rem;
|
||||
line-height: 78px;
|
||||
font-size: 78px;
|
||||
}
|
||||
|
||||
.small-heading {
|
||||
padding-left: 0.5rem;
|
||||
color: $white;
|
||||
line-height: 40px;
|
||||
font-size: 36px;
|
||||
}
|
||||
|
||||
.logo {
|
||||
width: 4.5rem;
|
||||
padding-top: 2rem;
|
||||
padding-left: 25px;
|
||||
}
|
||||
|
||||
34
src/common-components/BaseComponent.jsx
Normal file
34
src/common-components/BaseComponent.jsx
Normal file
@@ -0,0 +1,34 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
|
||||
import Responsive from 'react-responsive';
|
||||
|
||||
import SmallScreenLayout from './SmallScreenLayout';
|
||||
import MediumScreenLayout from './MediumScreenLayout';
|
||||
import LargeScreenLayout from './LargeScreenLayout';
|
||||
|
||||
const BaseComponent = ({ children }) => (
|
||||
<>
|
||||
<Responsive maxWidth={767}>
|
||||
<SmallScreenLayout>
|
||||
{children}
|
||||
</SmallScreenLayout>
|
||||
</Responsive>
|
||||
<Responsive minWidth={768} maxWidth={1199}>
|
||||
<MediumScreenLayout>
|
||||
{children}
|
||||
</MediumScreenLayout>
|
||||
</Responsive>
|
||||
<Responsive minWidth={1200}>
|
||||
<LargeScreenLayout>
|
||||
{children}
|
||||
</LargeScreenLayout>
|
||||
</Responsive>
|
||||
</>
|
||||
);
|
||||
|
||||
BaseComponent.propTypes = {
|
||||
children: PropTypes.node.isRequired,
|
||||
};
|
||||
|
||||
export default BaseComponent;
|
||||
29
src/common-components/LargeScreenLayout.jsx
Normal file
29
src/common-components/LargeScreenLayout.jsx
Normal file
@@ -0,0 +1,29 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
|
||||
import { Row } from '@edx/paragon';
|
||||
|
||||
import LargeScreenLeftLayout from './LargeScreenLeftLayout';
|
||||
import LargeScreenRightLayout from './LargeScreenRightLayout';
|
||||
|
||||
const LargeScreenLayout = (props) => {
|
||||
const { children } = props;
|
||||
|
||||
return (
|
||||
<>
|
||||
<div className="large-screen-top-stripe" />
|
||||
<Row className="large-screen-container">
|
||||
<LargeScreenLeftLayout />
|
||||
<LargeScreenRightLayout>
|
||||
{ children }
|
||||
</LargeScreenRightLayout>
|
||||
</Row>
|
||||
</>
|
||||
);
|
||||
};
|
||||
|
||||
LargeScreenLayout.propTypes = {
|
||||
children: PropTypes.node.isRequired,
|
||||
};
|
||||
|
||||
export default LargeScreenLayout;
|
||||
34
src/common-components/LargeScreenLeftLayout.jsx
Normal file
34
src/common-components/LargeScreenLeftLayout.jsx
Normal file
@@ -0,0 +1,34 @@
|
||||
import React from 'react';
|
||||
|
||||
import { injectIntl, intlShape } from '@edx/frontend-platform/i18n';
|
||||
import { getConfig } from '@edx/frontend-platform';
|
||||
import { Col } from '@edx/paragon';
|
||||
|
||||
import messages from './messages';
|
||||
|
||||
const LargeScreenLeftLayout = (props) => {
|
||||
const { intl } = props;
|
||||
|
||||
return (
|
||||
<Col xs={6} className="pr-0">
|
||||
<img alt="edx" className="logo" src={getConfig().LOGO_WHITE_URL} />
|
||||
<div className="d-flex mt-7">
|
||||
<svg className="svg-line pl-5">
|
||||
<line x1="50" y1="0" x2="10" y2="215" />
|
||||
</svg>
|
||||
<h1 className="large-heading">
|
||||
{intl.formatMessage(messages['start.learning'])}
|
||||
<span className="text-accent-a"><br />
|
||||
{intl.formatMessage(messages['with.site.name'], { siteName: getConfig().SITE_NAME })}
|
||||
</span>
|
||||
</h1>
|
||||
</div>
|
||||
</Col>
|
||||
);
|
||||
};
|
||||
|
||||
LargeScreenLeftLayout.propTypes = {
|
||||
intl: intlShape.isRequired,
|
||||
};
|
||||
|
||||
export default injectIntl(LargeScreenLeftLayout);
|
||||
20
src/common-components/LargeScreenRightLayout.jsx
Normal file
20
src/common-components/LargeScreenRightLayout.jsx
Normal file
@@ -0,0 +1,20 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
|
||||
import { Col } from '@edx/paragon';
|
||||
|
||||
const LargeScreenRightLayout = (props) => {
|
||||
const { children } = props;
|
||||
|
||||
return (
|
||||
<Col xs={6} className="min-vh-100 pt-5 pl-0">
|
||||
{ children }
|
||||
</Col>
|
||||
);
|
||||
};
|
||||
|
||||
LargeScreenRightLayout.propTypes = {
|
||||
children: PropTypes.node.isRequired,
|
||||
};
|
||||
|
||||
export default LargeScreenRightLayout;
|
||||
36
src/common-components/MediumScreenHeader.jsx
Normal file
36
src/common-components/MediumScreenHeader.jsx
Normal file
@@ -0,0 +1,36 @@
|
||||
import React from 'react';
|
||||
|
||||
import { injectIntl, intlShape } from '@edx/frontend-platform/i18n';
|
||||
import { getConfig } from '@edx/frontend-platform';
|
||||
|
||||
import messages from './messages';
|
||||
|
||||
const MediumScreenHeader = (props) => {
|
||||
const { intl } = props;
|
||||
|
||||
return (
|
||||
<>
|
||||
<div className="medium-screen-top-stripe" />
|
||||
<div className="medium-screen-header">
|
||||
<img alt="edx" className="logo" src={getConfig().LOGO_WHITE_URL} />
|
||||
<div className="row mt-4">
|
||||
<svg className="svg-line pl-5">
|
||||
<line x1="50" y1="0" x2="10" y2="215" />
|
||||
</svg>
|
||||
<h1 className="large-heading pb-3">
|
||||
{intl.formatMessage(messages['start.learning'])}
|
||||
<span className="text-accent-a"><br />
|
||||
{intl.formatMessage(messages['with.site.name'], { siteName: getConfig().SITE_NAME })}
|
||||
</span>
|
||||
</h1>
|
||||
</div>
|
||||
</div>
|
||||
</>
|
||||
);
|
||||
};
|
||||
|
||||
MediumScreenHeader.propTypes = {
|
||||
intl: intlShape.isRequired,
|
||||
};
|
||||
|
||||
export default injectIntl(MediumScreenHeader);
|
||||
21
src/common-components/MediumScreenLayout.jsx
Normal file
21
src/common-components/MediumScreenLayout.jsx
Normal file
@@ -0,0 +1,21 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
|
||||
import MediumScreenHeader from './MediumScreenHeader';
|
||||
|
||||
const MediumScreenLayout = (props) => {
|
||||
const { children } = props;
|
||||
|
||||
return (
|
||||
<>
|
||||
<MediumScreenHeader />
|
||||
{ children }
|
||||
</>
|
||||
);
|
||||
};
|
||||
|
||||
MediumScreenLayout.propTypes = {
|
||||
children: PropTypes.node.isRequired,
|
||||
};
|
||||
|
||||
export default MediumScreenLayout;
|
||||
37
src/common-components/SmallScreenHeader.jsx
Normal file
37
src/common-components/SmallScreenHeader.jsx
Normal file
@@ -0,0 +1,37 @@
|
||||
import React from 'react';
|
||||
|
||||
import { injectIntl, intlShape } from '@edx/frontend-platform/i18n';
|
||||
import { getConfig } from '@edx/frontend-platform';
|
||||
|
||||
import messages from './messages';
|
||||
|
||||
const SmallScreenHeader = (props) => {
|
||||
const { intl } = props;
|
||||
|
||||
return (
|
||||
<>
|
||||
<div className="small-screen-top-stripe" />
|
||||
<div className="bg-primary">
|
||||
<img alt="edx" className="logo" src={getConfig().LOGO_WHITE_URL} />
|
||||
<div className="d-flex mt-3">
|
||||
<svg className="small-screen-svg-line">
|
||||
<line x1="55" y1="0" x2="40" y2="65" />
|
||||
</svg>
|
||||
<h1 className="small-heading">
|
||||
{intl.formatMessage(messages['start.learning'])}
|
||||
<br />
|
||||
<span className="text-accent-a">
|
||||
{intl.formatMessage(messages['with.site.name'], { siteName: getConfig().SITE_NAME })}
|
||||
</span>
|
||||
</h1>
|
||||
</div>
|
||||
</div>
|
||||
</>
|
||||
);
|
||||
};
|
||||
|
||||
SmallScreenHeader.propTypes = {
|
||||
intl: intlShape.isRequired,
|
||||
};
|
||||
|
||||
export default injectIntl(SmallScreenHeader);
|
||||
21
src/common-components/SmallScreenLayout.jsx
Normal file
21
src/common-components/SmallScreenLayout.jsx
Normal file
@@ -0,0 +1,21 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
|
||||
import SmallScreenHeader from './SmallScreenHeader';
|
||||
|
||||
const SmallScreenLayout = (props) => {
|
||||
const { children } = props;
|
||||
|
||||
return (
|
||||
<>
|
||||
<SmallScreenHeader />
|
||||
{ children }
|
||||
</>
|
||||
);
|
||||
};
|
||||
|
||||
SmallScreenLayout.propTypes = {
|
||||
children: PropTypes.node.isRequired,
|
||||
};
|
||||
|
||||
export default SmallScreenLayout;
|
||||
@@ -12,3 +12,4 @@ export { default as APIFailureMessage } from './APIFailureMessage';
|
||||
export { default as reducer } from './data/reducers';
|
||||
export { default as saga } from './data/sagas';
|
||||
export { storeName } from './data/selectors';
|
||||
export { default as BaseComponent } from './BaseComponent';
|
||||
|
||||
@@ -60,6 +60,16 @@ const messages = defineMessages({
|
||||
defaultMessage: 'Create account using {providerName}',
|
||||
description: 'Screen reader text that appears before social auth provider name',
|
||||
},
|
||||
'start.learning': {
|
||||
id: 'start.learning',
|
||||
defaultMessage: 'Start Learning',
|
||||
description: 'Header text for logistration MFE pages',
|
||||
},
|
||||
'with.site.name': {
|
||||
id: 'with.site.name',
|
||||
defaultMessage: 'with {siteName}',
|
||||
description: 'Header text with site name for logistration MFE pages',
|
||||
},
|
||||
});
|
||||
|
||||
export default messages;
|
||||
|
||||
@@ -19,7 +19,7 @@ import {
|
||||
} from './data/constants';
|
||||
import ForgotPasswordPage from './forgot-password';
|
||||
import {
|
||||
HeaderLayout, UnAuthOnlyRoute, registerIcons, NotFoundPage,
|
||||
BaseComponent, UnAuthOnlyRoute, registerIcons, NotFoundPage,
|
||||
} from './common-components';
|
||||
import ResetPasswordPage from './reset-password';
|
||||
import WelcomePage from './welcome';
|
||||
@@ -32,7 +32,7 @@ registerIcons();
|
||||
subscribe(APP_READY, () => {
|
||||
ReactDOM.render(
|
||||
<AppProvider store={configureStore()}>
|
||||
<HeaderLayout>
|
||||
<BaseComponent>
|
||||
<Switch>
|
||||
<Route exact path="/">
|
||||
<Redirect to={PAGE_NOT_FOUND} />
|
||||
@@ -47,7 +47,7 @@ subscribe(APP_READY, () => {
|
||||
<Redirect to={PAGE_NOT_FOUND} />
|
||||
</Route>
|
||||
</Switch>
|
||||
</HeaderLayout>
|
||||
</BaseComponent>
|
||||
</AppProvider>,
|
||||
document.getElementById('root'),
|
||||
);
|
||||
|
||||
Reference in New Issue
Block a user