mirror of
https://github.com/penpot/penpot.git
synced 2025-05-16 23:06:10 +02:00
🎉 Give unique names to objects when pasting
This commit is contained in:
parent
83a02ad6e6
commit
82c264b75f
1 changed files with 49 additions and 21 deletions
|
@ -930,26 +930,34 @@
|
||||||
;; --- Add shape to Workspace
|
;; --- Add shape to Workspace
|
||||||
|
|
||||||
(defn impl-retrieve-used-names
|
(defn impl-retrieve-used-names
|
||||||
"Returns a set of already used names by shapes
|
[objects]
|
||||||
in the current workspace page."
|
(into #{} (map :name) (vals objects)))
|
||||||
[state]
|
|
||||||
(let [page-id (::page-id state)
|
(defn extract-numeric-suffix
|
||||||
objects (get-in state [:workspace-data page-id :objects])]
|
[basename]
|
||||||
(into #{} (map :name) (vals objects))))
|
(let [result (re-find #"(.*)-([0-9]+)$" basename)]
|
||||||
|
(if result
|
||||||
|
[(get result 1) (+ 1 (js/parseInt (get result 2)))]
|
||||||
|
[basename 1])))
|
||||||
|
|
||||||
(defn impl-generate-unique-name
|
(defn impl-generate-unique-name
|
||||||
"A unique name generator based on the current workspace page."
|
"A unique name generator"
|
||||||
[state basename]
|
[objects basename]
|
||||||
(let [used (impl-retrieve-used-names state)]
|
(let [used (impl-retrieve-used-names objects)
|
||||||
(loop [counter 1]
|
[prefix initial] (extract-numeric-suffix basename)]
|
||||||
(let [candidate (str basename "-" counter)]
|
(loop [counter initial]
|
||||||
|
(let [candidate (str prefix "-" counter)]
|
||||||
(if (contains? used candidate)
|
(if (contains? used candidate)
|
||||||
(recur (inc counter))
|
(recur (inc counter))
|
||||||
candidate)))))
|
candidate)))))
|
||||||
|
|
||||||
(defn impl-assoc-shape
|
(defn impl-assoc-shape
|
||||||
|
"Add a shape to the current workspace page, inside a given frame.
|
||||||
|
Give it a name that is unique in the page"
|
||||||
[state {:keys [id frame-id] :as data}]
|
[state {:keys [id frame-id] :as data}]
|
||||||
(let [name (impl-generate-unique-name state (:name data))
|
(let [page-id (::page-id state)
|
||||||
|
objects (get-in state [:workspace-data page-id :objects])
|
||||||
|
name (impl-generate-unique-name objects (:name data))
|
||||||
shape (assoc data :name name)
|
shape (assoc data :name name)
|
||||||
page-id (::page-id state)]
|
page-id (::page-id state)]
|
||||||
(-> state
|
(-> state
|
||||||
|
@ -2051,27 +2059,48 @@
|
||||||
|
|
||||||
(defn- paste-impl
|
(defn- paste-impl
|
||||||
[{:keys [selected objects] :as data}]
|
[{:keys [selected objects] :as data}]
|
||||||
(letfn [(prepare-change [delta id]
|
(letfn [(prepare-changes [state delta]
|
||||||
|
"Prepare objects to paste: generate new id, give them unique names,
|
||||||
|
and move to the position of mouse pointer"
|
||||||
|
(let [page-id (::page-id state)]
|
||||||
|
(loop [existing-objs (get-in state [:workspace-data page-id :objects])
|
||||||
|
chgs []
|
||||||
|
id (first selected)
|
||||||
|
ids (rest selected)]
|
||||||
|
(if (nil? id)
|
||||||
|
chgs
|
||||||
|
(let [result (prepare-change id existing-objs delta)
|
||||||
|
result (if (vector? result) result [result])]
|
||||||
|
(recur
|
||||||
|
(reduce conj existing-objs (map (fn [item] {(:id item) (:obj item)}) result))
|
||||||
|
(into chgs result)
|
||||||
|
(first ids)
|
||||||
|
(rest ids)))))))
|
||||||
|
|
||||||
|
(prepare-change [id existing-objs delta]
|
||||||
(let [obj (get objects id)]
|
(let [obj (get objects id)]
|
||||||
(if (= :frame (:type obj))
|
(if (= :frame (:type obj))
|
||||||
(prepare-frame-change obj delta)
|
(prepare-frame-change existing-objs obj delta)
|
||||||
(prepare-shape-change obj delta uuid/zero))))
|
(prepare-shape-change existing-objs obj delta uuid/zero))))
|
||||||
|
|
||||||
(prepare-shape-change [obj delta frame-id]
|
(prepare-shape-change [objects obj delta frame-id]
|
||||||
(let [id (uuid/next)
|
(let [id (uuid/next)
|
||||||
renamed-obj (assoc obj :id id :frame-id frame-id)
|
name (impl-generate-unique-name objects (:name obj))
|
||||||
|
renamed-obj (assoc obj :id id :frame-id frame-id :name name)
|
||||||
moved-obj (geom/move renamed-obj delta)]
|
moved-obj (geom/move renamed-obj delta)]
|
||||||
{:type :add-obj
|
{:type :add-obj
|
||||||
:id id
|
:id id
|
||||||
:frame-id frame-id
|
:frame-id frame-id
|
||||||
:obj moved-obj}))
|
:obj moved-obj}))
|
||||||
|
|
||||||
(prepare-frame-change [obj delta]
|
(prepare-frame-change [objects obj delta]
|
||||||
(let [frame-id (uuid/next)
|
(let [frame-id (uuid/next)
|
||||||
|
frame-name (impl-generate-unique-name objects (:name obj))
|
||||||
sch (->> (map #(get objects %) (:shapes obj))
|
sch (->> (map #(get objects %) (:shapes obj))
|
||||||
(map #(prepare-shape-change % delta frame-id)))
|
(map #(prepare-shape-change objects % delta frame-id)))
|
||||||
renamed-frame (-> obj
|
renamed-frame (-> obj
|
||||||
(assoc :id frame-id)
|
(assoc :id frame-id)
|
||||||
|
(assoc :name frame-name)
|
||||||
(assoc :frame-id uuid/zero)
|
(assoc :frame-id uuid/zero)
|
||||||
(assoc :shapes (mapv :id sch)))
|
(assoc :shapes (mapv :id sch)))
|
||||||
moved-frame (geom/move renamed-frame delta)
|
moved-frame (geom/move renamed-frame delta)
|
||||||
|
@ -2090,8 +2119,7 @@
|
||||||
delta {:x (- (:x mouse-pos) (:x orig-pos))
|
delta {:x (- (:x mouse-pos) (:x orig-pos))
|
||||||
:y (- (:y mouse-pos) (:y orig-pos))}
|
:y (- (:y mouse-pos) (:y orig-pos))}
|
||||||
|
|
||||||
rchanges (->> (map (partial prepare-change delta) selected)
|
rchanges (prepare-changes state delta)
|
||||||
(flatten))
|
|
||||||
uchanges (map (fn [ch]
|
uchanges (map (fn [ch]
|
||||||
{:type :del-obj
|
{:type :del-obj
|
||||||
:id (:id ch)})
|
:id (:id ch)})
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue