mirror of
https://github.com/DSpace/dspace-angular.git
synced 2025-10-08 10:34:15 +00:00
draggable form groups
This commit is contained in:
@@ -49,54 +49,13 @@
|
|||||||
|
|
||||||
<ng-container *ngTemplateOutlet="endTemplate?.templateRef; context: model"></ng-container>
|
<ng-container *ngTemplateOutlet="endTemplate?.templateRef; context: model"></ng-container>
|
||||||
|
|
||||||
<ng-container *ngTemplateOutlet="startTemplate?.templateRef; context: model"></ng-container>
|
|
||||||
<!-- Should be *ngIf instead of class d-none, but that breaks the #componentViewContainer reference-->
|
|
||||||
<div [ngClass]="{'form-row': model.hasLanguages || hasRelationLookup, 'd-none': hasRelationLookup && model.value}">
|
|
||||||
<div [ngClass]="getClass('grid', 'control')">
|
|
||||||
|
|
||||||
<ng-container #componentViewContainer></ng-container>
|
|
||||||
|
|
||||||
<small *ngIf="hasHint && (!showErrorMessages || errorMessages.length === 0)"
|
|
||||||
class="text-muted" [innerHTML]="model.hint | translate" [ngClass]="getClass('element', 'hint')"></small>
|
|
||||||
|
|
||||||
<div *ngIf="showErrorMessages" [ngClass]="[getClass('element', 'errors'), getClass('grid', 'errors')]">
|
|
||||||
<small *ngFor="let message of errorMessages" class="invalid-feedback d-block">{{ message | translate:model.validators }}</small>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div *ngIf="model.languageCodes && model.languageCodes.length > 0" class="col-xs-2">
|
|
||||||
<select
|
|
||||||
#language="ngModel"
|
|
||||||
[disabled]="model.readOnly"
|
|
||||||
[(ngModel)]="model.language"
|
|
||||||
class="form-control"
|
|
||||||
(blur)="onBlur($event)"
|
|
||||||
(change)="onChangeLanguage($event)"
|
|
||||||
[ngModelOptions]="{standalone: true}"
|
|
||||||
required>
|
|
||||||
<option *ngFor="let lang of model.languageCodes" [value]="lang.code">{{lang.display}}</option>
|
|
||||||
</select>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div *ngIf="hasRelationLookup" class="col-auto text-center">
|
|
||||||
<button class="btn btn-secondary"
|
|
||||||
type="submit"
|
|
||||||
ngbTooltip="{{'form.lookup-help' | translate}}"
|
|
||||||
placement="top"
|
|
||||||
(click)="openLookup(); $event.stopPropagation();">{{'form.lookup' | translate}}
|
|
||||||
</button>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<ng-container *ngTemplateOutlet="endTemplate?.templateRef; context: model"></ng-container>
|
|
||||||
<ng-container *ngIf="hasRelationLookup && model.value && reorderable">
|
<ng-container *ngIf="hasRelationLookup && model.value && reorderable">
|
||||||
<ds-existing-metadata-list-element cdkDrag
|
<ds-existing-metadata-list-element
|
||||||
[reoRel]="reorderable"
|
[reoRel]="reorderable"
|
||||||
[submissionItem]="item"
|
[submissionItem]="item"
|
||||||
[listId]="listId"
|
[listId]="listId"
|
||||||
[metadataFields]="model.metadataFields"
|
[metadataFields]="model.metadataFields"
|
||||||
[relationshipOptions]="model.relationship">
|
[relationshipOptions]="model.relationship">
|
||||||
</ds-existing-metadata-list-element>
|
</ds-existing-metadata-list-element>
|
||||||
</ng-container>
|
</ng-container>
|
||||||
<ng-content></ng-content>
|
<ng-content></ng-content>
|
||||||
|
@@ -228,9 +228,6 @@ export class DsDynamicFormControlContainerComponent extends DynamicFormControlCo
|
|||||||
}
|
}
|
||||||
|
|
||||||
ngOnInit(): void {
|
ngOnInit(): void {
|
||||||
if (this.model.type === 'ARRAY') {
|
|
||||||
console.log((this.model as DynamicRowArrayModel).get(1));
|
|
||||||
}
|
|
||||||
this.hasRelationLookup = hasValue(this.model.relationship);
|
this.hasRelationLookup = hasValue(this.model.relationship);
|
||||||
if (this.hasRelationLookup) {
|
if (this.hasRelationLookup) {
|
||||||
|
|
||||||
@@ -360,26 +357,6 @@ export class DsDynamicFormControlContainerComponent extends DynamicFormControlCo
|
|||||||
modalComp.item = this.item;
|
modalComp.item = this.item;
|
||||||
}
|
}
|
||||||
|
|
||||||
// moveSelection(event: CdkDragDrop<Relationship>) {
|
|
||||||
// this.zone.runOutsideAngular(() => {
|
|
||||||
// moveItemInArray(this.reorderables, event.previousIndex, event.currentIndex);
|
|
||||||
// const reorderables = this.reorderables.map((reo: Reorderable, index: number) => {
|
|
||||||
// reo.oldIndex = reo.getPlace();
|
|
||||||
// reo.newIndex = index;
|
|
||||||
// return reo;
|
|
||||||
// }
|
|
||||||
// );
|
|
||||||
// return observableCombineLatest(reorderables.map((rel: ReorderableRelationship) => {
|
|
||||||
// if (rel.oldIndex !== rel.newIndex) {
|
|
||||||
// return this.relationshipService.updatePlace(rel);
|
|
||||||
// } else {
|
|
||||||
// return observableOf(undefined);
|
|
||||||
// }
|
|
||||||
// })
|
|
||||||
// ).pipe(getSucceededRemoteData()).subscribe();
|
|
||||||
// })
|
|
||||||
// }
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Unsubscribe from all subscriptions
|
* Unsubscribe from all subscriptions
|
||||||
*/
|
*/
|
||||||
@@ -388,11 +365,4 @@ export class DsDynamicFormControlContainerComponent extends DynamicFormControlCo
|
|||||||
.filter((sub) => hasValue(sub))
|
.filter((sub) => hasValue(sub))
|
||||||
.forEach((sub) => sub.unsubscribe());
|
.forEach((sub) => sub.unsubscribe());
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Prevent unnecessary rerendering so fields don't lose focus
|
|
||||||
*/
|
|
||||||
trackReorderable(index, reorderable: Reorderable) {
|
|
||||||
return hasValue(reorderable) ? reorderable.getId() : undefined;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
@@ -1,14 +1,13 @@
|
|||||||
<ng-container [formGroup]="group">
|
<ng-container [formGroup]="group">
|
||||||
<div [dynamicId]="bindId && model.id"
|
<div [dynamicId]="bindId && model.id"
|
||||||
[formArrayName]="model.id"
|
[formArrayName]="model.id"
|
||||||
[ngClass]="getClass('element', 'control')">
|
[ngClass]="getClass('element', 'control')" cdkDropList (cdkDropListDropped)="moveSelection($event)">
|
||||||
|
|
||||||
<div *ngFor="let groupModel of model.groups; let idx = index" role="group"
|
<div *ngFor="let groupModel of model.groups; let idx = index" role="group"
|
||||||
[formGroupName]="idx" [ngClass]="[getClass('element', 'group'), getClass('grid', 'group')]"
|
[formGroupName]="idx" [ngClass]="[getClass('element', 'group'), getClass('grid', 'group')]" cdkDrag>
|
||||||
cdkDropList (cdkDropListDropped)="test($event)">
|
|
||||||
<ng-container *ngTemplateOutlet="startTemplate?.templateRef; context: groupModel"></ng-container>
|
<ng-container *ngTemplateOutlet="startTemplate?.templateRef; context: groupModel"></ng-container>
|
||||||
|
|
||||||
<ds-dynamic-form-control-container cdkDrag *ngFor="let _model of groupModel.group"
|
<ds-dynamic-form-control-container *ngFor="let _model of groupModel.group"
|
||||||
[bindId]="false"
|
[bindId]="false"
|
||||||
[context]="groupModel"
|
[context]="groupModel"
|
||||||
[group]="control.at(idx)"
|
[group]="control.at(idx)"
|
||||||
|
@@ -1,18 +1,24 @@
|
|||||||
import { Component, EventEmitter, Input, Output, QueryList } from '@angular/core';
|
import { Component, EventEmitter, Input, NgZone, Output, QueryList, SimpleChanges } from '@angular/core';
|
||||||
import { FormGroup } from '@angular/forms';
|
import { FormGroup } from '@angular/forms';
|
||||||
import {
|
import {
|
||||||
DynamicFormArrayComponent,
|
DynamicFormArrayComponent, DynamicFormArrayGroupModel,
|
||||||
DynamicFormArrayModel,
|
DynamicFormArrayModel,
|
||||||
DynamicFormControlCustomEvent, DynamicFormControlEvent,
|
DynamicFormControlCustomEvent, DynamicFormControlEvent,
|
||||||
DynamicFormLayout,
|
DynamicFormLayout,
|
||||||
DynamicFormLayoutService,
|
DynamicFormLayoutService, DynamicFormService,
|
||||||
DynamicFormValidationService,
|
DynamicFormValidationService,
|
||||||
DynamicTemplateDirective
|
DynamicTemplateDirective
|
||||||
} from '@ng-dynamic-forms/core';
|
} from '@ng-dynamic-forms/core';
|
||||||
|
import { CdkDragDrop, moveItemInArray } from '@angular/cdk/drag-drop';
|
||||||
|
import { Relationship } from '../../../../../../core/shared/item-relationships/relationship.model';
|
||||||
|
import { Reorderable, ReorderableRelationship } from '../../existing-metadata-list-element/existing-metadata-list-element.component';
|
||||||
|
import { combineLatest as observableCombineLatest, Observable, of as observableOf } from 'rxjs';
|
||||||
|
import { getSucceededRemoteData } from '../../../../../../core/shared/operators';
|
||||||
|
import { RelationshipService } from '../../../../../../core/data/relationship.service';
|
||||||
|
|
||||||
@Component({
|
@Component({
|
||||||
selector: 'ds-dynamic-form-array',
|
selector: 'ds-dynamic-form-array',
|
||||||
templateUrl: './dynamic-form-array.component.html'
|
templateUrl: './dynamic-form-array.component.html'
|
||||||
})
|
})
|
||||||
export class DsDynamicFormArrayComponent extends DynamicFormArrayComponent {
|
export class DsDynamicFormArrayComponent extends DynamicFormArrayComponent {
|
||||||
|
|
||||||
@@ -27,16 +33,35 @@ export class DsDynamicFormArrayComponent extends DynamicFormArrayComponent {
|
|||||||
@Output('dfChange') change: EventEmitter<DynamicFormControlEvent> = new EventEmitter<DynamicFormControlEvent>();
|
@Output('dfChange') change: EventEmitter<DynamicFormControlEvent> = new EventEmitter<DynamicFormControlEvent>();
|
||||||
@Output('dfFocus') focus: EventEmitter<DynamicFormControlEvent> = new EventEmitter<DynamicFormControlEvent>();
|
@Output('dfFocus') focus: EventEmitter<DynamicFormControlEvent> = new EventEmitter<DynamicFormControlEvent>();
|
||||||
@Output('ngbEvent') customEvent: EventEmitter<DynamicFormControlCustomEvent> = new EventEmitter();
|
@Output('ngbEvent') customEvent: EventEmitter<DynamicFormControlCustomEvent> = new EventEmitter();
|
||||||
|
|
||||||
/* tslint:enable:no-output-rename */
|
/* tslint:enable:no-output-rename */
|
||||||
|
|
||||||
constructor(protected layoutService: DynamicFormLayoutService,
|
constructor(protected layoutService: DynamicFormLayoutService,
|
||||||
protected validationService: DynamicFormValidationService) {
|
protected validationService: DynamicFormValidationService,
|
||||||
|
protected relationshipService: RelationshipService,
|
||||||
|
protected zone: NgZone,
|
||||||
|
protected formService: DynamicFormService
|
||||||
|
) {
|
||||||
super(layoutService, validationService);
|
super(layoutService, validationService);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
moveSelection(event: CdkDragDrop<Relationship>) {
|
||||||
test(event) {
|
this.zone.runOutsideAngular(() => {
|
||||||
console.log(event);
|
this.model.moveGroup(event.previousIndex,event.currentIndex - event.previousIndex);
|
||||||
|
this.model.groups.forEach(
|
||||||
|
(group: DynamicFormArrayGroupModel) => {
|
||||||
|
console.log(group.group[0]);
|
||||||
|
}
|
||||||
|
)
|
||||||
|
// return observableCombineLatest(reorderables.map((rel: ReorderableRelationship) => {
|
||||||
|
// if (rel.oldIndex !== rel.newIndex) {
|
||||||
|
// return this.relationshipService.updatePlace(rel);
|
||||||
|
// } else {
|
||||||
|
// return observableOf(undefined);
|
||||||
|
// }
|
||||||
|
// })
|
||||||
|
// ).pipe(getSucceededRemoteData()).subscribe();
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@@ -41,18 +41,18 @@ export abstract class FieldParser {
|
|||||||
&& (this.configData.input.type !== 'tag')
|
&& (this.configData.input.type !== 'tag')
|
||||||
&& (this.configData.input.type !== 'group')
|
&& (this.configData.input.type !== 'group')
|
||||||
) {
|
) {
|
||||||
|
let hideHints = false;
|
||||||
let arrayCounter = 0;
|
let arrayCounter = 0;
|
||||||
let fieldArrayCounter = 0;
|
let fieldArrayCounter = 0;
|
||||||
|
|
||||||
const config = {
|
const config = {
|
||||||
id: uniqueId() + '_array',
|
id: uniqueId() + '_array',
|
||||||
label: this.configData.label,
|
label: this.configData.label,
|
||||||
initialCount: this.getInitArrayIndex(),
|
initialCount: this.getInitArrayIndex() + 1,
|
||||||
notRepeatable: !this.configData.repeatable || hasValue(this.configData.selectableRelationship),
|
notRepeatable: !this.configData.repeatable || hasValue(this.configData.selectableRelationship),
|
||||||
required: isNotEmpty(this.configData.mandatory),
|
required: isNotEmpty(this.configData.mandatory),
|
||||||
groupFactory: () => {
|
groupFactory: () => {
|
||||||
let model;
|
let model;
|
||||||
console.log(arrayCounter);
|
|
||||||
if ((arrayCounter === 0)) {
|
if ((arrayCounter === 0)) {
|
||||||
model = this.modelFactory();
|
model = this.modelFactory();
|
||||||
arrayCounter++;
|
arrayCounter++;
|
||||||
@@ -60,8 +60,13 @@ export abstract class FieldParser {
|
|||||||
const fieldArrayOfValueLenght = this.getInitValueCount(arrayCounter - 1);
|
const fieldArrayOfValueLenght = this.getInitValueCount(arrayCounter - 1);
|
||||||
let fieldValue = null;
|
let fieldValue = null;
|
||||||
if (fieldArrayOfValueLenght > 0) {
|
if (fieldArrayOfValueLenght > 0) {
|
||||||
fieldValue = this.getInitFieldValue(arrayCounter - 1, fieldArrayCounter++);
|
if (fieldArrayCounter === 0) {
|
||||||
if (fieldArrayCounter === fieldArrayOfValueLenght) {
|
fieldValue = '';
|
||||||
|
} else {
|
||||||
|
fieldValue = this.getInitFieldValue(arrayCounter - 1, fieldArrayCounter - 1);
|
||||||
|
}
|
||||||
|
fieldArrayCounter++;
|
||||||
|
if (fieldArrayCounter === fieldArrayOfValueLenght + 1) {
|
||||||
fieldArrayCounter = 0;
|
fieldArrayCounter = 0;
|
||||||
arrayCounter++;
|
arrayCounter++;
|
||||||
}
|
}
|
||||||
@@ -72,6 +77,9 @@ export abstract class FieldParser {
|
|||||||
if (model.hasLanguages) {
|
if (model.hasLanguages) {
|
||||||
setLayout(model, 'grid', 'control', 'col');
|
setLayout(model, 'grid', 'control', 'col');
|
||||||
}
|
}
|
||||||
|
if (hideHints) {
|
||||||
|
model.hint = undefined;
|
||||||
|
}
|
||||||
return [model];
|
return [model];
|
||||||
}
|
}
|
||||||
} as DynamicRowArrayModelConfig;
|
} as DynamicRowArrayModelConfig;
|
||||||
|
Reference in New Issue
Block a user