feat: remove name from appState and use in component directly

This commit is contained in:
Aakansha Doshi 2024-02-05 15:05:01 +05:30
parent 0513b647ec
commit b2331ffd98
12 changed files with 46 additions and 33 deletions

View File

@ -45,6 +45,7 @@ import {
ResolvablePromise, ResolvablePromise,
resolvablePromise, resolvablePromise,
isRunningInIframe, isRunningInIframe,
getDateTime,
} from "../packages/excalidraw/utils"; } from "../packages/excalidraw/utils";
import { import {
FIREBASE_STORAGE_PREFIXES, FIREBASE_STORAGE_PREFIXES,
@ -775,6 +776,7 @@ const ExcalidrawWrapper = () => {
excalidrawAPI.getSceneElements(), excalidrawAPI.getSceneElements(),
excalidrawAPI.getAppState(), excalidrawAPI.getAppState(),
excalidrawAPI.getFiles(), excalidrawAPI.getFiles(),
`${t("labels.untitled")}-${getDateTime()}`,
); );
}} }}
> >

View File

@ -23,13 +23,14 @@ import { FILE_UPLOAD_MAX_BYTES } from "../app_constants";
import { encodeFilesForUpload } from "../data/FileManager"; import { encodeFilesForUpload } from "../data/FileManager";
import { MIME_TYPES } from "../../packages/excalidraw/constants"; import { MIME_TYPES } from "../../packages/excalidraw/constants";
import { trackEvent } from "../../packages/excalidraw/analytics"; import { trackEvent } from "../../packages/excalidraw/analytics";
import { getFrame } from "../../packages/excalidraw/utils"; import { getDateTime, getFrame } from "../../packages/excalidraw/utils";
import { ExcalidrawLogo } from "../../packages/excalidraw/components/ExcalidrawLogo"; import { ExcalidrawLogo } from "../../packages/excalidraw/components/ExcalidrawLogo";
export const exportToExcalidrawPlus = async ( export const exportToExcalidrawPlus = async (
elements: readonly NonDeletedExcalidrawElement[], elements: readonly NonDeletedExcalidrawElement[],
appState: Partial<AppState>, appState: Partial<AppState>,
files: BinaryFiles, files: BinaryFiles,
name: string,
) => { ) => {
const firebase = await loadFirebaseStorage(); const firebase = await loadFirebaseStorage();
@ -53,7 +54,7 @@ export const exportToExcalidrawPlus = async (
.ref(`/migrations/scenes/${id}`) .ref(`/migrations/scenes/${id}`)
.put(blob, { .put(blob, {
customMetadata: { customMetadata: {
data: JSON.stringify({ version: 2, name: appState.name }), data: JSON.stringify({ version: 2, name }),
created: Date.now().toString(), created: Date.now().toString(),
}, },
}); });
@ -117,7 +118,12 @@ export const ExportToExcalidrawPlus: React.FC<{
onClick={async () => { onClick={async () => {
try { try {
trackEvent("export", "eplus", `ui (${getFrame()})`); trackEvent("export", "eplus", `ui (${getFrame()})`);
await exportToExcalidrawPlus(elements, appState, files); await exportToExcalidrawPlus(
elements,
appState,
files,
`${t("labels.untitled")}-${getDateTime()}`,
);
onSuccess(); onSuccess();
} catch (error: any) { } catch (error: any) {
console.error(error); console.error(error);

View File

@ -13,6 +13,7 @@ import { exportCanvas, prepareElementsForExport } from "../data/index";
import { isTextElement } from "../element"; import { isTextElement } from "../element";
import { t } from "../i18n"; import { t } from "../i18n";
import { isFirefox } from "../constants"; import { isFirefox } from "../constants";
import { getDateTime } from "../utils";
export const actionCopy = register({ export const actionCopy = register({
name: "copy", name: "copy",
@ -138,6 +139,7 @@ export const actionCopyAsSvg = register({
{ {
...appState, ...appState,
exportingFrame, exportingFrame,
name: app.props.name || `${t("labels.untitled")}-${getDateTime()}`,
}, },
); );
return { return {
@ -184,6 +186,7 @@ export const actionCopyAsPng = register({
await exportCanvas("clipboard", exportedElements, appState, app.files, { await exportCanvas("clipboard", exportedElements, appState, app.files, {
...appState, ...appState,
exportingFrame, exportingFrame,
name: app.props.name || `${t("labels.untitled")}-${getDateTime()}`,
}); });
return { return {
appState: { appState: {

View File

@ -19,6 +19,7 @@ import { nativeFileSystemSupported } from "../data/filesystem";
import { Theme } from "../element/types"; import { Theme } from "../element/types";
import "../components/ToolIcon.scss"; import "../components/ToolIcon.scss";
import { getDateTime } from "../utils";
export const actionChangeProjectName = register({ export const actionChangeProjectName = register({
name: "changeProjectName", name: "changeProjectName",
@ -29,7 +30,7 @@ export const actionChangeProjectName = register({
PanelComponent: ({ appState, updateData, appProps, data }) => ( PanelComponent: ({ appState, updateData, appProps, data }) => (
<ProjectName <ProjectName
label={t("labels.fileTitle")} label={t("labels.fileTitle")}
value={appState.name || "Unnamed"} value={appProps.name}
onChange={(name: string) => updateData(name)} onChange={(name: string) => updateData(name)}
isNameEditable={ isNameEditable={
typeof appProps.name === "undefined" && !appState.viewModeEnabled typeof appProps.name === "undefined" && !appState.viewModeEnabled
@ -144,8 +145,18 @@ export const actionSaveToActiveFile = register({
try { try {
const { fileHandle } = isImageFileHandle(appState.fileHandle) const { fileHandle } = isImageFileHandle(appState.fileHandle)
? await resaveAsImageWithScene(elements, appState, app.files) ? await resaveAsImageWithScene(
: await saveAsJSON(elements, appState, app.files); elements,
appState,
app.files,
app.props.name || `${t("labels.untitled")}-${getDateTime()}`,
)
: await saveAsJSON(
elements,
appState,
app.files,
app.props.name || `${t("labels.untitled")}-${getDateTime()}`,
);
return { return {
commitToHistory: false, commitToHistory: false,
@ -190,6 +201,7 @@ export const actionSaveFileToDisk = register({
fileHandle: null, fileHandle: null,
}, },
app.files, app.files,
app.props.name || `${t("labels.untitled")}-${getDateTime()}`,
); );
return { return {
commitToHistory: false, commitToHistory: false,

View File

@ -65,7 +65,6 @@ export const getDefaultAppState = (): Omit<
isRotating: false, isRotating: false,
lastPointerDownWith: "mouse", lastPointerDownWith: "mouse",
multiElement: null, multiElement: null,
name: `${t("labels.untitled")}-${getDateTime()}`,
contextMenu: null, contextMenu: null,
openMenu: null, openMenu: null,
openPopup: null, openPopup: null,
@ -175,7 +174,6 @@ const APP_STATE_STORAGE_CONF = (<
isRotating: { browser: false, export: false, server: false }, isRotating: { browser: false, export: false, server: false },
lastPointerDownWith: { browser: true, export: false, server: false }, lastPointerDownWith: { browser: true, export: false, server: false },
multiElement: { browser: false, export: false, server: false }, multiElement: { browser: false, export: false, server: false },
name: { browser: true, export: false, server: false },
offsetLeft: { browser: false, export: false, server: false }, offsetLeft: { browser: false, export: false, server: false },
offsetTop: { browser: false, export: false, server: false }, offsetTop: { browser: false, export: false, server: false },
contextMenu: { browser: false, export: false, server: false }, contextMenu: { browser: false, export: false, server: false },

View File

@ -270,6 +270,7 @@ import {
updateStable, updateStable,
addEventListener, addEventListener,
normalizeEOL, normalizeEOL,
getDateTime,
} from "../utils"; } from "../utils";
import { import {
createSrcDoc, createSrcDoc,
@ -619,7 +620,6 @@ class App extends React.Component<AppProps, AppState> {
gridModeEnabled = false, gridModeEnabled = false,
objectsSnapModeEnabled = false, objectsSnapModeEnabled = false,
theme = defaultAppState.theme, theme = defaultAppState.theme,
name = defaultAppState.name,
} = props; } = props;
this.state = { this.state = {
...defaultAppState, ...defaultAppState,
@ -630,7 +630,6 @@ class App extends React.Component<AppProps, AppState> {
zenModeEnabled, zenModeEnabled,
objectsSnapModeEnabled, objectsSnapModeEnabled,
gridSize: gridModeEnabled ? GRID_SIZE : null, gridSize: gridModeEnabled ? GRID_SIZE : null,
name,
width: window.innerWidth, width: window.innerWidth,
height: window.innerHeight, height: window.innerHeight,
}; };
@ -1725,7 +1724,7 @@ class App extends React.Component<AppProps, AppState> {
this.files, this.files,
{ {
exportBackground: this.state.exportBackground, exportBackground: this.state.exportBackground,
name: this.state.name, name: this.props?.name || `${t("labels.untitled")}-${getDateTime()}`,
viewBackgroundColor: this.state.viewBackgroundColor, viewBackgroundColor: this.state.viewBackgroundColor,
exportingFrame: opts.exportingFrame, exportingFrame: opts.exportingFrame,
}, },
@ -2124,7 +2123,7 @@ class App extends React.Component<AppProps, AppState> {
let gridSize = actionResult?.appState?.gridSize || null; let gridSize = actionResult?.appState?.gridSize || null;
const theme = const theme =
actionResult?.appState?.theme || this.props.theme || THEME.LIGHT; actionResult?.appState?.theme || this.props.theme || THEME.LIGHT;
let name = actionResult?.appState?.name ?? this.state.name;
const errorMessage = const errorMessage =
actionResult?.appState?.errorMessage ?? this.state.errorMessage; actionResult?.appState?.errorMessage ?? this.state.errorMessage;
if (typeof this.props.viewModeEnabled !== "undefined") { if (typeof this.props.viewModeEnabled !== "undefined") {
@ -2139,10 +2138,6 @@ class App extends React.Component<AppProps, AppState> {
gridSize = this.props.gridModeEnabled ? GRID_SIZE : null; gridSize = this.props.gridModeEnabled ? GRID_SIZE : null;
} }
if (typeof this.props.name !== "undefined") {
name = this.props.name;
}
editingElement = editingElement =
editingElement || actionResult.appState?.editingElement || null; editingElement || actionResult.appState?.editingElement || null;
@ -2165,7 +2160,6 @@ class App extends React.Component<AppProps, AppState> {
zenModeEnabled, zenModeEnabled,
gridSize, gridSize,
theme, theme,
name,
errorMessage, errorMessage,
}); });
}, },
@ -2699,12 +2693,6 @@ class App extends React.Component<AppProps, AppState> {
}); });
} }
if (this.props.name && prevProps.name !== this.props.name) {
this.setState({
name: this.props.name,
});
}
this.excalidrawContainerRef.current?.classList.toggle( this.excalidrawContainerRef.current?.classList.toggle(
"theme--dark", "theme--dark",
this.state.theme === "dark", this.state.theme === "dark",

View File

@ -34,7 +34,7 @@ import { Tooltip } from "./Tooltip";
import "./ImageExportDialog.scss"; import "./ImageExportDialog.scss";
import { useAppProps } from "./App"; import { useAppProps } from "./App";
import { FilledButton } from "./FilledButton"; import { FilledButton } from "./FilledButton";
import { cloneJSON } from "../utils"; import { cloneJSON, getDateTime } from "../utils";
import { prepareElementsForExport } from "../data"; import { prepareElementsForExport } from "../data";
const supportsContextFilters = const supportsContextFilters =
@ -73,7 +73,9 @@ const ImageExportModal = ({
); );
const appProps = useAppProps(); const appProps = useAppProps();
const [projectName, setProjectName] = useState(appStateSnapshot.name); const [projectName, setProjectName] = useState(
appProps.name || `${t("labels.untitled")}-${getDateTime()}`,
);
const [exportSelectionOnly, setExportSelectionOnly] = useState(hasSelection); const [exportSelectionOnly, setExportSelectionOnly] = useState(hasSelection);
const [exportWithBackground, setExportWithBackground] = useState( const [exportWithBackground, setExportWithBackground] = useState(
appStateSnapshot.exportBackground, appStateSnapshot.exportBackground,
@ -109,7 +111,6 @@ const ImageExportModal = ({
elements: exportedElements, elements: exportedElements,
appState: { appState: {
...appStateSnapshot, ...appStateSnapshot,
name: projectName,
exportBackground: exportWithBackground, exportBackground: exportWithBackground,
exportWithDarkMode: exportDarkMode, exportWithDarkMode: exportDarkMode,
exportScale, exportScale,

View File

@ -1,14 +1,15 @@
import "./TextInput.scss"; import "./TextInput.scss";
import React, { useState } from "react"; import React, { useState } from "react";
import { focusNearestParent } from "../utils"; import { focusNearestParent, getDateTime } from "../utils";
import "./ProjectName.scss"; import "./ProjectName.scss";
import { useExcalidrawContainer } from "./App"; import { useExcalidrawContainer } from "./App";
import { KEYS } from "../keys"; import { KEYS } from "../keys";
import { t } from "../i18n";
type Props = { type Props = {
value: string; value?: string;
onChange: (value: string) => void; onChange: (value: string) => void;
label: string; label: string;
isNameEditable: boolean; isNameEditable: boolean;
@ -17,7 +18,9 @@ type Props = {
export const ProjectName = (props: Props) => { export const ProjectName = (props: Props) => {
const { id } = useExcalidrawContainer(); const { id } = useExcalidrawContainer();
const [fileName, setFileName] = useState<string>(props.value); const [fileName, setFileName] = useState<string>(
props.value || `${t("labels.untitled")}-${getDateTime()}`,
);
const handleBlur = (event: any) => { const handleBlur = (event: any) => {
if (!props.ignoreFocus) { if (!props.ignoreFocus) {

View File

@ -71,6 +71,7 @@ export const saveAsJSON = async (
elements: readonly ExcalidrawElement[], elements: readonly ExcalidrawElement[],
appState: AppState, appState: AppState,
files: BinaryFiles, files: BinaryFiles,
name: string,
) => { ) => {
const serialized = serializeAsJSON(elements, appState, files, "local"); const serialized = serializeAsJSON(elements, appState, files, "local");
const blob = new Blob([serialized], { const blob = new Blob([serialized], {
@ -78,7 +79,7 @@ export const saveAsJSON = async (
}); });
const fileHandle = await fileSave(blob, { const fileHandle = await fileSave(blob, {
name: appState.name, name,
extension: "excalidraw", extension: "excalidraw",
description: "Excalidraw file", description: "Excalidraw file",
fileHandle: isImageFileHandle(appState.fileHandle) fileHandle: isImageFileHandle(appState.fileHandle)

View File

@ -7,8 +7,9 @@ export const resaveAsImageWithScene = async (
elements: readonly ExcalidrawElement[], elements: readonly ExcalidrawElement[],
appState: AppState, appState: AppState,
files: BinaryFiles, files: BinaryFiles,
name: string,
) => { ) => {
const { exportBackground, viewBackgroundColor, name, fileHandle } = appState; const { exportBackground, viewBackgroundColor, fileHandle } = appState;
const fileHandleType = getFileHandleType(fileHandle); const fileHandleType = getFileHandleType(fileHandle);

View File

@ -26,7 +26,6 @@ const clearAppStatePropertiesForHistory = (appState: AppState) => {
viewBackgroundColor: appState.viewBackgroundColor, viewBackgroundColor: appState.viewBackgroundColor,
editingLinearElement: appState.editingLinearElement, editingLinearElement: appState.editingLinearElement,
editingGroupId: appState.editingGroupId, editingGroupId: appState.editingGroupId,
name: appState.name,
}; };
}; };

View File

@ -247,7 +247,6 @@ export interface AppState {
scrollY: number; scrollY: number;
cursorButton: "up" | "down"; cursorButton: "up" | "down";
scrolledOutside: boolean; scrolledOutside: boolean;
name: string;
isResizing: boolean; isResizing: boolean;
isRotating: boolean; isRotating: boolean;
zoom: Zoom; zoom: Zoom;