diff --git a/src/main/frontend/components/block.cljs b/src/main/frontend/components/block.cljs index c38f2d0da7..1267874735 100644 --- a/src/main/frontend/components/block.cljs +++ b/src/main/frontend/components/block.cljs @@ -6,7 +6,6 @@ [cljs-bean.core :as bean] [cljs.core.match :refer [match]] [cljs.reader :as reader] - [clojure.set :as set] [clojure.string :as string] [clojure.walk :as walk] [datascript.core :as d] @@ -67,7 +66,6 @@ [logseq.graph-parser.block :as gp-block] [logseq.graph-parser.config :as gp-config] [logseq.graph-parser.mldoc :as gp-mldoc] - [logseq.graph-parser.property :as gp-property] [logseq.graph-parser.text :as text] [logseq.graph-parser.util :as gp-util] [logseq.graph-parser.util.block-ref :as block-ref] @@ -2047,66 +2045,25 @@ :else (inline-text config (:block/format block) (str v)))]])) -(def hidden-editable-page-properties - "Properties that are hidden in the pre-block (page property)" - #{:title :filters :icon}) - -(assert (set/subset? hidden-editable-page-properties (gp-property/editable-built-in-properties)) - "Hidden editable page properties must be valid editable properties") - -(def hidden-editable-block-properties - "Properties that are hidden in a block (block property)" - (into #{:logseq.query/nlp-date} - gp-property/editable-view-and-table-properties)) - -(assert (set/subset? hidden-editable-block-properties (gp-property/editable-built-in-properties)) - "Hidden editable page properties must be valid editable properties") - -(defn- add-aliases-to-properties - [properties block] - (let [repo (state/get-current-repo) - aliases (db/get-page-alias-names repo - (:block/name (db/pull (:db/id (:block/page block)))))] - (if (seq aliases) - (if (:alias properties) - (update properties :alias (fn [c] - (util/distinct-by string/lower-case (concat c aliases)))) - (assoc properties :alias aliases)) - properties))) - (rum/defc properties-cp [config {:block/keys [pre-block?] :as block}] - (let [dissoc-keys (fn [m keys] (apply dissoc m keys)) - properties (cond-> (update-keys (:block/properties block) keyword) - true - (dissoc-keys (property/hidden-properties)) - pre-block? - (dissoc-keys hidden-editable-page-properties) - (not pre-block?) - (dissoc-keys hidden-editable-block-properties) - pre-block? - (add-aliases-to-properties block))] + (let [ordered-properties + (property/get-visible-ordered-properties (:block/properties block) + (:block/properties-order block) + {:pre-block? pre-block? + :page-id (:db/id (:block/page block))})] (cond - (seq properties) - (let [properties-order (cond->> (:block/properties-order block) - true - (remove (property/hidden-properties)) - pre-block? - (remove hidden-editable-page-properties)) - properties-order (distinct properties-order) - ordered-properties (if (seq properties-order) - (map (fn [k] [k (get properties k)]) properties-order) - properties)] - [:div.block-properties - {:class (when pre-block? "page-properties") - :title (if pre-block? - "Click to edit this page's properties" - "Click to edit this block's properties")} - (for [[k v] ordered-properties] - (rum/with-key (property-cp config block k v) - (str (:block/uuid block) "-" k)))]) + (seq ordered-properties) + [:div.block-properties + {:class (when pre-block? "page-properties") + :title (if pre-block? + "Click to edit this page's properties" + "Click to edit this block's properties")} + (for [[k v] ordered-properties] + (rum/with-key (property-cp config block k v) + (str (:block/uuid block) "-" k)))] - (and pre-block? properties) + (and pre-block? ordered-properties) [:span.opacity-50 "Properties"] :else diff --git a/src/main/frontend/util/property.cljs b/src/main/frontend/util/property.cljs index 80f22a841a..db46c0bd20 100644 --- a/src/main/frontend/util/property.cljs +++ b/src/main/frontend/util/property.cljs @@ -10,6 +10,8 @@ [logseq.graph-parser.util.page-ref :as page-ref] [frontend.format.mldoc :as mldoc] [logseq.graph-parser.text :as text] + [frontend.db :as db] + [frontend.state :as state] [frontend.util.cursor :as cursor])) (defn hidden-properties @@ -414,3 +416,50 @@ (util/format (config/properties-wrapper-pattern page-format) (string/join "\n" lines)))) + +(def hidden-editable-page-properties + "Properties that are hidden in the pre-block (page property)" + #{:title :filters :icon}) + +(assert (set/subset? hidden-editable-page-properties (gp-property/editable-built-in-properties)) + "Hidden editable page properties must be valid editable properties") + +(def hidden-editable-block-properties + "Properties that are hidden in a block (block property)" + (into #{:logseq.query/nlp-date} + gp-property/editable-view-and-table-properties)) + +(assert (set/subset? hidden-editable-block-properties (gp-property/editable-built-in-properties)) + "Hidden editable page properties must be valid editable properties") + +(defn- add-aliases-to-properties + "Adds aliases to a page when a page has aliases and is also an alias of other pages" + [properties page-id] + (let [repo (state/get-current-repo) + aliases (db/get-page-alias-names repo + (:block/name (db/pull page-id)))] + (if (seq aliases) + (if (:alias properties) + (update properties :alias (fn [c] + (util/distinct-by string/lower-case (concat c aliases)))) + (assoc properties :alias aliases)) + properties))) + +(defn get-visible-ordered-properties + "Given a block's properties, order of properties and any display context, + returns a tuple of property pairs that are visible when not being edited" + [properties* properties-order {:keys [pre-block? page-id]}] + (let [dissoc-keys (fn [m keys] (apply dissoc m keys)) + properties (cond-> (update-keys properties* keyword) + true + (dissoc-keys (hidden-properties)) + pre-block? + (dissoc-keys hidden-editable-page-properties) + (not pre-block?) + (dissoc-keys hidden-editable-block-properties) + pre-block? + (add-aliases-to-properties page-id))] + (if (seq properties-order) + (keep (fn [k] (when (contains? properties k) [k (get properties k)])) + (distinct properties-order)) + properties*))) \ No newline at end of file diff --git a/src/test/frontend/util/property_test.cljs b/src/test/frontend/util/property_test.cljs index 540f093e59..76f2283458 100644 --- a/src/test/frontend/util/property_test.cljs +++ b/src/test/frontend/util/property_test.cljs @@ -200,16 +200,49 @@ SCHEDULED: <2021-10-25 Mon>\n:PROPERTIES:\n:a: b\n:END:\nworld\n" "c" "d") (let [org-property ":PROPERTIES:\n:query-table: true\n:END:"] (are [x y] (= (property/with-built-in-properties {:query-table true} x :org) y) - content - (str org-property "\n" content) + content + (str org-property "\n" content) - "title" - (str "title\n" org-property) + "title" + (str "title\n" org-property) - "title\nbody" - (str "title\n" org-property "\nbody") + "title\nbody" + (str "title\n" org-property "\nbody") - "1. list" - (str org-property "\n1. list"))))) + "1. list" + (str org-property "\n1. list"))))) -#_(cljs.test/run-tests) +(deftest get-visible-ordered-properties + (testing "basic cases" + (are [x y expected] (= expected (property/get-visible-ordered-properties x y {})) + ;; returns in property order + {:prop "val" :prop2 "val2"} [:prop2 :prop] + [[:prop2 "val2"] [:prop "val"]] + ;; returns empty non-nil value if properties is non-nil + {} [:prop] + '() + ;; returns nil if properties is nil + nil [] + nil)) + + (testing "hidden properties" + (are [x y z expected] (= expected (property/get-visible-ordered-properties x y z)) + ;; page block + {:logseq.order-list-type "number" :foo "bar"} [:logseq.order-list-type :foo] {:pre-block false} + [[:foo "bar"]] + ;; normal block + {:logseq.order-list-type "number" :foo "bar"} [:logseq.order-list-type :foo] {:pre-block false} + [[:foo "bar"]])) + + (testing "hidden editable properties" + (are [x y z expected] (= expected (property/get-visible-ordered-properties x y z)) + ;; page block + {:title "foo"} [:title] {:pre-block? true} + '() + {:title "foo" :foo "bar"} [:title :foo] {:pre-block? true} + [[:foo "bar"]] + ;; normal block + {:logseq.table.version 2} [:logseq.table.version] {:pre-block? false} + '() + {:logseq.table.version 2 :foo "bar"} [:logseq.table.version :foo] {:pre-block? false} + [[:foo "bar"]]))) \ No newline at end of file