diff --git a/src/frontend/app/actions/send-external-signatory-book-action/maarch-paraph/maarch-paraph.component.ts b/src/frontend/app/actions/send-external-signatory-book-action/maarch-paraph/maarch-paraph.component.ts index 71299093f9e93cb30b96f89c3a86454a9194a59c..8e664411955d0bf7c0bfcf77a05576f4ad50af5b 100644 --- a/src/frontend/app/actions/send-external-signatory-book-action/maarch-paraph/maarch-paraph.component.ts +++ b/src/frontend/app/actions/send-external-signatory-book-action/maarch-paraph/maarch-paraph.component.ts @@ -63,7 +63,7 @@ export class MaarchParaphComponent implements OnInit { } getDatas() { - const formatedData: any = { steps : []}; + const formatedData: any = { steps: [] }; const workflow = this.appVisaWorkflow.getWorkflow(); this.resourcesToSign.forEach((resource: any) => { @@ -73,19 +73,18 @@ export class MaarchParaphComponent implements OnInit { 'resId': resource.resId, 'mainDocument': resource.mainDocument, 'externalId': element.externalId.maarchParapheur, - 'sequence' : index, + 'sequence': index, 'action': element.requested_signature ? 'sign' : 'visa', 'signaturePositions': resource.signaturePositions !== undefined ? resource.signaturePositions : [], + 'datePositions': resource.datePositions !== undefined ? resource.datePositions : [], } ); }); }); - return formatedData; } openSignaturePosition(resource: any) { - console.log('this.additionalsInfos', this.additionalsInfos); const dialogRef = this.dialog.open(SignaturePositionComponent, { height: '99vh', panelClass: 'maarch-modal', @@ -98,8 +97,8 @@ export class MaarchParaphComponent implements OnInit { dialogRef.afterClosed().pipe( filter((res: any) => !this.functions.empty(res)), tap((res: any) => { - this.resourcesToSign.filter((itemToSign: any) => itemToSign.resId === resource.resId && itemToSign.mainDocument === resource.mainDocument)[0]['signaturePositions'] = res; - console.log('result', this.resourcesToSign); + this.resourcesToSign.filter((itemToSign: any) => itemToSign.resId === resource.resId && itemToSign.mainDocument === resource.mainDocument)[0]['signaturePositions'] = res.signaturePositions; + this.resourcesToSign.filter((itemToSign: any) => itemToSign.resId === resource.resId && itemToSign.mainDocument === resource.mainDocument)[0]['datePositions'] = res.datePositions; }), finalize(() => this.loading = false), catchError((err: any) => { @@ -110,10 +109,12 @@ export class MaarchParaphComponent implements OnInit { } hasPositions(resource: any) { - if (this.resourcesToSign.filter((itemToSign: any) => itemToSign.resId === resource.resId && itemToSign.mainDocument === resource.mainDocument)[0]['signaturePositions'] === undefined) { - return false; - } else { - return this.resourcesToSign.filter((itemToSign: any) => itemToSign.resId === resource.resId && itemToSign.mainDocument === resource.mainDocument)[0]['signaturePositions'].length > 0; - } + + return ( + this.resourcesToSign.filter((itemToSign: any) => itemToSign.resId === resource.resId && itemToSign.mainDocument === resource.mainDocument)[0]['signaturePositions'] !== undefined && + this.resourcesToSign.filter((itemToSign: any) => itemToSign.resId === resource.resId && itemToSign.mainDocument === resource.mainDocument)[0]['signaturePositions'].length > 0) + || + (this.resourcesToSign.filter((itemToSign: any) => itemToSign.resId === resource.resId && itemToSign.mainDocument === resource.mainDocument)[0]['datePositions'] !== undefined && + this.resourcesToSign.filter((itemToSign: any) => itemToSign.resId === resource.resId && itemToSign.mainDocument === resource.mainDocument)[0]['datePositions'].length > 0); } } diff --git a/src/frontend/app/actions/send-external-signatory-book-action/maarch-paraph/signature-position/signature-position.component.html b/src/frontend/app/actions/send-external-signatory-book-action/maarch-paraph/signature-position/signature-position.component.html index 10d86aeac413e4514ac8908b3f45dd866fd2a5d8..4f4a51bb78c301d665d357cab3a4a1a5047855c4 100644 --- a/src/frontend/app/actions/send-external-signatory-book-action/maarch-paraph/signature-position/signature-position.component.html +++ b/src/frontend/app/actions/send-external-signatory-book-action/maarch-paraph/signature-position/signature-position.component.html @@ -22,6 +22,14 @@ [selected]="currentUser == i && currentPage === sign.page">Page {{sign.page}}</mat-chip> </ng-container> + <ng-container *ngFor="let date of dateList"> + <mat-chip *ngIf="!hasSign(i, date.page) && date.sequence === i" color="primary" style="font-size: 10px; + padding-top: 0px; + padding-bottom: 0px; + min-height: 20px;cursor: pointer;" (click)="goToSignUserPage(i,date.page)" + [selected]="currentUser == i && currentPage === date.page">Page + {{date.page}}</mat-chip> + </ng-container> </mat-chip-list> </div> </a> @@ -34,27 +42,68 @@ [position]="{x: (sign.position.positionX*workingAreaWidth)/100, y:(sign.position.positionY*workingAreaHeight)/100}" [style.width.%]="25" [ngDraggable]="currentUser===sign.sequence" (endOffset)="moveSign($event);" [preventDefaultEvent]="false" [bounds]="myBounds" - [inBounds]="true" class="signature" (click)="currentUser!=sign.sequence ? goToSignUserPage(sign.sequence, currentPage) : false"> - <button style="position: absolute;top: -50px;right: 0px;" mat-icon-button color="warn" [title]="'lang.delete' | translate" - (click)="deleteSign(indexSign)"> + [inBounds]="true" class="signature" + (click)="currentUser!=sign.sequence ? goToSignUserPage(sign.sequence, currentPage) : false"> + <button style="position: absolute;top: -50px;right: 0px;" mat-icon-button color="warn" + [title]="'lang.delete' | translate" (click)="deleteSign(indexSign)"> <mat-icon class="fa fa-trash-alt fa-2x"></mat-icon> </button> <span class="signUserName">{{getUserName(sign.sequence)}}</span> SIGNATURE </div> </ng-container> + <ng-container *ngFor="let date of dateList;let indexSign=index;"> + <div *ngIf="date.page === currentPage" [class.signDisabled]="currentUser!==date.sequence" + [position]="{x: (date.position.positionX*workingAreaWidth)/100, y:(date.position.positionY*workingAreaHeight)/100}" + [ngDraggable]="currentUser===date.sequence" (endOffset)="moveDate($event);" + [preventDefaultEvent]="false" [bounds]="myBounds" [inBounds]="true" class="dateBlock" + (click)="currentUser!=date.sequence ? goToSignUserPage(date.sequence, currentPage) : false"> + <div style="position: absolute;top: -50px;left: 50%;transform: translateX(-50%);"> + <button mat-icon-button (click)="colorPicker.click()"> + <mat-icon class="fas fa-circle" [style.color]="date.color"></mat-icon> + </button> + <input type="color" #colorPicker [(ngModel)]="date.color" name="color" style="display: none;" (click)="$event.stopPropagation()"> + <button mat-icon-button color="primary" [matMenuTriggerFor]="dateMenu"> + <mat-icon class="fas fa-spell-check"></mat-icon> + </button> + <mat-menu #dateMenu="matMenu"> + <button mat-menu-item [matMenuTriggerFor]="dateListFormat">Format</button> + <button mat-menu-item [matMenuTriggerFor]="dateListSize">Taille</button> + </mat-menu> + <mat-menu #dateListFormat="matMenu"> + <button mat-menu-item *ngFor="let format of formatList" (click)="date.format=format" [class.selected]="format === date.format"> + {{today | date:format : undefined : localDate}} + </button> + </mat-menu> + <mat-menu #dateListSize="matMenu"> + <button mat-menu-item *ngFor="let size of sizes" (click)="date.size=size" [class.selected]="size === date.size"> + {{size}} + </button> + </mat-menu> + <button mat-icon-button color="warn" [title]="'lang.delete' | translate" + (click)="deleteDate(indexSign)"> + <mat-icon class="fa fa-trash-alt"></mat-icon> + </button> + </div> + <div [style.color]="date.color" [style.fontSize.px]="date.size"> + {{today | date:date.format : undefined : localDate}}</div> + </div> + </ng-container> </div> - <mat-form-field *ngIf="!loading" class="pageList" style="position: fixed;"> + <button mat-mini-fab color="primary" style="position: fixed;margin-top: 10px;margin-left: 10px;" [matMenuTriggerFor]="actionPosMenu" [disabled]="!emptySign() && !emptyDate()"> + <mat-icon class="fas fa-plus" style="height: auto"></mat-icon> + </button> + <mat-menu #actionPosMenu="matMenu"> + <button mat-menu-item [disabled]="!emptyDate()" (click)="initDateBlock()">Ajouter le bloc date</button> + <button mat-menu-item [disabled]="!emptySign()" (click)="initSign()">Ajouter la position de signature</button> + </mat-menu> + <!--<mat-form-field *ngIf="!loading" class="pageList" style="position: fixed;"> <span matPrefix>Page : </span> <mat-select [(ngModel)]="currentPage" (selectionChange)="false"> <mat-option *ngFor="let page of pages" [value]="page">{{page}}</mat-option> </mat-select> - </mat-form-field> + </mat-form-field>--> <img class="img-content" [src]="imgContent" (load)="imgLoaded()" /> - <button *ngIf="emptySign() && !loading" mat-raised-button color="primary" type="button" - style="position: fixed;left: 50%;top: 50%;transform: translate(-50%,-50%);" - (click)="initSign()">Positionner la - signature</button> </div> </div> </div> diff --git a/src/frontend/app/actions/send-external-signatory-book-action/maarch-paraph/signature-position/signature-position.component.scss b/src/frontend/app/actions/send-external-signatory-book-action/maarch-paraph/signature-position/signature-position.component.scss index dfb74242acc0d4380d918b7ecaec04437e85923e..b1defbbb6559ac0adc44f615a0baa193da9e4cd0 100644 --- a/src/frontend/app/actions/send-external-signatory-book-action/maarch-paraph/signature-position/signature-position.component.scss +++ b/src/frontend/app/actions/send-external-signatory-book-action/maarch-paraph/signature-position/signature-position.component.scss @@ -37,8 +37,9 @@ .mat-tab-link { display: flex; - flex-direction: column; + flex-direction: column; } + .mat-tab-link:focus, .mat-tab-link:hover, .mat-tab-link:active { @@ -87,8 +88,9 @@ } .pageList { - position: fixed; + position: fixed; width: 100px !important; + ::ng-deep.mat-form-field-flex { background: white; } @@ -100,4 +102,17 @@ bottom: 5px; font-weight: normal; color: white; +} + +.dateBlock { + border: dashed 1px $warn; + position: absolute; + font-weight: normal; + white-space: pre; + width: auto; + padding: 10px; +} + +.selected { + background: rgba($secondary, 0.3); } \ No newline at end of file diff --git a/src/frontend/app/actions/send-external-signatory-book-action/maarch-paraph/signature-position/signature-position.component.ts b/src/frontend/app/actions/send-external-signatory-book-action/maarch-paraph/signature-position/signature-position.component.ts index 811c6c6a1882a930930069cb877eb4a88e91061f..a92365ca3fbf6e8d9d55fb4849e6a9bcbe8ecca6 100644 --- a/src/frontend/app/actions/send-external-signatory-book-action/maarch-paraph/signature-position/signature-position.component.ts +++ b/src/frontend/app/actions/send-external-signatory-book-action/maarch-paraph/signature-position/signature-position.component.ts @@ -25,11 +25,23 @@ export class SignaturePositionComponent implements OnInit { workingAreaWidth: number = 0; workingAreaHeight: number = 0; + formatList: any[] = [ + 'dd/MM/y', + 'dd-MM-y', + 'dd.MM.y', + 'd MMM y', + 'd MMMM y', + ]; + sizes = Array.from({ length: 50 }).map((_, i) => i + 1); signList: any[] = []; + dateList: any[] = []; pdfContent: any = null; imgContent: any = null; + today: Date = new Date(); + localDate = this.translate.instant('lang.langISO'); + constructor( public translate: TranslateService, public http: HttpClient, @@ -41,10 +53,13 @@ export class SignaturePositionComponent implements OnInit { ngOnInit(): void { this.currentPage = 1; this.getPageAttachment(); + if (this.data.resource.signaturePositions !== undefined) { this.signList = this.data.resource.signaturePositions; } - console.log(this.data.workflow); + if (this.data.resource.datePositions !== undefined) { + this.dateList = this.data.resource.datePositions; + } } onSubmit() { @@ -86,10 +101,22 @@ export class SignaturePositionComponent implements OnInit { this.signList.filter((item: any) => item.sequence === this.currentUser && item.page === this.currentPage)[0].position.positionY = percenty; } + moveDate(event: any) { + const percentx = (event.x * 100) / this.workingAreaWidth; + const percenty = (event.y * 100) / this.workingAreaHeight; + this.dateList.filter((item: any) => item.sequence === this.currentUser && item.page === this.currentPage)[0].position.positionX = percentx; + this.dateList.filter((item: any) => item.sequence === this.currentUser && item.page === this.currentPage)[0].position.positionY = percenty; + } + + emptySign() { return this.signList.filter((item: any) => item.sequence === this.currentUser && item.page === this.currentPage).length === 0; } + emptyDate() { + return this.dateList.filter((item: any) => item.sequence === this.currentUser && item.page === this.currentPage).length === 0; + } + initSign() { this.signList.push( { @@ -104,6 +131,24 @@ export class SignaturePositionComponent implements OnInit { document.getElementsByClassName('signatureContainer')[0].scrollTo(0, 0); } + initDateBlock() { + this.dateList.push( + { + sequence: this.currentUser, + page: this.currentPage, + color: '#666', + font: '', + format: 'd MMMM y', + size: 14, + position: { + positionX: 0, + positionY: 0 + } + } + ); + document.getElementsByClassName('signatureContainer')[0].scrollTo(0, 0); + } + getUserSignPosPage(workflowIndex: number) { return this.signList.filter((item: any) => item.sequence === workflowIndex); } @@ -130,13 +175,37 @@ export class SignaturePositionComponent implements OnInit { this.signList.splice(index, 1); } + deleteDate(index: number) { + this.dateList.splice(index, 1); + } + formatData() { - let objToSend: any[] = []; + const objToSend: any = { + signaturePositions: [], + datePositions: [] + }; this.data.workflow.forEach((element: any, index: number) => { if (this.signList.filter((item: any) => item.sequence === index).length > 0) { - objToSend = objToSend.concat(this.signList.filter((item: any) => item.sequence === index)); + objToSend['signaturePositions'] = objToSend['signaturePositions'].concat(this.signList.filter((item: any) => item.sequence === index)); + } + if (this.dateList.filter((item: any) => item.sequence === index).length > 0) { + objToSend['datePositions'] = objToSend['datePositions'].concat(this.dateList.filter((item: any) => item.sequence === index)); } }); return objToSend; } + + getUserPages() { + const allList = this.signList.concat(this.dateList); + + return allList; + } + + hasSign(userSequence: number, page: number) { + return this.signList.filter((item: any) => item.sequence === userSequence && item.page === page).length > 0; + } + + hasDate(userSequence: number, page: number) { + return this.dateList.filter((item: any) => item.sequence === userSequence && item.page === page).length > 0; + } } diff --git a/src/frontend/app/app.module.ts b/src/frontend/app/app.module.ts index 429ab57f05a408644c9fe66b542c59b0e5d92fa1..392baa35181a82a8f4b40a93dee90f7ed83fabd4 100755 --- a/src/frontend/app/app.module.ts +++ b/src/frontend/app/app.module.ts @@ -3,6 +3,9 @@ import { NgModule, Injectable } from '@angular/core'; import { SharedModule } from './app-common.module'; import { AppRoutingModule } from './app-routing.module'; +import localeFr from '@angular/common/locales/fr'; +import { registerLocaleData } from '@angular/common'; + import { AdministrationModule } from './administration/administration.module'; import { BrowserModule, HammerGestureConfig, HAMMER_GESTURE_CONFIG } from '@angular/platform-browser'; @@ -126,6 +129,7 @@ import { DevLangComponent } from '@service/debug/dev-lang.component'; import { AcknowledgementReceptionComponent } from './registeredMail/acknowledgement-reception/acknowledgement-reception.component'; import { DatePipe } from '@angular/common'; +registerLocaleData(localeFr, 'fr-FR'); @Injectable() export class MyHammerConfig extends HammerGestureConfig { overrides = <any>{