123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148 |
- import { VERTICAL_ALIGN } from "../constants";
- import { getNonDeletedElements, isTextElement } from "../element";
- import { mutateElement } from "../element/mutateElement";
- import {
- getBoundTextElement,
- measureText,
- redrawTextBoundingBox,
- } from "../element/textElement";
- import {
- getOriginalContainerHeightFromCache,
- resetOriginalContainerCache,
- } from "../element/textWysiwyg";
- import {
- hasBoundTextElement,
- isTextBindableContainer,
- } from "../element/typeChecks";
- import {
- ExcalidrawTextContainer,
- ExcalidrawTextElement,
- } from "../element/types";
- import { getSelectedElements } from "../scene";
- import { getFontString } from "../utils";
- import { register } from "./register";
- export const actionUnbindText = register({
- name: "unbindText",
- contextItemLabel: "labels.unbindText",
- trackEvent: { category: "element" },
- predicate: (elements, appState) => {
- const selectedElements = getSelectedElements(elements, appState);
- return selectedElements.some((element) => hasBoundTextElement(element));
- },
- perform: (elements, appState) => {
- const selectedElements = getSelectedElements(
- getNonDeletedElements(elements),
- appState,
- );
- selectedElements.forEach((element) => {
- const boundTextElement = getBoundTextElement(element);
- if (boundTextElement) {
- const { width, height, baseline } = measureText(
- boundTextElement.originalText,
- getFontString(boundTextElement),
- );
- const originalContainerHeight = getOriginalContainerHeightFromCache(
- element.id,
- );
- resetOriginalContainerCache(element.id);
- mutateElement(boundTextElement as ExcalidrawTextElement, {
- containerId: null,
- width,
- height,
- baseline,
- text: boundTextElement.originalText,
- });
- mutateElement(element, {
- boundElements: element.boundElements?.filter(
- (ele) => ele.id !== boundTextElement.id,
- ),
- height: originalContainerHeight
- ? originalContainerHeight
- : element.height,
- });
- }
- });
- return {
- elements,
- appState,
- commitToHistory: true,
- };
- },
- });
- export const actionBindText = register({
- name: "bindText",
- contextItemLabel: "labels.bindText",
- trackEvent: { category: "element" },
- predicate: (elements, appState) => {
- const selectedElements = getSelectedElements(elements, appState);
- if (selectedElements.length === 2) {
- const textElement =
- isTextElement(selectedElements[0]) ||
- isTextElement(selectedElements[1]);
- let bindingContainer;
- if (isTextBindableContainer(selectedElements[0])) {
- bindingContainer = selectedElements[0];
- } else if (isTextBindableContainer(selectedElements[1])) {
- bindingContainer = selectedElements[1];
- }
- if (
- textElement &&
- bindingContainer &&
- getBoundTextElement(bindingContainer) === null
- ) {
- return true;
- }
- }
- return false;
- },
- perform: (elements, appState) => {
- const selectedElements = getSelectedElements(
- getNonDeletedElements(elements),
- appState,
- );
- let textElement: ExcalidrawTextElement;
- let container: ExcalidrawTextContainer;
- if (
- isTextElement(selectedElements[0]) &&
- isTextBindableContainer(selectedElements[1])
- ) {
- textElement = selectedElements[0];
- container = selectedElements[1];
- } else {
- textElement = selectedElements[1] as ExcalidrawTextElement;
- container = selectedElements[0] as ExcalidrawTextContainer;
- }
- mutateElement(textElement, {
- containerId: container.id,
- verticalAlign: VERTICAL_ALIGN.MIDDLE,
- });
- mutateElement(container, {
- boundElements: (container.boundElements || []).concat({
- type: "text",
- id: textElement.id,
- }),
- });
- redrawTextBoundingBox(textElement, container);
- const updatedElements = elements.slice();
- const textElementIndex = updatedElements.findIndex(
- (ele) => ele.id === textElement.id,
- );
- updatedElements.splice(textElementIndex, 1);
- const containerIndex = updatedElements.findIndex(
- (ele) => ele.id === container.id,
- );
- updatedElements.splice(containerIndex + 1, 0, textElement);
- return {
- elements: updatedElements,
- appState: { ...appState, selectedElementIds: { [container.id]: true } },
- commitToHistory: true,
- };
- },
- });
|