mirror of
https://github.com/penpot/penpot.git
synced 2025-05-19 00:06:14 +02:00
✨ Allows groups to reflow the layout on transform
This commit is contained in:
parent
84c0825893
commit
6e5a23c190
4 changed files with 92 additions and 31 deletions
|
@ -75,7 +75,6 @@
|
||||||
|
|
||||||
[children-width children-height]
|
[children-width children-height]
|
||||||
(->> children
|
(->> children
|
||||||
(map #(-> (merge % (get modif-tree (:id %))) gtr/transform-shape))
|
|
||||||
(reduce (fn [[acc-width acc-height] shape]
|
(reduce (fn [[acc-width acc-height] shape]
|
||||||
[(+ acc-width (-> shape :points gre/points->rect :width))
|
[(+ acc-width (-> shape :points gre/points->rect :width))
|
||||||
(+ acc-height (-> shape :points gre/points->rect :height))]) [0 0]))
|
(+ acc-height (-> shape :points gre/points->rect :height))]) [0 0]))
|
||||||
|
@ -99,7 +98,7 @@
|
||||||
0)
|
0)
|
||||||
|
|
||||||
margin-y (if (and (row? shape) (= :space-around layout-type))
|
margin-y (if (and (row? shape) (= :space-around layout-type))
|
||||||
(/ (- height children-height) (dec num-children) 2)
|
(/ (- height children-height) (inc num-children))
|
||||||
0)
|
0)
|
||||||
|
|
||||||
children-gap (* layout-gap (dec num-children))
|
children-gap (* layout-gap (dec num-children))
|
||||||
|
@ -199,20 +198,17 @@
|
||||||
|
|
||||||
layout-data
|
layout-data
|
||||||
(assoc layout-data :start-x next-x :start-y next-y)]
|
(assoc layout-data :start-x next-x :start-y next-y)]
|
||||||
[corner-p layout-data])
|
[corner-p layout-data]))
|
||||||
)
|
|
||||||
|
|
||||||
(defn calc-layout-modifiers
|
(defn calc-layout-modifiers
|
||||||
"Calculates the modifiers for the layout"
|
"Calculates the modifiers for the layout"
|
||||||
[parent child modifiers layout-data]
|
[parent child layout-data]
|
||||||
|
|
||||||
(let [modifiers (-> modifiers (dissoc :displacement-after))
|
(let [bounds (-> child :points gre/points->selrect)
|
||||||
child (-> child (assoc :modifiers modifiers) gtr/transform-shape)
|
|
||||||
bounds (-> child :points gre/points->selrect)
|
|
||||||
|
|
||||||
[corner-p layout-data] (next-p parent bounds layout-data)
|
[corner-p layout-data] (next-p parent bounds layout-data)
|
||||||
|
|
||||||
delta-p (-> corner-p (gpt/subtract (gpt/point bounds)))
|
delta-p (-> corner-p (gpt/subtract (gpt/point bounds)))
|
||||||
modifiers (-> modifiers (assoc :displacement-after (gmt/translate-matrix delta-p)))]
|
modifiers {:displacement-after (gmt/translate-matrix delta-p)}]
|
||||||
|
|
||||||
[modifiers layout-data]))
|
[modifiers layout-data]))
|
||||||
|
|
|
@ -119,27 +119,51 @@
|
||||||
resize-modif? (or (:resize-vector modifiers) (:resize-vector-2 modifiers))]
|
resize-modif? (or (:resize-vector modifiers) (:resize-vector-2 modifiers))]
|
||||||
(reduce (partial set-child transformed-rect (and snap-pixel? resize-modif?)) modif-tree children))))
|
(reduce (partial set-child transformed-rect (and snap-pixel? resize-modif?)) modif-tree children))))
|
||||||
|
|
||||||
|
(defn group? [shape]
|
||||||
|
(or (= :group (:type shape))
|
||||||
|
(= :bool (:type shape))))
|
||||||
|
|
||||||
|
(defn merge-modifiers
|
||||||
|
[modif-tree ids modifiers]
|
||||||
|
(reduce
|
||||||
|
(fn [modif-tree id]
|
||||||
|
(update-in modif-tree [id :modifiers] #(merge % modifiers)))
|
||||||
|
modif-tree
|
||||||
|
ids))
|
||||||
|
|
||||||
(defn set-layout-modifiers
|
(defn set-layout-modifiers
|
||||||
[modif-tree objects id]
|
[modif-tree objects id]
|
||||||
|
|
||||||
(letfn [(set-layout-modifiers [parent [layout-data modif-tree] child]
|
(letfn [(transform-child [shape]
|
||||||
(let [modifiers (get-in modif-tree [(:id child) :modifiers])
|
(let [modifiers (get modif-tree (:id shape))]
|
||||||
|
(cond-> shape
|
||||||
|
(not (group? shape))
|
||||||
|
(-> (merge modifiers) gtr/transform-shape)
|
||||||
|
|
||||||
[modifiers layout-data]
|
(group? shape)
|
||||||
(gcl/calc-layout-modifiers parent child modifiers layout-data)
|
(gtr/apply-group-modifiers objects modif-tree))))
|
||||||
|
|
||||||
|
(set-layout-modifiers [parent [layout-data modif-tree] child]
|
||||||
|
(let [[modifiers layout-data]
|
||||||
|
(gcl/calc-layout-modifiers parent child layout-data)
|
||||||
|
|
||||||
modif-tree
|
modif-tree
|
||||||
(cond-> modif-tree
|
(cond-> modif-tree
|
||||||
(not (gtr/empty-modifiers? modifiers))
|
(not (gtr/empty-modifiers? modifiers))
|
||||||
(assoc-in [(:id child) :modifiers] modifiers))]
|
(merge-modifiers [(:id child)] modifiers)
|
||||||
|
|
||||||
|
(and (not (gtr/empty-modifiers? modifiers)) (group? child))
|
||||||
|
(merge-modifiers (:shapes child) modifiers))]
|
||||||
|
|
||||||
[layout-data modif-tree]))]
|
[layout-data modif-tree]))]
|
||||||
|
|
||||||
(let [shape (get objects id)
|
(let [shape (get objects id)
|
||||||
children (map (d/getf objects) (:shapes shape))
|
children (->> (:shapes shape)
|
||||||
|
(map (d/getf objects))
|
||||||
|
(map transform-child))
|
||||||
|
|
||||||
modifiers (get-in modif-tree [id :modifiers])
|
modifiers (get-in modif-tree [id :modifiers])
|
||||||
|
|
||||||
;;_ (.log js/console "layout" (:name shape) (clj->js modifiers))
|
|
||||||
transformed-rect (gtr/transform-selrect (:selrect shape) modifiers)
|
transformed-rect (gtr/transform-selrect (:selrect shape) modifiers)
|
||||||
layout-data (gcl/calc-layout-data shape children modif-tree transformed-rect)
|
layout-data (gcl/calc-layout-data shape children modif-tree transformed-rect)
|
||||||
children (cond-> children (:reverse? layout-data) reverse)
|
children (cond-> children (:reverse? layout-data) reverse)
|
||||||
|
@ -191,21 +215,41 @@
|
||||||
(let [modif-tree (reduce (fn [modif-tree id]
|
(let [modif-tree (reduce (fn [modif-tree id]
|
||||||
(assoc modif-tree id {:modifiers (get-modifier (get objects id))})) {} ids)
|
(assoc modif-tree id {:modifiers (get-modifier (get objects id))})) {} ids)
|
||||||
|
|
||||||
ids (resolve-layout-ids ids objects)]
|
ids (resolve-layout-ids ids objects)
|
||||||
|
|
||||||
(loop [current (first ids)
|
|
||||||
pending (rest ids)
|
|
||||||
modif-tree modif-tree]
|
|
||||||
(if (some? current)
|
|
||||||
(let [shape (get objects current)
|
|
||||||
pending (concat pending (:shapes shape))
|
|
||||||
|
|
||||||
modif-tree
|
;; First: Calculate children modifiers (constraints, etc)
|
||||||
(-> modif-tree
|
[modif-tree touched-layouts]
|
||||||
(set-children-modifiers shape objects ignore-constraints snap-pixel?)
|
(loop [current (first ids)
|
||||||
(cond-> (:layout shape)
|
pending (rest ids)
|
||||||
(set-layout-modifiers objects current)))]
|
modif-tree modif-tree
|
||||||
|
touched-layouts (d/ordered-set)]
|
||||||
|
(if (some? current)
|
||||||
|
(let [shape (get objects current)
|
||||||
|
pending (concat pending (:shapes shape))
|
||||||
|
|
||||||
(recur (first pending) (rest pending) modif-tree))
|
touched-layouts
|
||||||
|
(cond-> touched-layouts
|
||||||
|
(:layout shape)
|
||||||
|
(conj (:id shape)))
|
||||||
|
|
||||||
modif-tree))))
|
modif-tree
|
||||||
|
(-> modif-tree
|
||||||
|
(set-children-modifiers shape objects ignore-constraints snap-pixel?))]
|
||||||
|
|
||||||
|
(recur (first pending) (rest pending) modif-tree touched-layouts))
|
||||||
|
|
||||||
|
[modif-tree touched-layouts]))
|
||||||
|
|
||||||
|
;; Second: Calculate layout positioning
|
||||||
|
modif-tree
|
||||||
|
(loop [current (first touched-layouts)
|
||||||
|
pending (rest touched-layouts)
|
||||||
|
modif-tree modif-tree]
|
||||||
|
|
||||||
|
(if (some? current)
|
||||||
|
(let [modif-tree (set-layout-modifiers modif-tree objects current)]
|
||||||
|
(recur (first pending) (rest pending) modif-tree))
|
||||||
|
modif-tree))]
|
||||||
|
|
||||||
|
modif-tree))
|
||||||
|
|
|
@ -670,3 +670,17 @@
|
||||||
(map (comp gpr/points->selrect :points transform-shape))
|
(map (comp gpr/points->selrect :points transform-shape))
|
||||||
(gpr/join-selrects)))
|
(gpr/join-selrects)))
|
||||||
|
|
||||||
|
(defn apply-group-modifiers
|
||||||
|
"Apply the modifiers to the group children to calculate its selection rect"
|
||||||
|
[group objects modif-tree]
|
||||||
|
|
||||||
|
(let [children
|
||||||
|
(->> (:shapes group)
|
||||||
|
(map (d/getf objects))
|
||||||
|
(map (fn [shape]
|
||||||
|
(let [modifiers (get modif-tree (:id shape))
|
||||||
|
shape (-> shape (merge modifiers) transform-shape)]
|
||||||
|
(if (= :group (:type shape))
|
||||||
|
(apply-group-modifiers shape objects modif-tree)
|
||||||
|
shape)))))]
|
||||||
|
(update-group-selrect group children)))
|
||||||
|
|
|
@ -353,3 +353,10 @@
|
||||||
(let [root-node (dom/query ".viewport .render-shapes")
|
(let [root-node (dom/query ".viewport .render-shapes")
|
||||||
num-nodes (->> (dom/seq-nodes root-node) count)]
|
num-nodes (->> (dom/seq-nodes root-node) count)]
|
||||||
#js {:number num-nodes}))
|
#js {:number num-nodes}))
|
||||||
|
|
||||||
|
#_(defn modif->js
|
||||||
|
[modif-tree objects]
|
||||||
|
(clj->js (into {}
|
||||||
|
(map (fn [[k v]]
|
||||||
|
[(get-in objects [k :name]) v]))
|
||||||
|
modif-tree)))
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue