diff --git a/projects/editor/src/app/app.module.ts b/projects/editor/src/app/app.module.ts index 48dd13d913f6837626ef6a4a8ea4982e37d8250a..d76387d7defe96bfd532e40cf735c8be7daea8cd 100644 --- a/projects/editor/src/app/app.module.ts +++ b/projects/editor/src/app/app.module.ts @@ -61,17 +61,17 @@ import { ToolbarComponent } from './components/toolbar/toolbar.component'; import { UiElementToolboxComponent } from './components/new-ui-element-panel/ui-element-toolbox.component'; import { UnitViewComponent } from './components/unit-view/unit-view.component'; -import { CanvasComponent } from 'editor/src/app/components/unit-view/canvas/canvas.component'; +import { CanvasComponent } from 'editor/src/app/components/unit-view/page/canvas.component'; import { StaticCanvasOverlayComponent } from - 'editor/src/app/components/unit-view/canvas/section-static/static-canvas-overlay.component'; + 'editor/src/app/components/unit-view/element-overlay/static-canvas-overlay.component'; import { DynamicCanvasOverlayComponent } from - 'editor/src/app/components/unit-view/canvas/section-dynamic/dynamic-canvas-overlay.component'; + 'editor/src/app/components/unit-view/element-overlay/dynamic-canvas-overlay.component'; import { EditorTranslateLoader } from './editor-translate-loader'; import { - SectionMenuComponent, -} from 'editor/src/app/components/unit-view/canvas/section-menu.component'; -import { SectionStaticComponent } from 'editor/src/app/components/unit-view/canvas/section-static/section-static.component'; -import { SectionDynamicComponent } from 'editor/src/app/components/unit-view/canvas/section-dynamic/section-dynamic.component'; + SectionMenuComponent +} from 'editor/src/app/components/unit-view/page/section-menu.component'; +import { SectionStaticComponent } from 'editor/src/app/components/unit-view/section/section-static.component'; +import { SectionDynamicComponent } from 'editor/src/app/components/unit-view/section/section-dynamic.component'; import { RichTextEditorComponent } from './text-editor/rich-text-editor.component'; import { DeleteConfirmationDialogComponent } from './components/dialogs/delete-confirmation-dialog.component'; import { TextEditDialogComponent } from './components/dialogs/text-edit-dialog.component'; @@ -100,8 +100,8 @@ import { ElementStylePropertiesComponent } from './components/properties-panel/style-properties-tab/element-style-properties.component'; import { ElementModelPropertiesComponent, IsInputElementPipe } from './components/properties-panel/model-properties-tab/element-model-properties.component'; -import { DynamicSectionHelperGridComponent } from 'editor/src/app/components/unit-view/canvas/section-dynamic/dynamic-section-helper-grid.component'; -import { ElementGridChangeListenerDirective } from 'editor/src/app/components/unit-view/canvas/section-dynamic/element-grid-change-listener.directive'; +import { DynamicSectionHelperGridComponent } from 'editor/src/app/components/unit-view/section/dynamic-section-helper-grid.component'; +import { ElementGridChangeListenerDirective } from 'editor/src/app/components/unit-view/section/element-grid-change-listener.directive'; import { OptionsFieldSetComponent } from './components/properties-panel/model-properties-tab/input-groups/options-field-set.component'; @@ -130,6 +130,7 @@ import { MAT_TOOLTIP_DEFAULT_OPTIONS, MatTooltipDefaultOptions } from '@angular/ import { ReferenceListComponent } from 'editor/src/app/components/reference-list.component'; import { ElementListComponent } from 'editor/src/app/components/element-list.component'; import { MeasurePipe } from 'common/pipes/measure.pipe'; +import { SectionComponent } from 'editor/src/app/components/unit-view/section/section.component'; /** Custom options the configure the tooltip's default show/hide delays. */ export const myCustomTooltipDefaults: MatTooltipDefaultOptions = { @@ -146,12 +147,7 @@ export const myCustomTooltipDefaults: MatTooltipDefaultOptions = { UiElementToolboxComponent, UnitViewComponent, CanvasComponent, - StaticCanvasOverlayComponent, - DynamicCanvasOverlayComponent, ElementPropertiesPanelComponent, - SectionMenuComponent, - SectionStaticComponent, - SectionDynamicComponent, RichTextEditorComponent, ToggleButtonNodeviewComponent, TextFieldNodeviewComponent, @@ -171,8 +167,6 @@ export const myCustomTooltipDefaults: MatTooltipDefaultOptions = { DropListOptionEditDialogComponent, PositionFieldSetComponent, DimensionFieldSetComponent, - DynamicSectionHelperGridComponent, - ElementGridChangeListenerDirective, OptionsFieldSetComponent, ActionPropertiesComponent, TextFieldElementPropertiesComponent, @@ -239,7 +233,8 @@ export const myCustomTooltipDefaults: MatTooltipDefaultOptions = { ReferenceListComponent, ElementListComponent, SizeInputPanelComponent, - MeasurePipe + MeasurePipe, + SectionComponent ], providers: [ { provide: APIService, useExisting: VeronaAPIService }, diff --git a/projects/editor/src/app/components/properties-panel/element-properties-panel.component.ts b/projects/editor/src/app/components/properties-panel/element-properties-panel.component.ts index 081ec4b22217d9061578497ade3da956c4e4e722..a00d5bcb4f11ac3857d6e4db0cdaf4378d7e0951 100644 --- a/projects/editor/src/app/components/properties-panel/element-properties-panel.component.ts +++ b/projects/editor/src/app/components/properties-panel/element-properties-panel.component.ts @@ -10,7 +10,7 @@ import { UIElement } from 'common/models/elements/element'; import { LikertRowElement } from 'common/models/elements/compound-elements/likert/likert-row'; import { UnitService } from '../../services/unit-services/unit.service'; import { SelectionService } from '../../services/selection.service'; -import { CanvasElementOverlay } from 'editor/src/app/components/unit-view/canvas/canvas-element-overlay'; +import { CanvasElementOverlay } from 'editor/src/app/components/unit-view/element-overlay/canvas-element-overlay'; import { ElementService } from 'editor/src/app/services/unit-services/element.service'; import { SectionService } from 'editor/src/app/services/unit-services/section.service'; diff --git a/projects/editor/src/app/components/unit-view/canvas/canvas.component.html b/projects/editor/src/app/components/unit-view/canvas/canvas.component.html deleted file mode 100644 index 8924a17a847b4f767bcde0dded7e68dc60390e51..0000000000000000000000000000000000000000 --- a/projects/editor/src/app/components/unit-view/canvas/canvas.component.html +++ /dev/null @@ -1,51 +0,0 @@ -<div class="canvasBackground fx-flex" - (click)="selectionService.clearElementSelection()"> - <div [style.width.px]="page.hasMaxWidth ? page.maxWidth : null" - [style.padding.px]="page.margin" - [style.background-color]="page.backgroundColor"> - <div cdkDropListGroup> - <div *ngFor="let section of page.sections; let i = index" [style.position]="'relative'"> - <aspect-section-menu [class.hidden]="selectionService.selectedSectionIndex !== i" - class="section-menu fx-column-start-stretch" - [style.left.px]="-45" [style.z-index]="1" [style.position]="'absolute'" - [section]="section" [sectionIndex]="i" - [allowMoveUp]="i != 0" - [allowMoveDown]="i < page.sections.length - 1" - [allowDelete]="page.sections.length > 1" - (moveSection)="sectionService.moveSection(section, page, $event)" - (duplicateSection)="sectionService.duplicateSection(section, page, i)" - (selectElementComponent)="selectElementOverlay($event)"> - </aspect-section-menu> - <aspect-section-static *ngIf="!section.dynamicPositioning" - #sectionComponent - class="section drop-list" id="section-{{i}}" - [section]="section" - [isSelected]="selectionService.selectedSectionIndex === i" - (elementSelected)="selectionService.selectedSectionIndex = i" - cdkDropList cdkDropListSortingDisabled - [cdkDropListData]="{ sectionIndex: i }" - (cdkDropListDropped)="elementDropped($event)" - (click)="selectionService.selectedSectionIndex = i"> - </aspect-section-static> - <aspect-section-dynamic *ngIf="section.dynamicPositioning" - #sectionComponent - class="section drop-list" - [section]="section" [sectionIndex]="i" - [isSelected]="selectionService.selectedSectionIndex === i" - [ignoreSectionCounter]="!unitService.unit.enableSectionNumbering || page.alwaysVisible || section.ignoreNumbering" - (elementSelected)="selectionService.selectedSectionIndex = i" - (transferElement)="moveElementsBetweenSections(selectionService.getSelectedElements(), - $event.previousSectionIndex, - $event.newSectionIndex)" - (click)="selectionService.selectedSectionIndex = i"> - </aspect-section-dynamic> - </div> - </div> - </div> - - <button mat-raised-button class="add-section-button" - [style.width.px]="page.hasMaxWidth ? page.maxWidth : null" - (click)="addSection()"> - <mat-icon class="add-section-icon">add</mat-icon> - </button> -</div> diff --git a/projects/editor/src/app/components/unit-view/canvas/canvas.component.ts b/projects/editor/src/app/components/unit-view/canvas/canvas.component.ts deleted file mode 100644 index cf02a923bdd295e7abf7e5dc32ceacb0e674c7cc..0000000000000000000000000000000000000000 --- a/projects/editor/src/app/components/unit-view/canvas/canvas.component.ts +++ /dev/null @@ -1,138 +0,0 @@ -import { - Component, Input, OnDestroy, OnInit, QueryList, ViewChildren -} from '@angular/core'; -import { CdkDragDrop } from '@angular/cdk/drag-drop'; -import { PositionedUIElement, UIElement } from 'common/models/elements/element'; -import { Page } from 'common/models/page'; -import { Section } from 'common/models/section'; -import { UnitService } from '../../../services/unit-services/unit.service'; -import { SelectionService } from '../../../services/selection.service'; -import { CanvasElementOverlay } from './canvas-element-overlay'; -import { SectionStaticComponent } from './section-static/section-static.component'; -import { SectionDynamicComponent } from './section-dynamic/section-dynamic.component'; -import { SectionService } from 'editor/src/app/services/unit-services/section.service'; -import { ElementService } from 'editor/src/app/services/unit-services/element.service'; -import { takeUntil } from 'rxjs/operators'; -import { Subject } from 'rxjs'; - -@Component({ - selector: 'aspect-page-canvas', - templateUrl: './canvas.component.html', - styles: [` - .canvasBackground { - background-color: lightgrey; - padding: 20px 50px; - height: 100%; - overflow: auto; - } - .add-section-icon{ - font-size: 24px; - color: white; - margin-top: -5px; - } - .add-section-button { - width: 100%; - height: 25px; - background-color: #BABABA; - margin-top: 10px; - } - .hidden { - display: none !important; - } - `] - }) -export class CanvasComponent implements OnInit, OnDestroy { - @Input() page!: Page; - @ViewChildren('sectionComponent') - sectionComponents!: QueryList<SectionStaticComponent | SectionDynamicComponent>; - - private ngUnsubscribe = new Subject<void>(); - - constructor(public selectionService: SelectionService, - public unitService: UnitService, - public elementService: ElementService, - public sectionService: SectionService) { } - - ngOnInit(): void { - this.unitService.sectionCountUpdated - .pipe(takeUntil(this.ngUnsubscribe)) - .subscribe( - () => { - this.sectionComponents.toArray() - .filter(comp => comp instanceof SectionDynamicComponent) - .forEach(sectionComp => (sectionComp as SectionDynamicComponent).updateSectionCounter()); - } - ); - } - - moveElementsBetweenSections(elements: UIElement[], previousSectionIndex: number, newSectionIndex: number): void { - this.sectionService.transferElements(elements, - this.page.sections[previousSectionIndex], - this.page.sections[newSectionIndex]); - } - - elementDropped(event: CdkDragDrop<{ sectionIndex: number; gridCoordinates?: number[]; }>): void { - const selectedElements = this.selectionService.getSelectedElements() as PositionedUIElement[]; - - if (event.previousContainer !== event.container) { - this.moveElementsBetweenSections(selectedElements, - event.previousContainer.data.sectionIndex, - event.container.data.sectionIndex); - } else { - selectedElements.forEach((element: PositionedUIElement) => { - let newXPosition = element.position.xPosition + event.distance.x; - if (newXPosition < 0) { - newXPosition = 0; - } - if (this.page.hasMaxWidth && newXPosition > this.page.maxWidth - element.dimensions.width) { - newXPosition = this.page.maxWidth - element.dimensions.width; - } - this.elementService.updateElementsPositionProperty([element], 'xPosition', newXPosition); - - let newYPosition = element.position.yPosition + event.distance.y; - if (newYPosition < 0) { - newYPosition = 0; - } - if (newYPosition > this.getPageHeight() - element.dimensions.height) { - newYPosition = this.getPageHeight() - element.dimensions.height; - } - this.elementService.updateElementsPositionProperty([element], 'yPosition', newYPosition); - }); - } - } - - getPageHeight(): number { // TODO weg - const reduceFct = (accumulator: number, currentValue: Section) => accumulator + currentValue.height; - return this.page.sections.reduce(reduceFct, 0); - } - - addSection(): void { - this.sectionService.addSection(this.page); - this.selectionService.selectedSectionIndex = this.page.sections.length - 1; - } - - selectElementOverlay(element: UIElement): void { - const elementComponent = this.getElementOverlay(element); - if (elementComponent) { - this.selectionService.selectElement({ elementComponent: elementComponent, multiSelect: false }); - } else { - throw Error('Element not found. This is a bug!'); - } - } - - private getElementOverlay(element: UIElement): CanvasElementOverlay | null { - for (const sectionComponent of this.sectionComponents.toArray()) { - for (const elementComponent of sectionComponent.childElementComponents.toArray()) { - if (elementComponent.element.id === element.id) { - return elementComponent; - } - } - } - return null; - } - - ngOnDestroy(): void { - this.ngUnsubscribe.next(); - this.ngUnsubscribe.complete(); - } -} diff --git a/projects/editor/src/app/components/unit-view/canvas/section-dynamic/section-dynamic.component.ts b/projects/editor/src/app/components/unit-view/canvas/section-dynamic/section-dynamic.component.ts deleted file mode 100644 index 8e98e666d5b913ac6b837394386f31cabcdce03e..0000000000000000000000000000000000000000 --- a/projects/editor/src/app/components/unit-view/canvas/section-dynamic/section-dynamic.component.ts +++ /dev/null @@ -1,107 +0,0 @@ -import { - Component, Input, Output, EventEmitter, - ViewChildren, QueryList, ViewChild, OnInit -} from '@angular/core'; -import { Section } from 'common/models/section'; -import { SectionCounter } from 'common/util/section-counter'; -import { UnitService } from 'editor/src/app/services/unit-services/unit.service'; -import { DragNDropService } from 'editor/src/app/services/drag-n-drop.service'; -import { CanvasElementOverlay } from '../canvas-element-overlay'; -import { DynamicSectionHelperGridComponent } from './dynamic-section-helper-grid.component'; - -@Component({ - selector: 'aspect-section-dynamic', - template: ` - <div class="section-wrapper" - [ngClass]="unitService.unit.sectionNumberingPosition === 'left' ? 'row-align' : 'column-align'"> - <div *ngIf="unitService.unit.enableSectionNumbering" [style.min-width.px]="35" [style.font-size.px]="20"> - <b *ngIf="sectionCounter">{{sectionCounter}}.</b> - </div> - <div [style.display]="'grid'" - [style.flex-grow]="1" - [style.grid-template-columns]="section.autoColumnSize ? '' : section.gridColumnSizes | measure" - [style.grid-template-rows]="section.autoRowSize ? '' : section.gridRowSizes | measure" - [style.grid-auto-columns]="'auto'" - [style.grid-auto-rows]="'auto'" - [style.border]="isSelected ? '2px solid #ff4081': '1px dotted'" - [style.min-height.px]="section.autoRowSize ? 50 : null" - [style.height.px]="section.autoRowSize ? null : section.height" - [style.background-color]="section.backgroundColor" - app-dynamic-section-helper-grid - [autoColumnSize]="section.autoColumnSize" - [autoRowSize]="section.autoRowSize" - [gridColumnSizes]="section.gridColumnSizes" - [gridRowSizes]="section.gridRowSizes" - [section]="section" - [sectionIndex]="sectionIndex" - [style.isolation]="'isolate'" - (transferElement)="transferElement.emit($event)"> - - <!-- Angular content projection is used in the helper grid component, where the following - is the content.--> - <aspect-dynamic-canvas-overlay *ngFor="let element of section.elements" - #elementComponent - [style.z-index]="element.position.zIndex" - [element]="$any(element)" - [style.margin-left]="[element.position.marginLeft] | measure" - [style.margin-right]="[element.position.marginRight] | measure" - [style.margin-top]="[element.position.marginTop] | measure" - [style.margin-bottom]="[element.position.marginBottom] | measure" - [style.grid-column-start]="element.position.gridColumn" - [style.grid-column-end]="element.position.gridColumn ? - element.position.gridColumn + element.position.gridColumnRange : - null" - [style.grid-row-start]="element.position.gridRow" - [style.grid-row-end]="element.position.gridRow ? - element.position.gridRow + element.position.gridRowRange : - null" - cdkDropList cdkDropListSortingDisabled - [cdkDropListData]="{ sectionIndex: sectionIndex }" - [cdkDropListConnectedTo]="dropListList" - [style.position]="'relative'" - [style.pointer-events]="dragNDropService.isDragInProgress && - element.type == 'frame' ? - 'none' : 'auto'" - appElementGridChangeListener - [gridColumn]="element.position.gridColumn" - [gridColumnRange]="element.position.gridColumnRange" - [gridRow]="element.position.gridRow" - [gridRowRange]="element.position.gridRowRange" - [style.align-items]="'baseline'" - (elementSelected)="elementSelected.emit()" - (elementChanged)="helperGrid && helperGrid.refresh()"> - </aspect-dynamic-canvas-overlay> - </div> - </div> - `, - styles: ` - .section-wrapper {display: flex;} - .section-wrapper.row-align {flex-direction: row; align-items: baseline;} - .section-wrapper.column-align {flex-direction: column;} - ` -}) -export class SectionDynamicComponent implements OnInit { - @Input() section!: Section; - @Input() sectionIndex!: number; - @Input() dropListList!: string[]; - @Input() isSelected!: boolean; - @Input() ignoreSectionCounter: boolean = true; - @Output() transferElement = new EventEmitter<{ previousSectionIndex: number, newSectionIndex: number }>(); - @Output() elementSelected = new EventEmitter(); - - @ViewChild(DynamicSectionHelperGridComponent) helperGrid!: DynamicSectionHelperGridComponent; - @ViewChildren('elementComponent') childElementComponents!: QueryList<CanvasElementOverlay>; - - sectionCounter: number | undefined; - - constructor(protected dragNDropService: DragNDropService, protected unitService: UnitService) { } - - ngOnInit(): void { - this.updateSectionCounter(); - } - - updateSectionCounter(): void { - this.sectionCounter = undefined; - if (!this.ignoreSectionCounter) this.sectionCounter = SectionCounter.getNext(); - } -} diff --git a/projects/editor/src/app/components/unit-view/canvas/canvas-element-overlay.ts b/projects/editor/src/app/components/unit-view/element-overlay/canvas-element-overlay.ts similarity index 100% rename from projects/editor/src/app/components/unit-view/canvas/canvas-element-overlay.ts rename to projects/editor/src/app/components/unit-view/element-overlay/canvas-element-overlay.ts diff --git a/projects/editor/src/app/components/unit-view/canvas/section-dynamic/dynamic-canvas-overlay.component.ts b/projects/editor/src/app/components/unit-view/element-overlay/dynamic-canvas-overlay.component.ts similarity index 92% rename from projects/editor/src/app/components/unit-view/canvas/section-dynamic/dynamic-canvas-overlay.component.ts rename to projects/editor/src/app/components/unit-view/element-overlay/dynamic-canvas-overlay.component.ts index 4f86147aa2745137ee11044ed17394107a99b2bf..9a6853574c37ee9602d1a66ef914fc5d2246a262 100644 --- a/projects/editor/src/app/components/unit-view/canvas/section-dynamic/dynamic-canvas-overlay.component.ts +++ b/projects/editor/src/app/components/unit-view/element-overlay/dynamic-canvas-overlay.component.ts @@ -1,10 +1,16 @@ import { - Component, Input, ViewChild, ElementRef + Component, Input } from '@angular/core'; -import { CanvasElementOverlay } from '../canvas-element-overlay'; +import { CanvasElementOverlay } from './canvas-element-overlay'; +import { CdkDrag, CdkDragPlaceholder } from '@angular/cdk/drag-drop'; @Component({ selector: 'aspect-dynamic-canvas-overlay', + standalone: true, + imports: [ + CdkDrag, + CdkDragPlaceholder + ], template: ` <!-- TabIndex is needed to make the div selectable and catch keyboard events (delete). --> <!-- DragStart and DragEnd are part of a cursor hack to style the body. See global styling file. --> diff --git a/projects/editor/src/app/components/unit-view/canvas/section-static/static-canvas-overlay.component.ts b/projects/editor/src/app/components/unit-view/element-overlay/static-canvas-overlay.component.ts similarity index 89% rename from projects/editor/src/app/components/unit-view/canvas/section-static/static-canvas-overlay.component.ts rename to projects/editor/src/app/components/unit-view/element-overlay/static-canvas-overlay.component.ts index abc7df7f187975383db6b31a9be2c1631540adac..92badf60d3d26079bd8a88870d43a62d3880d5b2 100644 --- a/projects/editor/src/app/components/unit-view/canvas/section-static/static-canvas-overlay.component.ts +++ b/projects/editor/src/app/components/unit-view/element-overlay/static-canvas-overlay.component.ts @@ -1,11 +1,21 @@ import { Component } from '@angular/core'; import { take } from 'rxjs/operators'; -import { CdkDragEnd, CdkDragMove } from '@angular/cdk/drag-drop'; +import { CdkDrag, CdkDragEnd, CdkDragMove, CdkDragPlaceholder, CdkDropList } from '@angular/cdk/drag-drop'; import { UIElement } from 'common/models/elements/element'; -import { CanvasElementOverlay } from '../canvas-element-overlay'; +import { CanvasElementOverlay } from './canvas-element-overlay'; +import { NgIf } from '@angular/common'; +import { MatIconModule } from '@angular/material/icon'; @Component({ selector: 'aspect-static-canvas-overlay', + standalone: true, + imports: [ + NgIf, + CdkDrag, + CdkDropList, + CdkDragPlaceholder, + MatIconModule + ], template: ` <!-- Is also a droplist to catch the resize drop and not let it bubble up to the canvas drop handler. --> <!-- TabIndex is needed to make the div selectable and catch keyboard events (delete). --> diff --git a/projects/editor/src/app/components/unit-view/page/canvas.component.html b/projects/editor/src/app/components/unit-view/page/canvas.component.html new file mode 100644 index 0000000000000000000000000000000000000000..12da6937e22def6aeb030870bc69b5db8d5445ad --- /dev/null +++ b/projects/editor/src/app/components/unit-view/page/canvas.component.html @@ -0,0 +1,21 @@ +<div class="canvasBackground fx-flex" + (click)="selectionService.clearElementSelection()"> + <div [style.width.px]="page.hasMaxWidth ? page.maxWidth : null" + [style.padding.px]="page.margin" + [style.background-color]="page.backgroundColor"> + <div cdkDropListGroup> + <div *ngFor="let section of page.sections; let i = index" [style.position]="'relative'"> + <aspect-editor-section [section]="section" + [sectionIndex]="i" [lastSectionIndex]="page.sections.length - 1" + [alwaysVisiblePage]="page.alwaysVisible"> + </aspect-editor-section> + </div> + </div> + </div> + + <button mat-raised-button class="add-section-button" + [style.width.px]="page.hasMaxWidth ? page.maxWidth : null" + (click)="addSection()"> + <mat-icon class="add-section-icon">add</mat-icon> + </button> +</div> diff --git a/projects/editor/src/app/components/unit-view/page/canvas.component.ts b/projects/editor/src/app/components/unit-view/page/canvas.component.ts new file mode 100644 index 0000000000000000000000000000000000000000..25e851ca499ba3fe08d2fab72c049ac400b2259e --- /dev/null +++ b/projects/editor/src/app/components/unit-view/page/canvas.component.ts @@ -0,0 +1,75 @@ +import { + Component, Input, OnDestroy, OnInit, QueryList, ViewChildren +} from '@angular/core'; +import { CdkDragDrop } from '@angular/cdk/drag-drop'; +import { PositionedUIElement, UIElement } from 'common/models/elements/element'; +import { Page } from 'common/models/page'; +import { Section } from 'common/models/section'; +import { UnitService } from '../../../services/unit-services/unit.service'; +import { SelectionService } from '../../../services/selection.service'; +import { CanvasElementOverlay } from 'editor/src/app/components/unit-view/element-overlay/canvas-element-overlay'; +import { SectionStaticComponent } from 'editor/src/app/components/unit-view/section/section-static.component'; +import { SectionDynamicComponent } from 'editor/src/app/components/unit-view/section/section-dynamic.component'; +import { SectionService } from 'editor/src/app/services/unit-services/section.service'; +import { ElementService } from 'editor/src/app/services/unit-services/element.service'; +import { takeUntil } from 'rxjs/operators'; +import { Subject } from 'rxjs'; +import { SectionComponent } from 'editor/src/app/components/unit-view/section/section.component'; + +@Component({ + selector: 'aspect-page-canvas', + templateUrl: './canvas.component.html', + styles: [` + .canvasBackground { + background-color: lightgrey; + padding: 20px 50px; + height: 100%; + overflow: auto; + } + .add-section-icon{ + font-size: 24px; + color: white; + margin-top: -5px; + } + .add-section-button { + width: 100%; + height: 25px; + background-color: #BABABA; + margin-top: 10px; + } + `] + }) +export class CanvasComponent implements OnInit, OnDestroy { + @Input() page!: Page; + @ViewChildren(SectionComponent) sectionComponents!: QueryList<SectionComponent>; + + private ngUnsubscribe = new Subject<void>(); + + constructor(public selectionService: SelectionService, + public unitService: UnitService, + public elementService: ElementService, + public sectionService: SectionService) { } + + ngOnInit(): void { + this.unitService.sectionCountUpdated + .pipe(takeUntil(this.ngUnsubscribe)) + .subscribe( + () => { + this.sectionComponents.toArray() + .forEach(sectionComp => { + sectionComp.updateSectionCounter(); + }); + } + ); + } + + addSection(): void { + this.sectionService.addSection(this.page); + this.selectionService.selectedSectionIndex = this.page.sections.length - 1; + } + + ngOnDestroy(): void { + this.ngUnsubscribe.next(); + this.ngUnsubscribe.complete(); + } +} diff --git a/projects/editor/src/app/components/unit-view/canvas/section-menu.component.ts b/projects/editor/src/app/components/unit-view/page/section-menu.component.ts similarity index 88% rename from projects/editor/src/app/components/unit-view/canvas/section-menu.component.ts rename to projects/editor/src/app/components/unit-view/page/section-menu.component.ts index 0cf1f307f696354382e2f35f069319805b260b65..b14da9c3e409039d85b584201888db8af81e5d49 100644 --- a/projects/editor/src/app/components/unit-view/canvas/section-menu.component.ts +++ b/projects/editor/src/app/components/unit-view/page/section-menu.component.ts @@ -10,14 +10,39 @@ import { Section } from 'common/models/section'; import { DropListElement } from 'common/models/elements/input-elements/drop-list'; import { IDService } from 'editor/src/app/services/id.service'; import { VisibilityRule } from 'common/models/visibility-rule'; -import { ReferenceManager } from 'editor/src/app/services/reference-manager'; import { UnitService } from '../../../services/unit-services/unit.service'; import { DialogService } from '../../../services/dialog.service'; import { SelectionService } from '../../../services/selection.service'; import { SectionService } from 'editor/src/app/services/unit-services/section.service'; +import { MatMenuModule } from '@angular/material/menu'; +import { MatIconModule } from '@angular/material/icon'; +import { MatTooltipModule } from '@angular/material/tooltip'; +import { MatListModule } from '@angular/material/list'; +import { MatButtonModule } from '@angular/material/button'; +import { TranslateModule } from '@ngx-translate/core'; +import { MatCheckboxModule } from '@angular/material/checkbox'; +import { MatFormFieldModule } from '@angular/material/form-field'; +import { NgForOf, NgIf } from '@angular/common'; +import { MatInputModule } from '@angular/material/input'; +import { SizeInputPanelComponent } from 'editor/src/app/components/util/size-input-panel.component'; @Component({ selector: 'aspect-section-menu', + standalone: true, + imports: [ + MatMenuModule, + MatIconModule, + MatTooltipModule, + MatListModule, + MatButtonModule, + TranslateModule, + MatCheckboxModule, + MatFormFieldModule, + NgIf, + MatInputModule, + SizeInputPanelComponent, + NgForOf + ], template: ` <button mat-mini-fab [matMenuTriggerFor]="elementListMenu" [matTooltip]="'Elementliste'" @@ -44,16 +69,15 @@ import { SectionService } from 'editor/src/app/services/unit-services/section.se [value]="$any(section.backgroundColor)" (change)="updateModel('backgroundColor', $any($event.target).value)"> - <button mat-mini-fab [color]="section.ignoreNumbering ? 'primary' : 'accent'" (click)="ignoreNumbering()" [matTooltip]="'Von der Nummerierung ausnehmen'" [matTooltipPosition]="'left'"> <svg xmlns="http://www.w3.org/2000/svg" height="24px" viewBox="0 -960 960 960" width="24px" fill="white"> - <path d="m576-80-56-56 104-104-104-104 56-56 104 104 104-104 56 56-104 104 104 104-56 56-104-104L576-80ZM120-320v-80h280v80H120Zm0-160v-80h440v80H120Zm0-160v-80h440v80H120Z"/> + <path d="m576-80-56-56 104-104-104-104 56-56 104 104 104-104 56 56-104 104 104 104-56 + 56-104-104L576-80ZM120-320v-80h280v80H120Zm0-160v-80h440v80H120Zm0-160v-80h440v80H120Z"/> </svg> </button> - <button mat-mini-fab (click)="showVisibilityRulesDialog()" [matTooltip]="'Sichtbarkeit'" [matTooltipPosition]="'left'"> @@ -152,21 +176,21 @@ import { SectionService } from 'editor/src/app/services/unit-services/section.se (click)="showSectionInsertDialog()"> <mat-icon>content_paste</mat-icon> </button> - <button *ngIf="allowMoveUp" mat-mini-fab + <button *ngIf="sectionIndex !== 0" mat-mini-fab [matTooltip]="'Nach oben verschieben'" [matTooltipPosition]="'left'" - (click)="this.moveSection.emit('up')"> + (click)="this.moveSection('up')"> <mat-icon>north</mat-icon> </button> - <button *ngIf="allowMoveDown" mat-mini-fab + <button *ngIf="sectionIndex < lastSectionIndex" mat-mini-fab [matTooltip]="'Nach unten verschieben'" [matTooltipPosition]="'left'" - (click)="this.moveSection.emit('down')"> + (click)="this.moveSection('down')"> <mat-icon>south</mat-icon> </button> <button mat-mini-fab [matTooltip]="'Duplizieren'" [matTooltipPosition]="'left'" - (click)="duplicateSection.emit()"> + (click)="duplicateSection()"> <mat-icon>control_point_duplicate</mat-icon> </button> - <button *ngIf="allowDelete" mat-mini-fab + <button *ngIf="lastSectionIndex > 0" mat-mini-fab [matTooltip]="'Löschen'" [matTooltipPosition]="'left'" (click)="deleteSection()"> <mat-icon>clear</mat-icon> @@ -183,11 +207,7 @@ import { SectionService } from 'editor/src/app/services/unit-services/section.se export class SectionMenuComponent implements OnDestroy { @Input() section!: Section; @Input() sectionIndex!: number; - @Input() allowMoveUp!: boolean; - @Input() allowMoveDown!: boolean; - @Input() allowDelete!: boolean; - @Output() moveSection = new EventEmitter<'up' | 'down'>(); - @Output() duplicateSection = new EventEmitter(); + @Input() lastSectionIndex!: number; @Output() selectElementComponent = new EventEmitter<UIElement>(); @ViewChild('colorPicker') colorPicker!: ElementRef; @@ -312,4 +332,12 @@ export class SectionMenuComponent implements OnDestroy { ignoreNumbering() { this.updateModel('ignoreNumbering', !this.section.ignoreNumbering); } + + moveSection(direction: 'up' | 'down') { + this.sectionService.moveSection(this.section, direction); + } + + duplicateSection() { + this.sectionService.duplicateSection(this.section, this.sectionIndex); + } } diff --git a/projects/editor/src/app/components/unit-view/canvas/section-dynamic/dynamic-section-helper-grid.component.ts b/projects/editor/src/app/components/unit-view/section/dynamic-section-helper-grid.component.ts similarity index 95% rename from projects/editor/src/app/components/unit-view/canvas/section-dynamic/dynamic-section-helper-grid.component.ts rename to projects/editor/src/app/components/unit-view/section/dynamic-section-helper-grid.component.ts index b7154058e743fd2af487fa71254b448dafefcf3f..4943fd7f366e5b77425183550793fd96394a2d5b 100644 --- a/projects/editor/src/app/components/unit-view/canvas/section-dynamic/dynamic-section-helper-grid.component.ts +++ b/projects/editor/src/app/components/unit-view/section/dynamic-section-helper-grid.component.ts @@ -1,14 +1,20 @@ -import { CdkDragDrop } from '@angular/cdk/drag-drop'; +import { CdkDragDrop, CdkDropList } from '@angular/cdk/drag-drop'; import { Component, EventEmitter, Input, OnChanges, OnInit, Output, SimpleChanges } from '@angular/core'; import { UIElement, UIElementType } from 'common/models/elements/element'; import { Section } from 'common/models/section'; -import { UnitService } from '../../../../services/unit-services/unit.service'; +import { UnitService } from '../../../services/unit-services/unit.service'; import { ElementService } from 'editor/src/app/services/unit-services/element.service'; +import { NgForOf } from '@angular/common'; @Component({ selector: '[app-dynamic-section-helper-grid]', + standalone: true, + imports: [ + NgForOf, + CdkDropList + ], template: ` <ng-container *ngFor="let row of rowCountArray; let x = index;"> <ng-container *ngFor="let column of columnCountArray; let y = index;"> diff --git a/projects/editor/src/app/components/unit-view/canvas/section-dynamic/element-grid-change-listener.directive.ts b/projects/editor/src/app/components/unit-view/section/element-grid-change-listener.directive.ts similarity index 87% rename from projects/editor/src/app/components/unit-view/canvas/section-dynamic/element-grid-change-listener.directive.ts rename to projects/editor/src/app/components/unit-view/section/element-grid-change-listener.directive.ts index ef78ffcb6bc10ff08d6180c0ef17f5c82b9859ae..d29a7932062d646b4cdb5cfeeba1d76738a8cbd8 100644 --- a/projects/editor/src/app/components/unit-view/canvas/section-dynamic/element-grid-change-listener.directive.ts +++ b/projects/editor/src/app/components/unit-view/section/element-grid-change-listener.directive.ts @@ -3,7 +3,8 @@ import { } from '@angular/core'; @Directive({ - selector: '[appElementGridChangeListener]' + selector: '[appElementGridChangeListener]', + standalone: true }) export class ElementGridChangeListenerDirective implements OnChanges { @Input() autoColumnSize!: boolean; diff --git a/projects/editor/src/app/components/unit-view/section/section-dynamic.component.ts b/projects/editor/src/app/components/unit-view/section/section-dynamic.component.ts new file mode 100644 index 0000000000000000000000000000000000000000..c7371d9885a4d8693b9a6fffb22f1d6f673fb555 --- /dev/null +++ b/projects/editor/src/app/components/unit-view/section/section-dynamic.component.ts @@ -0,0 +1,104 @@ +import { + Component, Input, Output, EventEmitter, + ViewChildren, QueryList, ViewChild, OnInit +} from '@angular/core'; +import { Section } from 'common/models/section'; +import { DragNDropService } from 'editor/src/app/services/drag-n-drop.service'; +import { CanvasElementOverlay } from 'editor/src/app/components/unit-view/element-overlay/canvas-element-overlay'; +import { DynamicSectionHelperGridComponent } from './dynamic-section-helper-grid.component'; +import { NgClass, NgForOf, NgIf } from '@angular/common'; +import { MeasurePipe } from 'common/pipes/measure.pipe'; +import { + DynamicCanvasOverlayComponent +} from 'editor/src/app/components/unit-view/element-overlay/dynamic-canvas-overlay.component'; +import { CdkDropList } from '@angular/cdk/drag-drop'; +import { + ElementGridChangeListenerDirective +} from 'editor/src/app/components/unit-view/section/element-grid-change-listener.directive'; + +@Component({ + selector: 'aspect-section-dynamic', + standalone: true, + imports: [ + NgClass, + NgIf, + MeasurePipe, + DynamicSectionHelperGridComponent, + DynamicCanvasOverlayComponent, + NgForOf, + CdkDropList, + ElementGridChangeListenerDirective + ], + template: ` + <div [style.display]="'grid'" + [style.grid-template-columns]="section.autoColumnSize ? '' : section.gridColumnSizes | measure" + [style.grid-template-rows]="section.autoRowSize ? '' : section.gridRowSizes | measure" + [style.grid-auto-columns]="'auto'" + [style.grid-auto-rows]="'auto'" + [style.border]="isSelected ? '2px solid #ff4081': '1px dotted'" + [style.min-height.px]="section.autoRowSize ? 50 : null" + [style.height.px]="section.autoRowSize ? null : section.height" + [style.background-color]="section.backgroundColor" + app-dynamic-section-helper-grid + [autoColumnSize]="section.autoColumnSize" + [autoRowSize]="section.autoRowSize" + [gridColumnSizes]="section.gridColumnSizes" + [gridRowSizes]="section.gridRowSizes" + [section]="section" + [sectionIndex]="sectionIndex" + [style.isolation]="'isolate'" + (transferElement)="transferElement.emit($event)"> + + <!-- Angular content projection is used in the helper grid component, where the following + is the content.--> + <aspect-dynamic-canvas-overlay *ngFor="let element of section.elements" + #elementComponent + [style.z-index]="element.position.zIndex" + [element]="$any(element)" + [style.margin-left]="[element.position.marginLeft] | measure" + [style.margin-right]="[element.position.marginRight] | measure" + [style.margin-top]="[element.position.marginTop] | measure" + [style.margin-bottom]="[element.position.marginBottom] | measure" + [style.grid-column-start]="element.position.gridColumn" + [style.grid-column-end]="element.position.gridColumn ? + element.position.gridColumn + element.position.gridColumnRange : + null" + [style.grid-row-start]="element.position.gridRow" + [style.grid-row-end]="element.position.gridRow ? + element.position.gridRow + element.position.gridRowRange : + null" + cdkDropList cdkDropListSortingDisabled + [cdkDropListData]="{ sectionIndex: sectionIndex }" + [cdkDropListConnectedTo]="dropListList" + [style.position]="'relative'" + [style.pointer-events]="dragNDropService.isDragInProgress && + element.type == 'frame' ? + 'none' : 'auto'" + appElementGridChangeListener + [gridColumn]="element.position.gridColumn" + [gridColumnRange]="element.position.gridColumnRange" + [gridRow]="element.position.gridRow" + [gridRowRange]="element.position.gridRowRange" + [style.align-items]="'baseline'" + (elementSelected)="elementSelected.emit()" + (elementChanged)="helperGrid && helperGrid.refresh()"> + </aspect-dynamic-canvas-overlay> + </div> + `, + styles: ` + + ` +}) +export class SectionDynamicComponent { + @Input() section!: Section; + @Input() sectionIndex!: number; + @Input() dropListList!: string[]; + @Input() isSelected!: boolean; + @Output() transferElement = new EventEmitter<{ previousSectionIndex: number, newSectionIndex: number }>(); + @Output() elementSelected = new EventEmitter(); + + @ViewChild(DynamicSectionHelperGridComponent) helperGrid!: DynamicSectionHelperGridComponent; + @ViewChildren('elementComponent') childElementComponents!: QueryList<CanvasElementOverlay>; + + constructor(protected dragNDropService: DragNDropService) { } +} diff --git a/projects/editor/src/app/components/unit-view/canvas/section-static/section-static.component.ts b/projects/editor/src/app/components/unit-view/section/section-static.component.ts similarity index 81% rename from projects/editor/src/app/components/unit-view/canvas/section-static/section-static.component.ts rename to projects/editor/src/app/components/unit-view/section/section-static.component.ts index e583b11905560f29944c4ed7865f0ac615c039ce..69e348e13bb81a93dbb918891ac5130021b9083f 100644 --- a/projects/editor/src/app/components/unit-view/canvas/section-static/section-static.component.ts +++ b/projects/editor/src/app/components/unit-view/section/section-static.component.ts @@ -3,12 +3,21 @@ import { } from '@angular/core'; import { Section } from 'common/models/section'; import { UIElementType } from 'common/models/elements/element'; -import { UnitService } from '../../../../services/unit-services/unit.service'; -import { CanvasElementOverlay } from '../canvas-element-overlay'; +import { UnitService } from '../../../services/unit-services/unit.service'; +import { CanvasElementOverlay } from 'editor/src/app/components/unit-view/element-overlay/canvas-element-overlay'; import { ElementService } from 'editor/src/app/services/unit-services/element.service'; +import { + StaticCanvasOverlayComponent +} from 'editor/src/app/components/unit-view/element-overlay/static-canvas-overlay.component'; +import { NgForOf } from '@angular/common'; @Component({ selector: 'aspect-section-static', + standalone: true, + imports: [ + NgForOf, + StaticCanvasOverlayComponent + ], template: ` <div #sectionElement class="section-wrapper" [style.outline]="isSelected ? '2px solid #ff4081': '1px dotted'" diff --git a/projects/editor/src/app/components/unit-view/section/section.component.ts b/projects/editor/src/app/components/unit-view/section/section.component.ts new file mode 100644 index 0000000000000000000000000000000000000000..e9fce130e94a569753945c7eb03e4238c3e617d5 --- /dev/null +++ b/projects/editor/src/app/components/unit-view/section/section.component.ts @@ -0,0 +1,167 @@ +import { + Component, Input, OnInit, QueryList, ViewChildren +} from '@angular/core'; +import { SectionMenuComponent } from 'editor/src/app/components/unit-view/page/section-menu.component'; +import { SelectionService } from 'editor/src/app/services/selection.service'; +import { UnitService } from 'editor/src/app/services/unit-services/unit.service'; +import { ElementService } from 'editor/src/app/services/unit-services/element.service'; +import { SectionService } from 'editor/src/app/services/unit-services/section.service'; +import { Section } from 'common/models/section'; +import { PositionedUIElement, UIElement } from 'common/models/elements/element'; +import { CanvasElementOverlay } from 'editor/src/app/components/unit-view/element-overlay/canvas-element-overlay'; +import { SectionStaticComponent } from 'editor/src/app/components/unit-view/section/section-static.component'; +import { SectionDynamicComponent } from 'editor/src/app/components/unit-view/section/section-dynamic.component'; +import { CdkDragDrop, CdkDropList } from '@angular/cdk/drag-drop'; +import { NgClass, NgIf } from '@angular/common'; +import { SectionCounter } from 'common/util/section-counter'; + +@Component({ + selector: 'aspect-editor-section', + standalone: true, + imports: [ + NgIf, NgClass, + CdkDropList, + SectionMenuComponent, SectionStaticComponent, SectionDynamicComponent + ], + template: ` + <aspect-section-menu [class.hidden]="selectionService.selectedSectionIndex !== sectionIndex" + class="section-menu fx-column-start-stretch" + [style.left.px]="-45" [style.z-index]="1" [style.position]="'absolute'" + [section]="section" [sectionIndex]="sectionIndex" + [lastSectionIndex]="lastSectionIndex" + (selectElementComponent)="selectElementOverlay($event)"> + </aspect-section-menu> + + <div class="section-wrapper" + [ngClass]="unitService.unit.sectionNumberingPosition === 'left' ? 'row-align' : 'column-align'"> + <div *ngIf="unitService.unit.enableSectionNumbering" class="numbering-box"> + <b *ngIf="sectionCounter">{{sectionCounter}}.</b> + </div> + <aspect-section-static *ngIf="!section.dynamicPositioning" + #sectionComponent + class="section" id="section-{{sectionIndex}}" + [section]="section" + [isSelected]="selectionService.selectedSectionIndex === sectionIndex" + (elementSelected)="selectionService.selectedSectionIndex = sectionIndex" + cdkDropList cdkDropListSortingDisabled + [cdkDropListData]="{ sectionIndex: sectionIndex }" + (cdkDropListDropped)="elementDropped($event)" + (click)="selectionService.selectedSectionIndex = sectionIndex"> + </aspect-section-static> + <aspect-section-dynamic *ngIf="section.dynamicPositioning" + #sectionComponent + class="section" + [section]="section" [sectionIndex]="sectionIndex" + [isSelected]="selectionService.selectedSectionIndex === sectionIndex" + (elementSelected)="selectionService.selectedSectionIndex = sectionIndex" + (transferElement)="moveElementsBetweenSections(selectionService.getSelectedElements(), + $event.previousSectionIndex, + $event.newSectionIndex)" + (click)="selectionService.selectedSectionIndex = sectionIndex"> + </aspect-section-dynamic> + </div> + `, + styles: ` + .hidden { + display: none !important; + } + .section-wrapper {display: flex;} + .section-wrapper.row-align {flex-direction: row;} + .section-wrapper.column-align {flex-direction: column;} + .section-wrapper .numbering-box {min-width: 35px; font-size: 20px; padding-top: 1px;} + .section-wrapper .section {flex-grow: 1;} + ` +}) +export class SectionComponent implements OnInit { + @Input() section!: Section; + @Input() sectionIndex!: number; + @Input() lastSectionIndex!: number; + @Input() alwaysVisiblePage: boolean = false; + + @ViewChildren('sectionComponent') + sectionComponents!: QueryList<SectionStaticComponent | SectionDynamicComponent>; + + sectionCounter: number | undefined; + + constructor(public selectionService: SelectionService, + public unitService: UnitService, + public elementService: ElementService, + public sectionService: SectionService) { } + + ngOnInit(): void { + this.updateSectionCounter(); + } + + updateSectionCounter(): void { + this.sectionCounter = undefined; + if (this.unitService.unit.enableSectionNumbering && + !this.alwaysVisiblePage && + !this.section.ignoreNumbering) { + this.sectionCounter = SectionCounter.getNext(); + } + } + + selectElementOverlay(element: UIElement): void { + const elementComponent = this.getElementOverlay(element); + if (elementComponent) { + this.selectionService.selectElement({ elementComponent: elementComponent, multiSelect: false }); + } else { + throw Error('Element not found. This is a bug!'); + } + } + + private getElementOverlay(element: UIElement): CanvasElementOverlay | null { + for (const sectionComponent of this.sectionComponents.toArray()) { + for (const elementComponent of sectionComponent.childElementComponents.toArray()) { + if (elementComponent.element.id === element.id) { + return elementComponent; + } + } + } + return null; + } + + elementDropped(event: CdkDragDrop<{ sectionIndex: number; gridCoordinates?: number[]; }>): void { + const selectedElements = this.selectionService.getSelectedElements() as PositionedUIElement[]; + + if (event.previousContainer !== event.container) { + this.moveElementsBetweenSections(selectedElements, + event.previousContainer.data.sectionIndex, + event.container.data.sectionIndex); + } else { + const page = this.unitService.getSelectedPage(); + selectedElements.forEach((element: PositionedUIElement) => { + let newXPosition = element.position.xPosition + event.distance.x; + if (newXPosition < 0) { + newXPosition = 0; + } + if (page.hasMaxWidth && newXPosition > page.maxWidth - element.dimensions.width) { + newXPosition = page.maxWidth - element.dimensions.width; + } + this.elementService.updateElementsPositionProperty([element], 'xPosition', newXPosition); + + let newYPosition = element.position.yPosition + event.distance.y; + if (newYPosition < 0) { + newYPosition = 0; + } + if (newYPosition > this.getPageHeight() - element.dimensions.height) { + newYPosition = this.getPageHeight() - element.dimensions.height; + } + this.elementService.updateElementsPositionProperty([element], 'yPosition', newYPosition); + }); + } + } + + getPageHeight(): number { // TODO weg + const page = this.unitService.getSelectedPage(); + const reduceFct = (accumulator: number, currentValue: Section) => accumulator + currentValue.height; + return page.sections.reduce(reduceFct, 0); + } + + moveElementsBetweenSections(elements: UIElement[], previousSectionIndex: number, newSectionIndex: number): void { + const page = this.unitService.getSelectedPage(); + this.sectionService.transferElements(elements, + page.sections[previousSectionIndex], + page.sections[newSectionIndex]); + } +} diff --git a/projects/editor/src/app/services/selection.service.ts b/projects/editor/src/app/services/selection.service.ts index 5e906109a86fc10912526620e39820a2e1f82426..f453330c32f66716816aeacce670fe492a727812 100644 --- a/projects/editor/src/app/services/selection.service.ts +++ b/projects/editor/src/app/services/selection.service.ts @@ -1,7 +1,7 @@ import { Injectable } from '@angular/core'; import { BehaviorSubject, Observable } from 'rxjs'; import { UIElement } from 'common/models/elements/element'; -import { CanvasElementOverlay } from 'editor/src/app/components/unit-view/canvas/canvas-element-overlay'; +import { CanvasElementOverlay } from 'editor/src/app/components/unit-view/element-overlay/canvas-element-overlay'; import { ClozeChildOverlay } from 'common/components/compound-elements/cloze/cloze-child-overlay.component'; diff --git a/projects/editor/src/app/services/unit-services/section.service.ts b/projects/editor/src/app/services/unit-services/section.service.ts index 63c317ee51c253547b8a6e0b793e65980b11fbbb..1224b7e334087fe0b3af0b229407f6260e1173f2 100644 --- a/projects/editor/src/app/services/unit-services/section.service.ts +++ b/projects/editor/src/app/services/unit-services/section.service.ts @@ -87,7 +87,8 @@ export class SectionService { }); } - duplicateSection(section: Section, page: Page, sectionIndex: number): void { + duplicateSection(section: Section, sectionIndex: number): void { + const page = this.unitService.getSelectedPage(); this.unitService.updateUnitDefinition({ title: `Abschnitt dupliziert`, command: () => { @@ -109,7 +110,8 @@ export class SectionService { }); } - moveSection(section: Section, page: Page, direction: 'up' | 'down'): void { + moveSection(section: Section, direction: 'up' | 'down'): void { + const page = this.unitService.getSelectedPage(); this.unitService.updateUnitDefinition({ title: `Abschnitt verschoben`, command: () => { diff --git a/projects/editor/src/app/services/unit-services/unit.service.ts b/projects/editor/src/app/services/unit-services/unit.service.ts index a0b962871714270220280a150e4d14600ea9234d..05eb505fbc69384654bf3a1b01e45b3509246571 100644 --- a/projects/editor/src/app/services/unit-services/unit.service.ts +++ b/projects/editor/src/app/services/unit-services/unit.service.ts @@ -229,4 +229,8 @@ export class UnitService { this.updateUnitDefinition(); this.updateSectionCounter(); } + + getSelectedPage() { + return this.unit.pages[this.selectionService.selectedPageIndex]; + } }