From 8682c071488c8124a7ddfff087b1df37a1fa25b3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Andr=C3=A9s=20Moya?= Date: Mon, 21 Feb 2022 17:14:54 +0100 Subject: [PATCH] :wrench: Small refactor changes-builder --- .../src/app/common/pages/changes_builder.cljc | 142 +++++++++--------- frontend/src/app/main/data/workspace.cljs | 6 +- 2 files changed, 71 insertions(+), 77 deletions(-) diff --git a/common/src/app/common/pages/changes_builder.cljc b/common/src/app/common/pages/changes_builder.cljc index 1d6d06506..b039397b6 100644 --- a/common/src/app/common/pages/changes_builder.cljc +++ b/common/src/app/common/pages/changes_builder.cljc @@ -31,46 +31,69 @@ (defn with-objects [changes objects] (vary-meta changes assoc ::objects objects)) +(defn amend-last-change + "Modify the last redo-changes added with an update function." + [changes f] + (update changes :redo-changes + #(conj (pop %) (f (peek %))))) + +(defn amend-changes + "Modify all redo-changes with an update function." + [changes f] + (update changes :redo-changes #(mapv f %))) + +(defn- assert-page-id + [changes] + (assert (contains? (meta changes) ::page-id) "Give a page-id or call (with-page) before using this function")) + +(defn- assert-page + [changes] + (assert (contains? (meta changes) ::page) "Call (with-page) before using this function")) + +(defn- assert-objects + [changes] + (assert (contains? (meta changes) ::objects) "Call (with-objects) before using this function")) + ;; Page changes (defn add-empty-page - [chdata id name] - (-> chdata + [changes id name] + (-> changes (update :redo-changes conj {:type :add-page :id id :name name}) (update :undo-changes conj {:type :del-page :id id}))) (defn add-page - [chdata id page] - (-> chdata + [changes id page] + (-> changes (update :redo-changes conj {:type :add-page :id id :page page}) (update :undo-changes conj {:type :del-page :id id}))) (defn mod-page - [chdata page new-name] - (-> chdata + [changes page new-name] + (-> changes (update :redo-changes conj {:type :mod-page :id (:id page) :name new-name}) (update :undo-changes conj {:type :mod-page :id (:id page) :name (:name page)}))) (defn del-page - [chdata page] - (-> chdata + [changes page] + (-> changes (update :redo-changes conj {:type :del-page :id (:id page)}) (update :undo-changes conj {:type :add-page :id (:id page) :page page}))) (defn move-page - [chdata index prev-index] - (let [page-id (::page-id (meta chdata))] - (-> chdata - (update :redo-changes conj {:type :mov-page :id page-id :index index}) - (update :undo-changes conj {:type :mov-page :id page-id :index prev-index})))) + [changes page-id index prev-index] + (-> changes + (update :redo-changes conj {:type :mov-page :id page-id :index index}) + (update :undo-changes conj {:type :mov-page :id page-id :index prev-index}))) (defn set-page-option - [chdata option-key option-val] - (let [page-id (::page-id (meta chdata)) - page (::page (meta chdata)) + [changes option-key option-val] + (assert-page changes) + (let [page-id (::page-id (meta changes)) + page (::page (meta changes)) old-val (get-in page [:options option-key])] - (-> chdata + (-> changes (update :redo-changes conj {:type :set-option :page-id page-id :option option-key @@ -87,6 +110,7 @@ (add-obj changes obj nil)) ([changes obj {:keys [index ignore-touched] :or {index ::undefined ignore-touched false}}] + (assert-page-id changes) (let [obj (cond-> obj (not= index ::undefined) (assoc :index index)) @@ -111,10 +135,12 @@ (update :undo-changes d/preconj del-change))))) (defn change-parent - ([changes parent-id shapes] (change-parent changes parent-id shapes nil)) - ([changes parent-id shapes index] - (assert (contains? (meta changes) ::objects) "Call (with-objects) first to use this function") + ([changes parent-id shapes] + (change-parent changes parent-id shapes nil)) + ([changes parent-id shapes index] + (assert-page-id changes) + (assert-objects changes) (let [objects (::objects (meta changes)) set-parent-change (cond-> {:type :mov-objects @@ -139,18 +165,6 @@ (update :redo-changes conj set-parent-change) (update :undo-changes #(reduce mk-undo-change % shapes)))))) -(defn- generate-operation - "Given an object old and new versions and an attribute will append into changes - the set and undo operations" - [changes attr old new ignore-geometry?] - (let [old-val (get old attr) - new-val (get new attr)] - (if (= old-val new-val) - changes - (-> changes - (update :rops conj {:type :set :attr attr :val new-val :ignore-geometry ignore-geometry?}) - (update :uops conj {:type :set :attr attr :val old-val :ignore-touched true}))))) - (defn update-shapes "Calculate the changes and undos to be done when a function is applied to a single object" @@ -158,9 +172,20 @@ (update-shapes changes ids update-fn nil)) ([changes ids update-fn {:keys [attrs ignore-geometry?] :or {attrs nil ignore-geometry? false}}] - (assert (contains? (meta changes) ::objects) "Call (with-objects) first to use this function") + (assert-page-id changes) + (assert-objects changes) (let [objects (::objects (meta changes)) + generate-operation + (fn [changes attr old new ignore-geometry?] + (let [old-val (get old attr) + new-val (get new attr)] + (if (= old-val new-val) + changes + (-> changes + (update :rops conj {:type :set :attr attr :val new-val :ignore-geometry ignore-geometry?}) + (update :uops conj {:type :set :attr attr :val old-val :ignore-touched true}))))) + update-shape (fn [changes id] (let [old-obj (get objects id) @@ -192,7 +217,8 @@ (defn remove-objects [changes ids] - (assert (contains? (meta changes) ::objects) "Call (with-objects) first to use this function") + (assert-page-id changes) + (assert-objects changes) (let [page-id (::page-id (meta changes)) objects (::objects (meta changes)) @@ -235,44 +261,12 @@ (reduce add-undo-change-parent $ ids) (reduce add-undo-change-shape $ ids)))))) -(defn move-page - [chdata index prev-index] - (let [page-id (::page-id (meta chdata))] - (-> chdata - (update :redo-changes conj {:type :mov-page :id page-id :index index}) - (update :undo-changes conj {:type :mov-page :id page-id :index prev-index})))) - -(defn set-page-option - [chdata option-key option-val] - (let [page-id (::page-id (meta chdata)) - page (::page (meta chdata)) - old-val (get-in page [:options option-key])] - - (-> chdata - (update :redo-changes conj {:type :set-option - :page-id page-id - :option option-key - :value option-val}) - (update :undo-changes conj {:type :set-option - :page-id page-id - :option option-key - :value old-val})))) - -(defn reg-objects - [chdata shape-ids] - (let [page-id (::page-id (meta chdata))] - (-> chdata - (update :redo-changes conj {:type :reg-objects :page-id page-id :shapes shape-ids})))) - ;; No need to do anything to undo - -(defn amend-last-change - "Modify the last redo-changes added with an update function." - [chdata f] - (update chdata :redo-changes - #(conj (pop %) (f (peek %))))) - -(defn amend-changes - "Modify all redo-changes with an update function." - [chdata f] - (update chdata :redo-changes #(mapv f %))) +(defn resize-parents + [changes ids] + (assert-page-id changes) + (let [page-id (::page-id (meta changes)) + shapes (vec ids)] + (-> changes + (update :redo-changes conj {:type :reg-objects :page-id page-id :shapes shapes}) + (update :undo-changes conj {:type :reg-objects :page-id page-id :shapes shapes})))) diff --git a/frontend/src/app/main/data/workspace.cljs b/frontend/src/app/main/data/workspace.cljs index 6d207ba5d..383cc6df6 100644 --- a/frontend/src/app/main/data/workspace.cljs +++ b/frontend/src/app/main/data/workspace.cljs @@ -1163,8 +1163,8 @@ (watch [it state _] (let [prev-index (-> (get-in state [:workspace-data :pages]) (d/index-of id)) - changes (-> (pcb/empty-changes it id) - (pcb/move-page index prev-index))] + changes (-> (pcb/empty-changes it) + (pcb/move-page id index prev-index))] (rx/of (dch/commit-changes changes)))))) ;; --- Shape / Selection Alignment and Distribution @@ -1837,7 +1837,7 @@ ;; Adds a reg-objects operation so the groups are updated. We add all the new objects new-objects-ids (->> changes :redo-changes (filter #(= (:type %) :add-obj)) (mapv :id)) - changes (pcb/reg-objects changes new-objects-ids) + changes (pcb/resize-parents changes new-objects-ids) selected (->> changes :redo-changes