@aurigma/design-atoms
Version:
Design Atoms is a part of Customer's Canvas SDK which allows for manipulating individual design elements through your code.
404 lines • 16.7 kB
JavaScript
import { LayoutItem, BaseTextItem, AutoLayoutSettings, GroupItem } from "@aurigma/design-atoms-model/Product/Items";
import { RotatedRectangleF, RectangleF, Transform } from "@aurigma/design-atoms-model/Math";
import { GroupItemHandler } from "./GroupItemHandler";
import { BaseRectangleItemHandler } from "./BaseRectangleItemHandler";
import { PlaceholderItemHandler } from "./PlaceholderItemHandler";
import { BaseTextItemHandler } from "./BaseTextItemHandler";
import { ItemUtils } from "../Utils/ItemUtils";
import { AutoLayoutHandler } from "./LayoutItem/AutoLayoutHandler";
import { EventObject } from "@aurigma/design-atoms-model/EventObject";
import { NewBaseTextItemHandler } from "./NewBaseTextItemHandler";
export class LayoutItemHandler extends GroupItemHandler {
constructor(item, itemHandlers, _history, textWhizz = null) {
super(item, itemHandlers, textWhizz);
this._history = _history;
this._layoutEvent = new EventObject();
this._visibilityState = null;
this._visibilityStateChangedEvent = new EventObject();
this._isEmpty = null;
this._disableApplyLayout = false;
this._rectMap = {};
this._onChildItemChanged = (sender) => {
var handler = this.canvas.getItemHandler(sender);
var newRect = handler.rectangle;
if (newRect.equals(this._rectMap[handler.uniqueId]))
return;
this._rectMap[handler.uniqueId] = newRect;
this.applyLayout();
};
this._onChildItemHandlerVisibilityChanged = () => {
this._updateVisibilityState();
this.applyLayout();
};
this._onChildItemHandlerLayout = (changed) => {
if (changed) {
this._updateVisibilityState();
this.applyLayout();
}
};
this._onChildItemHandlerChanging = (sender) => {
if (this._layoutHandler == null || !(this._layoutHandler instanceof AutoLayoutHandler))
this._resetSourceRectangle();
this.raiseChanging(this.item);
};
this._transformStarted = false;
this._transformedRectangle = null;
this._applyMatrix = (matrix, finished, newAngle = null) => {
const transform = (handler) => handler.setRectangle(handler.rectangle.transformByMatrix(matrix, newAngle), !finished);
transform(this);
if (!this._transformStarted)
return;
const layoutItemHandlers = [this];
while (layoutItemHandlers.length > 0) {
const handler = layoutItemHandlers.shift();
const itemHandlers = handler.itemHandlers.ofType(BaseRectangleItemHandler);
itemHandlers.forEach(i => {
transform(i);
if (i instanceof LayoutItemHandler) {
layoutItemHandlers.push(i);
}
if (i instanceof PlaceholderItemHandler && i.content != null) {
transform(i.content);
}
});
}
};
this._onItemHandlerExitedEditMode = (sender) => {
this._updateVisibilityState();
this.applyLayout(sender);
};
this._onItemHandlerEnteredEditMode = (sender) => {
this._updateVisibilityState();
};
this._onChildGroupItemsChanged = (sender, property) => {
if (property == "items") {
this._subscribeChildItemChanges(sender);
}
};
this._subscribeChildItemHandlers();
}
getSelectionRectangle() {
return this._getRectangleFromChildren();
}
_getHighlightRectangle() {
return this._getRectangleFromChildren();
}
setItemHandlers(itemHandlers) {
this._unsubscribeChildItemHandlers();
this._disableApplyLayout = true;
super.setItemHandlers(itemHandlers);
this._disableApplyLayout = false;
this._initSourceRectangle().then(() => {
this._initLayoutHandler();
this.applyLayout(null);
});
this._subscribeChildItemHandlers();
}
_isGroupHandler() {
return true;
}
_onItemPropertyChanged(sender, propertyName) {
switch (propertyName) {
case "layoutSettings":
this._initLayoutHandler();
break;
}
}
_initLayoutHandler() {
if (this.item.layoutSettings instanceof AutoLayoutSettings) {
if (!(this._layoutHandler instanceof AutoLayoutHandler)) {
this._layoutHandler = new AutoLayoutHandler(this.item, this.itemHandlers, this, this._history);
this._layoutHandler.getLayoutEvent().add(this._onLayoutHandlerLayoutEvent.bind(this));
}
else {
this._layoutHandler._init();
}
}
else {
if (this._layoutHandler != null) {
this._layoutHandler.dispose();
}
this._layoutHandler = null;
}
}
getVisibilityStateChangedEvent() {
return this._visibilityStateChangedEvent;
}
getLayoutEvent() {
return this._layoutEvent;
}
_onLayoutHandlerLayoutEvent(changed) {
if (this.canvas != null) {
this.canvas.updateSelection();
this.canvas.updateButtonGroups({
placeholderHandler: this,
placeholderHandlerPosition: true,
violationContainerHandler: this,
violationContainerHandlerPosition: true
});
this.getChangingEvent().notify(this.item);
this.canvas.redraw();
}
this._layoutEvent.notify(changed);
}
async _initSourceRectangle() {
if (this.item.sourceRectangle && !this.item.sourceRectangle.isEmpty())
return;
await this._resetSourceRectangle();
}
async _resetSourceRectangle() {
await this.waitUpdate();
if (this.itemHandlers.any()) {
const sourceRectangle = this.itemHandlers.cast().select(x => x.rectangle).aggregate((a, b) => RotatedRectangleF.union(a, b));
this.setSourceRectangle(sourceRectangle);
}
}
async waitUpdate() {
await Promise.all(this.itemHandlers.toArray().map((vo) => { return vo.waitUpdate(); }));
}
startTransform() {
this._originalHeight = this.height;
this._transformStarted = true;
if (this._layoutHandler)
this._layoutHandler.ignoreLayoutApply = true;
super.startTransform();
}
onResized() {
var scale = this.height / this._originalHeight;
if (this.item.layoutSettings != null && this.item.layoutSettings instanceof AutoLayoutSettings)
this.item.layoutSettings.margin *= scale;
return super.onResized();
}
_endTransform(changed, resized, suppressOnChanged) {
var _a, _b, _c, _d;
super._endTransform(changed, resized, suppressOnChanged);
if (this._transformedRectangle == null) {
this._transformStarted = false;
if (this._layoutHandler)
this._layoutHandler.ignoreLayoutApply = false;
return;
}
(_a = this.canvas) === null || _a === void 0 ? void 0 : _a.pauseRedraw();
var t = this._transformedRectangle;
this._transformedRectangle = null;
this._transformStarted = false;
//await this.waitUpdate();
(_b = this._history) === null || _b === void 0 ? void 0 : _b.pause();
this.setSourceRectangle(t);
if (this._layoutHandler)
this._layoutHandler.ignoreLayoutApply = false;
this.applyLayout(null);
(_c = this._history) === null || _c === void 0 ? void 0 : _c.resume(true, false, true);
(_d = this.canvas) === null || _d === void 0 ? void 0 : _d.continueRedraw();
}
_getChildrenHighlights() {
if (this._layoutHandler == null)
return [];
let result = [];
this.itemHandlers
.toArray()
.filter(itemHandler => this._layoutHandler._filterHiddenItems(itemHandler))
.forEach((itemHandler) => result.push(...itemHandler.getHighlightRectangles()));
return result;
}
get _calculateRectangleFromChild() {
return false;
}
_getRectangle() {
if (this._transformedRectangle)
return this._transformedRectangle;
return super._getRectangle();
}
isEmpty() {
const value = this._calculateIsEmpty();
this._updateIsEmpty(value);
return value;
}
isVisible() {
return super.isVisible() && !this.isEmpty();
}
async applyLayout(sender) {
if (this._disableApplyLayout)
return;
if (sender instanceof PlaceholderItemHandler && sender.editing)
return;
await this.waitUpdate();
if (this.item.layoutSettings instanceof AutoLayoutSettings && this._layoutHandler) {
this._layoutHandler.applyLayout();
}
else {
this._resetSourceRectangle();
this._onLayoutHandlerLayoutEvent(false);
}
}
getControlBounds() {
if (!this.item.sourceRectangle)
return new RectangleF();
return this.item.sourceRectangle;
}
setRectangle(rectangle, suppressOnChanged, updateChildren = true) {
if (this._transformStarted) {
this._transformedRectangle = rectangle.clone();
if (updateChildren)
super.setRectangle(rectangle, suppressOnChanged);
return;
}
if (updateChildren)
super.setRectangle(rectangle, suppressOnChanged);
this.setSourceRectangle(rectangle);
}
setSourceRectangle(rectangle) {
this.item.sourceRectangle = rectangle.toRectangleF();
this.item.transform = new Transform(1, 1, 0, 0, rectangle.angle);
}
getOrderedItems() {
let result = null;
if (this.item.layoutSettings instanceof AutoLayoutSettings && this._layoutHandler != null)
result = this._layoutHandler.getOrderedItems();
else
result = super.getOrderedItems();
return result;
}
generateAndApplyAutolayoutSettings(alignItems, orientation, margin, justifyContent) {
this.item.layoutSettings = LayoutItem.generateAutoLayoutSettings(this.itemHandlers.toArray().map((itemHandler) => itemHandler.getTransformedRectangle(false, true).bounds), alignItems, orientation, margin, justifyContent);
}
async _onItemAdded(data) {
super._onItemAdded(data);
if (data.item instanceof BaseTextItem) {
await ItemUtils.waitForItemsUpdated([data.item], this.canvas);
}
this._subscribeChildItemChanges(data.item);
this.applyLayout(this.itemHandlers.first(itemHandler => itemHandler.item === data.item));
}
_onItemRemoved(data) {
super._onItemRemoved(data);
this._unsubscribeChildItemChanges(data.item);
if (this._layoutHandler)
this._layoutHandler.onItemRemoved(data);
else
this._resetSourceRectangle();
}
async _onItemHandlerAdded(data) {
super._onItemHandlerAdded(data);
if (this._layoutHandler instanceof AutoLayoutHandler)
this._layoutHandler.onItemHandlersCollectionChanged();
this.applyLayout();
}
_updateVisibilityState() {
let visible = this.isVisible();
if (visible === this._visibilityState)
return;
this._visibilityState = visible;
this._onVisibilityStateChanged();
}
_onVisibilityStateChanged() {
this.applyLayout();
this._visibilityStateChangedEvent.notify();
}
_onItemHandlerRemoved(data) {
super._onItemHandlerRemoved(data);
if (this._layoutHandler instanceof AutoLayoutHandler)
this._layoutHandler.onItemHandlersCollectionChanged();
}
;
_subscribeChildItemHandlers() {
var _a;
(_a = this.itemHandlers) === null || _a === void 0 ? void 0 : _a.forEach(x => this._subscribeChildItemHandler(x));
}
_unsubscribeChildItemHandlers() {
this.itemHandlers.forEach(x => this._unsubscribeChildItemHandler(x));
}
_subscribeChildItemHandler(itemHandler) {
itemHandler.getChangingEvent().add(this._onChildItemHandlerChanging);
if (itemHandler instanceof NewBaseTextItemHandler) {
itemHandler.exitedEditModeEvent.add(this._onItemHandlerExitedEditMode);
itemHandler.enteredEditModeEvent.add(this._onItemHandlerEnteredEditMode);
}
if (itemHandler instanceof LayoutItemHandler) {
itemHandler.getLayoutEvent().add(this._onChildItemHandlerLayout);
itemHandler.getVisibilityStateChangedEvent().add(this._onChildItemHandlerVisibilityChanged);
}
}
_unsubscribeChildItemHandler(itemHandler) {
itemHandler.getChangingEvent().remove(this._onChildItemHandlerChanging);
if (itemHandler instanceof NewBaseTextItemHandler) {
itemHandler.exitedEditModeEvent.remove(this._onItemHandlerExitedEditMode);
itemHandler.enteredEditModeEvent.remove(this._onItemHandlerEnteredEditMode);
}
if (itemHandler instanceof LayoutItemHandler) {
itemHandler.getLayoutEvent().remove(this._onChildItemHandlerLayout);
itemHandler.getVisibilityStateChangedEvent().remove(this._onChildItemHandlerVisibilityChanged);
}
}
_unsubscribeChildItems() {
this.item.items.forEach(x => this._unsubscribeChildItemChanges(x));
}
_subscribeChildItems() {
this.item.items.forEach(x => this._subscribeChildItemChanges(x));
}
_unsubscribeChildItemChanges(item) {
if (item instanceof GroupItem) {
item.applyToItems(x => this._unsubscribeChildItemChanges(x));
item.removePropertyChanged(this._onChildGroupItemsChanged);
}
item.getItemChangedEvent().remove(this._onChildItemChanged);
}
_subscribeChildItemChanges(item) {
if (item instanceof GroupItem) {
item.applyToItems(x => this._subscribeChildItemChanges(x));
item.addPropertyChanged(this._onChildGroupItemsChanged);
}
item.getItemChangedEvent().add(this._onChildItemChanged);
}
async _onRemovedFromCanvas(canvas) {
this._unsubscribeChildItems();
this._unsubscribeChildItemHandlers();
super._onRemovedFromCanvas(canvas);
}
async _onAddedOnCanvas(canvas) {
super._onAddedOnCanvas(canvas);
this._subscribeChildItems();
this._initLayoutHandler();
await this._initSourceRectangle();
}
drawItemHandler(itemHandlerCtx) {
if (this.isEmpty())
return;
super.drawItemHandler(itemHandlerCtx);
}
get item() {
return this._getItem();
}
isChildVisible(childItemHandler) {
if (childItemHandler instanceof BaseTextItemHandler || childItemHandler instanceof NewBaseTextItemHandler) {
return !childItemHandler.isEmpty();
}
return true;
}
_calculateIsEmpty() {
var itemHandlersToCheck = this.itemHandlers.where(x => {
let result = false;
if ((x instanceof BaseTextItemHandler || x instanceof NewBaseTextItemHandler) && !x.isLocked())
result = true;
else if (x instanceof LayoutItemHandler)
result = true;
return result;
});
if (!itemHandlersToCheck.any())
return false;
const hasNonEmptyChildren = itemHandlersToCheck.any(element => !element.isEmpty());
var result = !hasNonEmptyChildren;
return result;
}
_updateIsEmpty(value) {
if (value === this._isEmpty)
return;
this._isEmpty = value;
this._onEmptyStateChanged();
}
_onEmptyStateChanged() {
this.itemHandlers.forEach(x => x.update());
}
}
LayoutItemHandler.typeName = "LayoutItemHandler";
//# sourceMappingURL=LayoutItemHandler.js.map