UX improvements and bug fixes
This commit is contained in:
parent
60220d9ad4
commit
3a5e5ad7f6
680
components.js
680
components.js
File diff suppressed because it is too large
Load Diff
76
css/main.css
76
css/main.css
@ -7,7 +7,7 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
:root {
|
:root {
|
||||||
font-size: clamp(1rem, 1.2vmax, 3rem);
|
font-size: clamp(1rem, 1.2vmax, 1.2rem);
|
||||||
}
|
}
|
||||||
|
|
||||||
html,
|
html,
|
||||||
@ -46,13 +46,15 @@ body[data-theme=dark] * {
|
|||||||
--yellow: #ffd13a;
|
--yellow: #ffd13a;
|
||||||
}
|
}
|
||||||
|
|
||||||
p {
|
p,
|
||||||
|
strong {
|
||||||
font-size: 0.9rem;
|
font-size: 0.9rem;
|
||||||
max-width: 70ch;
|
max-width: 70ch;
|
||||||
line-height: 1.7;
|
line-height: 1.7;
|
||||||
color: rgba(var(--text-color), 0.8);
|
color: rgba(var(--text-color), 0.8);
|
||||||
}
|
}
|
||||||
p:not(:last-of-type) {
|
p:not(:last-of-type),
|
||||||
|
strong:not(:last-of-type) {
|
||||||
margin-bottom: 1.5rem;
|
margin-bottom: 1.5rem;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -409,7 +411,7 @@ button:active,
|
|||||||
}
|
}
|
||||||
#logo h4 {
|
#logo h4 {
|
||||||
text-transform: capitalize;
|
text-transform: capitalize;
|
||||||
font-size: 1rem;
|
font-size: 0.9rem;
|
||||||
font-weight: 600;
|
font-weight: 600;
|
||||||
}
|
}
|
||||||
#logo #main_logo {
|
#logo #main_logo {
|
||||||
@ -420,6 +422,12 @@ button:active,
|
|||||||
}
|
}
|
||||||
|
|
||||||
details summary {
|
details summary {
|
||||||
|
display: -webkit-box;
|
||||||
|
display: -ms-flexbox;
|
||||||
|
display: flex;
|
||||||
|
-webkit-box-pack: justify;
|
||||||
|
-ms-flex-pack: justify;
|
||||||
|
justify-content: space-between;
|
||||||
-webkit-user-select: none;
|
-webkit-user-select: none;
|
||||||
-moz-user-select: none;
|
-moz-user-select: none;
|
||||||
-ms-user-select: none;
|
-ms-user-select: none;
|
||||||
@ -576,6 +584,10 @@ details[open] > summary .icon {
|
|||||||
-ms-flex-align: center;
|
-ms-flex-align: center;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
}
|
}
|
||||||
|
.quick-action.disabled {
|
||||||
|
pointer-events: none;
|
||||||
|
opacity: 0.6;
|
||||||
|
}
|
||||||
.quick-action__icon {
|
.quick-action__icon {
|
||||||
padding: 1rem;
|
padding: 1rem;
|
||||||
border-radius: 1rem;
|
border-radius: 1rem;
|
||||||
@ -716,23 +728,41 @@ strip-option:last-of-type {
|
|||||||
}
|
}
|
||||||
|
|
||||||
.activity-card--request,
|
.activity-card--request,
|
||||||
|
.activity-card--pending,
|
||||||
.activity-card--admin {
|
.activity-card--admin {
|
||||||
grid-template-areas: "icon . amount" "icon time .";
|
grid-template-areas: "icon . amount" "icon time .";
|
||||||
}
|
}
|
||||||
.activity-card--request .activity-card__icon,
|
.activity-card--request .activity-card__icon,
|
||||||
|
.activity-card--pending .activity-card__icon,
|
||||||
.activity-card--admin .activity-card__icon {
|
.activity-card--admin .activity-card__icon {
|
||||||
grid-area: icon;
|
grid-area: icon;
|
||||||
}
|
}
|
||||||
.activity-card--request .activity-card__time,
|
.activity-card--request .activity-card__time,
|
||||||
|
.activity-card--pending .activity-card__time,
|
||||||
.activity-card--admin .activity-card__time {
|
.activity-card--admin .activity-card__time {
|
||||||
grid-area: time;
|
grid-area: time;
|
||||||
}
|
}
|
||||||
.activity-card--request .activity-card__amount,
|
.activity-card--request .activity-card__amount,
|
||||||
|
.activity-card--pending .activity-card__amount,
|
||||||
.activity-card--admin .activity-card__amount {
|
.activity-card--admin .activity-card__amount {
|
||||||
grid-area: amount;
|
grid-area: amount;
|
||||||
text-align: end;
|
text-align: end;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#pending_transaction:not(:empty) {
|
||||||
|
margin-bottom: 2rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.activity-card--pending:not(:empty) {
|
||||||
|
padding: 1rem;
|
||||||
|
margin-top: 0.8rem;
|
||||||
|
border: solid 0.1rem var(--accent-color);
|
||||||
|
}
|
||||||
|
.activity-card--pending:not(:empty) .activity-card__description {
|
||||||
|
font-size: 0.8rem;
|
||||||
|
color: rgba(var(--text-color), 0.8);
|
||||||
|
}
|
||||||
|
|
||||||
.status-tag:not(:empty) {
|
.status-tag:not(:empty) {
|
||||||
text-transform: uppercase;
|
text-transform: uppercase;
|
||||||
letter-spacing: 0.05em;
|
letter-spacing: 0.05em;
|
||||||
@ -1104,6 +1134,37 @@ strip-option:last-of-type {
|
|||||||
margin-top: 1rem;
|
margin-top: 1rem;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.loader-button-wrapper {
|
||||||
|
display: -webkit-box;
|
||||||
|
display: -ms-flexbox;
|
||||||
|
display: flex;
|
||||||
|
position: relative;
|
||||||
|
-webkit-box-pack: center;
|
||||||
|
-ms-flex-pack: center;
|
||||||
|
justify-content: center;
|
||||||
|
-webkit-box-align: center;
|
||||||
|
-ms-flex-align: center;
|
||||||
|
align-items: center;
|
||||||
|
}
|
||||||
|
.loader-button-wrapper sm-button {
|
||||||
|
width: 100%;
|
||||||
|
z-index: 1;
|
||||||
|
-webkit-transition: -webkit-clip-path 0.3s;
|
||||||
|
transition: -webkit-clip-path 0.3s;
|
||||||
|
transition: clip-path 0.3s;
|
||||||
|
transition: clip-path 0.3s, -webkit-clip-path 0.3s;
|
||||||
|
-webkit-clip-path: circle(100%);
|
||||||
|
clip-path: circle(100%);
|
||||||
|
}
|
||||||
|
.loader-button-wrapper sm-button.clip {
|
||||||
|
pointer-events: none;
|
||||||
|
-webkit-clip-path: circle(0);
|
||||||
|
clip-path: circle(0);
|
||||||
|
}
|
||||||
|
.loader-button-wrapper sm-spinner {
|
||||||
|
position: absolute;
|
||||||
|
}
|
||||||
|
|
||||||
#result {
|
#result {
|
||||||
place-content: center;
|
place-content: center;
|
||||||
}
|
}
|
||||||
@ -1238,7 +1299,7 @@ strip-option:last-of-type {
|
|||||||
|
|
||||||
#transaction_action_button,
|
#transaction_action_button,
|
||||||
#account_action_button,
|
#account_action_button,
|
||||||
#deposit_button {
|
.loader-button-wrapper {
|
||||||
margin-top: auto;
|
margin-top: auto;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1300,6 +1361,7 @@ strip-option:last-of-type {
|
|||||||
#user_section {
|
#user_section {
|
||||||
grid-area: user-section;
|
grid-area: user-section;
|
||||||
background-color: rgba(var(--background-color), 1);
|
background-color: rgba(var(--background-color), 1);
|
||||||
|
width: min(24rem, 100%);
|
||||||
}
|
}
|
||||||
|
|
||||||
#transaction_top,
|
#transaction_top,
|
||||||
@ -1372,6 +1434,10 @@ strip-option:last-of-type {
|
|||||||
.hide-on-desktop {
|
.hide-on-desktop {
|
||||||
display: none;
|
display: none;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.activity-card--pending:not(:empty) {
|
||||||
|
padding: 1.5rem;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
@media screen and (min-width: 1920px) {
|
@media screen and (min-width: 1920px) {
|
||||||
.page-layout {
|
.page-layout {
|
||||||
|
|||||||
2
css/main.min.css
vendored
2
css/main.min.css
vendored
File diff suppressed because one or more lines are too long
@ -6,7 +6,7 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
:root {
|
:root {
|
||||||
font-size: clamp(1rem, 1.2vmax, 3rem);
|
font-size: clamp(1rem, 1.2vmax, 1.2rem);
|
||||||
}
|
}
|
||||||
|
|
||||||
html,
|
html,
|
||||||
@ -48,7 +48,8 @@ body[data-theme="dark"] {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
p {
|
p,
|
||||||
|
strong {
|
||||||
font-size: 0.9rem;
|
font-size: 0.9rem;
|
||||||
max-width: 70ch;
|
max-width: 70ch;
|
||||||
line-height: 1.7;
|
line-height: 1.7;
|
||||||
@ -375,7 +376,7 @@ button:active,
|
|||||||
|
|
||||||
h4 {
|
h4 {
|
||||||
text-transform: capitalize;
|
text-transform: capitalize;
|
||||||
font-size: 1rem;
|
font-size: 0.9rem;
|
||||||
font-weight: 600;
|
font-weight: 600;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -388,6 +389,8 @@ button:active,
|
|||||||
}
|
}
|
||||||
details {
|
details {
|
||||||
summary {
|
summary {
|
||||||
|
display: flex;
|
||||||
|
justify-content: space-between;
|
||||||
user-select: none;
|
user-select: none;
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
}
|
}
|
||||||
@ -506,6 +509,10 @@ details {
|
|||||||
display: flex;
|
display: flex;
|
||||||
flex-direction: column;
|
flex-direction: column;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
|
&.disabled {
|
||||||
|
pointer-events: none;
|
||||||
|
opacity: 0.6;
|
||||||
|
}
|
||||||
&__icon {
|
&__icon {
|
||||||
padding: 1rem;
|
padding: 1rem;
|
||||||
border-radius: 1rem;
|
border-radius: 1rem;
|
||||||
@ -625,6 +632,7 @@ strip-option {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
.activity-card--request,
|
.activity-card--request,
|
||||||
|
.activity-card--pending,
|
||||||
.activity-card--admin {
|
.activity-card--admin {
|
||||||
grid-template-areas: "icon . amount" "icon time .";
|
grid-template-areas: "icon . amount" "icon time .";
|
||||||
.activity-card__icon {
|
.activity-card__icon {
|
||||||
@ -638,6 +646,18 @@ strip-option {
|
|||||||
text-align: end;
|
text-align: end;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
#pending_transaction:not(:empty) {
|
||||||
|
margin-bottom: 2rem;
|
||||||
|
}
|
||||||
|
.activity-card--pending:not(:empty) {
|
||||||
|
padding: 1rem;
|
||||||
|
margin-top: 0.8rem;
|
||||||
|
border: solid 0.1rem var(--accent-color);
|
||||||
|
.activity-card__description {
|
||||||
|
font-size: 0.8rem;
|
||||||
|
color: rgba(var(--text-color), 0.8);
|
||||||
|
}
|
||||||
|
}
|
||||||
.status-tag:not(:empty) {
|
.status-tag:not(:empty) {
|
||||||
text-transform: uppercase;
|
text-transform: uppercase;
|
||||||
letter-spacing: 0.05em;
|
letter-spacing: 0.05em;
|
||||||
@ -944,6 +964,25 @@ strip-option {
|
|||||||
--font-size: 1.5rem;
|
--font-size: 1.5rem;
|
||||||
margin-top: 1rem;
|
margin-top: 1rem;
|
||||||
}
|
}
|
||||||
|
.loader-button-wrapper {
|
||||||
|
display: flex;
|
||||||
|
position: relative;
|
||||||
|
justify-content: center;
|
||||||
|
align-items: center;
|
||||||
|
sm-button {
|
||||||
|
width: 100%;
|
||||||
|
z-index: 1;
|
||||||
|
transition: clip-path 0.3s;
|
||||||
|
clip-path: circle(100%);
|
||||||
|
&.clip {
|
||||||
|
pointer-events: none;
|
||||||
|
clip-path: circle(0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
sm-spinner {
|
||||||
|
position: absolute;
|
||||||
|
}
|
||||||
|
}
|
||||||
#result {
|
#result {
|
||||||
place-content: center;
|
place-content: center;
|
||||||
section {
|
section {
|
||||||
@ -1036,7 +1075,7 @@ strip-option {
|
|||||||
}
|
}
|
||||||
#transaction_action_button,
|
#transaction_action_button,
|
||||||
#account_action_button,
|
#account_action_button,
|
||||||
#deposit_button {
|
.loader-button-wrapper {
|
||||||
margin-top: auto;
|
margin-top: auto;
|
||||||
}
|
}
|
||||||
#transaction_top,
|
#transaction_top,
|
||||||
@ -1091,6 +1130,7 @@ strip-option {
|
|||||||
#user_section {
|
#user_section {
|
||||||
grid-area: user-section;
|
grid-area: user-section;
|
||||||
background-color: rgba(var(--background-color), 1);
|
background-color: rgba(var(--background-color), 1);
|
||||||
|
width: min(24rem, 100%);
|
||||||
}
|
}
|
||||||
#transaction_top,
|
#transaction_top,
|
||||||
#account_top,
|
#account_top,
|
||||||
@ -1150,6 +1190,9 @@ strip-option {
|
|||||||
.hide-on-desktop {
|
.hide-on-desktop {
|
||||||
display: none;
|
display: none;
|
||||||
}
|
}
|
||||||
|
.activity-card--pending:not(:empty) {
|
||||||
|
padding: 1.5rem;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
@media screen and (min-width: 1920px) {
|
@media screen and (min-width: 1920px) {
|
||||||
.page-layout {
|
.page-layout {
|
||||||
|
|||||||
220
index.html
220
index.html
@ -6,6 +6,11 @@
|
|||||||
<meta http-equiv="X-UA-Compatible" content="IE=edge">
|
<meta http-equiv="X-UA-Compatible" content="IE=edge">
|
||||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||||
<title>RanchiMall Bank</title>
|
<title>RanchiMall Bank</title>
|
||||||
|
|
||||||
|
<script src="components.js" defer></script>
|
||||||
|
<script defer src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/3.5.1/chart.min.js"
|
||||||
|
integrity="sha512-Wt1bJGtlnMtGP0dqNFH1xlkLBNpEodaiQ8ZN5JLA5wpc1sUlk/O5uuOMNgvzddzkpvZ9GLyYNa8w2s7rqiTk5Q=="
|
||||||
|
crossorigin="anonymous" referrerpolicy="no-referrer"></script>
|
||||||
<link rel="stylesheet" href="css/main.min.css">
|
<link rel="stylesheet" href="css/main.min.css">
|
||||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||||
@ -36,10 +41,6 @@
|
|||||||
application: "test_bank",
|
application: "test_bank",
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
<script src="components.js" defer></script>
|
|
||||||
<script defer src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/3.5.1/chart.min.js"
|
|
||||||
integrity="sha512-Wt1bJGtlnMtGP0dqNFH1xlkLBNpEodaiQ8ZN5JLA5wpc1sUlk/O5uuOMNgvzddzkpvZ9GLyYNa8w2s7rqiTk5Q=="
|
|
||||||
crossorigin="anonymous" referrerpolicy="no-referrer"></script>
|
|
||||||
</head>
|
</head>
|
||||||
|
|
||||||
<body onload="onLoadStartUp()" class="hide-completely">
|
<body onload="onLoadStartUp()" class="hide-completely">
|
||||||
@ -163,6 +164,7 @@
|
|||||||
<section id="subpage_container">
|
<section id="subpage_container">
|
||||||
<div id="dashboard" class="sub-page">
|
<div id="dashboard" class="sub-page">
|
||||||
<section>
|
<section>
|
||||||
|
<section id="pending_transaction"></section>
|
||||||
<h4 class="flex align-center">
|
<h4 class="flex align-center">
|
||||||
<svg xmlns="http://www.w3.org/2000/svg" class="icon button__icon--left" viewBox="0 0 20 20"
|
<svg xmlns="http://www.w3.org/2000/svg" class="icon button__icon--left" viewBox="0 0 20 20"
|
||||||
fill="currentColor">
|
fill="currentColor">
|
||||||
@ -475,7 +477,9 @@
|
|||||||
<sm-input id="get_deposit_amount" type="number" min="1" step="0.01"
|
<sm-input id="get_deposit_amount" type="number" min="1" step="0.01"
|
||||||
error-text="Amount should be at least ₹1" placeholder="₹Amount" required>
|
error-text="Amount should be at least ₹1" placeholder="₹Amount" required>
|
||||||
</sm-input>
|
</sm-input>
|
||||||
<sm-button id="deposit_button" variant="primary" disabled onclick="initDeposit()">Deposit</sm-button>
|
<div id="deposit_button_wrapper" class="loader-button-wrapper">
|
||||||
|
<sm-button id="deposit_button" variant="primary" disabled onclick="initDeposit()">Deposit</sm-button>
|
||||||
|
</div>
|
||||||
</sm-form>
|
</sm-form>
|
||||||
</article>
|
</article>
|
||||||
<article id="loan" class="page hide-completely page-layout">
|
<article id="loan" class="page hide-completely page-layout">
|
||||||
@ -487,7 +491,7 @@
|
|||||||
</svg>
|
</svg>
|
||||||
</a>
|
</a>
|
||||||
<sm-form>
|
<sm-form>
|
||||||
<div id="deposit__icon">
|
<div id="loan__icon">
|
||||||
<svg class="icon" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24">
|
<svg class="icon" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24">
|
||||||
<path
|
<path
|
||||||
d="M12.65,8.5H10.42a5.18,5.18,0,0,0-4,1.95L3.75,13.74a5,5,0,0,0-.68,5.31l0,0h0a5.07,5.07,0,0,0,4.5,2.73h7.88A5.08,5.08,0,0,0,20,19.05h0a5.39,5.39,0,0,0,.43-1.2,4.91,4.91,0,0,0-1-4.06l-2.66-3.34A5.17,5.17,0,0,0,12.65,8.5Z" />
|
d="M12.65,8.5H10.42a5.18,5.18,0,0,0-4,1.95L3.75,13.74a5,5,0,0,0-.68,5.31l0,0h0a5.07,5.07,0,0,0,4.5,2.73h7.88A5.08,5.08,0,0,0,20,19.05h0a5.39,5.39,0,0,0,.43-1.2,4.91,4.91,0,0,0-1-4.06l-2.66-3.34A5.17,5.17,0,0,0,12.65,8.5Z" />
|
||||||
@ -502,7 +506,9 @@
|
|||||||
<sm-input id="get_loan_amount" type="number" min="1" step="0.01" error-text="Amount should be at least ₹1"
|
<sm-input id="get_loan_amount" type="number" min="1" step="0.01" error-text="Amount should be at least ₹1"
|
||||||
placeholder="₹Amount" required>
|
placeholder="₹Amount" required>
|
||||||
</sm-input>
|
</sm-input>
|
||||||
<sm-button id="loan_button" variant="primary" disabled onclick="initLoan()">Request loan</sm-button>
|
<div id="loan_button_wrapper" class="loader-button-wrapper">
|
||||||
|
<sm-button id="loan_button" variant="primary" disabled onclick="initLoan()">Request loan</sm-button>
|
||||||
|
</div>
|
||||||
</sm-form>
|
</sm-form>
|
||||||
</article>
|
</article>
|
||||||
<article id="result" class="page hide-completely page-layout">
|
<article id="result" class="page hide-completely page-layout">
|
||||||
@ -607,6 +613,25 @@
|
|||||||
<p class="step__description"></p>
|
<p class="step__description"></p>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
<template id="pending_transaction_template">
|
||||||
|
<details open>
|
||||||
|
<summary>
|
||||||
|
<h4>Pending transaction</h4>
|
||||||
|
<svg class="icon" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" width="24" height="24">
|
||||||
|
<path fill="none" d="M0 0h24v24H0z" />
|
||||||
|
<path d="M12 13.172l4.95-4.95 1.414 1.414L12 16 5.636 9.636 7.05 8.222z" />
|
||||||
|
</svg>
|
||||||
|
</summary>
|
||||||
|
<a id="pending_request" class="activity-card activity-card--pending interact">
|
||||||
|
<div class="activity-card__icon pending"></div>
|
||||||
|
<div class="activity-card__title"></div>
|
||||||
|
<p class="activity-card__description">
|
||||||
|
You won't be able to do deposit or get a loan till process is completed.
|
||||||
|
</p>
|
||||||
|
<h4 class="activity-card__amount"></h4>
|
||||||
|
</a>
|
||||||
|
</details>
|
||||||
|
</template>
|
||||||
<script id="ui_utils">
|
<script id="ui_utils">
|
||||||
// Global variables
|
// Global variables
|
||||||
const domRefs = {};
|
const domRefs = {};
|
||||||
@ -896,11 +921,14 @@
|
|||||||
break;
|
break;
|
||||||
case 'deposit':
|
case 'deposit':
|
||||||
const { I_s } = bank_app.getRates()
|
const { I_s } = bank_app.getRates()
|
||||||
getRef('deposit_interest_rate').textContent = `Make a deposit at ${I_s * 100}% rate of interest`
|
getRef('deposit_interest_rate').textContent = `Make a deposit at ${I_s * 100}%.p.a`
|
||||||
|
// checks if there is transaction pending, if so then shows warning
|
||||||
|
checkIfAllowed('deposit')
|
||||||
break;
|
break;
|
||||||
case 'loan':
|
case 'loan':
|
||||||
const { I_b } = bank_app.getRates()
|
const { I_b } = bank_app.getRates()
|
||||||
getRef('loan_interest_rate').textContent = `Get a loan at ${I_b * 100}% rate of interest`
|
getRef('loan_interest_rate').textContent = `Get a loan at ${I_b * 100}%.p.a`
|
||||||
|
checkIfAllowed('loan')
|
||||||
break;
|
break;
|
||||||
case 'transaction':
|
case 'transaction':
|
||||||
showTransactionDetails(params)
|
showTransactionDetails(params)
|
||||||
@ -939,6 +967,7 @@
|
|||||||
accountLoader = new LazyLoader('#user_accounts', getAccounts, render.accountCard, { batchSize: 10 })
|
accountLoader = new LazyLoader('#user_accounts', getAccounts, render.accountCard, { batchSize: 10 })
|
||||||
accountLoader.init()
|
accountLoader.init()
|
||||||
}
|
}
|
||||||
|
checkPendingTransaction()
|
||||||
break;
|
break;
|
||||||
case 'admin':
|
case 'admin':
|
||||||
if (pagesData.openedSubPages.includes(subPageId)) {
|
if (pagesData.openedSubPages.includes(subPageId)) {
|
||||||
@ -1125,6 +1154,15 @@
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
return icon
|
return icon
|
||||||
|
},
|
||||||
|
getLastTransaction() {
|
||||||
|
const allRequests = bank_app.viewAllRequests()
|
||||||
|
let key
|
||||||
|
for (key in allRequests);
|
||||||
|
return {
|
||||||
|
uid: key,
|
||||||
|
isPending: !requestResponsePairs.has(key)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
const render = {
|
const render = {
|
||||||
@ -1226,7 +1264,7 @@
|
|||||||
card.setAttribute('href', `#/account?index=${index}`)
|
card.setAttribute('href', `#/account?index=${index}`)
|
||||||
card.querySelector('.activity-card__icon').innerHTML = icon
|
card.querySelector('.activity-card__icon').innerHTML = icon
|
||||||
card.querySelector('.activity-card__type').textContent = type
|
card.querySelector('.activity-card__type').textContent = type
|
||||||
card.querySelector('.activity-card__time').textContent = getFormattedTime(parseInt(status === 'active' ? openTime : closeTime))
|
card.querySelector('.activity-card__time').textContent = getFormattedTime(parseInt(status === 'active' ? openTime : closeTime), true)
|
||||||
card.querySelector('.activity-card__amount').textContent = netAmt.toLocaleString(`en-IN`, { style: 'currency', currency: 'INR' })
|
card.querySelector('.activity-card__amount').textContent = netAmt.toLocaleString(`en-IN`, { style: 'currency', currency: 'INR' })
|
||||||
return card
|
return card
|
||||||
},
|
},
|
||||||
@ -1259,7 +1297,7 @@
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
function signOut() {
|
function signOut() {
|
||||||
getConfirmation('Sign out?', 'You are about to sign out of the app, continue?')
|
getConfirmation('Sign out?', 'You are about to sign out of the app, continue?', 'Stay', 'Leave')
|
||||||
.then(async (res) => {
|
.then(async (res) => {
|
||||||
if (res) {
|
if (res) {
|
||||||
await floDapps.clearCredentials()
|
await floDapps.clearCredentials()
|
||||||
@ -1304,13 +1342,17 @@
|
|||||||
index,
|
index,
|
||||||
amount,
|
amount,
|
||||||
rtype,
|
rtype,
|
||||||
requestID: requestID,
|
requestID,
|
||||||
timestamp: requestID.split('_')[0],
|
timestamp: requestID.split('_')[0],
|
||||||
}
|
}
|
||||||
if (reqStatus === 'completed') {
|
if (reqStatus === 'completed') {
|
||||||
transactionDetails.status = 'completed'
|
transactionDetails.status = 'completed'
|
||||||
} else {
|
} else {
|
||||||
transactionDetails.status = requestResponsePairs[requestID] ? bank_app.viewAllResponses()[requestResponsePairs[requestID]].status : 'pending'
|
if (requestResponsePairs.has(requestID)) {
|
||||||
|
transactionDetails.status = bank_app.viewAllResponses()[requestResponsePairs.get(requestID)].status
|
||||||
|
} else {
|
||||||
|
transactionDetails.status = 'pending'
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return transactionDetails
|
return transactionDetails
|
||||||
}
|
}
|
||||||
@ -1321,9 +1363,9 @@
|
|||||||
for (const key in transactions) {
|
for (const key in transactions) {
|
||||||
const details = getRequestDetails(key)
|
const details = getRequestDetails(key)
|
||||||
if (details)
|
if (details)
|
||||||
requests.push(details)
|
requests.unshift(details)
|
||||||
}
|
}
|
||||||
return requests.reverse()
|
return requests
|
||||||
}
|
}
|
||||||
function getResponses() {
|
function getResponses() {
|
||||||
return utils.getArrayOfObj(bank_app.viewAllResponses()).reverse()
|
return utils.getArrayOfObj(bank_app.viewAllResponses()).reverse()
|
||||||
@ -1356,8 +1398,8 @@
|
|||||||
getRef('transaction__steps').innerHTML = ''
|
getRef('transaction__steps').innerHTML = ''
|
||||||
getRef('transaction__steps').append(render.accountProgressStep('success', `Sent ${type} request`, getFormattedTime(timestamp)))
|
getRef('transaction__steps').append(render.accountProgressStep('success', `Sent ${type} request`, getFormattedTime(timestamp)))
|
||||||
|
|
||||||
if (requestResponsePairs[requestID]) {
|
if (requestResponsePairs.has(requestID)) {
|
||||||
const { status, reason } = bank_app.viewAllResponses()[requestResponsePairs[requestID]]
|
const { status, reason } = bank_app.viewAllResponses()[requestResponsePairs.get(requestID)]
|
||||||
// Check if response is positive or not
|
// Check if response is positive or not
|
||||||
if (status === 'success') {
|
if (status === 'success') {
|
||||||
let action
|
let action
|
||||||
@ -1491,17 +1533,17 @@
|
|||||||
const { type, netAmt } = bank_app.getUserDetails(myFloID).accounts[index]
|
const { type, netAmt } = bank_app.getUserDetails(myFloID).accounts[index]
|
||||||
let ans
|
let ans
|
||||||
if (type === 'deposit') {
|
if (type === 'deposit') {
|
||||||
ans = await getConfirmation('Withdraw deposit?', 'Are you sure to withdraw this deposit now?')
|
ans = await getConfirmation('Withdraw deposit?', 'Are you sure to withdraw this deposit now?', 'No', 'Yes')
|
||||||
} else {
|
} else {
|
||||||
ans = await getConfirmation('Repay loan?', 'Make sure you have required amount to repay the loan!')
|
ans = await getConfirmation('Repay loan?', 'Make sure you have required amount to repay the loan!', 'No', 'Yes')
|
||||||
}
|
}
|
||||||
if (ans) {
|
if (ans) {
|
||||||
|
getRef('account_action_button').classList.add('hide-completely')
|
||||||
const actionToDo = type === 'deposit' ? 'withdraw' : 'Repay'
|
const actionToDo = type === 'deposit' ? 'withdraw' : 'Repay'
|
||||||
getRef('account_process__steps').append(render.accountProgressStep('loading', `Sending ${actionToDo} request`))
|
getRef('account_process__steps').append(render.accountProgressStep('loading', `Sending ${actionToDo} request`))
|
||||||
if (type === 'deposit') {
|
if (type === 'deposit') {
|
||||||
bank_app.withdrawDeposit(parseInt(index))
|
bank_app.withdrawDeposit(parseInt(index))
|
||||||
.then(res => {
|
.then(res => {
|
||||||
getRef('account_process__steps').lastElementChild.remove()
|
|
||||||
renderAccountProgress(index)
|
renderAccountProgress(index)
|
||||||
})
|
})
|
||||||
.catch(err => {
|
.catch(err => {
|
||||||
@ -1513,7 +1555,6 @@
|
|||||||
} else {
|
} else {
|
||||||
bank_app.repayLoan(parseInt(index))
|
bank_app.repayLoan(parseInt(index))
|
||||||
.then(res => {
|
.then(res => {
|
||||||
getRef('account_process__steps').lastElementChild.remove()
|
|
||||||
renderAccountProgress(index)
|
renderAccountProgress(index)
|
||||||
})
|
})
|
||||||
.catch(err => {
|
.catch(err => {
|
||||||
@ -1625,20 +1666,30 @@
|
|||||||
getRef('result__icon').innerHTML = utils.getRelatedIcon(status)
|
getRef('result__icon').innerHTML = utils.getRelatedIcon(status)
|
||||||
getRef('result__icon').className = status
|
getRef('result__icon').className = status
|
||||||
getRef('result__back_button').href = `#/${type}`
|
getRef('result__back_button').href = `#/${type}`
|
||||||
if (status === 'pending') {
|
debugger
|
||||||
getRef('result__title').textContent = `Sent ${type} request`
|
switch (status) {
|
||||||
getRef('result__description').textContent = `Waiting for ${type} confirmation. Meanwhile you can go back and continue using app.`
|
case 'pending':
|
||||||
} else if (status === 'failed') {
|
getRef('result__title').textContent = `Sent ${type} request`
|
||||||
getRef('result__title').textContent = `Failed to send ${type} request`
|
getRef('result__description').textContent = `Waiting for ${type} confirmation. Meanwhile you can go back and continue using app.`
|
||||||
getRef('result__description').textContent = reason
|
break
|
||||||
|
case 'failed':
|
||||||
|
getRef('result__title').textContent = `Failed to send ${type} request`
|
||||||
|
getRef('result__description').textContent = reason
|
||||||
|
break
|
||||||
|
case 'loading':
|
||||||
|
getRef('result__icon').innerHTML = '<sm-spinner></sm-spinner>'
|
||||||
|
getRef('result__title').textContent = `Sending ${type} request`
|
||||||
|
getRef('result__description').textContent = ''
|
||||||
|
break
|
||||||
}
|
}
|
||||||
getRef(`get_${type}_amount`).value = ''
|
getRef(`get_${type}_amount`).value = ''
|
||||||
}
|
}
|
||||||
|
|
||||||
async function initDeposit() {
|
async function initDeposit() {
|
||||||
const amount = parseFloat(getRef('get_deposit_amount').value)
|
const amount = parseFloat(getRef('get_deposit_amount').value)
|
||||||
const confirm = await getConfirmation(`Confirm deposit of ${amount.toLocaleString('en-IN', { currency: 'INR', style: 'currency' })}?`)
|
const confirm = await getConfirmation(`Confirm deposit of ${amount.toLocaleString('en-IN', { currency: 'INR', style: 'currency' })}?`, 'Cancel', 'Confirm')
|
||||||
if (confirm) {
|
if (confirm) {
|
||||||
|
showProcess('deposit')
|
||||||
bank_app.makeDeposit(amount)
|
bank_app.makeDeposit(amount)
|
||||||
.then(() => {
|
.then(() => {
|
||||||
window.location.hash = `#/result?type=deposit&amount=${amount}&status=pending`
|
window.location.hash = `#/result?type=deposit&amount=${amount}&status=pending`
|
||||||
@ -1646,12 +1697,16 @@
|
|||||||
.catch(err => {
|
.catch(err => {
|
||||||
window.location.hash = `#/result?type=deposit&amount=${amount}&status=failed&reason=${err}`
|
window.location.hash = `#/result?type=deposit&amount=${amount}&status=failed&reason=${err}`
|
||||||
})
|
})
|
||||||
|
.finally(() => {
|
||||||
|
hideProcess('deposit')
|
||||||
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
async function initLoan() {
|
async function initLoan() {
|
||||||
const amount = parseFloat(getRef('get_loan_amount').value)
|
const amount = parseFloat(getRef('get_loan_amount').value)
|
||||||
const confirm = await getConfirmation(`Confirm loan of ${amount.toLocaleString('en-IN', { currency: 'INR', style: 'currency' })}?`)
|
const confirm = await getConfirmation(`Confirm loan of ${amount.toLocaleString('en-IN', { currency: 'INR', style: 'currency' })}?`, 'Cancel', 'Confirm')
|
||||||
if (confirm) {
|
if (confirm) {
|
||||||
|
showInitProcess('loan')
|
||||||
bank_app.requestLoan(amount)
|
bank_app.requestLoan(amount)
|
||||||
.then(() => {
|
.then(() => {
|
||||||
window.location.hash = `#/result?type=loan&amount=${amount}&status=pending`
|
window.location.hash = `#/result?type=loan&amount=${amount}&status=pending`
|
||||||
@ -1659,9 +1714,21 @@
|
|||||||
.catch(err => {
|
.catch(err => {
|
||||||
window.location.hash = `#/result?type=loan&amount=${amount}&status=failed&reason=${err}`
|
window.location.hash = `#/result?type=loan&amount=${amount}&status=failed&reason=${err}`
|
||||||
})
|
})
|
||||||
|
.finally(() => {
|
||||||
|
hideProcess('loan')
|
||||||
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function showProcess(type) {
|
||||||
|
getRef(`${type}_button_wrapper`).children[0].classList.add('clip')
|
||||||
|
getRef(`${type}_button_wrapper`).append(document.createElement('sm-spinner'))
|
||||||
|
}
|
||||||
|
function hideProcess(type) {
|
||||||
|
getRef(`${type}_button_wrapper`).children[0].classList.remove('clip')
|
||||||
|
getRef(`${type}_button_wrapper`).children[1].remove()
|
||||||
|
}
|
||||||
|
|
||||||
function toggleUserSection() {
|
function toggleUserSection() {
|
||||||
getRef('user_section').classList.toggle('reveal')
|
getRef('user_section').classList.toggle('reveal')
|
||||||
}
|
}
|
||||||
@ -1711,11 +1778,71 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
|
||||||
|
function checkPendingTransaction() {
|
||||||
|
const { isPending, uid } = utils.getLastTransaction()
|
||||||
|
if (uid) {
|
||||||
|
const { amount, rtype } = getRequestDetails(uid)
|
||||||
|
getRef('pending_transaction').innerHTML = ''
|
||||||
|
if (isPending && (rtype === 'openDeposit' || rtype === 'openLoan')) {
|
||||||
|
const card = getRef('pending_transaction_template').content.cloneNode(true)
|
||||||
|
const action = rtype === 'openDeposit' ? 'Deposit' : 'Loan'
|
||||||
|
card.querySelector('.activity-card').setAttribute('href', `#/transaction?requestID=${uid}`)
|
||||||
|
card.querySelector('.activity-card__icon').innerHTML = utils.getRelatedIcon('pending')
|
||||||
|
card.querySelector('.activity-card__title').textContent = `${action} in process`
|
||||||
|
card.querySelector('.activity-card__amount').textContent = amount.toLocaleString(`en-IN`, { style: 'currency', currency: 'INR' })
|
||||||
|
getRef('pending_transaction').append(card)
|
||||||
|
getRef('quick_actions_container').querySelectorAll('a').forEach(elem => {
|
||||||
|
elem.classList.add('disabled')
|
||||||
|
})
|
||||||
|
} else {
|
||||||
|
getRef('quick_actions_container').querySelectorAll('a').forEach(elem => {
|
||||||
|
elem.classList.remove('disabled')
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function checkIfAllowed(type) {
|
||||||
|
const { isPending, uid } = utils.getLastTransaction()
|
||||||
|
getRef(`${type}_button`).nextElementSibling?.remove()
|
||||||
|
// check if there is a last transaction
|
||||||
|
if (uid) {
|
||||||
|
const { amount, rtype } = getRequestDetails(uid)
|
||||||
|
if (isPending && (rtype === 'openDeposit' || rtype === 'openLoan')) {
|
||||||
|
const action = rtype === 'openDeposit' ? 'Deposit' : 'Loan'
|
||||||
|
getRef(`${type}_button`).classList.add('hide-completely')
|
||||||
|
getRef(`${type}_button`).after(createElement('strong', {
|
||||||
|
textContent: `${action} in process. You can't ${type === 'deposit' ? 'deposit' : 'request loan'} until that's completed.`,
|
||||||
|
attributes: { 'style': 'background-color: khaki; color: rgba(0,0,0,0.7); padding: 1rem; border-radius: 0.5rem' }
|
||||||
|
}))
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
getRef(`${type}_button`).classList.remove('hide-completely')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
let requestResponsePairs
|
||||||
|
class ReqResp {
|
||||||
|
constructor() {
|
||||||
|
this._mappedRequests = new Map()
|
||||||
|
}
|
||||||
|
get mappedRequests() {
|
||||||
|
return this._mappedRequests
|
||||||
|
}
|
||||||
|
updateMap() {
|
||||||
|
const allResponses = bank_app.viewAllResponses()
|
||||||
|
for (const key in allResponses) {
|
||||||
|
// stores requests as requests => response relation
|
||||||
|
this._mappedRequests.set(allResponses[key].requestID, key)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
const requestResponse = new ReqResp()
|
||||||
</script>
|
</script>
|
||||||
<script id="onLoadStartUp">
|
<script id="onLoadStartUp">
|
||||||
const requestResponsePairs = {}
|
let isStartUpComplete
|
||||||
function onLoadStartUp() {
|
function onLoadStartUp() {
|
||||||
|
isStartUpComplete = false
|
||||||
//floDapps.addStartUpFunction('Sample', Promised Function)
|
//floDapps.addStartUpFunction('Sample', Promised Function)
|
||||||
//floDapps.setAppObjectStores({sampleObs1:{}, sampleObs2:{options{autoIncrement:true, keyPath:'SampleKey'}, Indexes:{sampleIndex:{}}}})
|
//floDapps.setAppObjectStores({sampleObs1:{}, sampleObs2:{options{autoIncrement:true, keyPath:'SampleKey'}, Indexes:{sampleIndex:{}}}})
|
||||||
floDapps.setCustomPrivKeyInput(getSignedIn)
|
floDapps.setCustomPrivKeyInput(getSignedIn)
|
||||||
@ -1732,20 +1859,18 @@
|
|||||||
getRef('user_flo_id').value = myFloID
|
getRef('user_flo_id').value = myFloID
|
||||||
// alert(`Welcome FLO_ID: ${myFloID}`);
|
// alert(`Welcome FLO_ID: ${myFloID}`);
|
||||||
//App functions....
|
//App functions....
|
||||||
bank_app.launchApp(reqCallback, DummyCallBack)
|
bank_app.launchApp(reqCallback, responseCallback)
|
||||||
.then(result => {
|
.then(result => {
|
||||||
|
isStartUpComplete = true
|
||||||
console.log(result)
|
console.log(result)
|
||||||
|
// create pairs of requestIDs and their respective responses for efficient lookup
|
||||||
|
requestResponse.updateMap()
|
||||||
|
requestResponsePairs = requestResponse.mappedRequests
|
||||||
if (floGlobals.adminID === myFloID) {
|
if (floGlobals.adminID === myFloID) {
|
||||||
console.log('Logged in as admin')
|
console.log('Logged in as admin')
|
||||||
document.querySelectorAll('.admin-option').forEach(option => option.classList.remove('hide-completely'))
|
document.querySelectorAll('.admin-option').forEach(option => option.classList.remove('hide-completely'))
|
||||||
document.querySelectorAll('.user-option').forEach(option => option.classList.add('hide-completely'))
|
document.querySelectorAll('.user-option').forEach(option => option.classList.add('hide-completely'))
|
||||||
} else {
|
} else {
|
||||||
// create pairs of requestIDs and their respective responses for efficient lookup
|
|
||||||
const allResponses = bank_app.viewAllResponses()
|
|
||||||
for (const key in allResponses) {
|
|
||||||
const { requestID } = allResponses[key]
|
|
||||||
requestResponsePairs[requestID] = key
|
|
||||||
}
|
|
||||||
chartObserver.observe(getRef('account_chart_container'))
|
chartObserver.observe(getRef('account_chart_container'))
|
||||||
document.querySelectorAll('.admin-option').forEach(option => option.classList.add('hide-completely'))
|
document.querySelectorAll('.admin-option').forEach(option => option.classList.add('hide-completely'))
|
||||||
document.querySelectorAll('.user-option').forEach(option => option.classList.remove('hide-completely'))
|
document.querySelectorAll('.user-option').forEach(option => option.classList.remove('hide-completely'))
|
||||||
@ -1763,17 +1888,29 @@
|
|||||||
|
|
||||||
const reqCallback = (d, e) => {
|
const reqCallback = (d, e) => {
|
||||||
console.log(d)
|
console.log(d)
|
||||||
|
if (isStartUpComplete) {
|
||||||
|
requestResponse.updateMap()
|
||||||
|
}
|
||||||
if (floGlobals.adminID === myFloID) {
|
if (floGlobals.adminID === myFloID) {
|
||||||
if (adminRequestsLoader) {
|
if (adminRequestsLoader) {
|
||||||
adminRequestsLoader.reset()
|
adminRequestsLoader.reset()
|
||||||
notify('New request arrived')
|
notify('New request arrived')
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
// checkPendingTransaction()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const DummyCallBack = (d, e) => {
|
const responseCallback = (d, e) => {
|
||||||
if (e) console.error("DummyCallback", e);
|
if (e) console.error("DummyCallback", e);
|
||||||
console.log("DummyCallback", d);
|
console.log("response", d);
|
||||||
|
if (floGlobals.adminID === myFloID) {
|
||||||
|
} else {
|
||||||
|
checkPendingTransaction()
|
||||||
|
}
|
||||||
|
if (isStartUpComplete) {
|
||||||
|
requestResponse.updateMap()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
<script id="init_lib" version="1.0.1">
|
<script id="init_lib" version="1.0.1">
|
||||||
@ -11397,7 +11534,8 @@
|
|||||||
acc[d[0]] = d[1];
|
acc[d[0]] = d[1];
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
console.warn("Unknown parse data", d);
|
// console.warn("Unknown parse data", d);
|
||||||
|
console.warn("Unknown parse data");
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
console.debug(time, txid, acc);
|
console.debug(time, txid, acc);
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user