Merge branch 'RED-8320' into 'master'

RED-8320: updated edit dialog for imported redactions.

See merge request redactmanager/red-ui!268
This commit is contained in:
Dan Percic 2024-01-23 16:08:30 +01:00
commit 7c2148e901
4 changed files with 61 additions and 39 deletions

View File

@ -7,19 +7,21 @@
></div>
<div class="dialog-content redaction" [class.fixed-height]="isRedacted && isImage">
<div *ngIf="!isImage && redactedTexts" class="iqser-input-group">
<label [translate]="'edit-redaction.dialog.content.redacted-text'" class="selected-text"></label>
<cdk-virtual-scroll-viewport
[itemSize]="16"
[ngStyle]="{ height: redactedTexts.length <= 5 ? 16 * redactedTexts.length + 'px' : 80 + 'px' }"
>
<ul *cdkVirtualFor="let text of redactedTexts">
<li>{{ text }}</li>
</ul>
</cdk-virtual-scroll-viewport>
<div *ngIf="!isImage">
<label [translate]="isImported ? 'edit-redaction.dialog.content.imported' : 'edit-redaction.dialog.content.redacted-text'"></label>
<div *ngIf="!!redactedTexts.length" class="iqser-input-group">
<cdk-virtual-scroll-viewport
[itemSize]="16"
[ngStyle]="{ height: redactedTexts.length <= 5 ? 16 * redactedTexts.length + 'px' : 80 + 'px' }"
>
<ul *cdkVirtualFor="let text of redactedTexts">
<li>{{ text }}</li>
</ul>
</cdk-virtual-scroll-viewport>
</div>
</div>
<div *ngIf="!isManualRedaction" class="iqser-input-group required w-450">
<div *ngIf="!isManualRedaction" class="iqser-input-group w-450" [class.required]="!form.controls.type.disabled">
<label [translate]="'edit-redaction.dialog.content.type'"></label>
<mat-form-field>
@ -30,7 +32,7 @@
<mat-select-trigger>{{ displayedDictionaryLabel }}</mat-select-trigger>
<mat-option
(click)="typeChanged()"
*ngFor="let dictionary of dictionaries"
*ngFor="let dictionary of typeSelectOptions"
[matTooltip]="dictionary.description"
[value]="dictionary.type"
matTooltipPosition="after"

View File

@ -10,6 +10,12 @@ import { getEditRedactionOptions, RedactOrHintOption } from '../../utils/dialog-
import { EditRedactionData, EditRedactResult } from '../../utils/dialog-types';
import { LegalBasisOption } from '../manual-redaction-dialog/manual-annotation-dialog.component';
interface TypeSelectOptions {
type: string;
description: string;
label: string;
}
@Component({
templateUrl: './edit-redaction-dialog.component.html',
styleUrls: ['./edit-redaction-dialog.component.scss'],
@ -20,17 +26,22 @@ export class EditRedactionDialogComponent
{
readonly #dossier = inject(ActiveDossiersService).find(this.data.dossierId);
readonly #applyToAllDossiers = this.data.applyToAllDossiers;
readonly annotations = this.data.annotations;
readonly iconButtonTypes = IconButtonTypes;
readonly redactedTexts?: string[];
readonly isModifyDictionary: boolean;
readonly isImage: boolean;
readonly isManualRedaction: boolean;
readonly isHint: boolean;
readonly isRedacted: boolean;
readonly allRectangles = this.data.annotations.reduce((acc, a) => acc && a.AREA, true);
readonly isModifyDictionary = this.annotations.every(annotation => annotation.isModifyDictionary);
readonly isImage = this.annotations.reduce((acc, next) => acc && next.isImage, true);
readonly redactedTexts = !this.isImage ? this.annotations.map(annotation => annotation.value).filter(value => !!value) : null;
readonly isManualRedaction = this.annotations.every(annotation => annotation.type === SuperTypes.ManualRedaction);
readonly isHint = this.annotations.every(annotation => annotation.HINT);
readonly isRedacted = this.annotations.every(annotation => annotation.isRedacted);
readonly isImported: boolean = this.annotations.every(annotation => annotation.imported);
readonly allRectangles = this.annotations.reduce((acc, a) => acc && a.AREA, true);
options: DetailsRadioOption<RedactOrHintOption>[] | undefined;
legalOptions: LegalBasisOption[] = [];
dictionaries: Dictionary[] = [];
typeSelectOptions: TypeSelectOptions[] = [];
readonly form = this.#getForm();
hasTypeChanged = false;
initialReasonDisabled = this.someSkipped;
@ -40,19 +51,12 @@ export class EditRedactionDialogComponent
private readonly _dictionaryService: DictionaryService,
) {
super();
const annotations = this.data.annotations;
this.isImage = annotations.reduce((acc, next) => acc && next.isImage, true);
this.redactedTexts = !this.isImage ? annotations.map(annotation => annotation.value) : null;
this.isModifyDictionary = annotations.every(annotation => annotation.isModifyDictionary);
this.isManualRedaction = annotations.every(annotation => annotation.type === SuperTypes.ManualRedaction);
this.isHint = annotations.every(annotation => annotation.HINT);
this.isRedacted = annotations.every(annotation => annotation.isRedacted);
}
get displayedDictionaryLabel() {
const selectedDictionaryType = this.form.controls.type.value;
if (selectedDictionaryType) {
return this.dictionaries.find(d => d.type === selectedDictionaryType)?.label ?? null;
return this.typeSelectOptions.find(option => option.type === selectedDictionaryType)?.label ?? null;
}
return null;
}
@ -69,7 +73,7 @@ export class EditRedactionDialogComponent
}
get someSkipped() {
return this.data.annotations.some(annotation => annotation.isSkipped);
return this.annotations.some(annotation => annotation.isSkipped);
}
get redactBasedTypes() {
@ -83,7 +87,7 @@ export class EditRedactionDialogComponent
}
get hideReasonPlaceholder() {
return (this.hasTypeChanged && this.isRedactBasedType) || this.#isFieldEmpty('legalBasis');
return (this.hasTypeChanged && this.isRedactBasedType) || this.#isFieldEmpty('legalBasisValue');
}
get hideParagraphPlaceholder() {
@ -95,7 +99,7 @@ export class EditRedactionDialogComponent
}
get isBulkEdit() {
return this.data.annotations.length > 1;
return this.annotations.length > 1;
}
async ngOnInit() {
@ -107,8 +111,8 @@ export class EditRedactionDialogComponent
label: lbm.name,
}));
const reason = this.legalOptions.find(o => o.legalBasis === this.data.annotations[0].legalBasis);
const sameLegalBasis = this.data.annotations.every(annotation => annotation.legalBasis === reason?.legalBasis);
const reason = this.legalOptions.find(o => o.legalBasis === this.annotations[0].legalBasis);
const sameLegalBasis = this.annotations.every(annotation => annotation.legalBasis === reason?.legalBasis);
this.form.patchValue({
reason: sameLegalBasis ? reason : null,
});
@ -152,8 +156,19 @@ export class EditRedactionDialogComponent
this.#dossier.dossierTemplateId,
this.isImage,
this.isHint,
this.data.annotations.every(annotation => annotation.isOCR),
this.annotations.every(annotation => annotation.isOCR),
);
this.typeSelectOptions = this.dictionaries.map(dictionary => ({
type: dictionary.type,
label: dictionary.label,
description: dictionary.description,
}));
if (this.isImported) {
const importedAnnotation = this.annotations[0];
this.typeSelectOptions.push({ type: this.annotations[0].type, label: importedAnnotation.typeLabel, description: '' });
}
}
#setOptions(type: string, reasonChanged = false) {
@ -173,19 +188,22 @@ export class EditRedactionDialogComponent
}
#getForm() {
const sameType = this.data.annotations.every(annotation => annotation.type === this.data.annotations[0].type);
const sameSection = this.data.annotations.every(annotation => annotation.section === this.data.annotations[0].section);
const sameType = this.annotations.every(annotation => annotation.type === this.annotations[0].type);
const sameSection = this.annotations.every(annotation => annotation.section === this.annotations[0].section);
return new FormGroup({
reason: new FormControl<LegalBasisOption>({ value: null, disabled: this.someSkipped }),
comment: new FormControl<string>(null),
type: new FormControl<string>(sameType ? this.data.annotations[0].type : null),
section: new FormControl<string>(sameSection ? this.data.annotations[0].section : null),
type: new FormControl<string>({
value: sameType ? this.annotations[0].type : null,
disabled: this.isImported,
}),
section: new FormControl<string>({ value: sameSection ? this.annotations[0].section : null, disabled: this.isImported }),
option: new FormControl<LegalBasisOption>(null),
value: new FormControl<string>(this.allRectangles ? this.data.annotations[0].value : null),
value: new FormControl<string>(this.allRectangles ? this.annotations[0].value : null),
});
}
#isFieldEmpty(field: string) {
return this.data.annotations.every(annotation => !annotation[field].length);
return this.annotations.every(annotation => !annotation[field]?.length);
}
}

View File

@ -1211,6 +1211,7 @@
},
"reason": "Reason",
"redacted-text": "Annotated text",
"imported": "Imported Redaction",
"section": "Paragraph / location",
"type": "Type",
"unchanged": "Unchanged"

View File

@ -1211,6 +1211,7 @@
},
"reason": "Reason",
"redacted-text": "Annotated text",
"imported": "Imported Redaction",
"section": "Paragraph / location",
"type": "Type",
"unchanged": "Unchanged"