diff --git a/apps/maarch_entreprise/xml/chrono.xml b/apps/maarch_entreprise/xml/chrono.xml index 68b8382cba86ad86a48ae596bcfcc2534faaff0a..04fb277f1efab67577168992ea6bae1e8f945bc1 100755 --- a/apps/maarch_entreprise/xml/chrono.xml +++ b/apps/maarch_entreprise/xml/chrono.xml @@ -70,7 +70,7 @@ For developper : </ELEMENT> <ELEMENT> <type>maarch_functions</type> - <value>chr_by_category</value> + <value>chr_by_res_id</value> </ELEMENT> </CHRONO> diff --git a/modules/sendmail/batch/scripts/sendmail.sh b/modules/sendmail/batch/scripts/sendmail.sh index c1105313494fb16ab95169804a24f6fd5f13b261..693c7bfaaa8a01ab3afef69924190c0f3693b16a 100755 --- a/modules/sendmail/batch/scripts/sendmail.sh +++ b/modules/sendmail/batch/scripts/sendmail.sh @@ -1,5 +1,5 @@ #!/bin/sh -cd /var/www/MaarchCourrier/modules/sendmail/batch/ -emailsPath='/var/www/MaarchCourrier/modules/sendmail/batch/process_emails.php' -php $emailsPath -c /var/www/MaarchCourrier/modules/sendmail/batch/config/config.xml +cd /var/www/html/maarch_courrier_develop/modules/sendmail/batch/ +emailsPath='/var/www/html/maarch_courrier_develop/modules/sendmail/batch/process_emails.php' +php $emailsPath -c /var/www/html/maarch_courrier_develop/modules/sendmail/batch/config/config.xml diff --git a/modules/visa/xml/remoteSignatoryBooks.xml b/modules/visa/xml/remoteSignatoryBooks.xml index cfc95d1d8566da3cc95be13337534e5f04f59d0c..21c4bbd25d068062e0a7b80d3917c43a287693d1 100755 --- a/modules/visa/xml/remoteSignatoryBooks.xml +++ b/modules/visa/xml/remoteSignatoryBooks.xml @@ -5,7 +5,7 @@ <id>maarchParapheur</id> <userId>ccornillac@maarch.com</userId> <password>maarch</password> - <url>http://217.70.190.119/MaarchParapheur</url> + <url>http://localhost/new_paraf_ws</url> <signature>SIGN</signature> <annotation>NOTE</annotation> <externalValidated>VAL</externalValidated> diff --git a/src/frontend/app/app-routing.module.ts b/src/frontend/app/app-routing.module.ts index bf6f3623a8bec854899d7fecbcaaf6b3dfa1a961..271f4700bd0731d919b9204e0fe19e0d9bf61e6a 100755 --- a/src/frontend/app/app-routing.module.ts +++ b/src/frontend/app/app-routing.module.ts @@ -6,7 +6,7 @@ import { PasswordModificationComponent } from './password-modification.compon import { ProfileComponent } from './profile.component'; import { AboutUsComponent } from './about-us.component'; import { HomeComponent } from './home.component'; -import { BasketListComponent } from './basket/basket-list.component'; +import { BasketListComponent } from './list/basket-list.component'; import { SignatureBookComponent } from './signature-book.component'; import { SaveNumericPackageComponent } from './save-numeric-package.component'; diff --git a/src/frontend/app/app.module.ts b/src/frontend/app/app.module.ts index d5d2c5d1dac2635fd5df3a18f43eb707cd8da7a5..794879d4572d9d9448e45b9bc2c9c47e9ca8ce96 100755 --- a/src/frontend/app/app.module.ts +++ b/src/frontend/app/app.module.ts @@ -6,6 +6,7 @@ import { CustomSnackbarComponent } from './notification.service'; import { ConfirmModalComponent } from './confirmModal.component'; import { ShortcutMenuService } from '../service/shortcut-menu.service'; import { HeaderService } from '../service/header.service'; +import { FiltersListService } from '../service/filtersList.service'; import { AppComponent } from './app.component'; import { AppRoutingModule } from './app-routing.module'; @@ -14,12 +15,15 @@ import { AdministrationModule } from './administration/administr import { ProfileComponent } from './profile.component'; import { AboutUsComponent } from './about-us.component'; import { HomeComponent } from './home.component'; -import { BasketListComponent, BottomSheetNoteList, BottomSheetAttachmentList, BottomSheetDiffusionList } from './basket/basket-list.component'; +import { BasketListComponent, BottomSheetNoteList, BottomSheetAttachmentList, BottomSheetDiffusionList } from './list/basket-list.component'; import { PasswordModificationComponent, InfoChangePasswordModalComponent, } from './password-modification.component'; import { SignatureBookComponent, SafeUrlPipe } from './signature-book.component'; import { SaveNumericPackageComponent } from './save-numeric-package.component'; import { ActivateUserComponent } from './activate-user.component'; + +import { FiltersListComponent } from './list/filters/filters-list.component'; + @NgModule({ imports: [ SharedModule, @@ -42,7 +46,8 @@ import { ActivateUserComponent } from './activate-user.component' ActivateUserComponent, BottomSheetNoteList, BottomSheetAttachmentList, - BottomSheetDiffusionList + BottomSheetDiffusionList, + FiltersListComponent ], entryComponents: [ CustomSnackbarComponent, @@ -52,7 +57,7 @@ import { ActivateUserComponent } from './activate-user.component' BottomSheetAttachmentList, BottomSheetDiffusionList ], - providers: [ ShortcutMenuService, HeaderService ], + providers: [ ShortcutMenuService, HeaderService, FiltersListService ], bootstrap: [ AppComponent ] }) export class AppModule { } diff --git a/src/frontend/app/basket/basket-home.component.html b/src/frontend/app/basket/basket-home.component.html index aa86694b4712aad5b9a8d96f1b8f4047c84d5b4e..3d2ebc12d7fca98f5416030e77b4633f286cfd5a 100644 --- a/src/frontend/app/basket/basket-home.component.html +++ b/src/frontend/app/basket/basket-home.component.html @@ -31,14 +31,14 @@ </p> </a> <!-- TODO NEW BASKET LIST--> - <!--<a mat-list-item *ngIf="!basket.redirected" (click)="closePanelLeft();" routerLink="/basketList/{{regroupedBasket.groupSerialId}}/baskets/{{basket.basket_id}}" style="cursor:pointer;" [ngStyle]="{'opacity': basket.resourceNumber==0 ? '0.5' : '1'}"> + <!-- <a mat-list-item *ngIf="!basket.redirected" (click)="closePanelLeft();" routerLink="/basketList/{{regroupedBasket.groupSerialId}}/baskets/{{basket.basket_id}}" style="cursor:pointer;" [ngStyle]="{'opacity': basket.resourceNumber==0 ? '0.5' : '1'}"> <mat-icon [ngStyle]="{'color': basket.color}" *ngIf="!mobileMode" mat-list-icon class="fa fa-inbox"></mat-icon> <span *ngIf="basket.resourceNumber==0" class="badge" style="min-width:auto;">{{basket.resourceNumber}}</span> <span *ngIf="basket.resourceNumber!=0" bgcolor="warn" class="badge" style="min-width:auto;">{{basket.resourceNumber}}</span> <p mat-line title="{{basket.basket_name}}" [ngStyle]="{'color': basket.color}"> {{basket.basket_name}} </p> - </a>--> + </a> --> </ng-container> </mat-nav-list> </ng-container> diff --git a/src/frontend/app/basket/basket-list.component.html b/src/frontend/app/basket/basket-list.component.html deleted file mode 100644 index 2ab53c4c3031182f0a5db084365b53f1e46ffbb9..0000000000000000000000000000000000000000 --- a/src/frontend/app/basket/basket-list.component.html +++ /dev/null @@ -1,153 +0,0 @@ -<div class="admin-container" [class.admin-is-mobile]="mobileQuery.matches"> - <mat-sidenav-container autosize class="admin-sidenav-container"> - <mat-sidenav #snav [mode]="mobileMode ? 'over' : 'side'" [fixedInViewport]="mobileMode" fixedTopGap="56" [opened]="mobileMode ? false : true" - autoFocus="false" style="overflow-x:hidden;" [ngStyle]="{'width': mobileMode ? '80%' : '400px'}"> - <menu-shortcut></menu-shortcut> - <menu-nav></menu-nav> - <basket-home *ngIf="homeData" [homeData]="homeData" [snavL]="snav"></basket-home> - <mat-divider></mat-divider> - </mat-sidenav> - <mat-sidenav-content> - <div *ngIf="loading" style="display:flex;height:100%;"> - <mat-spinner style="margin:auto;"></mat-spinner> - </div> - <mat-card class="card-app-content"> - <div class="example-loading-shade" *ngIf="isLoadingResults"> - <mat-spinner *ngIf="isLoadingResults"></mat-spinner> - </div> - <div class="row" style="margin:0px;"> - <div class="col-md-6 col-xs-6"> - <mat-button-toggle-group #group="matButtonToggleGroup" multiple> - <mat-button-toggle value="left"> - <mat-icon class="fa fa-stopwatch" style="height:auto;"></mat-icon> - </mat-button-toggle> - <mat-button-toggle value="center"> - <mat-icon class="fa fa-circle" style="height:auto;color:blue;"></mat-icon> - </mat-button-toggle> - <mat-button-toggle value="center"> - <mat-icon class="fa fa-circle" style="height:auto;color:orange;"></mat-icon> - </mat-button-toggle> - <mat-button-toggle value="center"> - <mat-icon class="fa fa-circle" style="height:auto;color:red;"></mat-icon> - </mat-button-toggle> - </mat-button-toggle-group> - </div> - <div class="col-md-6 col-xs-6"> - <mat-paginator [length]="resultsLength" [pageSize]="10"></mat-paginator> - </div> - </div> - <table #tableBasketListSort="matSort" mat-table [dataSource]="data" matSort matSortActive="res_id" matSortDisableClear matSortDirection="asc" - style="width:100%;table-layout: fixed;"> - <!-- Number Column --> - <ng-container matColumnDef="res_id"> - <td mat-cell *matCellDef="let row" [ngStyle]="{'width': mobileMode ? '30%' : '10%'}" style="text-align:center;overflow:hidden;text-overflow: ellipsis;white-space: nowrap;padding: 5px;vertical-align: middle;"> - <div *ngIf="row.closing_date == null && mobileMode" id="{{row.res_id}}_creation_date" style="color: rgba(0,0,0,0.4);font-size: 90%;overflow: hidden;text-overflow: ellipsis;" - title='{{row.creation_date | date : "le dd/MM/y à HH:mm"}}'> - <i class="fa fa-calendar" title="{{lang.creationDate}}"></i> {{row.creation_date | timeAgo}} - </div> - <div *ngIf="!mobileMode" style="padding-top: 5px;color: rgba(0,0,0,0.4);font-size: 90%;overflow: hidden;text-overflow: ellipsis;" title="{{lang[row.category_id]}}"> - {{lang[row.category_id]}} - </div> - <div style="overflow: hidden;text-overflow: ellipsis;"> - <mat-icon [ngStyle]="{'color': row.priority_color}" color="primary" class="{{row.status_icon.charAt(0)}}{{row.status_icon.charAt(1)}} {{row.status_icon}} {{row.status_icon.charAt(0)}}{{row.status_icon.charAt(1)}}-2x" title="{{row.status_label}} ({{row.status_id}})"></mat-icon> - </div> - <div style="padding-top: 5px;color: rgba(0,0,0,0.4);font-size: 90%;overflow: hidden;text-overflow: ellipsis;" title="{{row.alt_identifier}} (n°{{row.res_id}})"> - {{row.alt_identifier}} - </div> - - </td> - </ng-container> - <ng-container matColumnDef="subject"> - <td mat-cell *matCellDef="let row" style="width:50%;overflow:hidden;text-overflow: ellipsis;white-space: nowrap;padding: 5px;vertical-align: middle;"> - <div *ngIf="row.closing_date == null && mobileMode" style="color: rgba(0,0,0,0.4);font-size: 90%;overflow: hidden;text-overflow: ellipsis;text-align: right;"> - <i class="fa fa-stopwatch" title="{{lang.processLimitDate}}"></i> - <span [innerHTML]="row.process_limit_date | timeLimit" title='{{row.process_limit_date | date : "le dd/MM/y à HH:mm"}}'></span> - </div> - <div style="overflow: hidden;text-overflow: ellipsis;" title="{{row.subject}}"> - <span *ngIf="!mobileMode" class="label" [ngStyle]="{'background': row.priority_color}">{{row.priority_label}}</span> - <span>{{row.subject}}</span> - </div> - <div *ngIf="mobileMode" style="padding-top: 5px;color: rgba(0,0,0,0.4);font-size: 90%;overflow: hidden;text-overflow: ellipsis;text-align: right;"> - {{row.dest_user}} - </div> - <div style="display:hidden;"> - - </div> - <div *ngIf="!mobileMode && (row.folder_name || row.case_label)"> - <span *ngIf="row.folder_name" class="label label-default" style="background-color:rgba(0,0,0,0.2);margin-left: 5px;margin-right: 5px;" title="{{lang.folder}}"><i class="fa fa-folder"></i> {{row.folder_name}}</span> - <span *ngIf="row.case_label" class="label label-default" style="background-color:rgba(0,0,0,0.2);margin-left: 5px;margin-right: 5px;" title="{{lang.case}}"><i class="fa fa-suitcase"></i> {{row.case_label}}</span> - </div> - <!--<div> - <button mat-stroked-button color="primary" style="margin:5px;line-height: 20px;width: 150px;overflow: hidden;text-overflow: ellipsis;">réponse du zpfezk zekf opezf</button> - <button mat-stroked-button color="primary" style="margin:5px;line-height: 20px;width: 150px;overflow: hidden;text-overflow: ellipsis;">réponse du zpfezk zekf opezf</button> - <button mat-stroked-button color="primary" style="margin:5px;line-height: 20px;width: 150px;overflow: hidden;text-overflow: ellipsis;">réponse du zpfezk zekf opezf</button> - </div> - <div style="padding-top: 5px;color: rgba(0,0,0,0.4);font-size: 90%;overflow: hidden;text-overflow: ellipsis;"> - <span><i class="fa fa-check" color="accent"></i> Barbara BAIN </span> <i class="fa fa-arrow-right"></i> <span><i class="fa fa-user"></i> Patricia PETIT</span> - </div>--> - </td> - </ng-container> - <ng-container matColumnDef="contact_society"> - <td mat-cell *matCellDef="let row" style="width:25%;overflow:hidden;text-overflow: ellipsis;white-space: nowrap;padding: 5px;vertical-align: middle;"> - <div style="color: rgba(0,0,0,0.4);font-size: 90%;overflow: hidden;text-overflow: ellipsis;"> - <b>De:</b> - <span *ngIf="row.user_firstname">{{row.user_firstname}}</span> - <span *ngIf="row.user_lastname">{{row.user_lastname}}</span> - <span *ngIf="row.contact_lastname==''">{{row.contact_society}}</span> - <span *ngIf="row.contact_society==''">{{row.contact_lastname}}</span> - </div> - <div style="color: rgba(0,0,0,0.4);font-size: 90%;overflow: hidden;text-overflow: ellipsis;"> - <b>Pour:</b> - <span title="{{row.user_dest_firstname}} {{row.user_dest_lastname}} ({{row.entity_destination}})">{{row.user_dest_firstname}} {{row.user_dest_lastname}} ({{row.entity_destination}})</span> - </div> - <div style="padding-top:10px;"> - <i class="fa fa-file" color="primary"></i> {{row.doctype_label}} - </div> - </td> - </ng-container> - - <ng-container matColumnDef="creation_date"> - <td mat-cell *matCellDef="let row" style="text-align: right;width:15%;overflow:hidden;text-overflow: ellipsis;white-space: nowrap;padding: 5px;vertical-align: middle;"> - <div *ngIf="row.closing_date == null" id="{{row.res_id}}_creation_date" style="color: rgba(0,0,0,0.4);font-size: 90%;overflow: hidden;text-overflow: ellipsis;" - title='{{row.creation_date | date : "le dd/MM/y à HH:mm"}}'> - <i class="fa fa-calendar" title="{{lang.creationDate}}"></i> {{row.creation_date | timeAgo}} - </div> - <div *ngIf="row.closing_date == null" style="color: rgba(0,0,0,0.4);font-size: 90%;overflow: hidden;text-overflow: ellipsis;"> - <i class="fa fa-stopwatch" title="{{lang.processLimitDate}}"></i> - <span [innerHTML]="row.process_limit_date | timeLimit" title='{{row.process_limit_date | date : "le dd/MM/y à HH:mm"}}'></span> - </div> - <div *ngIf="row.closing_date != null" style="color: rgba(0,0,0,0.4);font-size: 90%;overflow: hidden;text-overflow: ellipsis;"> - <i class="fa fa-lock" title="{{lang.closingDate}}"></i> - <span title='{{row.closing_date | date : "le dd/MM/y à HH:mm"}}'>{{row.closing_date | timeAgo}}</span> - </div> - <div style="white-space:normal;"> - <button mat-icon-button (click)="openAttachSheet(row)"> - <mat-icon color="primary" class="fa fa-paperclip"></mat-icon> - </button> - <button mat-icon-button (click)="openBottomSheet(row)"> - <mat-icon color="primary" class="fa fa-sticky-note"></mat-icon> - </button> - <button mat-icon-button (click)="goTo(row);"> - <mat-icon color="primary" class="fa fa-eye"></mat-icon> - </button> - <button mat-icon-button (click)="openDiffusionSheet(row)"> - <mat-icon color="primary" class="fa fa-share-alt"></mat-icon> - </button> - <button mat-icon-button (click)="goToDetail(row);"> - <mat-icon color="primary" class="fa fa-info-circle"></mat-icon> - </button> - </div> - </td> - </ng-container> - - <tr mat-row *matRowDef="let row; columns: displayedColumnsBasket;" (click)="test();"></tr> - </table> - <div class="mat-paginator" style="min-height:48px;min-height: 48px;display: flex;justify-content: end;align-items: center;padding-right: 20px;">{{resultsLength}} {{lang.entries}}</div> - </mat-card> - </mat-sidenav-content> - <mat-sidenav #snav2 mode="over" [fixedInViewport]="mobileQuery.matches" fixedTopGap="56" - position='end' [opened]="mobileQuery.matches ? false : false" style="overflow-x:hidden;" [ngStyle]="{'width': mobileMode ? '80%' : '40%'}"> - <div *ngIf="innerHtml" [innerHTML]="innerHtml" style="height: 100%;overflow: hidden;"></div> - </mat-sidenav> - </mat-sidenav-container> -</div> \ No newline at end of file diff --git a/src/frontend/app/basket/attachment-list.component.html b/src/frontend/app/list/attachment-list.component.html similarity index 100% rename from src/frontend/app/basket/attachment-list.component.html rename to src/frontend/app/list/attachment-list.component.html diff --git a/src/frontend/app/list/basket-list.component.html b/src/frontend/app/list/basket-list.component.html new file mode 100644 index 0000000000000000000000000000000000000000..dd2759e7f08dc0e55a0ad54cb267320c38b9cc15 --- /dev/null +++ b/src/frontend/app/list/basket-list.component.html @@ -0,0 +1,168 @@ +<div class="admin-container" [class.admin-is-mobile]="mobileQuery.matches"> + <mat-sidenav-container autosize class="admin-sidenav-container"> + <mat-sidenav #snav [mode]="mobileMode ? 'over' : 'side'" [fixedInViewport]="mobileMode" fixedTopGap="56" + [opened]="mobileMode ? false : true" autoFocus="false" style="overflow-x:hidden;" [ngStyle]="{'width': mobileMode ? '80%' : '400px'}"> + <menu-shortcut></menu-shortcut> + <menu-nav></menu-nav> + <basket-home *ngIf="homeData" [homeData]="homeData" [snavL]="snav"></basket-home> + <mat-divider></mat-divider> + </mat-sidenav> + <mat-sidenav-content> + <div *ngIf="loading" style="display:flex;height:100%;"> + <mat-spinner style="margin:auto;"></mat-spinner> + </div> + <mat-card class="card-app-content"> + <div class="example-loading-shade" *ngIf="isLoadingResults"> + <mat-spinner *ngIf="isLoadingResults"></mat-spinner> + </div> + <div class="row" style="margin:0px;"> + <div class="col-md-9 col-xs-9"> + <mat-button-toggle-group #group="matButtonToggleGroup" class="envFilter" (change)="updateFilters($event)" multiple> + <mat-checkbox color="primary" style="margin: 10px;" title="Sélectionner tous les courriers de la bannette"></mat-checkbox> + <button mat-stroked-button (click)="openFilter()">Filtres</button> + <mat-button-toggle [checked]="this.listProperties.onlyProcesLimit" value="onlyProcesLimit" title="Afficher les courriers en retard"> + <mat-icon fontSet="fas" fontIcon="fa-stopwatch fa-2x"></mat-icon> + </mat-button-toggle> + <mat-button-toggle [checked]="this.listProperties.onlyNewRes"value="onlyNewRes" title="Afficher les courriers non lu"> + <mat-icon fontSet="fas" fontIcon="fa-eye-slash fa-2x"></mat-icon> + </mat-button-toggle> + <mat-button-toggle [checked]="this.listProperties.withPj" value="withPj" title="Afficher les courriers avec réponses"> + <mat-icon fontSet="fas" fontIcon="fa-reply fa-2x"></mat-icon> + </mat-button-toggle> + <mat-button-toggle [checked]="this.listProperties.withNote" value="withNote" title="Afficher les courriers avec annotations"> + <mat-icon fontSet="fas" fontIcon="fa-comments fa-2x"></mat-icon> + </mat-button-toggle> + <mat-form-field appearance="outline" [style.fontSize.px]="10" style="width:200px !important;"> + <mat-label>Trier par</mat-label> + <mat-select multiple> + <mat-option value="test"> + Numéro chrono + </mat-option> + <mat-option value="test"> + Date de création + </mat-option> + </mat-select> + </mat-form-field> + <button mat-icon-button [matMenuTriggerFor]="menuParamList"> + <mat-icon color="primary" fontSet="fas" fontIcon="fa-cog fa-2x"></mat-icon> + </button> + <mat-menu #menuParamList="matMenu"> + <button mat-menu-item> + <mat-icon fontSet="fas" fontIcon="fa-print fa-2x"></mat-icon> + <span>Imprimer la liste</span> + </button> + <button mat-menu-item> + <mat-icon fontSet="fas" fontIcon="fa-file-export fa-2x"></mat-icon> + <span>Exporter les données</span> + </button> + <button mat-menu-item> + <mat-icon fontSet="far" fontIcon="fa-list-alt fa-2x"></mat-icon> + <span>Paramétrer l'affichage</span> + </button> + </mat-menu> + </mat-button-toggle-group> + <div class="filterBadges"> + <span class="label label-info" title="Fitre(s) actif(s)" *ngFor="let category of this.listProperties.categories" (click)="openFilter()">{{category.label}}</span> + <span class="label label-info" title="Fitre(s) actif(s)" *ngFor="let priority of this.listProperties.priorities" (click)="openFilter()">{{priority.label}}</span> + <span class="label label-info" title="Fitre(s) actif(s)" *ngFor="let entity of this.listProperties.entities" (click)="openFilter()">{{entity.label}}</span> + </div> + </div> + <div class="col-md-3 col-xs-3"> + <mat-paginator [length]="resultsLength" [pageSize]="10"></mat-paginator> + </div> + </div> + + <table #tableBasketListSort="matSort" mat-table [dataSource]="data" matSort matSortActive="res_id" + matSortDisableClear matSortDirection="asc" style="width:100%;table-layout: fixed;"> + <ng-container matColumnDef="res_id"> + <td mat-cell *matCellDef="let row" class="resultContainer" [class.resultContainer-mobile]="mobileMode"> + <!-- Secondary Info Line --> + <mat-toolbar *ngIf="displayedSecondaryData.length > 0"> + <div class="resultCol {{data.class}}" *ngFor="let data of displayedSecondaryData"> + <span *ngIf="data.id == 'status_label'"> + <mat-icon [ngStyle]="{'color': row.priority_color}" color="primary" class="{{row.status_icon.charAt(0)}}{{row.status_icon.charAt(1)}} {{row.status_icon}} {{row.status_icon.charAt(0)}}{{row.status_icon.charAt(1)}}-2x" + title="{{row.status_label}} ({{row.status_id}})"></mat-icon><br /> + </span> + <ng-container *ngIf="data.id == 'date'"> + <i class="fa fa-calendar" title="{{lang.creationDate}}"></i> {{row.creation_date + | timeAgo}} - <i class="fa fa-stopwatch" title="{{lang.processLimitDate}}"></i> <span + [innerHTML]="row.process_limit_date | timeLimit" title='{{row.process_limit_date | date : "le dd/MM/y à HH:mm"}}'></span> + </ng-container> + <ng-container *ngIf="data.icon != ''"> + <i class="{{data.icon}}"></i> + + </ng-container> + <ng-container *ngIf="data.id == 'category_id'"> + {{lang[row.category_id]}} + </ng-container> + <ng-container *ngIf="data.id != 'status_label' && data.id != 'date' && data.id != 'category_id'"> + {{row[data.id]}} + </ng-container> + </div> + </mat-toolbar> + <!-- Primary Info Line --> + <div class="resultRow newRow" [class.resultRow-mobile]="mobileMode"> + <div *ngIf="!mobileMode" class="checkThis"> + <mat-checkbox color="primary"></mat-checkbox> + </div> + <div class="resultCol {{data.class}}" *ngFor="let data of displayedMainData"> + <span *ngIf="data.id == 'status_label'"> + <mat-icon [ngStyle]="{'color': row.priority_color}" color="primary" class="{{row.status_icon.charAt(0)}}{{row.status_icon.charAt(1)}} {{row.status_icon}} {{row.status_icon.charAt(0)}}{{row.status_icon.charAt(1)}}-2x" + title="{{row.status_label}} ({{row.status_id}})"></mat-icon><br /> + </span> + <ng-container *ngIf="data.id == 'date'"> + <i class="fa fa-calendar" title="{{lang.creationDate}}"></i> {{row.creation_date + | timeAgo}} - <i class="fa fa-stopwatch" title="{{lang.processLimitDate}}"></i> <span + [innerHTML]="row.process_limit_date | timeLimit" title='{{row.process_limit_date | date : "le dd/MM/y à HH:mm"}}'></span> + </ng-container> + <ng-container *ngIf="data.icon != ''"> + <i class="{{data.icon}}"></i> + + </ng-container> + <ng-container *ngIf="data.id == 'category_id'"> + {{lang[row.category_id]}} + </ng-container> + <ng-container *ngIf="data.id != 'status_label' && data.id != 'date' && data.id != 'category_id'"> + {{row[data.id]}} + </ng-container> + </div> + </div> + <div class="resultRow"> + <div class="resultCol smallFontData softColorData"> + <b>Traité par</b> : {{row.user_dest_firstname}} {{row.user_dest_lastname}} ({{row.entity_destination}}) + </div> + <mat-button-toggle-group #group="matButtonToggleGroup" class="actions" multiple> + <button color="primary" mat-icon-button (click)="openBottomSheet(row)"> + <mat-icon fontSet="fas" matBadge="??" fontIcon="fa-comments fa-2x"></mat-icon> + </button> + <button color="primary" mat-icon-button (click)="openAttachSheet(row)"> + <mat-icon fontSet="fas" matBadge="??" fontIcon="fa-paperclip fa-2x"></mat-icon> + </button> + <button color="primary" mat-icon-button (click)="openDiffusionSheet(row)"> + <mat-icon matBadgeSize="medium" fontSet="fas" fontIcon="fa-sitemap fa-2x"></mat-icon> + </button> + <button color="primary" mat-icon-button (click)="goTo(row)"> + <mat-icon fontSet="fas" fontIcon="fa-eye fa-2x"></mat-icon> + </button> + <button color="primary" mat-icon-button (click)="goToDetail(row);"> + <mat-icon fontSet="fas" fontIcon="fa-info-circle fa-2x"></mat-icon> + </button> + </mat-button-toggle-group> + </div> + </td> + </ng-container> + <tr mat-row *matRowDef="let row; columns: displayedColumnsBasket;" (click)="test();"></tr> + </table> + <div class="mat-paginator" style="min-height:48px;min-height: 48px;display: flex;justify-content: end;align-items: center;padding-right: 20px;">{{resultsLength}} + {{lang.entries}}</div> + </mat-card> + </mat-sidenav-content> + <mat-sidenav #snav2 mode="over" [fixedInViewport]="mobileQuery.matches" fixedTopGap="56" position='end' + [opened]="mobileQuery.matches ? false : false" style="overflow-x:hidden;" [class.docView]="!filterMode" [ngStyle]="{'width': mobileMode ? '80%' : '40%'}"> + <div *ngIf="innerHtml && !filterMode" [innerHTML]="innerHtml" style="height: 100%;overflow: hidden;"></div> + + <app-filters-list *ngIf="filterMode" [listProperties]="this.listProperties"></app-filters-list> + <mat-divider></mat-divider> + </mat-sidenav> + </mat-sidenav-container> +</div> \ No newline at end of file diff --git a/src/frontend/app/list/basket-list.component.scss b/src/frontend/app/list/basket-list.component.scss new file mode 100644 index 0000000000000000000000000000000000000000..42aec0d03763d8bf13a1c12414f5bfa4af289b52 --- /dev/null +++ b/src/frontend/app/list/basket-list.component.scss @@ -0,0 +1,128 @@ +.docView { + overflow: hidden; +} + +mat-toolbar { + border: solid 1px #F9983066; + font-size: 10px; + height: 20px; + color: #666; +} + +.resultContainer { + // color : rgb(102, 102, 102); + padding: 10px; + + &-mobile { + padding-left: 0px !important; + padding-right: 0px !important; + } +} + +.resultRow { + align-items: center; + display: flex; + padding: 5px; + + &-mobile { + font-size: 80%; + } +} + +.resultCol { + flex: 1; + overflow: hidden; + text-overflow: ellipsis; + + &-mobile { + overflow: inherit; + text-overflow: inherit; + word-break: break-all; + } +} + +.twoCol { + flex: 2; +} + +.mat-row:hover { + background: inherit; +} + +.newRow { + // font-weight: bold; +} +.endCol { + text-align: right; +} + +.chrono { + color: #666; + &-mobile { + font-size: 70%; + } +} + +.envFilter { + height: 40px; + + mat-icon{ + height: auto; + } + + .mat-button-toggle-checked { + background-color: #F99830; + color: white; + } +} + +.checkThis { + width: 40px; + text-align: center; +} + +.statusCol { + width: 80px; + text-align: center; +} + +.actionsCol { + width: 40px; +} + + +.actions { + box-shadow: none; + flex: 1; + justify-content: end; + overflow: inherit; +} +.mat-badge-content { + background: #F99830; +} + +.smallFontData { + font-size: 10px; +} + +.centerData { + text-align: center; +} + +.rightData { + text-align: right; +} + +.softColorData { + color: #666; +} + +.longData { + flex: 3; +} + +.filterBadges>.label { + margin: 5px; + background: #F99830; + cursor: pointer; +} \ No newline at end of file diff --git a/src/frontend/app/basket/basket-list.component.ts b/src/frontend/app/list/basket-list.component.ts similarity index 73% rename from src/frontend/app/basket/basket-list.component.ts rename to src/frontend/app/list/basket-list.component.ts index 48618a6861266d41fb258d6bc95691d48f4c77ae..b5c92eae05433e961b970938067e2c41780a92b7 100644 --- a/src/frontend/app/basket/basket-list.component.ts +++ b/src/frontend/app/list/basket-list.component.ts @@ -1,14 +1,17 @@ -import { ChangeDetectorRef, Component, OnInit, ViewChild, QueryList, ViewChildren, Inject } from '@angular/core'; +import { ChangeDetectorRef, Component, OnInit, ViewChild, Inject } from '@angular/core'; import { MediaMatcher } from '@angular/cdk/layout'; import { HttpClient } from '@angular/common/http'; import { LANG } from '../translate.component'; import { merge, Observable, of as observableOf } from 'rxjs'; import { NotificationService } from '../notification.service'; -import { MatDialog, MatSidenav, MatExpansionPanel, MatTableDataSource, MatPaginator, MatSort, MatBottomSheet, MatBottomSheetRef, MAT_BOTTOM_SHEET_DATA } from '@angular/material'; +import { MatDialog, MatSidenav, MatPaginator, MatSort, MatBottomSheet, MatBottomSheetRef, MAT_BOTTOM_SHEET_DATA, MatButtonToggleGroup } from '@angular/material'; import { DomSanitizer, SafeHtml } from '@angular/platform-browser'; import { startWith, switchMap, map, catchError } from 'rxjs/operators'; import { ActivatedRoute } from '@angular/router'; +import { HeaderService } from '../../service/header.service'; +import { FiltersListService } from '../../service/filtersList.service'; + declare function $j(selector: any): any; @@ -16,6 +19,7 @@ declare var angularGlobals: any; @Component({ templateUrl: "basket-list.component.html", + styleUrls: ['basket-list.component.scss'], providers: [NotificationService] }) export class BasketListComponent implements OnInit { @@ -32,20 +36,73 @@ export class BasketListComponent implements OnInit { basketUrl: string; homeData: any; - + filterMode: boolean = false; @ViewChild('snav') sidenavLeft: MatSidenav; @ViewChild('snav2') sidenavRight: MatSidenav; - - displayedColumnsBasket: string[] = ['res_id', 'subject', 'contact_society', 'creation_date']; + displayedColumnsBasket: string[] = ['res_id']; + + displayedMainData: any = [ + { + 'id' : 'status_label', + 'class' : 'centerData', + 'icon' : '' + }, + { + 'id' : 'alt_identifier', + 'class' : 'softColorData', + 'icon' : '' + }, + { + 'id' : 'subject', + 'class' : 'longData', + 'icon' : '' + } + ]; + + displayedSecondaryData: any = [ + { + 'id' : 'priority_label', + 'class' : '', + 'icon' : '' + }, + { + 'id' : 'category_id', + 'class' : '', + 'icon' : '' + }, + { + 'id' : 'doctype_label', + 'class' : '', + 'icon' : 'fa fa-file' + }, + { + 'id' : 'contact_society', + 'class' : '', + 'icon' : '' + }, + { + 'id' : 'contact_society', + 'class' : '', + 'icon' : '' + }, + { + 'id' : 'date', + 'class' : 'rightData', + 'icon' : '' + }, + ]; exampleDatabase: ExampleHttpDao | null; data: any[] = []; resultsLength = 0; isLoadingResults = true; + listProperties: any = {}; + listPropertiesIndex: number = 0; + @ViewChild(MatPaginator) paginator: MatPaginator; @ViewChild('tableBasketListSort') sort: MatSort; - constructor(changeDetectorRef: ChangeDetectorRef, private route: ActivatedRoute, media: MediaMatcher, public http: HttpClient, public dialog: MatDialog, private sanitizer: DomSanitizer, private bottomSheet: MatBottomSheet) { + constructor(changeDetectorRef: ChangeDetectorRef, private route: ActivatedRoute, media: MediaMatcher, public http: HttpClient, public dialog: MatDialog, private sanitizer: DomSanitizer, private bottomSheet: MatBottomSheet, private headerService: HeaderService, private filtersListService: FiltersListService) { this.mobileMode = angularGlobals.mobileMode; $j("link[href='merged_css.php']").remove(); this.mobileQuery = media.matchMedia('(max-width: 768px)'); @@ -59,7 +116,8 @@ export class BasketListComponent implements OnInit { this.loading = false; if (this.mobileMode) { - this.displayedColumnsBasket = ['res_id', 'subject']; + $j('.mat-paginator-navigation-previous').hide(); + $j('.mat-paginator-navigation-next').hide(); } this.http.get(this.coreUrl + "rest/home") @@ -67,18 +125,21 @@ export class BasketListComponent implements OnInit { this.homeData = data; }); - + this.isLoadingResults = false; this.route.params.subscribe(params => { this.basketUrl = this.coreUrl + 'rest/resources/groups/' + params['groupSerialId'] + '/baskets/' + params['basketId']; - this.http.get(this.coreUrl + "rest/baskets/" + params['basketId']) + this.http.get(this.basketUrl) .subscribe((data: any) => { - window['MainHeaderComponent'].refreshTitle(data.basket.basket_name); + console.log(data); + this.filterMode = false; window['MainHeaderComponent'].setSnav(this.sidenavLeft); - window['MainHeaderComponent'].setSnavRight(null); - this.exampleDatabase = new ExampleHttpDao(this.http); + window['MainHeaderComponent'].setSnavRight(this.sidenavRight); + this.exampleDatabase = new ExampleHttpDao(this.http, this.filtersListService); + + this.listProperties = this.filtersListService.initListsProperties('bbain', params['groupSerialId'], params['basketId']); // If the user changes the sort order, reset back to the first page. - this.paginator.pageIndex = 0; + this.paginator.pageIndex = this.listProperties.page; this.sort.sortChange.subscribe(() => this.paginator.pageIndex = 0); merge(this.sort.sortChange, this.paginator.page) @@ -92,7 +153,7 @@ export class BasketListComponent implements OnInit { map(data => { // Flip flag to show that loading has finished. this.isLoadingResults = false; - this.resultsLength = data.number; + this.resultsLength = data.count; return data.resources; }), @@ -111,6 +172,7 @@ export class BasketListComponent implements OnInit { } goTo(row: any) { + this.filterMode = false; if (this.docUrl == this.coreUrl + 'rest/res/' + row.res_id + '/content' && this.sidenavRight.opened) { this.sidenavRight.close(); } else { @@ -122,6 +184,11 @@ export class BasketListComponent implements OnInit { } } + openFilter() { + this.filterMode = true; + this.sidenavRight.open(); + } + goToDetail(row: any) { location.href = "index.php?page=details&dir=indexing_searching&id=" + row.res_id; } @@ -151,18 +218,32 @@ export class BasketListComponent implements OnInit { console.log(data); }); } + + updateFilters(e: any) { + this.listProperties.onlyProcesLimit = false; + this.listProperties.onlyNewRes = false; + this.listProperties.withPj = false; + this.listProperties.withNote = false; + + e.value.forEach((element: any) => { + this.listProperties[element] = true; + }); + this.filtersListService.updateListsProperties(this.listProperties); + } } export interface BasketList { resources: any[]; - number: number; + count: number; } export class ExampleHttpDao { - constructor(private http: HttpClient) { } + constructor(private http: HttpClient, private filtersListService: FiltersListService) { } getRepoIssues(sort: string, order: string, page: number, href: string): Observable<BasketList> { + + this.filtersListService.updateListsPropertiesPage(page); let offset = page * 10; const requestUrl = `${href}?limit=10&offset=${offset}`; @@ -172,6 +253,7 @@ export class ExampleHttpDao { @Component({ templateUrl: 'note-list.component.html', + styleUrls: ['note-list.component.scss'], }) export class BottomSheetNoteList { coreUrl: string; diff --git a/src/frontend/app/basket/diffusion-list.component.html b/src/frontend/app/list/diffusion-list.component.html similarity index 100% rename from src/frontend/app/basket/diffusion-list.component.html rename to src/frontend/app/list/diffusion-list.component.html diff --git a/src/frontend/app/list/filters/filters-list.component.html b/src/frontend/app/list/filters/filters-list.component.html new file mode 100644 index 0000000000000000000000000000000000000000..f23a41adcc2cb0a135e9275b557a44db4e500f55 --- /dev/null +++ b/src/frontend/app/list/filters/filters-list.component.html @@ -0,0 +1,49 @@ +<mat-nav-list disableRipple="true"> + <h3 mat-subheader>{{lang.filterBy}}</h3> + <mat-form-field appearance="outline" style="padding-left:10px;padding-right:10px;"> + <mat-label>Numéro chrono</mat-label> + <input matInput> + </mat-form-field> + <mat-expansion-panel #categoriesPan> + <mat-expansion-panel-header> + <mat-panel-title style="color: rgba(0,0,0,0.54);font-size: 14px;font-weight: 500;"> + Categories + </mat-panel-title> + <mat-panel-description> + </mat-panel-description> + </mat-expansion-panel-header> + <mat-selection-list #categories (selectionChange)="updateFilters(categories, 'categories')"> + <mat-list-option checkboxPosition="before" color="primary" [value]="category.id" *ngFor="let category of categoriesList" [selected]="category.selected"> + {{category.label}} + </mat-list-option> + </mat-selection-list> + </mat-expansion-panel> + <mat-expansion-panel #prioritiesPan> + <mat-expansion-panel-header> + <mat-panel-title style="color: rgba(0,0,0,0.54);font-size: 14px;font-weight: 500;"> + Priorités + </mat-panel-title> + <mat-panel-description> + </mat-panel-description> + </mat-expansion-panel-header> + <mat-selection-list #priorities (selectionChange)="updateFilters(priorities, 'priorities')"> + <mat-list-option checkboxPosition="before" color="primary" [value]="priority.id" *ngFor="let priority of prioritiesList" [selected]="priority.selected"> + {{priority.label}} + </mat-list-option> + </mat-selection-list> + </mat-expansion-panel> + <mat-expansion-panel #entitiesPan> + <mat-expansion-panel-header> + <mat-panel-title style="color: rgba(0,0,0,0.54);font-size: 14px;font-weight: 500;"> + Services + </mat-panel-title> + <mat-panel-description> + </mat-panel-description> + </mat-expansion-panel-header> + <mat-selection-list #entities (selectionChange)="updateFilters(entities, 'entities')"> + <mat-list-option checkboxPosition="before" color="primary" [value]="entity.id" *ngFor="let entity of entitiesList" [selected]="entity.selected"> + {{entity.label}} + </mat-list-option> + </mat-selection-list> + </mat-expansion-panel> +</mat-nav-list> \ No newline at end of file diff --git a/src/frontend/app/list/filters/filters-list.component.ts b/src/frontend/app/list/filters/filters-list.component.ts new file mode 100644 index 0000000000000000000000000000000000000000..b237fb1cb4dc05432701da1d8219c9159fa82b95 --- /dev/null +++ b/src/frontend/app/list/filters/filters-list.component.ts @@ -0,0 +1,75 @@ +import { Component, OnInit, Input, ViewChild } from '@angular/core'; +import { HttpClient } from '@angular/common/http'; +import { LANG } from '../../translate.component'; +import { NotificationService } from '../../notification.service'; +import { FiltersListService } from '../../../service/filtersList.service'; +import { MatSelectionList, MatExpansionPanel } from '@angular/material'; + +declare function $j(selector: any): any; + +declare var angularGlobals: any; + +@Component({ + selector: 'app-filters-list', + templateUrl: 'filters-list.component.html', + providers: [NotificationService] +}) +export class FiltersListComponent implements OnInit { + + coreUrl: string; + lang: any = LANG; + prioritiesList: any[] = []; + categoriesList: any[] = []; + entitiesList: any[] = []; + + @Input('listProperties') listProperties: any; + + @ViewChild('categoriesPan') categoriesPan: MatExpansionPanel; + @ViewChild('prioritiesPan') prioritiesPan: MatExpansionPanel; + @ViewChild('enetitiesPan') enetitiesPan: MatExpansionPanel; + + + constructor(public http: HttpClient, private filtersListService: FiltersListService) { } + + ngOnInit(): void { + this.http.get("../../rest/priorities") + .subscribe((data: any) => { + this.prioritiesList = data.priorities; + this.prioritiesList.forEach((element) => { + element.selected = false; + this.listProperties.priorities.forEach((listPropertyPrio: any) => { + if (element.id === listPropertyPrio.id) { + element.selected = true; + this.prioritiesPan.open(); + } + }); + }); + console.log(this.prioritiesList); + }); + + this.http.get("../../rest/categories") + .subscribe((data: any) => { + this.categoriesList = data.categories; + this.categoriesList.forEach(element => { + element.selected = false; + this.listProperties.categories.forEach((listPropertyCat: any) => { + if (element.id === listPropertyCat.id) { + element.selected = true; + this.categoriesPan.open(); + } + }); + }); + console.log(this.categoriesList); + }); + } + updateFilters(e: MatSelectionList, id: string) { + this.listProperties[id] = []; + e.selectedOptions.selected.forEach(element => { + this.listProperties[id].push({ + 'id' : element.value, + 'label': element._text.nativeElement.innerText + }); + }); + this.filtersListService.updateListsProperties(this.listProperties); + } +} \ No newline at end of file diff --git a/src/frontend/app/basket/note-list.component.html b/src/frontend/app/list/note-list.component.html similarity index 89% rename from src/frontend/app/basket/note-list.component.html rename to src/frontend/app/list/note-list.component.html index c964c1067c0fed4426715afbcd37e7f3f8a9b881..58c3f0d61034994ee9325aa75d968695276dbb7a 100644 --- a/src/frontend/app/basket/note-list.component.html +++ b/src/frontend/app/list/note-list.component.html @@ -21,4 +21,9 @@ <span *ngFor="let entity of note.entities_restriction" class="label label-default" style="background-color:rgba(0,0,0,0.4);white-space:normal;display:inline-block;margin-right: 5px;" title="Entité restreinte"><i class="fa fa-sitemap"></i> {{entity}}</span> </mat-card-content> </mat-card> + <mat-form-field appearance="outline"> + <mat-label>Ecrire une note</mat-label> + <input matInput> + <mat-icon matSuffix></mat-icon> + </mat-form-field> </ng-container> \ No newline at end of file diff --git a/src/frontend/app/list/note-list.component.scss b/src/frontend/app/list/note-list.component.scss new file mode 100644 index 0000000000000000000000000000000000000000..ef0193d9887f854b65d12c5f1f2c47bb38d9b286 --- /dev/null +++ b/src/frontend/app/list/note-list.component.scss @@ -0,0 +1,3 @@ +.mat-form-field-wrapper{ + padding-bottom: 0px; +} \ No newline at end of file diff --git a/src/frontend/service/filtersList.service.ts b/src/frontend/service/filtersList.service.ts new file mode 100644 index 0000000000000000000000000000000000000000..d46a10940eefb9d558ba5a7db7e0cc036507c2df --- /dev/null +++ b/src/frontend/service/filtersList.service.ts @@ -0,0 +1,77 @@ +import { Injectable } from '@angular/core'; + +interface listProperties { + 'id' : string, + 'groupId' : number, + 'basketId' : number, + 'page' : string, + 'onlyProcesLimit': boolean, + 'onlyNewRes': boolean, + 'withPj': boolean, + 'withNote': boolean, + 'categories' : string[], + 'priorities' : string[], + 'entities' : string[] +} + +@Injectable() +export class FiltersListService { + + listsProperties: any[] = []; + listsPropertiesIndex: number = 0; + + constructor() { + this.listsProperties = JSON.parse(sessionStorage.getItem('propertyList')); + } + + initListsProperties(userId: string, groupId: number, basketId: number) { + this.listsPropertiesIndex = 0; + let listProperties: listProperties; + + + if (this.listsProperties != null) { + this.listsProperties.forEach((element, index) => { + if (element.id == userId && element.groupId == groupId && element.basketId == basketId) { + this.listsPropertiesIndex = index; + listProperties = element; + } + }); + } else { + this.listsProperties = []; + } + + if (!listProperties) { + listProperties = { + 'id' : userId, + 'groupId' : groupId, + 'basketId' : basketId, + 'page' : '0', + 'onlyProcesLimit': false, + 'onlyNewRes': false, + 'withPj': false, + 'withNote': false, + 'categories' : [], + 'priorities' : [], + 'entities' : [], + }; + this.listsProperties.push(listProperties); + this.saveListsProperties(); + } + return listProperties; + } + + updateListsPropertiesPage(page : number) { + this.listsProperties[this.listsPropertiesIndex].page = page; + this.saveListsProperties(); + } + + updateListsProperties(listProperties : any) { + this.listsProperties[this.listsPropertiesIndex] = listProperties; + this.saveListsProperties(); + } + + saveListsProperties() { + sessionStorage.setItem('propertyList', JSON.stringify(this.listsProperties)); + } + +} diff --git a/src/frontend/service/header.service.ts b/src/frontend/service/header.service.ts index 0b6e598d72b51dd2d04c2e31edd3a4260db060c0..618d1e3f9587b61a46e05a9f7c88e4fbbcda8e59 100644 --- a/src/frontend/service/header.service.ts +++ b/src/frontend/service/header.service.ts @@ -2,6 +2,5 @@ import { Injectable } from '@angular/core'; @Injectable() export class HeaderService { - - headerMessage : string = ""; + headerMessage : string = ""; }