Merge pull request #3115 from penpot/hiru-components-boards

🎉 Now all component roots are frames
This commit is contained in:
Pablo Alba 2023-04-14 12:40:32 +02:00 committed by GitHub
commit 33656f8eb4
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
11 changed files with 312 additions and 189 deletions

View File

@ -181,7 +181,9 @@
;; incoming shapes to the parent. ;; incoming shapes to the parent.
(update :shapes d/vec-without-nils))] (update :shapes d/vec-without-nils))]
(cond-> parent (cond-> parent
(and (:shape-ref parent) (= (:type parent) :group) (not ignore-touched)) (and (:shape-ref parent)
(#{:group :frame} (:type parent))
(not ignore-touched))
(-> (update :touched cph/set-touched-group :shapes-group) (-> (update :touched cph/set-touched-group :shapes-group)
(dissoc :remote-synced?))))) (dissoc :remote-synced?)))))

View File

@ -13,6 +13,7 @@
[app.common.types.components-list :as ctkl] [app.common.types.components-list :as ctkl]
[app.common.types.pages-list :as ctpl] [app.common.types.pages-list :as ctpl]
[app.common.types.shape-tree :as ctst] [app.common.types.shape-tree :as ctst]
[app.common.uuid :as uuid]
[clojure.spec.alpha :as s])) [clojure.spec.alpha :as s]))
(s/def ::type #{:page :component}) (s/def ::type #{:page :component})
@ -147,7 +148,8 @@
(ctpl/get-page library-data (:main-instance-page component))) (ctpl/get-page library-data (:main-instance-page component)))
component-shape (if components-v2 component-shape (if components-v2
(-> (get-shape component-page (:main-instance-id component)) (-> (get-shape component-page (:main-instance-id component))
(assoc :parent-id nil)) (assoc :parent-id nil)
(assoc :frame-id uuid/zero))
(get-shape component (:id component))) (get-shape component (:id component)))
orig-pos (gpt/point (:x component-shape) (:y component-shape)) orig-pos (gpt/point (:x component-shape) (:y component-shape))
@ -156,8 +158,10 @@
objects (:objects container) objects (:objects container)
unames (volatile! (common/retrieve-used-names objects)) unames (volatile! (common/retrieve-used-names objects))
frame-id (ctst/frame-id-by-position objects (gpt/add orig-pos delta)) frame-id (ctst/frame-id-by-position objects
frame-ids-map (volatile! {}) (gpt/add orig-pos delta)
{:skip-components? true}) ; It'd be weird to make an instance
frame-ids-map (volatile! {}) ; inside other component
update-new-shape update-new-shape
(fn [new-shape original-shape] (fn [new-shape original-shape]
@ -172,7 +176,13 @@
(cond-> new-shape (cond-> new-shape
:always :always
(-> (gsh/move delta) (-> (gsh/move delta)
(dissoc :touched :main-instance?)) (dissoc :touched))
main-instance?
(assoc :main-instance? true)
(not main-instance?)
(dissoc :main-instance?)
(and (not main-instance?) (nil? (:shape-ref original-shape))) (and (not main-instance?) (nil? (:shape-ref original-shape)))
(assoc :shape-ref (:id original-shape)) (assoc :shape-ref (:id original-shape))
@ -205,5 +215,6 @@
(update $ :frame-id #(get @frame-ids-map % frame-id)) (update $ :frame-id #(get @frame-ids-map % frame-id))
(update $ :parent-id #(or % (:frame-id $)))))] (update $ :parent-id #(or % (:frame-id $)))))]
[new-shape (map remap-frame-id new-shapes)]))) [(remap-frame-id new-shape)
(map remap-frame-id new-shapes)])))

View File

@ -346,7 +346,7 @@
(map (partial get-component-root file-data) components) (map (partial get-component-root file-data) components)
start-pos start-pos
grid-gap)] grid-gap)]
(loop [file-data file-data (loop [file-data file-data
components-seq (seq components) components-seq (seq components)
position-seq position-seq] position-seq position-seq]
(let [component (first components-seq) (let [component (first components-seq)
@ -355,10 +355,26 @@
file-data file-data
(recur (add-main-instance file-data component position) (recur (add-main-instance file-data component position)
(rest components-seq) (rest components-seq)
(rest position-seq)))))))] (rest position-seq)))))))
root-to-board
(fn [shape]
(cond-> shape
(and (ctk/instance-root? shape)
(not= (:type shape) :frame))
(assoc :type :frame
:fills []
:hide-in-viewer true
:rx 0
:ry 0)))
roots-to-board
(fn [page]
(update page :objects update-vals root-to-board))]
(-> file-data (-> file-data
(add-instance-grid (sort-by :name components)) (add-instance-grid (sort-by :name components))
(update :pages-index update-vals roots-to-board)
(assoc-in [:options :components-v2] true)))))) (assoc-in [:options :components-v2] true))))))
(defn- absorb-components (defn- absorb-components

View File

@ -13,6 +13,7 @@
[app.common.math :as mth] [app.common.math :as mth]
[app.common.pages.helpers :as cph] [app.common.pages.helpers :as cph]
[app.common.spec :as us] [app.common.spec :as us]
[app.common.types.component :as ctk]
[app.common.types.shape :as cts] [app.common.types.shape :as cts]
[app.common.types.shape.layout :as ctl] [app.common.types.shape.layout :as ctl]
[app.common.uuid :as uuid] [app.common.uuid :as uuid]
@ -108,20 +109,24 @@
(defn get-frames (defn get-frames
"Retrieves all frame objects as vector" "Retrieves all frame objects as vector"
[objects] ([objects] (get-frames objects nil))
(or (-> objects meta ::index-frames) ([objects {:keys [skip-components?] :or {skip-components? false}}]
(let [lookup (d/getf objects) (->> (or (-> objects meta ::index-frames)
xform (comp (remove #(= uuid/zero %)) (let [lookup (d/getf objects)
(keep lookup) xform (comp (remove #(= uuid/zero %))
(filter cph/frame-shape?))] (keep lookup)
(->> (keys objects) (filter cph/frame-shape?))]
(into [] xform))))) (->> (keys objects)
(into [] xform))))
(filter #(or (not skip-components?)
(not (ctk/instance-root? %)))))))
(defn get-frames-ids (defn get-frames-ids
"Retrieves all frame ids as vector" "Retrieves all frame ids as vector"
[objects] ([objects] (get-frames-ids objects nil))
(->> (get-frames objects) ([objects options]
(mapv :id))) (->> (get-frames objects options)
(mapv :id))))
(defn get-nested-frames (defn get-nested-frames
[objects frame-id] [objects frame-id]
@ -228,24 +233,27 @@
(sort comp ids)))) (sort comp ids))))
(defn frame-id-by-position (defn frame-id-by-position
[objects position] ([objects position] (frame-id-by-position objects position nil))
(assert (gpt/point? position)) ([objects position options]
(let [top-frame (assert (gpt/point? position))
(->> (get-frames-ids objects) (let [top-frame
(sort-z-index objects) (->> (get-frames-ids objects options)
(d/seek #(and position (gsh/has-point? (get objects %) position))))] (sort-z-index objects)
(or top-frame uuid/zero))) (d/seek #(and position (gsh/has-point? (get objects %) position))))]
(or top-frame uuid/zero))))
(defn frame-by-position (defn frame-by-position
[objects position] ([objects position] (frame-by-position objects position nil))
(let [frame-id (frame-id-by-position objects position)] ([objects position options]
(get objects frame-id))) (let [frame-id (frame-id-by-position objects position options)]
(get objects frame-id))))
(defn all-frames-by-position (defn all-frames-by-position
[objects position] ([objects position] (all-frames-by-position objects position nil))
(->> (get-frames-ids objects) ([objects position options]
(filter #(and position (gsh/has-point? (get objects %) position))) (->> (get-frames-ids objects options)
(sort-z-index objects))) (filter #(and position (gsh/has-point? (get objects %) position)))
(sort-z-index objects))))
(defn top-nested-frame (defn top-nested-frame
"Search for the top nested frame for positioning shapes when moving or creating. "Search for the top nested frame for positioning shapes when moving or creating.

View File

@ -315,11 +315,13 @@
objects (wsh/lookup-page-objects state page-id) objects (wsh/lookup-page-objects state page-id)
shapes (dwg/shapes-for-grouping objects selected)] shapes (dwg/shapes-for-grouping objects selected)]
(when-not (empty? shapes) (when-not (empty? shapes)
(let [[group _ changes] (let [[root _ changes]
(dwlh/generate-add-component it shapes objects page-id file-id components-v2 dwg/prepare-create-group)] (dwlh/generate-add-component it shapes objects page-id file-id components-v2
dwg/prepare-create-group
dwsh/prepare-create-artboard-from-selection)]
(when-not (empty? (:redo-changes changes)) (when-not (empty? (:redo-changes changes))
(rx/of (dch/commit-changes changes) (rx/of (dch/commit-changes changes)
(dws/select-shapes (d/ordered-set (:id group))))))))))) (dws/select-shapes (d/ordered-set (:id root)))))))))))
(defn add-component (defn add-component
"Add a new component to current file library, from the currently selected shapes. "Add a new component to current file library, from the currently selected shapes.

View File

@ -62,37 +62,48 @@
;; ---- Components and instances creation ---- ;; ---- Components and instances creation ----
(defn generate-add-component (defn generate-add-component
"If there is exactly one id, and it's a group or a frame, and not already a component, "If there is exactly one id, and it's a frame (or a group in v1), and not already a component,
use it as root. Otherwise, create a group that contains all ids. Then, make a use it as root. Otherwise, create a frame (v2) or group (v1) that contains all ids. Then, make a
component with it, and link all shapes to their corresponding one in the component." component with it, and link all shapes to their corresponding one in the component."
[it shapes objects page-id file-id components-v2 prepare-create-group] [it shapes objects page-id file-id components-v2 prepare-create-group prepare-create-board]
(let [[group changes] (let [changes (pcb/empty-changes it page-id)
[root changes]
(if (and (= (count shapes) 1) (if (and (= (count shapes) 1)
(or (= (:type (first shapes)) :group) (or (and (= (:type (first shapes)) :group) (not components-v2))
(= (:type (first shapes)) :frame)) (= (:type (first shapes)) :frame))
(not (ctk/instance-root? (first shapes)))) (not (ctk/instance-root? (first shapes))))
[(first shapes) (-> (pcb/empty-changes it page-id) [(first shapes) (-> (pcb/empty-changes it page-id)
(pcb/with-objects objects))] (pcb/with-objects objects))]
(let [group-name (if (= 1 (count shapes)) (let [root-name (if (= 1 (count shapes))
(:name (first shapes)) (:name (first shapes))
"Component 1")] "Component 1")]
(prepare-create-group it ; This function needs to be passed as argument (if-not components-v2
objects ; to avoid a circular dependence (prepare-create-group it ; These functions needs to be passed as argument
page-id objects ; to avoid a circular dependence
shapes page-id
group-name shapes
(not (ctk/instance-root? (first shapes)))))) root-name
(not (ctk/instance-root? (first shapes))))
(prepare-create-board changes
(uuid/next)
(:parent-id (first shapes))
objects
(map :id shapes)
nil
root-name
true))))
name (:name group) name (:name root)
[path name] (cph/parse-path-name name) [path name] (cph/parse-path-name name)
[root-shape new-shapes updated-shapes] [root-shape new-shapes updated-shapes]
(if-not components-v2 (if-not components-v2
(ctn/make-component-shape group objects file-id components-v2) (ctn/make-component-shape root objects file-id components-v2)
(let [new-id (uuid/next)] (let [new-id (uuid/next)]
[(assoc group :id new-id) [(assoc root :id new-id)
nil nil
[(assoc group [(assoc root
:component-id new-id :component-id new-id
:component-file file-id :component-file file-id
:component-root? true :component-root? true
@ -104,9 +115,9 @@
name name
new-shapes new-shapes
updated-shapes updated-shapes
(:id group) (:id root)
page-id))] page-id))]
[group (:id root-shape) changes])) [root (:id root-shape) changes]))
(defn duplicate-component (defn duplicate-component
"Clone the root shape of the component and all children. Generate new "Clone the root shape of the component and all children. Generate new
@ -163,7 +174,7 @@
components-v2) components-v2)
changes (cond-> (pcb/add-object changes (first new-shapes) {:ignore-touched true}) changes (cond-> (pcb/add-object changes (first new-shapes) {:ignore-touched true})
(some? old-id) (pcb/amend-last-change #(assoc % :old-id old-id))) ; on copy/paste old id is used later to reorder the paster layers (some? old-id) (pcb/amend-last-change #(assoc % :old-id old-id))) ; on copy/paste old id is used later to reorder the paster layers
changes (reduce #(pcb/add-object %1 %2 {:ignore-touched true}) changes (reduce #(pcb/add-object %1 %2 {:ignore-touched true})
changes changes

View File

@ -74,6 +74,31 @@
:parent-id parent-id :parent-id parent-id
:index index)))) :index index))))
(defn prepare-add-shape
[changes attrs objects selected]
(let [id (or (:id attrs) (uuid/next))
name (:name attrs)
shape (make-new-shape
(assoc attrs :id id :name name)
objects
selected)
index (:index (meta attrs))
changes (-> changes
(pcb/with-objects objects)
(cond-> (some? index)
(pcb/add-object shape {:index index}))
(cond-> (nil? index)
(pcb/add-object shape))
(cond-> (some? (:parent-id attrs))
(pcb/change-parent (:parent-id attrs) [shape]))
(cond-> (ctl/grid-layout? objects (:parent-id shape))
(pcb/update-shapes [(:parent-id shape)] ctl/assign-cells)))]
[shape changes]))
(defn add-shape (defn add-shape
([attrs] ([attrs]
(add-shape attrs {})) (add-shape attrs {}))
@ -87,27 +112,11 @@
objects (wsh/lookup-page-objects state page-id) objects (wsh/lookup-page-objects state page-id)
selected (wsh/lookup-selected state) selected (wsh/lookup-selected state)
id (or (:id attrs) (uuid/next)) changes (pcb/empty-changes it page-id)
name (:name attrs)
shape (make-new-shape [shape changes]
(assoc attrs :id id :name name) (prepare-add-shape changes attrs objects selected)
objects
selected)
index (:index (meta attrs))
changes (-> (pcb/empty-changes it page-id)
(pcb/with-objects objects)
(cond-> (some? index)
(pcb/add-object shape {:index index}))
(cond-> (nil? index)
(pcb/add-object shape))
(cond-> (some? (:parent-id attrs))
(pcb/change-parent (:parent-id attrs) [shape]))
(cond-> (ctl/grid-layout? objects (:parent-id shape))
(pcb/update-shapes [(:parent-id shape)] ctl/assign-cells))
)
undo-id (js/Symbol)] undo-id (js/Symbol)]
(rx/concat (rx/concat
@ -116,36 +125,39 @@
(when-not no-update-layout? (when-not no-update-layout?
(ptk/data-event :layout/update [(:parent-id shape)])) (ptk/data-event :layout/update [(:parent-id shape)]))
(when-not no-select? (when-not no-select?
(dws/select-shapes (d/ordered-set id))) (dws/select-shapes (d/ordered-set (:id shape))))
(dwu/commit-undo-transaction undo-id)) (dwu/commit-undo-transaction undo-id))
(when (= :text (:type attrs)) (when (= :text (:type attrs))
(->> (rx/of (dwe/start-edition-mode id)) (->> (rx/of (dwe/start-edition-mode (:id shape)))
(rx/observe-on :async))))))))) (rx/observe-on :async)))))))))
(defn prepare-move-shapes-into-frame
[changes frame-id shapes objects]
(let [ordered-indexes (cph/order-by-indexed-shapes objects shapes)
parent-id (get-in objects [frame-id :parent-id])
ordered-indexes (->> ordered-indexes (remove #(= % parent-id)))
to-move-shapes (map (d/getf objects) ordered-indexes)]
(when (d/not-empty? to-move-shapes)
(-> changes
(cond-> (not (ctl/any-layout? objects frame-id))
(pcb/update-shapes ordered-indexes ctl/remove-layout-item-data))
(pcb/update-shapes ordered-indexes #(cond-> % (cph/frame-shape? %) (assoc :hide-in-viewer true)))
(pcb/change-parent frame-id to-move-shapes 0)
(cond-> (ctl/grid-layout? objects frame-id)
(pcb/update-shapes [frame-id] ctl/assign-cells))))))
(defn move-shapes-into-frame [frame-id shapes] (defn move-shapes-into-frame [frame-id shapes]
(ptk/reify ::move-shapes-into-frame (ptk/reify ::move-shapes-into-frame
ptk/WatchEvent ptk/WatchEvent
(watch [it state _] (watch [it state _]
(let [page-id (:current-page-id state) (let [page-id (:current-page-id state)
objects (wsh/lookup-page-objects state page-id) objects (wsh/lookup-page-objects state page-id)
changes (-> (pcb/empty-changes it page-id)
ordered-indexes (cph/order-by-indexed-shapes objects shapes) (pcb/with-objects objects))
parent-id (get-in objects [frame-id :parent-id]) changes (prepare-move-shapes-into-frame changes
frame-id
ordered-indexes (->> ordered-indexes (remove #(= % parent-id))) shapes
to-move-shapes (map (d/getf objects) ordered-indexes) objects)]
changes
(when (d/not-empty? to-move-shapes)
(-> (pcb/empty-changes it page-id)
(pcb/with-objects objects)
(cond-> (not (ctl/any-layout? objects frame-id))
(pcb/update-shapes ordered-indexes ctl/remove-layout-item-data))
(pcb/update-shapes ordered-indexes #(cond-> % (cph/frame-shape? %) (assoc :hide-in-viewer true)))
(pcb/change-parent frame-id to-move-shapes 0)
(cond-> (ctl/grid-layout? objects frame-id)
(pcb/update-shapes [frame-id] ctl/assign-cells))))]
(if (some? changes) (if (some? changes)
(rx/of (dch/commit-changes changes)) (rx/of (dch/commit-changes changes))
(rx/empty)))))) (rx/empty))))))
@ -362,6 +374,35 @@
;; Artboard ;; Artboard
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
(defn prepare-create-artboard-from-selection
[changes id parent-id objects selected index frame-name without-fill?]
(let [selected-objs (map #(get objects %) selected)
new-index (or index
(cph/get-index-replacement selected objects))]
(when (d/not-empty? selected)
(let [srect (gsh/selection-rect selected-objs)
frame-id (get-in objects [(first selected) :frame-id])
parent-id (or parent-id (get-in objects [(first selected) :parent-id]))
shape (-> (cts/make-minimal-shape :frame)
(merge {:x (:x srect) :y (:y srect) :width (:width srect) :height (:height srect)})
(cond-> id
(assoc :id id))
(cond-> frame-name
(assoc :name frame-name))
(assoc :frame-id frame-id :parent-id parent-id)
(with-meta {:index new-index})
(cond-> (or (not= frame-id uuid/zero) without-fill?)
(assoc :fills [] :hide-in-viewer true))
(cts/setup-rect-selrect))
[shape changes]
(prepare-add-shape changes shape objects selected)
changes
(prepare-move-shapes-into-frame changes (:id shape) selected objects)]
[shape changes]))))
(defn create-artboard-from-selection (defn create-artboard-from-selection
([] ([]
(create-artboard-from-selection nil)) (create-artboard-from-selection nil))
@ -372,34 +413,33 @@
([id parent-id index] ([id parent-id index]
(ptk/reify ::create-artboard-from-selection (ptk/reify ::create-artboard-from-selection
ptk/WatchEvent ptk/WatchEvent
(watch [_ state _] (watch [it state _]
(let [page-id (:current-page-id state) (let [page-id (:current-page-id state)
objects (wsh/lookup-page-objects state page-id) objects (wsh/lookup-page-objects state page-id)
selected (wsh/lookup-selected state) selected (wsh/lookup-selected state)
selected (cph/clean-loops objects selected) selected (cph/clean-loops objects selected)
selected-objs (map #(get objects %) selected)
new-index (or index changes (pcb/empty-changes it page-id)
(cph/get-index-replacement selected objects))]
(when (d/not-empty? selected) [frame-shape changes]
(let [srect (gsh/selection-rect selected-objs) (prepare-create-artboard-from-selection changes
frame-id (get-in objects [(first selected) :frame-id]) id
parent-id (or parent-id (get-in objects [(first selected) :parent-id])) parent-id
shape (-> (cts/make-minimal-shape :frame) objects
(merge {:x (:x srect) :y (:y srect) :width (:width srect) :height (:height srect)}) selected
(cond-> id index
(assoc :id id)) nil
(assoc :frame-id frame-id :parent-id parent-id) false)
(with-meta {:index new-index})
(cond-> (not= frame-id uuid/zero) undo-id (js/Symbol)]
(assoc :fills [] :hide-in-viewer true))
(cts/setup-rect-selrect)) (when changes
undo-id (js/Symbol)] (rx/of
(rx/of (dwu/start-undo-transaction undo-id)
(dwu/start-undo-transaction undo-id) (dch/commit-changes changes)
(add-shape shape {:no-update-layout? true}) (dws/select-shapes (d/ordered-set (:id frame-shape)))
(move-shapes-into-frame (:id shape) selected) (ptk/data-event :layout/update [(:id frame-shape)])
(ptk/data-event :layout/update [(:id shape)]) (dwu/commit-undo-transaction undo-id))))))))
(dwu/commit-undo-transaction undo-id)))))))))
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; Shape Flags ;; Shape Flags

View File

@ -179,8 +179,10 @@
modifiers modifiers
(-> (ctm/empty) (-> (ctm/empty)
(cond-> displacement (cond-> displacement
(ctm/move displacement)) (ctm/move displacement))
(ctm/resize scalev resize-origin shape-transform shape-transform-inverse) (ctm/resize scalev resize-origin shape-transform shape-transform-inverse)
(cond-> set-fix-width? (cond-> set-fix-width?

View File

@ -6,6 +6,7 @@
(ns frontend-tests.helpers.pages (ns frontend-tests.helpers.pages
(:require (:require
[app.common.data :as d]
[app.common.geom.point :as gpt] [app.common.geom.point :as gpt]
[app.common.pages :as cp] [app.common.pages :as cp]
[app.common.pages.changes-builder :as pcb] [app.common.pages.changes-builder :as pcb]
@ -15,6 +16,7 @@
[app.main.data.workspace.groups :as dwg] [app.main.data.workspace.groups :as dwg]
[app.main.data.workspace.layout :as layout] [app.main.data.workspace.layout :as layout]
[app.main.data.workspace.libraries-helpers :as dwlh] [app.main.data.workspace.libraries-helpers :as dwlh]
[app.main.data.workspace.shapes :as dwsh]
[app.main.data.workspace.state-helpers :as wsh])) [app.main.data.workspace.state-helpers :as wsh]))
;; ---- Helpers to manage pages and objects ;; ---- Helpers to manage pages and objects
@ -102,6 +104,28 @@
(update state :workspace-data (update state :workspace-data
cp/process-changes (:redo-changes changes))))))) cp/process-changes (:redo-changes changes)))))))
(defn frame-shapes
([state label ids] (frame-shapes state label ids "Board"))
([state label ids frame-name]
(let [page (current-page state)
shapes (dwg/shapes-for-grouping (:objects page) ids)
changes (pcb/empty-changes nil (:id page))]
(if (empty? shapes)
state
(let [[frame changes]
(dwsh/prepare-create-artboard-from-selection changes
nil
nil
(:objects page)
(map :id shapes)
nil
frame-name
true)]
(swap! idmap assoc label (:id frame))
(update state :workspace-data
cp/process-changes (:redo-changes changes)))))))
(defn make-component (defn make-component
[state instance-label component-label shape-ids] [state instance-label component-label shape-ids]
(let [page (current-page state) (let [page (current-page state)
@ -115,7 +139,8 @@
(:id page) (:id page)
current-file-id current-file-id
true true
dwg/prepare-create-group)] dwg/prepare-create-group
dwsh/prepare-create-artboard-from-selection)]
(swap! idmap assoc instance-label (:id group) (swap! idmap assoc instance-label (:id group)
component-label component-id) component-label component-id)

View File

@ -6,17 +6,18 @@
(ns frontend-tests.state-components-sync-test (ns frontend-tests.state-components-sync-test
(:require (:require
[app.common.colors :as clr] [app.common.colors :as clr]
[app.main.data.workspace :as dw] [app.common.types.file :as ctf]
[app.main.data.workspace.changes :as dch] [app.main.data.workspace :as dw]
[app.main.data.workspace.libraries :as dwl] [app.main.data.workspace.changes :as dch]
[app.main.data.workspace.shapes :as dwsh] [app.main.data.workspace.libraries :as dwl]
[app.main.data.workspace.state-helpers :as wsh] [app.main.data.workspace.shapes :as dwsh]
[cljs.test :as t :include-macros true] [app.main.data.workspace.state-helpers :as wsh]
[frontend-tests.helpers.events :as the] [cljs.test :as t :include-macros true]
[frontend-tests.helpers.libraries :as thl] [frontend-tests.helpers.events :as the]
[frontend-tests.helpers.pages :as thp] [frontend-tests.helpers.libraries :as thl]
[potok.core :as ptk])) [frontend-tests.helpers.pages :as thp]
[potok.core :as ptk]))
(t/use-fixtures :each (t/use-fixtures :each
{:before thp/reset-idmap!}) {:before thp/reset-idmap!})
@ -41,6 +42,11 @@
store (the/prepare-store state done store (the/prepare-store state done
(fn [new-state] (fn [new-state]
;; Uncomment to debug
;; (ctf/dump-tree (get new-state :workspace-data)
;; (get new-state :current-page-id)
;; (get new-state :workspace-libraries)
;; false true)
; Expected shape tree: ; Expected shape tree:
; ;
; [Page] ; [Page]
@ -355,11 +361,11 @@
{:name "Circle 1" {:name "Circle 1"
:fill-color clr/black :fill-color clr/black
:fill-opacity 0}) :fill-opacity 0})
(thp/group-shapes :group1 (thp/frame-shapes :frame1
[(thp/id :instance1) [(thp/id :instance1)
(thp/id :shape2)]) (thp/id :shape2)])
(thp/make-component :main2 :component2 (thp/make-component :main2 :component2
[(thp/id :group1)]) [(thp/id :frame1)])
(thp/instantiate-component :instance2 (thp/instantiate-component :instance2
(thp/id :component2))) (thp/id :component2)))
@ -396,7 +402,7 @@
new-state new-state
(thp/id :instance2))] (thp/id :instance2))]
(t/is (= (:name instance2) "Group")) (t/is (= (:name instance2) "Board"))
(t/is (= (:touched instance2) nil)) (t/is (= (:touched instance2) nil))
(t/is (= (:name instance1) "Rect 1")) (t/is (= (:name instance1) "Rect 1"))
(t/is (= (:touched instance1) nil)) (t/is (= (:touched instance1) nil))
@ -409,7 +415,7 @@
(t/is (= (:fill-color shape2) clr/white)) (t/is (= (:fill-color shape2) clr/white))
(t/is (= (:fill-opacity shape2) 1)) (t/is (= (:fill-opacity shape2) 1))
(t/is (= (:name c-instance2) "Group")) (t/is (= (:name c-instance2) "Board"))
(t/is (= (:touched c-instance2) nil)) (t/is (= (:touched c-instance2) nil))
(t/is (= (:name c-instance1) "Rect 1")) (t/is (= (:name c-instance1) "Rect 1"))
(t/is (= (:touched c-instance1) nil)) (t/is (= (:touched c-instance1) nil))
@ -446,11 +452,11 @@
{:name "Circle 1" {:name "Circle 1"
:fill-color clr/black :fill-color clr/black
:fill-opacity 0}) :fill-opacity 0})
(thp/group-shapes :group1 (thp/frame-shapes :frame1
[(thp/id :instance1) [(thp/id :instance1)
(thp/id :shape2)]) (thp/id :shape2)])
(thp/make-component :instance2 :component2 (thp/make-component :instance2 :component2
[(thp/id :group1)]) [(thp/id :frame1)])
(thp/instantiate-component :instance2 (thp/instantiate-component :instance2
(thp/id :component2))) (thp/id :component2)))
@ -487,7 +493,7 @@
new-state new-state
(thp/id :instance2))] (thp/id :instance2))]
(t/is (= (:name instance2) "Group")) (t/is (= (:name instance2) "Board"))
(t/is (= (:touched instance2) nil)) (t/is (= (:touched instance2) nil))
(t/is (= (:name instance1) "Rect 1")) (t/is (= (:name instance1) "Rect 1"))
(t/is (= (:touched instance1) nil)) (t/is (= (:touched instance1) nil))
@ -500,7 +506,7 @@
(t/is (= (:fill-color shape2) clr/test)) (t/is (= (:fill-color shape2) clr/test))
(t/is (= (:fill-opacity shape2) 0.5)) (t/is (= (:fill-opacity shape2) 0.5))
(t/is (= (:name c-instance2) "Group")) (t/is (= (:name c-instance2) "Board"))
(t/is (= (:touched c-instance2) nil)) (t/is (= (:touched c-instance2) nil))
(t/is (= (:name c-instance1) "Rect 1")) (t/is (= (:name c-instance1) "Rect 1"))
(t/is (= (:touched c-instance1) nil)) (t/is (= (:touched c-instance1) nil))
@ -537,11 +543,11 @@
{:name "Circle 1" {:name "Circle 1"
:fill-color clr/black :fill-color clr/black
:fill-opacity 0}) :fill-opacity 0})
(thp/group-shapes :group1 (thp/frame-shapes :frame1
[(thp/id :instance1) [(thp/id :instance1)
(thp/id :shape2)]) (thp/id :shape2)])
(thp/make-component :instance2 :component2 (thp/make-component :instance2 :component2
[(thp/id :group1)]) [(thp/id :frame1)])
(thp/instantiate-component :instance2 (thp/instantiate-component :instance2
(thp/id :component2))) (thp/id :component2)))
@ -578,7 +584,7 @@
new-state new-state
(thp/id :instance2))] (thp/id :instance2))]
(t/is (= (:name instance2) "Group")) (t/is (= (:name instance2) "Board"))
(t/is (= (:touched instance2) nil)) (t/is (= (:touched instance2) nil))
(t/is (= (:name instance1) "Rect 1")) (t/is (= (:name instance1) "Rect 1"))
(t/is (= (:touched instance1) nil)) (t/is (= (:touched instance1) nil))
@ -591,7 +597,7 @@
(t/is (= (:fill-color shape2) clr/test)) (t/is (= (:fill-color shape2) clr/test))
(t/is (= (:fill-opacity shape2) 0.5)) (t/is (= (:fill-opacity shape2) 0.5))
(t/is (= (:name c-instance2) "Group")) (t/is (= (:name c-instance2) "Board"))
(t/is (= (:touched c-instance2) nil)) (t/is (= (:touched c-instance2) nil))
(t/is (= (:name c-instance1) "Rect 1")) (t/is (= (:name c-instance1) "Rect 1"))
(t/is (= (:touched c-instance1) nil)) (t/is (= (:touched c-instance1) nil))
@ -943,11 +949,11 @@
{:name "Circle 1" {:name "Circle 1"
:fill-color clr/black :fill-color clr/black
:fill-opacity 0}) :fill-opacity 0})
(thp/group-shapes :group1 (thp/frame-shapes :frame1
[(thp/id :instance1) [(thp/id :instance1)
(thp/id :shape2)]) (thp/id :shape2)])
(thp/make-component :main2 :component2 (thp/make-component :main2 :component2
[(thp/id :group1)]) [(thp/id :frame1)])
(thp/instantiate-component :instance2 (thp/instantiate-component :instance2
(thp/id :component2))) (thp/id :component2)))
@ -983,7 +989,7 @@
new-state new-state
(thp/id :instance2))] (thp/id :instance2))]
(t/is (= (:name instance2) "Group")) (t/is (= (:name instance2) "Board"))
(t/is (= (:touched instance2) nil)) (t/is (= (:touched instance2) nil))
(t/is (= (:name instance1) "Rect 1")) (t/is (= (:name instance1) "Rect 1"))
(t/is (= (:touched instance1) nil)) (t/is (= (:touched instance1) nil))
@ -996,7 +1002,7 @@
(t/is (= (:fill-color shape2) clr/white)) (t/is (= (:fill-color shape2) clr/white))
(t/is (= (:fill-opacity shape2) 1)) (t/is (= (:fill-opacity shape2) 1))
(t/is (= (:name c-instance2) "Group")) (t/is (= (:name c-instance2) "Board"))
(t/is (= (:touched c-instance2) nil)) (t/is (= (:touched c-instance2) nil))
(t/is (= (:name c-instance1) "Rect 1")) (t/is (= (:name c-instance1) "Rect 1"))
(t/is (= (:touched c-instance1) nil)) (t/is (= (:touched c-instance1) nil))
@ -1034,11 +1040,11 @@
{:name "Circle 1" {:name "Circle 1"
:fill-color clr/black :fill-color clr/black
:fill-opacity 0}) :fill-opacity 0})
(thp/group-shapes :group1 (thp/frame-shapes :frame1
[(thp/id :instance1) [(thp/id :instance1)
(thp/id :shape2)]) (thp/id :shape2)])
(thp/make-component :instance2 :component2 (thp/make-component :instance2 :component2
[(thp/id :group1)]) [(thp/id :frame1)])
(thp/instantiate-component :instance2 (thp/instantiate-component :instance2
(thp/id :component2))) (thp/id :component2)))
@ -1074,7 +1080,7 @@
new-state new-state
(thp/id :instance2))] (thp/id :instance2))]
(t/is (= (:name instance2) "Group")) (t/is (= (:name instance2) "Board"))
(t/is (= (:touched instance2) nil)) (t/is (= (:touched instance2) nil))
(t/is (= (:name instance1) "Rect 1")) (t/is (= (:name instance1) "Rect 1"))
(t/is (= (:touched instance1) nil)) (t/is (= (:touched instance1) nil))
@ -1087,7 +1093,7 @@
(t/is (= (:fill-color shape2) clr/white)) (t/is (= (:fill-color shape2) clr/white))
(t/is (= (:fill-opacity shape2) 1)) (t/is (= (:fill-opacity shape2) 1))
(t/is (= (:name c-instance2) "Group")) (t/is (= (:name c-instance2) "Board"))
(t/is (= (:touched c-instance2) nil)) (t/is (= (:touched c-instance2) nil))
(t/is (= (:name c-instance1) "Rect 1")) (t/is (= (:name c-instance1) "Rect 1"))
(t/is (= (:touched c-instance1) nil)) (t/is (= (:touched c-instance1) nil))
@ -1126,11 +1132,11 @@
{:name "Circle 1" {:name "Circle 1"
:fill-color clr/black :fill-color clr/black
:fill-opacity 0}) :fill-opacity 0})
(thp/group-shapes :group1 (thp/frame-shapes :frame1
[(thp/id :instance1) [(thp/id :instance1)
(thp/id :shape2)]) (thp/id :shape2)])
(thp/make-component :instance2 :component2 (thp/make-component :instance2 :component2
[(thp/id :group1)]) [(thp/id :frame1)])
(thp/instantiate-component :instance2 (thp/instantiate-component :instance2
(thp/id :component2))) (thp/id :component2)))
@ -1169,7 +1175,7 @@
new-state new-state
(thp/id :instance2))] (thp/id :instance2))]
(t/is (= (:name instance2) "Group")) (t/is (= (:name instance2) "Board"))
(t/is (= (:touched instance2) nil)) (t/is (= (:touched instance2) nil))
(t/is (= (:name instance1) "Rect 1")) (t/is (= (:name instance1) "Rect 1"))
(t/is (= (:touched instance1) nil)) (t/is (= (:touched instance1) nil))
@ -1182,7 +1188,7 @@
(t/is (= (:fill-color shape2) clr/white)) (t/is (= (:fill-color shape2) clr/white))
(t/is (= (:fill-opacity shape2) 1)) (t/is (= (:fill-opacity shape2) 1))
(t/is (= (:name c-instance2) "Group")) (t/is (= (:name c-instance2) "Board"))
(t/is (= (:touched c-instance2) nil)) (t/is (= (:touched c-instance2) nil))
(t/is (= (:name c-instance1) "Rect 1")) (t/is (= (:name c-instance1) "Rect 1"))
(t/is (= (:touched c-instance1) nil)) (t/is (= (:touched c-instance1) nil))
@ -1929,11 +1935,11 @@
{:name "Circle 1" {:name "Circle 1"
:fill-color clr/black :fill-color clr/black
:fill-opacity 0}) :fill-opacity 0})
(thp/group-shapes :group1 (thp/frame-shapes :frame1
[(thp/id :instance1) [(thp/id :instance1)
(thp/id :shape2)]) (thp/id :shape2)])
(thp/make-component :main2 :component2 (thp/make-component :main2 :component2
[(thp/id :group1)]) [(thp/id :frame1)])
(thp/instantiate-component :instance2 (thp/instantiate-component :instance2
(thp/id :component2)) (thp/id :component2))
(thp/instantiate-component :instance3 (thp/instantiate-component :instance3
@ -1983,7 +1989,7 @@
new-state new-state
(thp/id :instance3))] (thp/id :instance3))]
(t/is (= (:name instance2) "Group")) (t/is (= (:name instance2) "Board"))
(t/is (= (:touched instance2) nil)) (t/is (= (:touched instance2) nil))
(t/is (= (:name instance1) "Rect 1")) (t/is (= (:name instance1) "Rect 1"))
(t/is (= (:touched instance1) nil)) (t/is (= (:touched instance1) nil))
@ -1996,7 +2002,7 @@
(t/is (= (:fill-color shape2) clr/white)) (t/is (= (:fill-color shape2) clr/white))
(t/is (= (:fill-opacity shape2) 1)) (t/is (= (:fill-opacity shape2) 1))
(t/is (= (:name c-instance2) "Group")) (t/is (= (:name c-instance2) "Board"))
(t/is (= (:touched c-instance2) nil)) (t/is (= (:touched c-instance2) nil))
(t/is (= (:name c-instance1) "Rect 1")) (t/is (= (:name c-instance1) "Rect 1"))
(t/is (= (:touched c-instance1) nil)) (t/is (= (:touched c-instance1) nil))
@ -2009,7 +2015,7 @@
(t/is (= (:fill-color c-shape2) clr/white)) (t/is (= (:fill-color c-shape2) clr/white))
(t/is (= (:fill-opacity c-shape2) 1)) (t/is (= (:fill-opacity c-shape2) 1))
(t/is (= (:name instance4) "Group")) (t/is (= (:name instance4) "Board"))
(t/is (= (:touched instance4) nil)) (t/is (= (:touched instance4) nil))
(t/is (= (:name instance3) "Rect 1")) (t/is (= (:name instance3) "Rect 1"))
(t/is (= (:touched instance3) nil)) (t/is (= (:touched instance3) nil))
@ -2047,11 +2053,11 @@
{:name "Circle 1" {:name "Circle 1"
:fill-color clr/black :fill-color clr/black
:fill-opacity 0}) :fill-opacity 0})
(thp/group-shapes :group1 (thp/frame-shapes :frame1
[(thp/id :instance1) [(thp/id :instance1)
(thp/id :shape2)]) (thp/id :shape2)])
(thp/make-component :main2 :component2 (thp/make-component :main2 :component2
[(thp/id :group1)]) [(thp/id :frame1)])
(thp/instantiate-component :instance2 (thp/instantiate-component :instance2
(thp/id :component2)) (thp/id :component2))
(thp/instantiate-component :instance3 (thp/instantiate-component :instance3
@ -2101,7 +2107,7 @@
new-state new-state
(thp/id :instance3))] (thp/id :instance3))]
(t/is (= (:name instance2) "Group")) (t/is (= (:name instance2) "Board"))
(t/is (= (:touched instance2) nil)) (t/is (= (:touched instance2) nil))
(t/is (= (:name instance1) "Rect 1")) (t/is (= (:name instance1) "Rect 1"))
(t/is (= (:touched instance1) nil)) (t/is (= (:touched instance1) nil))
@ -2114,7 +2120,7 @@
(t/is (= (:fill-color shape2) clr/test)) (t/is (= (:fill-color shape2) clr/test))
(t/is (= (:fill-opacity shape2) 0.5)) (t/is (= (:fill-opacity shape2) 0.5))
(t/is (= (:name c-instance2) "Group")) (t/is (= (:name c-instance2) "Board"))
(t/is (= (:touched c-instance2) nil)) (t/is (= (:touched c-instance2) nil))
(t/is (= (:name c-instance1) "Rect 1")) (t/is (= (:name c-instance1) "Rect 1"))
(t/is (= (:touched c-instance1) nil)) (t/is (= (:touched c-instance1) nil))
@ -2127,7 +2133,7 @@
(t/is (= (:fill-color c-shape2) clr/test)) (t/is (= (:fill-color c-shape2) clr/test))
(t/is (= (:fill-opacity c-shape2) 0.5)) (t/is (= (:fill-opacity c-shape2) 0.5))
(t/is (= (:name instance4) "Group")) (t/is (= (:name instance4) "Board"))
(t/is (= (:touched instance4) nil)) (t/is (= (:touched instance4) nil))
(t/is (= (:name instance3) "Rect 1")) (t/is (= (:name instance3) "Rect 1"))
(t/is (= (:touched instance3) nil)) (t/is (= (:touched instance3) nil))
@ -2166,11 +2172,11 @@
{:name "Circle 1" {:name "Circle 1"
:fill-color clr/black :fill-color clr/black
:fill-opacity 0}) :fill-opacity 0})
(thp/group-shapes :group1 (thp/frame-shapes :frame1
[(thp/id :instance1) [(thp/id :instance1)
(thp/id :shape2)]) (thp/id :shape2)])
(thp/make-component :main2 :component2 (thp/make-component :main2 :component2
[(thp/id :group1)]) [(thp/id :frame1)])
(thp/instantiate-component :instance2 (thp/instantiate-component :instance2
(thp/id :component2)) (thp/id :component2))
(thp/instantiate-component :instance3 (thp/instantiate-component :instance3
@ -2222,7 +2228,7 @@
new-state new-state
(thp/id :instance3))] (thp/id :instance3))]
(t/is (= (:name instance2) "Group")) (t/is (= (:name instance2) "Board"))
(t/is (= (:touched instance2) nil)) (t/is (= (:touched instance2) nil))
(t/is (= (:name instance1) "Rect 1")) (t/is (= (:name instance1) "Rect 1"))
(t/is (= (:touched instance1) nil)) (t/is (= (:touched instance1) nil))
@ -2235,7 +2241,7 @@
(t/is (= (:fill-color shape2) clr/test)) (t/is (= (:fill-color shape2) clr/test))
(t/is (= (:fill-opacity shape2) 0.5)) (t/is (= (:fill-opacity shape2) 0.5))
(t/is (= (:name c-instance2) "Group")) (t/is (= (:name c-instance2) "Board"))
(t/is (= (:touched c-instance2) nil)) (t/is (= (:touched c-instance2) nil))
(t/is (= (:name c-instance1) "Rect 1")) (t/is (= (:name c-instance1) "Rect 1"))
(t/is (= (:touched c-instance1) nil)) (t/is (= (:touched c-instance1) nil))
@ -2248,7 +2254,7 @@
(t/is (= (:fill-color c-shape2) clr/test)) (t/is (= (:fill-color c-shape2) clr/test))
(t/is (= (:fill-opacity c-shape2) 0.5)) (t/is (= (:fill-opacity c-shape2) 0.5))
(t/is (= (:name instance4) "Group")) (t/is (= (:name instance4) "Board"))
(t/is (= (:touched instance4) nil)) (t/is (= (:touched instance4) nil))
(t/is (= (:name instance3) "Rect 1")) (t/is (= (:name instance3) "Rect 1"))
(t/is (= (:touched instance3) nil)) (t/is (= (:touched instance3) nil))

View File

@ -5,8 +5,8 @@
[app.common.types.container :as ctn] [app.common.types.container :as ctn]
[app.common.types.file :as ctf] [app.common.types.file :as ctf]
[app.main.data.workspace :as dw] [app.main.data.workspace :as dw]
[app.main.data.workspace.groups :as dwg]
[app.main.data.workspace.libraries :as dwl] [app.main.data.workspace.libraries :as dwl]
[app.main.data.workspace.shapes :as dwsh]
[app.main.data.workspace.state-helpers :as wsh] [app.main.data.workspace.state-helpers :as wsh]
[cljs.test :as t :include-macros true] [cljs.test :as t :include-macros true]
[frontend-tests.helpers.events :as the] [frontend-tests.helpers.events :as the]
@ -119,7 +119,7 @@
(dwl/add-component) (dwl/add-component)
:the/end)))) :the/end))))
(t/deftest test-add-component-from-group (t/deftest test-add-component-from-frame
(t/async (t/async
done done
(let [state (-> thp/initial-state (let [state (-> thp/initial-state
@ -128,7 +128,7 @@
{:name "Rect 1"}) {:name "Rect 1"})
(thp/sample-shape :shape2 :rect (thp/sample-shape :shape2 :rect
{:name "Rect-2"}) {:name "Rect-2"})
(thp/group-shapes :group1 (thp/frame-shapes :frame1
[(thp/id :shape1) [(thp/id :shape1)
(thp/id :shape2)])) (thp/id :shape2)]))
@ -150,23 +150,23 @@
component] component]
(thl/resolve-instance-and-main (thl/resolve-instance-and-main
new-state new-state
(thp/id :group1)) (thp/id :frame1))
file (wsh/get-local-file new-state)] file (wsh/get-local-file new-state)]
(t/is (= (:name shape1) "Rect 1")) (t/is (= (:name shape1) "Rect 1"))
(t/is (= (:name shape2) "Rect-2")) (t/is (= (:name shape2) "Rect-2"))
(t/is (= (:name group) "Group")) (t/is (= (:name group) "Board"))
(t/is (= (:name component) "Group")) (t/is (= (:name component) "Board"))
(t/is (= (:name c-shape1) "Rect 1")) (t/is (= (:name c-shape1) "Rect 1"))
(t/is (= (:name c-shape2) "Rect-2")) (t/is (= (:name c-shape2) "Rect-2"))
(t/is (= (:name c-group) "Group")) (t/is (= (:name c-group) "Board"))
(thl/is-from-file group file))))] (thl/is-from-file group file))))]
(ptk/emit! (ptk/emit!
store store
(dw/select-shape (thp/id :group1)) (dw/select-shape (thp/id :frame1))
(dwl/add-component) (dwl/add-component)
:the/end)))) :the/end))))
@ -621,11 +621,11 @@
new-state new-state
(:parent-id parent1))] (:parent-id parent1))]
(t/is (= (:name group) "Group")) (t/is (= (:name group) "Board"))
(t/is (= (:name shape1) "Rect 1")) (t/is (= (:name shape1) "Rect 1"))
(t/is (= (:name shape2) "Rect 1")) (t/is (= (:name shape2) "Rect 1"))
(t/is (= (:name component) "Group")) (t/is (= (:name component) "Board"))
(t/is (= (:name c-group) "Group")) (t/is (= (:name c-group) "Board"))
(t/is (= (:name c-shape1) "Rect 1")) (t/is (= (:name c-shape1) "Rect 1"))
(t/is (= (:name c-shape2) "Rect 1")))))] (t/is (= (:name c-shape2) "Rect 1")))))]
@ -633,7 +633,7 @@
store store
(dw/select-shape (thp/id :shape1)) (dw/select-shape (thp/id :shape1))
(dwl/add-component) (dwl/add-component)
dwg/group-selected (dwsh/create-artboard-from-selection)
(dwl/add-component) (dwl/add-component)
:the/end)))) :the/end))))
@ -740,10 +740,10 @@
new-state new-state
(:parent-id instance1))] (:parent-id instance1))]
(t/is (= (:name group1) "Group")) (t/is (= (:name group1) "Board"))
(t/is (= (:name shape1) "Rect 1")) (t/is (= (:name shape1) "Rect 1"))
(t/is (= (:name shape2) "Rect 1")) (t/is (= (:name shape2) "Rect 1"))
(t/is (= (:name c-group1) "Group")) (t/is (= (:name c-group1) "Board"))
(t/is (= (:name c-shape1) "Rect 1")) (t/is (= (:name c-shape1) "Rect 1"))
(t/is (= (:name c-shape2) "Rect 1")) (t/is (= (:name c-shape2) "Rect 1"))
(t/is (= (:component-file group1) thp/current-file-id)) (t/is (= (:component-file group1) thp/current-file-id))
@ -756,6 +756,6 @@
(ptk/emit! (ptk/emit!
store store
(dw/select-shape (thp/id :instance1)) (dw/select-shape (thp/id :instance1))
dwg/group-selected (dwsh/create-artboard-from-selection)
(dwl/add-component) (dwl/add-component)
:the/end)))) :the/end))))