Feature/ora lecoffr 420 file component (#15)
This commit is contained in:
commit
d1c9988099
1
.vscode/settings.json
vendored
1
.vscode/settings.json
vendored
@ -1,6 +1,5 @@
|
|||||||
{
|
{
|
||||||
"editor.defaultFormatter": "esbenp.prettier-vscode",
|
"editor.defaultFormatter": "esbenp.prettier-vscode",
|
||||||
"editor.formatOnSave": true,
|
|
||||||
"[typescript]": {
|
"[typescript]": {
|
||||||
"editor.defaultFormatter": "esbenp.prettier-vscode"
|
"editor.defaultFormatter": "esbenp.prettier-vscode"
|
||||||
},
|
},
|
||||||
|
3
src/front/Assets/Icons/left-arrow.svg
Normal file
3
src/front/Assets/Icons/left-arrow.svg
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||||
|
<path d="M15 6L9 12L15 18" stroke="black" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||||
|
</svg>
|
After Width: | Height: | Size: 211 B |
3
src/front/Assets/Icons/right-arrow.svg
Normal file
3
src/front/Assets/Icons/right-arrow.svg
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||||
|
<path d="M9 18L15 12L9 6" stroke="black" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/>
|
||||||
|
</svg>
|
After Width: | Height: | Size: 210 B |
BIN
src/front/Assets/images/validate_anchoring.gif
Normal file
BIN
src/front/Assets/images/validate_anchoring.gif
Normal file
Binary file not shown.
After Width: | Height: | Size: 1.3 MiB |
@ -7,11 +7,22 @@
|
|||||||
justify-content: space-between;
|
justify-content: space-between;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
&.PENDING {
|
&.PENDING {
|
||||||
border-color: $orange-soft;
|
cursor: pointer;
|
||||||
|
border: 1px solid $orange-soft;
|
||||||
|
&:hover {
|
||||||
|
border: 1px solid $orange-soft;
|
||||||
|
outline: 1px solid $orange-soft;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
&.VALIDATED {
|
&.VALIDATED {
|
||||||
border-color: $green-soft;
|
cursor: pointer;
|
||||||
|
border: 1px solid $green-soft;
|
||||||
|
&:hover {
|
||||||
|
border: 1px solid $green-soft;
|
||||||
|
outline: 1px solid $green-soft;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
.valid-radius {
|
.valid-radius {
|
||||||
background-color: $green-flash;
|
background-color: $green-flash;
|
||||||
padding: 6px;
|
padding: 6px;
|
||||||
|
@ -1,12 +1,14 @@
|
|||||||
import React from "react";
|
|
||||||
import classes from "./classes.module.scss";
|
|
||||||
import { Document } from "le-coffre-resources/dist/Customer";
|
|
||||||
import Typography, { ITypo } from "../../Typography";
|
|
||||||
import Image from "next/image";
|
|
||||||
import TrashIcon from "@Assets/Icons/trash.svg";
|
|
||||||
import ValidIcon from "@Assets/Icons/check-valid.svg";
|
import ValidIcon from "@Assets/Icons/check-valid.svg";
|
||||||
|
import TrashIcon from "@Assets/Icons/trash.svg";
|
||||||
import classNames from "classnames";
|
import classNames from "classnames";
|
||||||
|
import { Document } from "le-coffre-resources/dist/Customer";
|
||||||
|
import Image from "next/image";
|
||||||
|
import { NextRouter, useRouter } from "next/router";
|
||||||
|
import React from "react";
|
||||||
|
|
||||||
|
import Typography, { ITypo } from "../../Typography";
|
||||||
import WarningBadge from "../../WarningBadge";
|
import WarningBadge from "../../WarningBadge";
|
||||||
|
import classes from "./classes.module.scss";
|
||||||
|
|
||||||
type IProps = {
|
type IProps = {
|
||||||
document: {
|
document: {
|
||||||
@ -16,16 +18,22 @@ type IProps = {
|
|||||||
};
|
};
|
||||||
openDeletionModal?: (uid: Document["uid"]) => void;
|
openDeletionModal?: (uid: Document["uid"]) => void;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
type IPropsClass = IProps & {
|
||||||
|
router: NextRouter;
|
||||||
|
};
|
||||||
|
|
||||||
type IState = {};
|
type IState = {};
|
||||||
|
|
||||||
export default class DocumentNotary extends React.Component<IProps, IState> {
|
class DocumentNotaryClass extends React.Component<IPropsClass, IState> {
|
||||||
public constructor(props: IProps) {
|
public constructor(props: IPropsClass) {
|
||||||
super(props);
|
super(props);
|
||||||
this.onOpenDeletionModal = this.onOpenDeletionModal.bind(this);
|
this.onOpenDeletionModal = this.onOpenDeletionModal.bind(this);
|
||||||
|
this.onClick = this.onClick.bind(this);
|
||||||
}
|
}
|
||||||
public override render(): JSX.Element {
|
public override render(): JSX.Element {
|
||||||
return (
|
return (
|
||||||
<div className={classNames(classes["root"], classes[this.props.document.document_status])}>
|
<div className={classNames(classes["root"], classes[this.props.document.document_status])} onClick={this.onClick}>
|
||||||
<div>
|
<div>
|
||||||
<Typography typo={ITypo.P_SB_16}>{this.props.document?.document_type?.name}</Typography>
|
<Typography typo={ITypo.P_SB_16}>{this.props.document?.document_type?.name}</Typography>
|
||||||
<Typography typo={ITypo.CAPTION_14}>Aucun document déposé</Typography>
|
<Typography typo={ITypo.CAPTION_14}>Aucun document déposé</Typography>
|
||||||
@ -35,6 +43,11 @@ export default class DocumentNotary extends React.Component<IProps, IState> {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private onClick() {
|
||||||
|
if (this.props.document.document_status !== "VALIDATED" && this.props.document.document_status !== "PENDING") return;
|
||||||
|
this.props.router.push(`/folder/${this.props.document.folder.uid}/document/${this.props.document.uid}`);
|
||||||
|
}
|
||||||
|
|
||||||
private renderIcon(): JSX.Element {
|
private renderIcon(): JSX.Element {
|
||||||
switch (this.props.document.document_status) {
|
switch (this.props.document.document_status) {
|
||||||
case "VALIDATED":
|
case "VALIDATED":
|
||||||
@ -55,3 +68,8 @@ export default class DocumentNotary extends React.Component<IProps, IState> {
|
|||||||
this.props.openDeletionModal(this.props.document.uid);
|
this.props.openDeletionModal(this.props.document.uid);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export default function DocumentNotary(props: IProps): JSX.Element {
|
||||||
|
const router = useRouter();
|
||||||
|
return <DocumentNotaryClass {...props} router={router} />;
|
||||||
|
}
|
||||||
|
@ -1,15 +1,19 @@
|
|||||||
.root {
|
.root {
|
||||||
height: inherit;
|
height: inherit;
|
||||||
|
min-height: inherit;
|
||||||
.file-container {
|
.file-container {
|
||||||
height: inherit;
|
height: inherit;
|
||||||
|
min-height: inherit;
|
||||||
.image {
|
.image {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
height: inherit;
|
height: inherit;
|
||||||
|
min-height: inherit;
|
||||||
object-fit: contain;
|
object-fit: contain;
|
||||||
}
|
}
|
||||||
|
|
||||||
.pdf {
|
.pdf {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
|
min-height: inherit;
|
||||||
height: inherit;
|
height: inherit;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -11,6 +11,7 @@ type IProps = IPropsModal & {
|
|||||||
cancelPath?: string;
|
cancelPath?: string;
|
||||||
confirmText: string | JSX.Element;
|
confirmText: string | JSX.Element;
|
||||||
showCancelButton: boolean;
|
showCancelButton: boolean;
|
||||||
|
showButtons: boolean;
|
||||||
canConfirm: boolean;
|
canConfirm: boolean;
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -21,7 +22,8 @@ export default class Confirm extends React.Component<IProps, IState> {
|
|||||||
showCancelButton: true,
|
showCancelButton: true,
|
||||||
cancelText: "Cancel",
|
cancelText: "Cancel",
|
||||||
confirmText: "Confirm",
|
confirmText: "Confirm",
|
||||||
canConfirm: false,
|
canConfirm: true,
|
||||||
|
showButtons: true,
|
||||||
...Modal.defaultProps,
|
...Modal.defaultProps,
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -29,17 +31,17 @@ export default class Confirm extends React.Component<IProps, IState> {
|
|||||||
return (
|
return (
|
||||||
<Modal
|
<Modal
|
||||||
closeBtn={this.props.closeBtn}
|
closeBtn={this.props.closeBtn}
|
||||||
isOpen={this.props.isOpen}
|
|
||||||
onClose={this.props.onClose}
|
|
||||||
header={this.props.header}
|
header={this.props.header}
|
||||||
footer={this.footer()}
|
footer={this.footer()}
|
||||||
animationDelay={this.props.animationDelay}>
|
animationDelay={this.props.animationDelay}
|
||||||
|
{...this.props}>
|
||||||
{this.props.children}
|
{this.props.children}
|
||||||
</Modal>
|
</Modal>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
private footer(): JSX.Element {
|
private footer(): JSX.Element | null {
|
||||||
|
if (!this.props.showButtons) return null;
|
||||||
return (
|
return (
|
||||||
<div className={classes["buttons-container"]}>
|
<div className={classes["buttons-container"]}>
|
||||||
{this.props.showCancelButton &&
|
{this.props.showCancelButton &&
|
||||||
|
@ -11,7 +11,7 @@ import Loader from "./Elements/Loader";
|
|||||||
export type IProps = {
|
export type IProps = {
|
||||||
closeBtn?: boolean;
|
closeBtn?: boolean;
|
||||||
header?: string | JSX.Element;
|
header?: string | JSX.Element;
|
||||||
footer?: JSX.Element;
|
footer?: JSX.Element | null;
|
||||||
textLoader?: string | JSX.Element;
|
textLoader?: string | JSX.Element;
|
||||||
isOpen: boolean;
|
isOpen: boolean;
|
||||||
onClose: () => void;
|
onClose: () => void;
|
||||||
@ -87,6 +87,7 @@ export default class Modal extends React.Component<IProps, IState> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
protected close() {
|
protected close() {
|
||||||
|
if (this.props.hasContainerClosable === false) return;
|
||||||
if (this.state.willClose) return;
|
if (this.state.willClose) return;
|
||||||
this.props.onClose();
|
this.props.onClose();
|
||||||
}
|
}
|
||||||
|
@ -124,9 +124,10 @@ export default class UserFolder extends React.Component<IProps, IState> {
|
|||||||
|
|
||||||
private getDocumentsByStatus(status: string): Document[] | null {
|
private getDocumentsByStatus(status: string): Document[] | null {
|
||||||
if (!this.props.customer.documents) return null;
|
if (!this.props.customer.documents) return null;
|
||||||
return this.props.customer.documents.filter(
|
const filteredDocuments = this.props.customer.documents.filter(
|
||||||
(document) => document.document_status === status && document.folder.uid === this.props.folder.uid,
|
(document) => document.document_status === status && document.folder.uid === this.props.folder.uid,
|
||||||
);
|
);
|
||||||
|
return filteredDocuments;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get all documents Validated, pending
|
// Get all documents Validated, pending
|
||||||
|
@ -36,8 +36,8 @@
|
|||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
|
|
||||||
@media (max-width: ($screen-m - 1px)) {
|
@media (max-width: ($screen-m - 1px)) {
|
||||||
width: 83px;
|
width: 56px;
|
||||||
min-width: 83px;
|
min-width: 56px;
|
||||||
transform: translateX(-389px);
|
transform: translateX(-389px);
|
||||||
|
|
||||||
&.opened {
|
&.opened {
|
||||||
@ -46,6 +46,16 @@
|
|||||||
min-width: 389px;
|
min-width: 389px;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@media (max-width: $screen-s) {
|
||||||
|
width: 0px;
|
||||||
|
min-width: 0px;
|
||||||
|
|
||||||
|
&.opened {
|
||||||
|
width: 100vw;
|
||||||
|
min-width: 100vw;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.closable-left-side {
|
.closable-left-side {
|
||||||
@ -54,8 +64,8 @@
|
|||||||
z-index: 0;
|
z-index: 0;
|
||||||
display: flex;
|
display: flex;
|
||||||
justify-content: center;
|
justify-content: center;
|
||||||
min-width: 83px;
|
min-width: 56px;
|
||||||
max-width: 83px;
|
max-width: 56px;
|
||||||
height: calc(100vh - 83px);
|
height: calc(100vh - 83px);
|
||||||
border-right: 1px $grey-medium solid;
|
border-right: 1px $grey-medium solid;
|
||||||
|
|
||||||
@ -68,6 +78,10 @@
|
|||||||
transform: rotate(180deg);
|
transform: rotate(180deg);
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@media (max-width: $screen-s) {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.right-side {
|
.right-side {
|
||||||
@ -76,7 +90,25 @@
|
|||||||
overflow-y: auto;
|
overflow-y: auto;
|
||||||
|
|
||||||
@media (max-width: ($screen-m - 1px)) {
|
@media (max-width: ($screen-m - 1px)) {
|
||||||
min-width: calc(100vw - 83px);
|
min-width: calc(100vw - 56px);
|
||||||
|
}
|
||||||
|
|
||||||
|
@media(max-width: $screen-s){
|
||||||
|
flex: 1;
|
||||||
|
min-width: unset;
|
||||||
|
}
|
||||||
|
|
||||||
|
.back-arrow-mobile{
|
||||||
|
display: none;
|
||||||
|
@media (max-width: $screen-s) {
|
||||||
|
display: block;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.back-arrow-desktop{
|
||||||
|
@media (max-width: $screen-s) {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,8 +1,11 @@
|
|||||||
import "reflect-metadata";
|
import "reflect-metadata";
|
||||||
|
|
||||||
import ChevronIcon from "@Assets/Icons/chevron.svg";
|
import ChevronIcon from "@Assets/Icons/chevron.svg";
|
||||||
|
import Button, { EButtonVariant } from "@Front/Components/DesignSystem/Button";
|
||||||
import FolderListContainer from "@Front/Components/DesignSystem/FolderListContainer";
|
import FolderListContainer from "@Front/Components/DesignSystem/FolderListContainer";
|
||||||
import Header from "@Front/Components/DesignSystem/Header";
|
import Header from "@Front/Components/DesignSystem/Header";
|
||||||
import Version from "@Front/Components/DesignSystem/Version";
|
import Version from "@Front/Components/DesignSystem/Version";
|
||||||
|
import BackArrow from "@Front/Components/Elements/BackArrow";
|
||||||
import { folders } from "@Front/Components/Layouts/DesignSystem/dummyData";
|
import { folders } from "@Front/Components/Layouts/DesignSystem/dummyData";
|
||||||
import { foldersArchived } from "@Front/Components/Layouts/DesignSystem/dummyData";
|
import { foldersArchived } from "@Front/Components/Layouts/DesignSystem/dummyData";
|
||||||
import WindowStore from "@Front/Stores/WindowStore";
|
import WindowStore from "@Front/Stores/WindowStore";
|
||||||
@ -13,11 +16,15 @@ import React, { ReactNode } from "react";
|
|||||||
|
|
||||||
import classes from "./classes.module.scss";
|
import classes from "./classes.module.scss";
|
||||||
|
|
||||||
|
|
||||||
type IProps = {
|
type IProps = {
|
||||||
title: string;
|
title: string;
|
||||||
children?: ReactNode;
|
children?: ReactNode;
|
||||||
isArchived?: boolean;
|
isArchived?: boolean;
|
||||||
onSelectedFolder: (folder: IDashBoardFolder) => void;
|
onSelectedFolder: (folder: IDashBoardFolder) => void;
|
||||||
|
hasBackArrow: boolean;
|
||||||
|
backArrowUrl?: string;
|
||||||
|
mobileBackText?: string;
|
||||||
};
|
};
|
||||||
type IState = {
|
type IState = {
|
||||||
folders: IDashBoardFolder[] | null;
|
folders: IDashBoardFolder[] | null;
|
||||||
@ -37,8 +44,8 @@ export type IDashBoardFolder = {
|
|||||||
};
|
};
|
||||||
export default class DefaultNotaryDashboard extends React.Component<IProps, IState> {
|
export default class DefaultNotaryDashboard extends React.Component<IProps, IState> {
|
||||||
private onWindowResize = () => {};
|
private onWindowResize = () => {};
|
||||||
public static defaultProps = {
|
public static defaultProps: Partial<IProps> = {
|
||||||
scrollTop: 0,
|
hasBackArrow: false,
|
||||||
isArchived: false,
|
isArchived: false,
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -72,7 +79,27 @@ export default class DefaultNotaryDashboard extends React.Component<IProps, ISta
|
|||||||
<div className={classNames(classes["closable-left-side"])}>
|
<div className={classNames(classes["closable-left-side"])}>
|
||||||
<Image alt="open side menu" src={ChevronIcon} className={classes["chevron-icon"]} onClick={this.onOpenLeftSide} />
|
<Image alt="open side menu" src={ChevronIcon} className={classes["chevron-icon"]} onClick={this.onOpenLeftSide} />
|
||||||
</div>
|
</div>
|
||||||
<div className={classes["right-side"]}>{this.props.children}</div>
|
|
||||||
|
<div className={classes["right-side"]}>
|
||||||
|
{this.props.hasBackArrow && (
|
||||||
|
<>
|
||||||
|
<div className={classes["back-arrow-desktop"]}>
|
||||||
|
<BackArrow url={this.props.backArrowUrl ?? ""} />
|
||||||
|
</div>
|
||||||
|
<div className={classes["back-arrow-mobile"]}>
|
||||||
|
<Button
|
||||||
|
icon={ChevronIcon}
|
||||||
|
iconposition={"left"}
|
||||||
|
iconstyle={{ transform: "rotate(180deg)", width: "22px", height: "22px" }}
|
||||||
|
variant={EButtonVariant.LINE}
|
||||||
|
onClick={this.onOpenLeftSide}>
|
||||||
|
{this.props.mobileBackText ?? "Retour"}
|
||||||
|
</Button>
|
||||||
|
</div>
|
||||||
|
</>
|
||||||
|
)}
|
||||||
|
{this.props.children}
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<Version />
|
<Version />
|
||||||
</div>
|
</div>
|
||||||
|
@ -1,17 +1,6 @@
|
|||||||
import {
|
|
||||||
Address,
|
|
||||||
Office,
|
|
||||||
DeedType,
|
|
||||||
Deed,
|
|
||||||
OfficeFolder,
|
|
||||||
Contact,
|
|
||||||
Customer,
|
|
||||||
DocumentType,
|
|
||||||
Document,
|
|
||||||
OfficeFolderHasCustomer,
|
|
||||||
} from "le-coffre-resources/dist/Notary";
|
|
||||||
import { ECustomerStatus } from "le-coffre-resources/dist/Customer/Customer";
|
import { ECustomerStatus } from "le-coffre-resources/dist/Customer/Customer";
|
||||||
import { EFolderStatus } from "le-coffre-resources/dist/Customer/OfficeFolder";
|
import { EFolderStatus } from "le-coffre-resources/dist/Customer/OfficeFolder";
|
||||||
|
import { Address, Contact, Customer, Deed, DeedType, Document, DocumentType, File, Office, OfficeFolder, OfficeFolderHasCustomer } from "le-coffre-resources/dist/Notary";
|
||||||
|
|
||||||
export const address: Address = {
|
export const address: Address = {
|
||||||
uid: "a&2azedzaa3",
|
uid: "a&2azedzaa3",
|
||||||
@ -92,7 +81,7 @@ export const customer: Customer = {
|
|||||||
status: ECustomerStatus.VALIDATED,
|
status: ECustomerStatus.VALIDATED,
|
||||||
};
|
};
|
||||||
export const folder: OfficeFolder = {
|
export const folder: OfficeFolder = {
|
||||||
uid: "zfaefergregrezterf",
|
uid: "mkovrijvrezviev",
|
||||||
folder_number: "12331",
|
folder_number: "12331",
|
||||||
name: "Mon dossier",
|
name: "Mon dossier",
|
||||||
status: EFolderStatus.ARCHIVED,
|
status: EFolderStatus.ARCHIVED,
|
||||||
@ -104,6 +93,8 @@ export const folder: OfficeFolder = {
|
|||||||
archived_description: "Archived description",
|
archived_description: "Archived description",
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
export const document: Document = {
|
export const document: Document = {
|
||||||
uid: "fzeafergreztyzgrf",
|
uid: "fzeafergreztyzgrf",
|
||||||
depositor: customer,
|
depositor: customer,
|
||||||
@ -114,6 +105,24 @@ export const document: Document = {
|
|||||||
created_at: new Date(),
|
created_at: new Date(),
|
||||||
};
|
};
|
||||||
|
|
||||||
|
export const fileMock: File = {
|
||||||
|
uid: "super_file_uid_1",
|
||||||
|
created_at: new Date(),
|
||||||
|
updated_at: new Date(),
|
||||||
|
document: document,
|
||||||
|
file_path:
|
||||||
|
"https://minteed-stg-euwest3-s3.s3.eu-west-3.amazonaws.com/Qmf_Yb_Eh_X9st_F_Srq_Ve_Bj_Yb_Aj56xv_AV_Nj6_Wjypo_B4r5ubce_U_ae3303e7ab.pdf",
|
||||||
|
};
|
||||||
|
|
||||||
|
export const fileMock2: File = {
|
||||||
|
uid: "super_file_uid_2",
|
||||||
|
created_at: new Date(),
|
||||||
|
updated_at: new Date(),
|
||||||
|
document: document,
|
||||||
|
file_path:
|
||||||
|
"https://minteed-prod-euwest3-s3.s3.eu-west-3.amazonaws.com/Qm_Wq_En1_DCA_8yt_RX_Qx_QFA_9_Fm_ZKZH_Qqb_VH_1_Q_Mnv_G_Jtt1_FS_Xp_2a35a36e19",
|
||||||
|
};
|
||||||
|
|
||||||
export const documentPending: Document = {
|
export const documentPending: Document = {
|
||||||
uid: "fzefeazdagrtetrury",
|
uid: "fzefeazdagrtetrury",
|
||||||
depositor: customer,
|
depositor: customer,
|
||||||
@ -122,6 +131,7 @@ export const documentPending: Document = {
|
|||||||
document_type: docType,
|
document_type: docType,
|
||||||
updated_at: new Date(),
|
updated_at: new Date(),
|
||||||
created_at: new Date(),
|
created_at: new Date(),
|
||||||
|
files: [fileMock2],
|
||||||
};
|
};
|
||||||
|
|
||||||
export const documentDeposited: Document = {
|
export const documentDeposited: Document = {
|
||||||
@ -132,6 +142,7 @@ export const documentDeposited: Document = {
|
|||||||
document_type: docType,
|
document_type: docType,
|
||||||
updated_at: new Date(),
|
updated_at: new Date(),
|
||||||
created_at: new Date(),
|
created_at: new Date(),
|
||||||
|
files: [fileMock],
|
||||||
};
|
};
|
||||||
|
|
||||||
export const customer2: Customer = {
|
export const customer2: Customer = {
|
||||||
|
@ -0,0 +1,59 @@
|
|||||||
|
@import "@Themes/constants.scss";
|
||||||
|
|
||||||
|
.root {
|
||||||
|
.title {
|
||||||
|
margin-top: 24px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.subtitle {
|
||||||
|
margin-top: 32px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.document-container {
|
||||||
|
margin-top: 32px;
|
||||||
|
gap: 64px;
|
||||||
|
display: flex;
|
||||||
|
justify-content: space-between;
|
||||||
|
align-items: center;
|
||||||
|
|
||||||
|
.arrow-container{
|
||||||
|
cursor: pointer;
|
||||||
|
|
||||||
|
&[data-disabled="true"]{
|
||||||
|
opacity: 0.3;
|
||||||
|
cursor: not-allowed;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.file-container{
|
||||||
|
min-height: 700px;
|
||||||
|
flex: 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.buttons-container {
|
||||||
|
display: flex;
|
||||||
|
gap: 24px;
|
||||||
|
justify-content: center;
|
||||||
|
margin-top: 32px;
|
||||||
|
@media (max-width: $screen-s) {
|
||||||
|
flex-direction: column-reverse;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.refuse-document-container {
|
||||||
|
.refuse-text {
|
||||||
|
margin-bottom: 24px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.validate-document-container {
|
||||||
|
.document-validating-container {
|
||||||
|
.validate-gif {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
object-fit: contain;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
249
src/front/Components/Layouts/Folder/ViewDocuments/index.tsx
Normal file
249
src/front/Components/Layouts/Folder/ViewDocuments/index.tsx
Normal file
@ -0,0 +1,249 @@
|
|||||||
|
import "reflect-metadata";
|
||||||
|
import LeftArrowIcon from "@Assets/Icons/left-arrow.svg";
|
||||||
|
import RightArrowIcon from "@Assets/Icons/right-arrow.svg";
|
||||||
|
import ValidateAnchoringGif from "@Front/Assets/images/validate_anchoring.gif";
|
||||||
|
import Button, { EButtonVariant } from "@Front/Components/DesignSystem/Button";
|
||||||
|
import CheckBox from "@Front/Components/DesignSystem/CheckBox";
|
||||||
|
import FilePreview from "@Front/Components/DesignSystem/FilePreview";
|
||||||
|
import InputField from "@Front/Components/DesignSystem/Form/Elements/InputField";
|
||||||
|
import Confirm from "@Front/Components/DesignSystem/Modal/Confirm";
|
||||||
|
import Typography, { ITypo, ITypoColor } from "@Front/Components/DesignSystem/Typography";
|
||||||
|
import { folders } from "@Front/Components/Layouts/DesignSystem/dummyData";
|
||||||
|
import DefaultNotaryDashboard from "@Front/Components/LayoutTemplates/DefaultNotaryDashboard";
|
||||||
|
import { Document } from "le-coffre-resources/dist/Customer";
|
||||||
|
import Image from "next/image";
|
||||||
|
import { NextRouter, useRouter } from "next/router";
|
||||||
|
import React from "react";
|
||||||
|
|
||||||
|
import BasePage from "../../Base";
|
||||||
|
import classes from "./classes.module.scss";
|
||||||
|
|
||||||
|
|
||||||
|
type IProps = {};
|
||||||
|
type IPropsClass = {
|
||||||
|
documentsList: Document[];
|
||||||
|
selectedDocument: Document | null;
|
||||||
|
router: NextRouter;
|
||||||
|
folderUid: string;
|
||||||
|
};
|
||||||
|
|
||||||
|
type IState = {
|
||||||
|
isRefuseModalVisible: boolean;
|
||||||
|
isValidateModalVisible: boolean;
|
||||||
|
refuseText: string;
|
||||||
|
hasValidateAnchoring: boolean;
|
||||||
|
selectedDocument: Document | null;
|
||||||
|
selectedDocumentIndex: number;
|
||||||
|
};
|
||||||
|
|
||||||
|
class ViewDocumentsClass extends BasePage<IPropsClass, IState> {
|
||||||
|
public constructor(props: IPropsClass) {
|
||||||
|
super(props);
|
||||||
|
|
||||||
|
this.state = {
|
||||||
|
isValidateModalVisible: false,
|
||||||
|
isRefuseModalVisible: false,
|
||||||
|
refuseText: "",
|
||||||
|
hasValidateAnchoring: false,
|
||||||
|
selectedDocument: null,
|
||||||
|
selectedDocumentIndex: -1,
|
||||||
|
};
|
||||||
|
|
||||||
|
this.closeModals = this.closeModals.bind(this);
|
||||||
|
this.openValidateModal = this.openValidateModal.bind(this);
|
||||||
|
this.openRefuseModal = this.openRefuseModal.bind(this);
|
||||||
|
this.onRefuseTextChange = this.onRefuseTextChange.bind(this);
|
||||||
|
this.validateAnchoring = this.validateAnchoring.bind(this);
|
||||||
|
this.goToNext = this.goToNext.bind(this);
|
||||||
|
this.goToPrevious = this.goToPrevious.bind(this);
|
||||||
|
|
||||||
|
this.hasPrevious = this.hasPrevious.bind(this);
|
||||||
|
this.hasNext = this.hasNext.bind(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
public override render(): JSX.Element | null {
|
||||||
|
return (
|
||||||
|
<DefaultNotaryDashboard title={"Demander des documents"} hasBackArrow mobileBackText="Retour aux documents">
|
||||||
|
{this.state.selectedDocument && (
|
||||||
|
<div className={classes["root"]}>
|
||||||
|
<Typography typo={ITypo.H1} color={ITypoColor.BLACK} className={classes["title"]}>
|
||||||
|
App 23 rue Torus Toulon
|
||||||
|
</Typography>
|
||||||
|
<Typography typo={ITypo.H3} color={ITypoColor.PURPLE_FLASH} className={classes["subtitle"]}>
|
||||||
|
{this.state.selectedDocument.document_type.name}
|
||||||
|
</Typography>
|
||||||
|
<div className={classes["document-container"]}>
|
||||||
|
{this.props.documentsList.length > 1 && (
|
||||||
|
<div className={classes["arrow-container"]} onClick={this.goToPrevious} data-disabled={(!this.hasPrevious()).toString()}>
|
||||||
|
<Image src={LeftArrowIcon} alt="left arrow" />
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
<div className={classes["file-container"]}>
|
||||||
|
{this.state.selectedDocument.files?.map((file) => (
|
||||||
|
<FilePreview href={file.file_path as string} key={file.uid} />
|
||||||
|
))}
|
||||||
|
</div>
|
||||||
|
{this.props.documentsList.length > 1 && (
|
||||||
|
<div className={classes["arrow-container"]} onClick={this.goToNext} data-disabled={(!this.hasNext()).toString()}>
|
||||||
|
<Image src={RightArrowIcon} alt="right arrow" />
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
<div className={classes["buttons-container"]}>
|
||||||
|
<Button variant={EButtonVariant.GHOST} onClick={this.openRefuseModal}>
|
||||||
|
Refuser
|
||||||
|
</Button>
|
||||||
|
<Button onClick={this.openValidateModal}>Valider et ancrer</Button>
|
||||||
|
<Button disabled>Télécharger</Button>
|
||||||
|
</div>
|
||||||
|
<Confirm
|
||||||
|
isOpen={this.state.isValidateModalVisible}
|
||||||
|
onClose={this.closeModals}
|
||||||
|
onAccept={this.validateAnchoring}
|
||||||
|
closeBtn={!this.state.hasValidateAnchoring}
|
||||||
|
hasContainerClosable={!this.state.hasValidateAnchoring}
|
||||||
|
header={this.state.hasValidateAnchoring ? "Document en cours de validation" : "Ancrer le document"}
|
||||||
|
cancelText={"Annuler"}
|
||||||
|
confirmText={"Confirmer"}
|
||||||
|
showButtons={!this.state.hasValidateAnchoring}>
|
||||||
|
<div className={classes["validate-document-container"]}>
|
||||||
|
{!this.state.hasValidateAnchoring && (
|
||||||
|
<Typography typo={ITypo.P_16} color={ITypoColor.BLACK} className={classes["validate-text"]}>
|
||||||
|
Êtes-vous sûr de vouloir ancrer ce document ?
|
||||||
|
</Typography>
|
||||||
|
)}
|
||||||
|
{this.state.hasValidateAnchoring && (
|
||||||
|
<div className={classes["document-validating-container"]}>
|
||||||
|
<Typography typo={ITypo.P_16} color={ITypoColor.BLACK} className={classes["validate-text"]}>
|
||||||
|
Le document s'ancre dans la blockchain.
|
||||||
|
</Typography>
|
||||||
|
<Image src={ValidateAnchoringGif} alt="Anchoring animation" className={classes["validate-gif"]} />
|
||||||
|
<div className={classes["dont-show-again"]}>
|
||||||
|
<CheckBox option={{ label: "Ne plus afficher ce message", value: false }} toolTip={"Test"} />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
</Confirm>
|
||||||
|
<Confirm
|
||||||
|
isOpen={this.state.isRefuseModalVisible}
|
||||||
|
onClose={this.closeModals}
|
||||||
|
onAccept={this.closeModals}
|
||||||
|
closeBtn
|
||||||
|
header={"Refuser le document ?"}
|
||||||
|
cancelText={"Annuler"}
|
||||||
|
confirmText={"Refuser"}
|
||||||
|
canConfirm={this.state.refuseText !== ""}>
|
||||||
|
<div className={classes["refuse-document-container"]}>
|
||||||
|
<Typography typo={ITypo.P_16} color={ITypoColor.BLACK} className={classes["refuse-text"]}>
|
||||||
|
Veuillez indiquer au client le motif du refus de son document afin qu'il puisse vous renvoyer une bonne
|
||||||
|
version.
|
||||||
|
</Typography>
|
||||||
|
<InputField fakeplaceholder="Motif du refus" textarea onChange={this.onRefuseTextChange} />
|
||||||
|
</div>
|
||||||
|
</Confirm>
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
{!this.state.selectedDocument && (
|
||||||
|
<div className={classes["root"]}>
|
||||||
|
<Typography typo={ITypo.P_16} color={ITypoColor.BLACK} className={classes["refuse-text"]}>
|
||||||
|
Document non trouvé
|
||||||
|
</Typography>
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
</DefaultNotaryDashboard>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
override componentDidMount(): void {
|
||||||
|
if (!this.props.selectedDocument) return;
|
||||||
|
this.setState({
|
||||||
|
selectedDocument: this.props.selectedDocument,
|
||||||
|
selectedDocumentIndex: this.props.documentsList.findIndex((doc) => doc.uid === this.props.selectedDocument!.uid),
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
override componentDidUpdate(prevProps: Readonly<IPropsClass>, prevState: Readonly<IState>, snapshot?: any): void {
|
||||||
|
if (prevProps.selectedDocument !== this.props.selectedDocument) {
|
||||||
|
this.setState({
|
||||||
|
selectedDocument: this.props.selectedDocument,
|
||||||
|
selectedDocumentIndex: this.props.documentsList.findIndex((doc) => doc.uid === this.props.selectedDocument!.uid),
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private goToPrevious() {
|
||||||
|
if (this.hasPrevious()) {
|
||||||
|
this.props.router.push(
|
||||||
|
`/folder/${this.props.folderUid}/document/${this.props.documentsList[this.state.selectedDocumentIndex - 1]!.uid}`,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private goToNext() {
|
||||||
|
if (this.hasNext()) {
|
||||||
|
this.props.router.push(
|
||||||
|
`/folder/${this.props.folderUid}/document/${this.props.documentsList[this.state.selectedDocumentIndex + 1]!.uid}`,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private hasPrevious() {
|
||||||
|
const index = this.state.selectedDocumentIndex - 1;
|
||||||
|
return index >= 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
private hasNext() {
|
||||||
|
const index = this.state.selectedDocumentIndex + 1;
|
||||||
|
return index < this.props.documentsList.length;
|
||||||
|
}
|
||||||
|
|
||||||
|
private validateAnchoring() {
|
||||||
|
this.setState({
|
||||||
|
hasValidateAnchoring: true,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
private onRefuseTextChange(e: React.ChangeEvent<HTMLInputElement>) {
|
||||||
|
this.setState({
|
||||||
|
refuseText: e.target.value,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
private openValidateModal() {
|
||||||
|
this.setState({
|
||||||
|
isValidateModalVisible: true,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
private openRefuseModal() {
|
||||||
|
this.setState({
|
||||||
|
isRefuseModalVisible: true,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
private closeModals() {
|
||||||
|
this.setState({
|
||||||
|
isValidateModalVisible: false,
|
||||||
|
isRefuseModalVisible: false,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export default function ViewDocuments(props: IProps) {
|
||||||
|
const router = useRouter();
|
||||||
|
let { folderUid, documentUid } = router.query;
|
||||||
|
|
||||||
|
const folder = folders[0]!;
|
||||||
|
const documents = folder.documents!.filter((document) => document.document_status !== "ASKED");
|
||||||
|
const selectedDocument = documents.find((document) => document.uid === documentUid) ?? null;
|
||||||
|
return (
|
||||||
|
<ViewDocumentsClass
|
||||||
|
{...props}
|
||||||
|
documentsList={documents}
|
||||||
|
selectedDocument={selectedDocument}
|
||||||
|
router={router}
|
||||||
|
folderUid={folderUid as string}
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
}
|
@ -1,6 +1,7 @@
|
|||||||
import DefaultNotaryDashboard, { IDashBoardFolder } from "@Front/Components/LayoutTemplates/DefaultNotaryDashboard";
|
|
||||||
import BasePage from "../Base";
|
|
||||||
import Typography, { ITypo, ITypoColor } from "@Front/Components/DesignSystem/Typography";
|
import Typography, { ITypo, ITypoColor } from "@Front/Components/DesignSystem/Typography";
|
||||||
|
import DefaultNotaryDashboard, { IDashBoardFolder } from "@Front/Components/LayoutTemplates/DefaultNotaryDashboard";
|
||||||
|
|
||||||
|
import BasePage from "../Base";
|
||||||
import classes from "./classes.module.scss";
|
import classes from "./classes.module.scss";
|
||||||
|
|
||||||
type IProps = {};
|
type IProps = {};
|
||||||
|
@ -0,0 +1,5 @@
|
|||||||
|
import ViewDocuments from "@Front/Components/Layouts/Folder/ViewDocuments";
|
||||||
|
|
||||||
|
export default function Route() {
|
||||||
|
return <ViewDocuments />;
|
||||||
|
}
|
Loading…
x
Reference in New Issue
Block a user