change login screen images as per new layout (#15526)

* change login screen images as per new layout

* fix the image size and layout background color

* class naming change
This commit is contained in:
Ashish Gupta 2024-03-14 10:35:45 +05:30 committed by GitHub
parent 7718f1c560
commit 22cd2ca74e
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
15 changed files with 298 additions and 263 deletions

Binary file not shown.

Before

Width:  |  Height:  |  Size: 840 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 780 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 741 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 556 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 633 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 259 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 246 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 237 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 266 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 240 KiB

View File

@ -12,36 +12,40 @@
*/ */
import { CarouselProps } from 'antd'; import { CarouselProps } from 'antd';
import collaborationImg from '../assets/img/data-collaboration.png'; import loginClassBase from './LoginClassBase';
import discoveryImg from '../assets/img/data-discovery.png';
import governanceImg from '../assets/img/data-governance.png'; const {
import insightImg from '../assets/img/data-insights.png'; dataDiscovery,
import dataQualityImg from '../assets/img/data-qauality.png'; dataQuality,
governance,
dataInsightPlural,
dataCollaboration,
} = loginClassBase.carouselImages();
export const LOGIN_SLIDE = [ export const LOGIN_SLIDE = [
{ {
title: 'data-discovery', title: 'data-discovery',
image: discoveryImg, image: dataDiscovery,
descriptionKey: 'enables-end-to-end-metadata-management', descriptionKey: 'enables-end-to-end-metadata-management',
}, },
{ {
title: 'data-quality', title: 'data-quality',
image: dataQualityImg, image: dataQuality,
descriptionKey: 'discover-your-data-and-unlock-the-value-of-data-assets', descriptionKey: 'discover-your-data-and-unlock-the-value-of-data-assets',
}, },
{ {
title: 'governance', title: 'governance',
image: governanceImg, image: governance,
descriptionKey: 'assess-data-reliability-with-data-profiler-lineage', descriptionKey: 'assess-data-reliability-with-data-profiler-lineage',
}, },
{ {
title: 'data-insight-plural', title: 'data-insight-plural',
image: insightImg, image: dataInsightPlural,
descriptionKey: 'fosters-collaboration-among-producers-and-consumers', descriptionKey: 'fosters-collaboration-among-producers-and-consumers',
}, },
{ {
title: 'data-collaboration', title: 'data-collaboration',
image: collaborationImg, image: dataCollaboration,
descriptionKey: 'deeply-understand-table-relations-message', descriptionKey: 'deeply-understand-table-relations-message',
}, },
]; ];

View File

@ -0,0 +1,35 @@
/*
* Copyright 2024 Collate.
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
* http://www.apache.org/licenses/LICENSE-2.0
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
import collaborationImg from '../assets/img/login-screen/data-collaboration.png';
import discoveryImg from '../assets/img/login-screen/data-discovery.png';
import governanceImg from '../assets/img/login-screen/data-governance.png';
import insightImg from '../assets/img/login-screen/data-insights.png';
import dataQualityImg from '../assets/img/login-screen/data-quality.png';
class LoginClassBase {
public carouselImages() {
return {
dataDiscovery: discoveryImg,
dataQuality: dataQualityImg,
governance: governanceImg,
dataInsightPlural: insightImg,
dataCollaboration: collaborationImg,
};
}
}
const loginClassBase = new LoginClassBase();
export default loginClassBase;
export { LoginClassBase };

View File

@ -190,136 +190,134 @@ const SignInPage = () => {
const onClickForgotPassword = () => history.push(ROUTES.FORGOT_PASSWORD); const onClickForgotPassword = () => history.push(ROUTES.FORGOT_PASSWORD);
return ( return (
<div className="d-flex flex-col h-full bg-white"> <Row className="h-full" data-testid="signin-page">
<Row className="flex flex-grow" data-testid="signin-page"> <Col className="bg-white" span={8}>
<Col span={8}> <div
<div className={classNames('mt-24 text-center flex-center flex-col', {
className={classNames('mt-24 text-center flex-center flex-col', { 'sso-container': !isAuthProviderBasic,
'sso-container': !isAuthProviderBasic, })}>
})}> <BrandImage height="auto" width={200} />
<BrandImage height="auto" width={200} /> <Typography.Text className="mt-8 w-80 text-xl font-medium text-grey-muted">
<Typography.Text className="mt-8 w-80 text-xl font-medium text-grey-muted"> {t('message.om-description')}{' '}
{t('message.om-description')}{' '} </Typography.Text>
</Typography.Text>
{isAuthProviderBasic ? ( {isAuthProviderBasic ? (
<div className="login-form "> <div className="login-form ">
<Form <Form
className="w-full" className="w-full"
form={form} form={form}
layout="vertical" layout="vertical"
validateMessages={VALIDATION_MESSAGES} validateMessages={VALIDATION_MESSAGES}
onFinish={handleSubmit}> onFinish={handleSubmit}>
<Form.Item <Form.Item
data-testid="email" data-testid="email"
label={ label={
isAuthProviderLDAP
? t('label.email')
: t('label.username-or-email')
}
name="email"
requiredMark={false}
rules={[{ required: true }]}>
<Input
autoFocus
placeholder={
isAuthProviderLDAP isAuthProviderLDAP
? t('label.email') ? t('label.email')
: t('label.username-or-email') : t('label.username-or-email')
} }
name="email" />
requiredMark={false} </Form.Item>
rules={[{ required: true }]}> <Form.Item
<Input data-testid="password"
autoFocus label={t('label.password')}
placeholder={ name="password"
isAuthProviderLDAP requiredMark={false}
? t('label.email') rules={[{ required: true }]}>
: t('label.username-or-email') <Input.Password
} autoComplete="off"
/> placeholder={t('label.password')}
</Form.Item> />
<Form.Item </Form.Item>
data-testid="password"
label={t('label.password')}
name="password"
requiredMark={false}
rules={[{ required: true }]}>
<Input.Password
autoComplete="off"
placeholder={t('label.password')}
/>
</Form.Item>
<Button <Button
className="w-full" className="w-full"
data-testid="login" data-testid="login"
disabled={loading} disabled={loading}
htmlType="submit" htmlType="submit"
loading={loading} loading={loading}
type="primary"> type="primary">
{t('label.login')} {t('label.login')}
</Button> </Button>
</Form> </Form>
{loginError && ( {loginError && (
<div <div
className="d-flex flex-col m-y-md" className="d-flex flex-col m-y-md"
data-testid="login-error-container"> data-testid="login-error-container">
<div className="flex global-border rounded-4 p-sm error-alert "> <div className="flex global-border rounded-4 p-sm error-alert ">
<div className="m-r-xs"> <div className="m-r-xs">
<Icon <Icon
component={IconFailBadge} component={IconFailBadge}
style={{ fontSize: '20px' }} style={{ fontSize: '20px' }}
/> />
</div>
<p data-testid="success-line">
<span>{loginError}</span>
</p>
</div> </div>
<p data-testid="success-line">
<span>{loginError}</span>
</p>
</div> </div>
)} </div>
{!isAuthProviderLDAP && ( )}
<> {!isAuthProviderLDAP && (
<div className="mt-8" onClick={onClickForgotPassword}> <>
<Typography.Link underline data-testid="forgot-password"> <div className="mt-8" onClick={onClickForgotPassword}>
{t('label.forgot-password')} <Typography.Link underline data-testid="forgot-password">
</Typography.Link> {t('label.forgot-password')}
</div> </Typography.Link>
{authConfig?.enableSelfSignup && ( </div>
<> {authConfig?.enableSelfSignup && (
<Divider className="w-min-0 mt-8 mb-12 justify-center"> <>
<Typography.Text className="text-sm" type="secondary"> <Divider className="w-min-0 mt-8 mb-12 justify-center">
{t('label.or-lowercase')} <Typography.Text className="text-sm" type="secondary">
</Typography.Text> {t('label.or-lowercase')}
</Divider> </Typography.Text>
</Divider>
<div className="mt-4 d-flex flex-center"> <div className="mt-4 d-flex flex-center">
<Typography.Text className="mr-4"> <Typography.Text className="mr-4">
{t('message.new-to-the-platform')} {t('message.new-to-the-platform')}
</Typography.Text> </Typography.Text>
<Button <Button
data-testid="signup" data-testid="signup"
type="link" type="link"
onClick={onClickSignUp}> onClick={onClickSignUp}>
{t('label.create-entity', { {t('label.create-entity', {
entity: t('label.account'), entity: t('label.account'),
})} })}
</Button> </Button>
</div> </div>
</> </>
)} )}
</> </>
)} )}
</div> </div>
) : ( ) : (
<div className="">{getSignInButton()}</div> <div className="">{getSignInButton()}</div>
)} )}
</div> </div>
</Col> </Col>
<Col className="relative" span={16}> <Col className="relative" span={16}>
<div className="absolute inset-0"> <div className="absolute inset-0">
<img <img
alt="bg-image" alt="bg-image"
className="w-full h-full" className="w-full h-full"
data-testid="bg-image" data-testid="bg-image"
src={loginBG} src={loginBG}
/> />
</div> </div>
<LoginCarousel /> <LoginCarousel />
</Col> </Col>
</Row> </Row>
</div>
); );
}; };

View File

@ -49,6 +49,7 @@
transform: translate(-50%, -50%); transform: translate(-50%, -50%);
.slick-dots.slick-dots-bottom { .slick-dots.slick-dots-bottom {
position: initial;
.slick-active { .slick-active {
button { button {
background-color: @primary-color; background-color: @primary-color;

View File

@ -11,7 +11,7 @@
* limitations under the License. * limitations under the License.
*/ */
import { Button, Divider, Form, Input, Typography } from 'antd'; import { Button, Col, Divider, Form, Input, Row, Typography } from 'antd';
import { isEmpty } from 'lodash'; import { isEmpty } from 'lodash';
import React, { useMemo } from 'react'; import React, { useMemo } from 'react';
import { useTranslation } from 'react-i18next'; import { useTranslation } from 'react-i18next';
@ -66,149 +66,146 @@ const BasicSignUp = () => {
const handleLogin = () => history.push(ROUTES.SIGNIN); const handleLogin = () => history.push(ROUTES.SIGNIN);
return ( return (
<div className="d-flex flex-col h-full bg-white"> <Row className="h-full" data-testid="signin-page">
<div className="d-flex flex-grow" data-testid="signin-page"> <Col className="bg-white" span={10}>
<div className="w-5/12"> <div className="mt-4 text-center flex-center flex-col">
<div className="mt-4 text-center flex-center flex-col"> <BrandImage height="auto" width={200} />
<BrandImage height="auto" width={200} /> <Typography.Text className="mt-8 w-80 text-xl font-medium text-grey-muted">
<Typography.Text className="mt-8 w-80 text-xl font-medium text-grey-muted"> {t('message.om-description')}
{t('message.om-description')} </Typography.Text>
</Typography.Text>
{isAuthProviderBasic ? ( {isAuthProviderBasic ? (
<div className="m-t-lg" style={{ width: '334px' }}> <div className="m-t-lg" style={{ width: '334px' }}>
<Form <Form
autoComplete="off" autoComplete="off"
form={form} form={form}
layout="vertical" layout="vertical"
validateMessages={VALIDATION_MESSAGES} validateMessages={VALIDATION_MESSAGES}
onFinish={handleSubmit}> onFinish={handleSubmit}>
<Form.Item <Form.Item
label={t('label.entity-name', { label={t('label.entity-name', {
entity: t('label.first'), entity: t('label.first'),
})}
name="firstName"
rules={[{ whitespace: true, required: true }]}>
<Input
autoFocus
placeholder={t('label.enter-entity-name', {
entity: t('label.first-lowercase'),
})} })}
name="firstName" />
rules={[{ whitespace: true, required: true }]}> </Form.Item>
<Input <Form.Item
autoFocus label={t('label.entity-name', {
placeholder={t('label.enter-entity-name', { entity: t('label.last'),
entity: t('label.first-lowercase'), })}
})} name="lastName"
/> rules={[{ whitespace: true, required: true }]}>
</Form.Item> <Input
<Form.Item placeholder={t('label.enter-entity', {
label={t('label.entity-name', { entity: t('label.last-name-lowercase'),
entity: t('label.last'),
})} })}
name="lastName" />
rules={[{ whitespace: true, required: true }]}> </Form.Item>
<Input <Form.Item
placeholder={t('label.enter-entity', { label={t('label.email')}
entity: t('label.last-name-lowercase'), name="email"
})} rules={[{ type: 'email', required: true }]}>
/> <Input
</Form.Item> placeholder={t('label.enter-entity', {
<Form.Item entity: t('label.email-lowercase'),
label={t('label.email')}
name="email"
rules={[{ type: 'email', required: true }]}>
<Input
placeholder={t('label.enter-entity', {
entity: t('label.email-lowercase'),
})}
/>
</Form.Item>
<Form.Item
label={t('label.password')}
name="password"
rules={[
{
required: true,
},
{
pattern: passwordRegex,
message: t('message.password-error-message'),
},
]}>
<Input.Password
autoComplete="off"
placeholder={t('label.enter-entity', {
entity: t('label.password-lowercase'),
})}
/>
</Form.Item>
<Form.Item
label={t('label.password-type', {
type: t('label.confirm'),
})} })}
name="confirmPassword" />
rules={[ </Form.Item>
{ <Form.Item
validator: (_, value) => { label={t('label.password')}
if (isEmpty(password)) { name="password"
return Promise.reject( rules={[
t('label.please-password-type-first') {
); required: true,
} },
if (value !== password) { {
return Promise.reject( pattern: passwordRegex,
t('label.password-not-match') message: t('message.password-error-message'),
); },
} ]}>
<Input.Password
autoComplete="off"
placeholder={t('label.enter-entity', {
entity: t('label.password-lowercase'),
})}
/>
</Form.Item>
<Form.Item
label={t('label.password-type', {
type: t('label.confirm'),
})}
name="confirmPassword"
rules={[
{
validator: (_, value) => {
if (isEmpty(password)) {
return Promise.reject(
t('label.please-password-type-first')
);
}
if (value !== password) {
return Promise.reject(t('label.password-not-match'));
}
return Promise.resolve(); return Promise.resolve();
},
}, },
]}> },
<Input.Password ]}>
autoComplete="off" <Input.Password
placeholder={t('label.confirm-password')} autoComplete="off"
/> placeholder={t('label.confirm-password')}
</Form.Item> />
</Form.Item>
<Button className="w-full" htmlType="submit" type="primary"> <Button className="w-full" htmlType="submit" type="primary">
{t('label.create-entity', { {t('label.create-entity', {
entity: t('label.account'), entity: t('label.account'),
})} })}
</Button>
<Divider className="w-min-0 mt-8 mb-12 justify-center">
<Typography.Text type="secondary">
{t('label.or-lowercase')}
</Typography.Text>
</Divider>
<div className="mt-4 d-flex flex-center">
<Typography.Text className="mr-4">
{t('message.already-a-user')}
</Typography.Text>
<Button
ghost
data-testid="login"
type="link"
onClick={handleLogin}>
{t('label.login')}
</Button> </Button>
</div>
<Divider className="w-min-0 mt-8 mb-12 justify-center"> </Form>
<Typography.Text type="secondary"> </div>
{t('label.or-lowercase')} ) : null}
</Typography.Text>
</Divider>
<div className="mt-4 d-flex flex-center">
<Typography.Text className="mr-4">
{t('message.already-a-user')}
</Typography.Text>
<Button
ghost
data-testid="login"
type="link"
onClick={handleLogin}>
{t('label.login')}
</Button>
</div>
</Form>
</div>
) : null}
</div>
</div> </div>
<div className="w-7/12 relative"> </Col>
<div className="absolute inset-0">
<img
alt="bg-image"
className="w-full h-full"
data-testid="bg-image"
src={loginBG}
/>
</div>
<LoginCarousel /> <Col className="relative" span={14}>
<div className="absolute inset-0">
<img
alt="bg-image"
className="w-full h-full"
data-testid="bg-image"
src={loginBG}
/>
</div> </div>
</div>
</div> <LoginCarousel />
</Col>
</Row>
); );
}; };