diff --git a/README.md b/README.md index 39ff2d6..1e7b2d9 100644 --- a/README.md +++ b/README.md @@ -25,9 +25,6 @@ Translate component variants, properties, and more into dynamic code snippets fo - [Global Templates](#global-templates) - [“Details mode”](#details-mode) - [Bulk Operations](#bulk-operations) - - [Import/Export](#importexport) - - [Component Data](#component-data) - - [Node Params](#node-params) - [Full Examples](#full-examples) - [React](#react) - [HTML/CSS](#htmlcss) @@ -451,8 +448,6 @@ Details mode is really useful when you’re building or debuigging your template Running the plugin in design mode will open a window allowing you to perform bulk operations. -### Import/Export - You can bulk export and import templates for the current file (currently only available for components and component sets). The JSON schema for import and export is: @@ -473,14 +468,14 @@ As an example: ```json { - "19ab8ffd23dae11c49cdecb3bd9860dc388df0de": [ + "componentKeyABC123": [ { "language": "JAVASCRIPT", "code": "}\n {{?property.iconEnd.b=true}}iconEnd={<{{property.iconEnd.i|pascal}} />}\n onClick={() => {}}\n>\n {{property.label|raw}}\n", "title": "My Special Template" } ], - "6d607532d158046a9a6a3cc6f68a40e9cf59f006": [] + "componentKeyDEF456": [] } ``` @@ -490,49 +485,6 @@ Importing an empty array for a component key will remove all snippets for that c Components whose keys are not definied in the JSON are not effected by an import, even if they have snippets defined in Figma. -### Component Data - -The `"Component data"` action exports all component data for all non-variant components in the file as JSON. - -```json -{ - "19ab8ffd23dae11c49cdecb3bd9860dc388df0de": { - "name": "Button", - "description": "Common button used for user actions.", - "lineage": "Button/Button Frame" - }, - "d4f127de723bbc099be23260a223af942b194606": { - "name": "Icon Button", - "description": "Common icon button used for user actions.", - "lineage": "Icon Button/Icon Button Frame" - } -} -``` - -This is useful if you want to start building snippet templates in bulk, but dont know the component keys for your components. - -The JSON schema for component data is: - -```ts -type FileData = { - [k: ComponentKey]: { - name: string; - description: string; - lineage: string; - }; -}; -``` - -`name` and `description` are the name and description of the component. The lineage is a `/` separated breadcrumbs of node names to the page. This can be helpful when trying to understand which component you’re looking at. - -### Node Params - -The `"Node Data"` action returns [params](#params) for all nodes in the current selection. - -This output is useful if you want to analyze params for many nodes outside of the plugin interface, especially if youre building your snippet templates externally. - -In addition to hyphenated default `params`, it includes the `raw` params as a separate object. - ## Full Examples ### React diff --git a/code.js b/code.js index 41c7314..f0b740a 100644 --- a/code.js +++ b/code.js @@ -74,6 +74,54 @@ } } + // src/bulk.ts + var bulk = { + performImport, + performExport + }; + function performImport(data) { + const componentsByKey = getComponentsInFileByKey(); + let componentCount = 0; + for (let componentKey in data) { + const component = componentsByKey[componentKey]; + if (component) { + componentCount++; + setCodegenResultsInPluginData(component, data[componentKey]); + } + } + const s = componentCount === 1 ? "" : "s"; + figma.notify(`Updated ${componentCount} Component${s}`); + } + function performExport() { + const data = {}; + const components = findComponentNodesInFile(); + components.forEach((component) => { + const codegenResults = getCodegenResultsFromPluginData(component); + if (codegenResults && codegenResults.length) { + data[component.key] = codegenResults; + } + }); + const message = { + type: "BULK_EXPORT", + code: JSON.stringify(data, null, 2) + }; + figma.ui.postMessage(message); + } + function findComponentNodesInFile() { + if (figma.currentPage.parent) { + return figma.currentPage.parent.findAllWithCriteria({ + types: ["COMPONENT", "COMPONENT_SET"] + }) || []; + } + return []; + } + function getComponentsInFileByKey() { + const components = findComponentNodesInFile(); + const data = {}; + components.forEach((component) => data[component.key] = component); + return data; + } + // src/snippets.ts var MAX_RECURSION = 12; var regexSymbols = /(? { - const codegenResults = getCodegenResultsFromPluginData(component); - if (codegenResults) { - data[component.key] = codegenResults; - } - }); - const message = { - type: "BULK_EXPORT", - code: JSON.stringify(data, null, 2) - }; - figma.ui.postMessage(message); - } - function performGetComponentData() { - const components = findComponentNodesInFile(); - const componentData = {}; - const data = components.reduce((into, component) => { - if (component.parent && component.parent.type !== "COMPONENT_SET") { - const lineage = []; - let node = component.parent; - if (node) { - while (node && node.type !== "PAGE") { - lineage.push(node.name); - node = node.parent; - } - } - lineage.reverse(); - into[component.key] = { - name: component.name, - description: component.description, - lineage: lineage.join("/") - }; - } - return into; - }, componentData); - const message = { - type: "BULK_COMPONENT_DATA", - code: JSON.stringify(data, null, 2) - }; - figma.ui.postMessage(message); - } - async function performGetNodeData() { - const nodes = figma.currentPage.selection; - const data = {}; - await Promise.all( - nodes.map(async (node) => { - data[keyFromNode(node)] = await paramsFromNode(node); - return; - }) - ); - const message = { - type: "BULK_NODE_DATA", - code: JSON.stringify(data, null, 2) - }; - figma.ui.postMessage(message); - } - function keyFromNode(node) { - return `${node.name} ${node.type} ${node.id}`; - } - function findComponentNodesInFile() { - if (figma.currentPage.parent) { - return figma.currentPage.parent.findAllWithCriteria({ - types: ["COMPONENT", "COMPONENT_SET"] - }) || []; - } - return []; - } - function getComponentsInFileByKey() { - const components = findComponentNodesInFile(); - const data = {}; - components.forEach((component) => data[component.key] = component); - return data; - } - // src/templates.ts var CLIENT_STORAGE_GLOBAL_TEMPLATES_KEY = "global-templates"; function templatesIsCodeSnippetGlobalTemplates(templates) { @@ -753,10 +705,6 @@ ${indent}`); figma.ui.on("message", async (event) => { if (event.type === "BULK_INITIALIZE") { handleCurrentSelection(); - } else if (event.type === "BULK_COMPONENT_DATA") { - bulk.performGetComponentData(); - } else if (event.type === "BULK_NODE_DATA") { - await bulk.performGetNodeData(); } else if (event.type === "BULK_EXPORT") { bulk.performExport(); } else if (event.type === "BULK_IMPORT") { diff --git a/src/bulk.ts b/src/bulk.ts index 9b5afe5..4265f1e 100644 --- a/src/bulk.ts +++ b/src/bulk.ts @@ -2,7 +2,6 @@ import { getCodegenResultsFromPluginData, setCodegenResultsInPluginData, } from "./pluginData"; -import { paramsFromNode } from "./params"; /** * Bulk operations when run in design mode. @@ -11,8 +10,6 @@ import { paramsFromNode } from "./params"; export const bulk = { performImport, performExport, - performGetComponentData, - performGetNodeData, }; /** @@ -45,7 +42,7 @@ function performExport() { const components = findComponentNodesInFile(); components.forEach((component) => { const codegenResults = getCodegenResultsFromPluginData(component); - if (codegenResults) { + if (codegenResults && codegenResults.length) { data[component.key] = codegenResults; } }); @@ -56,70 +53,6 @@ function performExport() { figma.ui.postMessage(message); } -/** - * Export component data, posting stringified ComponentDataByComponentKey to UI - * https://github.com/figma/code-snippet-editor-plugin#component-data - * @returns void - */ -function performGetComponentData() { - const components = findComponentNodesInFile(); - const componentData: ComponentDataByComponentKey = {}; - const data = components.reduce((into, component) => { - if (component.parent && component.parent.type !== "COMPONENT_SET") { - const lineage = []; - let node: BaseNode | null = component.parent; - if (node) { - while (node && node.type !== "PAGE") { - lineage.push(node.name); - node = node.parent; - } - } - lineage.reverse(); - into[component.key] = { - name: component.name, - description: component.description, - lineage: lineage.join("/"), - }; - } - return into; - }, componentData); - const message: EventToBulk = { - type: "BULK_COMPONENT_DATA", - code: JSON.stringify(data, null, 2), - }; - figma.ui.postMessage(message); -} - -/** - * Get node params for all nodes in a selection and posting data to UI - * https://github.com/figma/code-snippet-editor-plugin#node-params - * @returns Promise - */ -async function performGetNodeData() { - const nodes = figma.currentPage.selection; - const data: { [k: string]: CodeSnippetParamsMap } = {}; - await Promise.all( - nodes.map(async (node) => { - data[keyFromNode(node)] = await paramsFromNode(node); - return; - }) - ); - const message: EventToBulk = { - type: "BULK_NODE_DATA", - code: JSON.stringify(data, null, 2), - }; - figma.ui.postMessage(message); -} - -/** - * Generate a key descriptive and unique to the node for indexing node data - * @param node node to generate a key from - * @returns a unique key for indexing the node data - */ -function keyFromNode(node: SceneNode) { - return `${node.name} ${node.type} ${node.id}`; -} - /** * Find all component and component set nodes in a file * @returns array of all components and component sets in a file. diff --git a/src/code.ts b/src/code.ts index 61de451..ce64bd2 100644 --- a/src/code.ts +++ b/src/code.ts @@ -142,10 +142,6 @@ function initializeDesignMode() { figma.ui.on("message", async (event: EventFromBulk) => { if (event.type === "BULK_INITIALIZE") { handleCurrentSelection(); - } else if (event.type === "BULK_COMPONENT_DATA") { - bulk.performGetComponentData(); - } else if (event.type === "BULK_NODE_DATA") { - await bulk.performGetNodeData(); } else if (event.type === "BULK_EXPORT") { bulk.performExport(); } else if (event.type === "BULK_IMPORT") { diff --git a/src/index.d.ts b/src/index.d.ts index 9c56e34..81931b6 100644 --- a/src/index.d.ts +++ b/src/index.d.ts @@ -61,25 +61,12 @@ interface NodeSnippetTemplateData { } /** - * JSON format of bulk codegen result payload for bulk import and export - * Where key is the component key and value is an array of codegenResultTemplates + * JSON format of codegen result where key is the component key and value is an array of CodegenResult templates */ type CodegenResultTemplatesByComponentKey = { [componentKey: string]: CodegenResult[]; }; -/** - * JSON format of bulk component export result payload for bulk import and export - * Where key is the component key and value is an array of codegenResultTemplates - */ -type ComponentDataByComponentKey = { - [componentKey: string]: { - name: string; - description: string; - lineage: string; - }; -}; - /** * Object of components and component sets by key */ @@ -130,11 +117,7 @@ type EventToTemplates = { */ type EventFromBulk = | { - type: - | "BULK_INITIALIZE" - | "BULK_COMPONENT_DATA" - | "BULK_NODE_DATA" - | "BULK_EXPORT"; + type: "BULK_INITIALIZE" | "BULK_EXPORT"; } | EventFromBulkImport; @@ -147,6 +130,6 @@ type EventFromBulkImport = { * Events sending to the bulk.html ui */ type EventToBulk = { - type: "BULK_COMPONENT_DATA" | "BULK_NODE_DATA" | "BULK_EXPORT"; + type: "BULK_EXPORT"; code: string; }; diff --git a/ui/bulk.html b/ui/bulk.html index 7f1a3a5..ea93bf1 100644 --- a/ui/bulk.html +++ b/ui/bulk.html @@ -73,36 +73,19 @@
- -