Ben Yorke 2 лет назад
Родитель
Сommit
246e904457

+ 7 - 5
deps/shui/src/logseq/shui/button/v2.cljs

@@ -6,15 +6,17 @@
     [logseq.shui.icon.v2 :as icon]
     [clojure.string :as string]))
 
-
 (rum/defc root 
-  [{:keys [theme text depth size icon interactive shortcut tiled on-click] :or {theme :color depth 1 size :md interactive true}} context]
-  (let [theme-class (str "shui__button-theme-" (name theme))
+  [{:keys [theme color text depth size icon interactive shortcut tiled on-click muted class] 
+    :or {theme :color depth 1 size :md interactive true muted false class ""}} context]
+  (let [color-string (or (some-> color name) (some-> context :state deref :ui/radix-color name) "custom")
+        theme-class (str "shui__button-theme-" (name theme))
         depth-class (when-not (= :text theme) (str "shui__button-depth-" depth)) 
-        color-class (str "shui__button-color-" (some-> context :state deref :ui/radix-color name))
+        color-class (str "shui__button-color-" color-string) 
+        muted-class (when muted "shui__button-muted")
         size-class  (str "shui__button-size-" (name size))
         tiled-class (when tiled "shui__button-tiled")]
-    [:button.shui__button {:class (str theme-class " " depth-class " " color-class " " size-class " " tiled-class) 
+    [:button.shui__button {:class (str theme-class " " depth-class " " color-class " " size-class " " tiled-class " " muted-class " " class) 
                            :on-click (when on-click on-click)}
      (if-not tiled text
        (for [[index tile] (map-indexed vector (rest (string/split text #"")))]

+ 0 - 277
deps/shui/src/logseq/shui/cmdk/v2.cljs

@@ -1,277 +0,0 @@
-(ns logseq.shui.cmdk.v2
-  (:require 
-    [clojure.string :as str]
-    [logseq.shui.util :as util]
-    [logseq.shui.button.v2 :as button]
-    [logseq.shui.icon.v2 :as icon]
-    [rum.core :as rum]))
-
-(def state (atom {:current-engine "All"
-                  :highlight-index 0 
-                  :button {:text "Open" :theme :gray :shortcut ["return"]}
-                  :query ""
-                  :results {:blocks [] :pages [] :files []}}))
-
-; (let [entity (-> @state :context :entity)
-;       block (-> @state :results :blocks first)
-;       preview-uuid (-> @state :preview-uuid)
-;       {:keys [blocks-container get-block-and-children get-current-repo]} (:context @state)]
-;   ; (keys (entity (:block/page block)))
-;   ; blockgc)
-;   ; (blocks-container
-;   ;   (get-block-and-children (get-current-repo) preview-uuid) 
-;   ;   {:id preview-uuid :preview? true}))
-;   ; puuid)
-;   (get-block-and-children (get-current-repo) (keyword preview-uuid)))
-;   ; preview-uuid)
-;   ; (get-current-repo))
-
-; "6492d9e2-7554-4015-a28b-d6acbb6c1a19"
-; "logseq_local_shui-graph"
-  
-
-(defn handle-query-change [e context]
-  (let [query (.. e -target -value)]
-    (swap! state assoc :query query)
-    (when (and (seq query) (seq (str/trim query)))
-      (-> ((:search context) query)
-          (.then #(swap! state assoc :results %))))))
-
-(defn get-results []
-  [])
-
-(defn get-preview []
-  nil)
-
-(rum/defc result-heading [text]
-  [:div.text-xs.font-bold.pt-4.pb-1.px-6 {:style {:color "var(--lx-gray-11)"}} text])
-
-(rum/defc result-item [{:keys [icon icon-theme text info shortcut value-label value title highlighted on-highlight on-highlight-dep]}]
-  (rum/use-effect! 
-    (fn [] 
-      (when highlighted 
-        (on-highlight)))
-    [highlighted on-highlight-dep])
-  [:div.flex.px-6.gap-3.py-4 {:style {:background (if highlighted "var(--lx-gray-01)" "var(--lx-gray-02)")}}
-   [:div.w-5.h-5.rounded.flex.items-center.justify-center 
-    {:style {:background (case icon-theme :color "var(--lx-accent-09)" :gray "var(--lx-gray-09)" :gradient "linear-gradient(-65deg, #8AE8FF, #5373E7, #369EFF, #00B1CC)")
-             :box-shadow (when (#{:color :gradient} icon-theme) "inset 0 0 0 1px rgba(255,255,255,0.3) ")}}
-    (icon/root icon {:size "14"})]
-   [:div.flex.flex-1.flex-col
-    (when title
-      [:div.text-sm.pb-2.font-bold {:style {:color "var(--lx-gray-11)"}} title])
-    [:div {:class "text-sm font-medium"} text
-     (when info 
-       [:span {:style {:color "var(--lx-gray-11)"}} (str " — " info)])]]
-   (when (or value-label value)
-     [:div {:class "text-xs"}
-      [:span {:style {:color "var(--lx-gray-11)"}} (str value-label ": ")]
-      [:span {:style {:color "var(--lx-gray-12)"}} value]])
-   (when shortcut 
-     [:div
-      (for [key shortcut]
-        [:span (str key)])])])
-
-(rum/defc engines < rum/reactive [context]
-  (let [state-value (rum/react state)
-        {:keys [current-engine]} state-value
-        active-themes {"Quick capture" :color "AI" :gradient}]
-    [:div.flex.gap-4.px-6
-     (for [engine ["All" "Pages" "Blocks" "Quick capture" "AI"]
-           :let [theme (if (= engine current-engine) (get active-themes engine :gray) :gray)
-                 muted (if (= engine current-engine) "" " opacity-50")]]
-       [:div {:class (str "inline-block text-sm font-medium" muted)}
-        (button/root {:text engine :depth 0 :size :sm :theme theme} context)])]))
-
-(defn button-updater [text theme & shortcut]
-  (fn []
-    (swap! state assoc :button {:text text :theme theme :shortcut (map name shortcut)})))
-
-(defn button-updater-with-preview [preview-uuid text theme & shortcut]
-  (fn [] 
-    (apply button-updater text theme shortcut)
-    (if (string? preview-uuid)
-      (swap! state assoc :preview-uuid (uuid preview-uuid))
-      (swap! state assoc :preview-uuid preview-uuid))))
-
-(rum/defc results < rum/reactive []
-  (let [state-value (rum/react state)
-        {:keys [current-engine highlight-index results]} state-value
-        filtered-actions (when (#{"All" "Actions"} current-engine) 
-                           [{:icon-theme :color :icon "plus" :text "Quick capture" :info "Add a block to todays journal page" :on-highlight (button-updater "Quick capture" :color :return)}
-                            {:icon-theme :gradient :icon "question-mark" :text "Generate short answer" :on-highlight (button-updater "Generate" :gradient :return)} 
-                            {:icon-theme :gray :icon "toggle-left" :text "Toggle Logseq Sync" :value-label "Current State" :value "On" :on-highlight (button-updater "Toggle" :gray :return)} 
-                            {:icon-theme :gray :icon "player-play" :text "Restart Logseq Sync Onboarding" :on-highlight (button-updater "Restart" :gray :return)}])
-        filtered-qc-actions (when (#{"Quick capture"} current-engine)
-                              [{:icon-theme :color :icon "block" :text "Create block" :info "Add a block to todays journal page" :on-highlight (button-updater "Create" :color :cmd :return)} 
-                               {:icon-theme :color :icon "page" :text "Create page" :on-highlight (button-updater "Create" :color :cmd :return)} 
-                               {:icon-theme :color :icon "whiteboard" :text "Create whiteboard" :info "Create a whiteboard with this block on it" :on-highlight (button-updater "Create" :color :cmd :return)}]) 
-        filtered-ai-actions (when (#{"AI"} current-engine)
-                              [{:icon-theme :gradient :icon "page" :text "Ask about the current page" :on-highlight (button-updater "Query" :gradient :return)}
-                               {:icon-theme :gradient :icon "graph" :text "Ask about the current graph" :on-highlight (button-updater "Query" :gradient :return)} 
-                               {:icon-theme :gradient :icon "messages" :text "Chat" :info "Chat with an AI about any topic" :on-highlight (button-updater "Start chat" :gradient :return)} 
-                               {:icon-theme :gradient :icon "question-mark" :text "Generate short answer" :on-highlight (button-updater "Generate" :gradient :return)}])
-        filtered-blocks  (when (#{"All" "Blocks"} current-engine) 
-                           (->> (:blocks results) 
-                                (map #(hash-map :title (:block/content %) :on-highlight (button-updater-with-preview (:block/uuid %) "Open" :gray :return) :icon-theme :gray :icon "block"))))
-                           ; [{:icon-theme :gray :icon "block" :title "Not a real document" :on-highlight (button-updater "Open" :gray :return) :text "When working on cmdk, we want to display blocks that appear from search. These can have quite a long body of text, and that body of text should potentially be truncated"} 
-                           ;  {:icon-theme :gray :icon "block" :title "Not a real document" :on-highlight (button-updater "Open" :gray :return) :text "Of course, that truncated text should be truncated in a way that makes sense, and doesn't cut off in the middle of a word, and contains the search query if there is one"} 
-                           ;  {:icon-theme :gray :icon "block" :title "Not a real document" :on-highlight (button-updater "Open" :gray :return) :text "We should play around with displaying the blocks hierarchy, currently it's very noisy, and I'm not sure if it's adding much value. It's possible that the preview will be a sufficient replacement"}])
-        filtered-pages   (when (#{"All" "Pages"} current-engine)
-                           (->> (:pages results) 
-                                (map #(hash-map :title % :on-highlight (button-updater "Open" :gray :return) :icon-theme :gray :icon "page"))))
-                           ; [{:icon-theme :gray :icon "page" :text "Memo/CMDK" :on-highlight (button-updater "Open" :gray :return)} 
-                           ;  {:icon-theme :gray :icon "page" :text "Logseq Logo Community Contest" :on-highlight (button-updater "Open" :gray :return)}]) 
-        grouped-items    (->> [["Actions" filtered-actions] ["Actions" filtered-qc-actions] ["Actions" filtered-ai-actions] ["Blocks" filtered-blocks] ["Pages" filtered-pages]]
-                              (filter #(not-empty (second %))))
-        item-count       (count (mapcat second grouped-items))
-        highlight-index-normalized (cond 
-                                     (zero? item-count)
-                                     nil
-                                     (<= 0 (mod highlight-index item-count))
-                                     (mod highlight-index item-count)
-                                     :else
-                                     (- item-count (mod highlight-index item-count)))
-        highlight-item   (some->> highlight-index-normalized (nth (mapcat second grouped-items)))] 
-    [:div.overflow-y-auto {:style {:max-height "50dvh"}}
-     (for [[index [group items]] (map-indexed vector grouped-items)] 
-       [:<> 
-        (when-not (zero? index) 
-         [:div.w-full {:style {:background "var(--lx-gray-07)"}
-                       :class "h-px"}])
-        (result-heading group)
-        (for [item items]
-          (result-item (assoc item :highlighted (= item highlight-item) :on-highlight-dep current-engine)))])]))
-
-(rum/defc preview < rum/reactive 
-  [_ {:keys [blocks-container get-block-and-children get-current-repo entity get-page page-cp get-page-blocks-no-cache get-block-children page] :as context}]
-  (let [state-value (rum/react state)
-        preview-uuid (:preview-uuid state-value)
-        preview-entity (entity [:block/uuid preview-uuid])
-        preview-page (:block/page preview-entity)
-        preview-page-uuid (:block/uuid preview-page)
-        preview-page-name (:block/name preview-page)]
-    (-> {:preview-uuid preview-uuid :preview-page-uuid preview-page-uuid :preview-page-name preview-page-name} 
-        pr-str 
-        js/console.log)
-    [:div 
-     ;; page 
-     (page {:page-name preview-page-name})]))
-     ; (page-cp {:preview? true
-     ;           :contents-page? (= "contents" (str/lower-case (str preview-page-name))) 
-     ;           :children (get-block-children (get-current-repo) preview-page-uuid)}
-     ;          preview-page)]))
-     ;; block
-     ; (blocks-container
-     ;   (get-block-and-children (get-current-repo) preview-uuid) 
-     ;   ; (get-block-and-children (get-current-repo) preview-page-uuid) 
-     ;   ; (get-page preview-page-uuid) 
-     ;   {:id preview-uuid :preview? true})]))
-
-; (let [preview-uuid (:preview-uuid @state)
-;       entity (-> @state :context :entity)]
-;   (keys (:block/page (entity [:block/uuid preview-uuid]))))
-
-(rum/defc actions < rum/reactive []
-  (let [state-value (rum/react state)
-        button-props (:button state-value)]
-    [:div.py-4.px-6.flex.justify-end.gap-6.border-t
-     {:style {:background-color "var(--lx-gray-03)"
-              :border-color "var(--lx-gray-07)"}}
-     (button/root {:text "Cancel" :theme :gray} {})
-     (button/root button-props {})]))
-
-(rum/defc quick-capture []
-  [:div.px-6
-   [:div.flex.items-center
-    [:div.w-4.h-4.flex.items-center.justify-center
-     [:div.w-2.h-2.bg-white.rounded-full.opacity-25]]
-    [:input {:class "w-full border-0 px-6 bg-transparent" 
-             :type "text"}]]
-   [:div.flex.items-center 
-    (icon/root "circle-plus" {:style {:opacity 0.5}})
-    [:input {:class "w-full border-0 px-6 bg-transparent"
-             :type "text"}]]])
-
-(rum/defc search < rum/reactive [context]
-  (let [state-value (rum/react state)
-        query (:query state-value)]
-    [:input {:class "w-full border-0 px-6"
-             :type "text" 
-             :placeholder "Search"
-             :value query
-             :on-change #(handle-query-change % context)}]))
-
-(rum/defc header < rum/reactive 
-  [context]
-  (let [state-value (rum/react state) 
-        current-engine (:current-engine state-value)]
-    [:div.relative.border-b.flex.flex-col.gap-4.pt-4.pb-1.rounded 
-     {:style {:border-color "var(--lx-gray-07)" 
-              :background (when (= current-engine "Quick capture") "var(--lx-accent-02")}
-      :class (when (= current-engine "Quick capture") "shui__cmdk-quick-capture-glow")}
-     (engines context)
-     (if (= current-engine "Quick capture")
-       (quick-capture)
-       (search context))]))
-
-(defn prev-engine [current-engine]
-  (->> ["All" "Pages" "Blocks" "Quick capture" "AI" "All"]
-       (reverse)
-       (drop-while (complement #{current-engine}))
-       (second)))
-
-(defn next-engine [current-engine]
-  (->> ["All" "Pages" "Blocks" "Quick capture" "AI" "All"]
-       (drop-while (complement #{current-engine}))
-       (second)))
-
-(defonce keydown-handler
-  (fn [e]
-    (case (.-key e)
-      ; "Escape" (rum/dispatch! :close)
-      "ArrowDown" (swap! state update :highlight-index inc)
-      "ArrowUp" (swap! state update :highlight-index dec)
-      "j" (when (.-metaKey e) 
-            (if (.-shiftKey e)
-              (swap! state update :current-engine prev-engine)
-              (swap! state update :current-engine next-engine)))
-      ; "ArrowUp" (rum/dispatch! :highlight-prev)
-      ; "Enter" (rum/dispatch! :select)
-      (println (.-key e)))))
-
-(defn use-cmdk-keyboard-bindings! []
-  (rum/use-effect! 
-    (fn []
-      (js/window.addEventListener "keydown" keydown-handler)
-      #(js/window.removeEventListener "keydown" keydown-handler))
-    []))
-
-(rum/defc body < rum/reactive [context]
-  (let [state-value (rum/react state)
-        preview-uuid (:preview-uuid state-value)]
-    (if preview-uuid
-      [:div.grid.grid-cols-2
-       (results)
-       (preview preview-uuid context)]
-      [:div.grid.grid-cols-1 
-       (results)])))
-  
-
-(rum/defc root < rum/reactive
-  {:did-mount (fn [_] 
-                (js/window.removeEventListener "keydown" keydown-handler)
-                (js/window.addEventListener "keydown" keydown-handler))
-   :will-unmount (fn [_] (js/window.removeEventListener "keydown" keydown-handler))}
-  [props context]
-  (swap! state assoc :context context)
-  ; (use-cmdk-keyboard-bindings!)
-  [:div.-m-8 {:style {:background-color "var(--lx-gray-02)"
-                      :width "75vw" 
-                      :max-width 800}}
-   (header context)
-   (body context)
-   [:div
-    (actions)]])
-   
-

+ 3 - 23
deps/shui/src/logseq/shui/context.cljs

@@ -1,10 +1,4 @@
-(ns logseq.shui.context
-  (:require 
-    [frontend.colors :as colors]
-    [frontend.db :as db]
-    [frontend.db.utils :as db-utils]
-    [frontend.handler.search :as search-handler]
-    [frontend.state :as state]))
+(ns logseq.shui.context)
 
 (defn inline->inline-block [inline block-config]
   (fn [_context item]
@@ -15,9 +9,9 @@
     (fn [context col]
       (map #(inline* context %) col))))
 
-(defn make-context [{:keys [block-config app-config inline int->local-time-2 blocks-container page-cp page]}]
+(defn make-context [{:keys [block-config config inline int->local-time-2 blocks-container page-cp page]}]
   {;; Shui needs access to the global configuration of the application
-   :config app-config
+   :config config
    ;; Until components are converted over, they need to fallback to the old inline function 
    ;; Wrap the old inline function to allow for interception, but fallback to the old inline function
    :inline-block (inline->inline-block inline block-config)
@@ -40,21 +34,7 @@
    ;; Some functions from logseq's application will be used in the shui components. To avoid circular dependencies,
    ;; they will be provided via the context object
    :int->local-time-2 int->local-time-2
-   ;; We need some variable from the state to carry over 
-   :color-accent (state/get-color-accent) 
-   :color-gradient (state/get-color-gradient)
-   :sub-color-gradient-bg-styles state/sub-color-gradient-bg-styles 
-   :sub-color-gradient-text-styles state/sub-color-gradient-text-styles
-   :linear-gradient colors/linear-gradient
-   :state state/state
    ;; Add search to context 
-   :search search-handler/search
-   :entity db-utils/entity
    :blocks-container blocks-container
-   :get-block-and-children db/get-block-and-children
-   :get-block-children db/get-block-children
-   :get-current-repo state/get-current-repo
-   :get-page-blocks-no-cache db/get-page-blocks-no-cache
-   :get-page db/get-page
    :page-cp page-cp
    :page page})

+ 0 - 5
deps/shui/src/logseq/shui/core.cljs

@@ -1,7 +1,6 @@
 (ns logseq.shui.core
   (:require 
     [logseq.shui.button.v2 :as shui.button.v2]
-    [logseq.shui.cmdk.v2 :as shui.cmdk.v2]
     [logseq.shui.context :as shui.context]
     [logseq.shui.icon.v2 :as shui.icon.v2]
     [logseq.shui.list-item.v1 :as shui.list-item.v1]
@@ -15,10 +14,6 @@
 (def button shui.button.v2/root)
 (def button-v2 shui.button.v2/root)
 
-;; cmdk 
-(def cmdk shui.cmdk.v2/root)
-(def cmdk-v2 shui.cmdk.v2/root)
-
 ;; icon 
 (def icon shui.icon.v2/root)
 (def icon-v2 shui.icon.v2/root)

+ 67 - 6
deps/shui/src/logseq/shui/list_item/v1.cljs

@@ -1,5 +1,6 @@
 (ns logseq.shui.list-item.v1
   (:require 
+    ["remove-accents" :as remove-accents]
     [rum.core :as rum]
     [clojure.string :as string]
     [logseq.shui.icon.v2 :as icon]
@@ -23,9 +24,69 @@
     (nil) ""
     (name key)))
 
+(defn normalize-text [app-config text]
+  (cond-> (or text "") 
+    :lower-case (string/lower-case)
+    :normalize (.normalize "NFKC")
+    (:feature/enable-search-remove-accents? app-config) (remove-accents)))
+
+(defn split-text-on-highlight [text query normal-text normal-query]
+  (let [start-index (string/index-of normal-text normal-query)
+        end-index (+ start-index (count query))]
+    [(subs text 0 start-index)
+     (subs text start-index end-index) 
+     (subs text end-index)]))
+
+(defn span-with-single-highlight-token [text query normal-text normal-query]
+  (let [[before-text highlighted-text after-text] (split-text-on-highlight text query normal-text normal-query)]
+    [:span 
+     (when-not (string/blank? before-text) [:span before-text])
+     (when-not (string/blank? highlighted-text) [:span {:style {:background "var(--lx-accent-09)"}} highlighted-text])
+     (when-not (string/blank? after-text) [:span after-text])]))
+
+(defn span-with-mutliple-highlight-tokens [app-config text query normal-text normal-query]
+  (loop [[query-token & more] (string/split normal-query #" ")
+         result [[:text text]]]
+    (if-not query-token 
+      (->> result 
+           (map (fn [[type value]] 
+                  (if (= type :text) 
+                    [:span value] 
+                    [:span {:style {:background "var(--lx-accent-09)"}} value])))
+           (into [:span]))
+      (->> result 
+           (mapcat (fn [[type value]]
+                     (if-not (and (= type :text) (string? value) (string/includes? value query-token))
+                       [[type value]]
+                       (let [normal-value (normalize-text app-config value)
+                             normal-query-token (normalize-text app-config query-token)
+                             [before-text highlighted-text after-text] (split-text-on-highlight value query-token normal-value normal-query-token)]
+                        [[:text before-text] 
+                         [:match highlighted-text] 
+                         [:text after-text]]))))
+           (recur more)))))
+
+(defn highlight-query* [app-config query text]
+  (if-not (seq query) [:span text]
+    (let [normal-text (normalize-text app-config text)
+          normal-query (normalize-text app-config query)]
+      (cond 
+        ;; When the match is present but is multiple tokens, highlight all tokens
+        (and (string? query) (re-find #" " query))
+        (span-with-mutliple-highlight-tokens app-config text query normal-text normal-query)
+        ;; When the match is present and only a single token, highlight that token
+        (string/includes? normal-text normal-query)
+        (span-with-single-highlight-token text query normal-text normal-query)
+        ;; Otherwise, just return the text
+        :else
+        [:span text]))))
+        
+
 ;; result-item
-(rum/defc root [{:keys [icon icon-theme text info shortcut value-label value title highlighted on-highlight on-highlight-dep header on-click]}]
-  (let [ref (rum/create-ref)]
+(rum/defc root [{:keys [icon icon-theme query text info shortcut value-label value title highlighted on-highlight on-highlight-dep header on-click]} 
+                {:keys [app-config]}]
+  (let [ref (rum/create-ref)
+        highlight-query (partial highlight-query* app-config query)]
     (rum/use-effect! 
       (fn [] 
         (when (and highlighted on-highlight) 
@@ -41,7 +102,7 @@
      (when header
       [:div.text-xs.pl-8.font-light {:class "-mt-1"
                                      :style {:color "var(--lx-gray-11)"}}
-                                    header])
+                                    (highlight-query header)])
      ;; main row
      [:div.flex.items-center.gap-3
       [:div.w-5.h-5.rounded.flex.items-center.justify-center 
@@ -50,11 +111,11 @@
        (icon/root icon {:size "14"})]
       [:div.flex.flex-1.flex-col
        (when title
-         [:div.text-sm.pb-2.font-bold {:style {:color "var(--lx-gray-11)"}} title])
+         [:div.text-sm.pb-2.font-bold {:style {:color "var(--lx-gray-11)"}} (highlight-query title)])
        [:div {:class "text-sm font-medium"
-              :style {:color "var(--lx-gray-12)"}} text
+              :style {:color "var(--lx-gray-12)"}} (highlight-query text)
         (when info 
-          [:span {:style {:color "var(--lx-gray-11)"}} (str " — " info)])]]
+          [:span {:style {:color "var(--lx-gray-11)"}} " — " (highlight-query info)])]]
       (when (or value-label value)
         [:div {:class "text-xs"}
          (when (and value-label value)

+ 149 - 0
resources/css/radix.css

@@ -1377,3 +1377,152 @@ html.dark, html[data-theme=dark] {
   --rx-yellow-11-alpha: hsla(48, 100%, 50.0%, 0.934);
   --rx-yellow-12-alpha: hsla(60, 100%, 91.8%, 0.980);
 }
+
+/* LOGSEQ X RADIX */
+
+.border-gray-01 { border-color: var(--lx-gray-01); }
+.border-gray-01-alpha { border-color: var(--lx-gray-01-alpha); }
+.border-gray-02 { border-color: var(--lx-gray-02); }
+.border-gray-02-alpha { border-color: var(--lx-gray-02-alpha); }
+.border-gray-03 { border-color: var(--lx-gray-03); }
+.border-gray-03-alpha { border-color: var(--lx-gray-03-alpha); }
+.border-gray-04 { border-color: var(--lx-gray-04); }
+.border-gray-04-alpha { border-color: var(--lx-gray-04-alpha); }
+.border-gray-05 { border-color: var(--lx-gray-05); }
+.border-gray-05-alpha { border-color: var(--lx-gray-05-alpha); }
+.border-gray-06 { border-color: var(--lx-gray-06); }
+.border-gray-06-alpha { border-color: var(--lx-gray-06-alpha); }
+.border-gray-07 { border-color: var(--lx-gray-07); }
+.border-gray-07-alpha { border-color: var(--lx-gray-07-alpha); }
+.border-gray-08 { border-color: var(--lx-gray-08); }
+.border-gray-08-alpha { border-color: var(--lx-gray-08-alpha); }
+.border-gray-09 { border-color: var(--lx-gray-09); }
+.border-gray-09-alpha { border-color: var(--lx-gray-09-alpha); }
+.border-gray-10 { border-color: var(--lx-gray-10); }
+.border-gray-10-alpha { border-color: var(--lx-gray-10-alpha); }
+.border-gray-11 { border-color: var(--lx-gray-11); }
+.border-gray-11-alpha { border-color: var(--lx-gray-11-alpha); }
+.border-gray-12 { border-color: var(--lx-gray-12); }
+.border-gray-12-alpha { border-color: var(--lx-gray-12-alpha); }
+.border-accent-01 { border-color: var(--lx-accent-01); }
+.border-accent-01-alpha { border-color: var(--lx-accent-01-alpha); }
+.border-accent-02 { border-color: var(--lx-accent-02); }
+.border-accent-02-alpha { border-color: var(--lx-accent-02-alpha); }
+.border-accent-03 { border-color: var(--lx-accent-03); }
+.border-accent-03-alpha { border-color: var(--lx-accent-03-alpha); }
+.border-accent-04 { border-color: var(--lx-accent-04); }
+.border-accent-04-alpha { border-color: var(--lx-accent-04-alpha); }
+.border-accent-05 { border-color: var(--lx-accent-05); }
+.border-accent-05-alpha { border-color: var(--lx-accent-05-alpha); }
+.border-accent-06 { border-color: var(--lx-accent-06); }
+.border-accent-06-alpha { border-color: var(--lx-accent-06-alpha); }
+.border-accent-07 { border-color: var(--lx-accent-07); }
+.border-accent-07-alpha { border-color: var(--lx-accent-07-alpha); }
+.border-accent-08 { border-color: var(--lx-accent-08); }
+.border-accent-08-alpha { border-color: var(--lx-accent-08-alpha); }
+.border-accent-09 { border-color: var(--lx-accent-09); }
+.border-accent-09-alpha { border-color: var(--lx-accent-09-alpha); }
+.border-accent-10 { border-color: var(--lx-accent-10); }
+.border-accent-10-alpha { border-color: var(--lx-accent-10-alpha); }
+.border-accent-11 { border-color: var(--lx-accent-11); }
+.border-accent-11-alpha { border-color: var(--lx-accent-11-alpha); }
+.border-accent-12 { border-color: var(--lx-accent-12); }
+.border-accent-12-alpha { border-color: var(--lx-accent-12-alpha); }
+
+.bg-gray-01 { background-color: var(--lx-gray-01); }
+.bg-gray-01-alpha { background-color: var(--lx-gray-01-alpha); }
+.bg-gray-02 { background-color: var(--lx-gray-02); }
+.bg-gray-02-alpha { background-color: var(--lx-gray-02-alpha); }
+.bg-gray-03 { background-color: var(--lx-gray-03); }
+.bg-gray-03-alpha { background-color: var(--lx-gray-03-alpha); }
+.bg-gray-04 { background-color: var(--lx-gray-04); }
+.bg-gray-04-alpha { background-color: var(--lx-gray-04-alpha); }
+.bg-gray-05 { background-color: var(--lx-gray-05); }
+.bg-gray-05-alpha { background-color: var(--lx-gray-05-alpha); }
+.bg-gray-06 { background-color: var(--lx-gray-06); }
+.bg-gray-06-alpha { background-color: var(--lx-gray-06-alpha); }
+.bg-gray-07 { background-color: var(--lx-gray-07); }
+.bg-gray-07-alpha { background-color: var(--lx-gray-07-alpha); }
+.bg-gray-08 { background-color: var(--lx-gray-08); }
+.bg-gray-08-alpha { background-color: var(--lx-gray-08-alpha); }
+.bg-gray-09 { background-color: var(--lx-gray-09); }
+.bg-gray-09-alpha { background-color: var(--lx-gray-09-alpha); }
+.bg-gray-10 { background-color: var(--lx-gray-10); }
+.bg-gray-10-alpha { background-color: var(--lx-gray-10-alpha); }
+.bg-gray-11 { background-color: var(--lx-gray-11); }
+.bg-gray-11-alpha { background-color: var(--lx-gray-11-alpha); }
+.bg-gray-12 { background-color: var(--lx-gray-12); }
+.bg-gray-12-alpha { background-color: var(--lx-gray-12-alpha); }
+.bg-accent-01 { background-color: var(--lx-accent-01); }
+.bg-accent-01-alpha { background-color: var(--lx-accent-01-alpha); }
+.bg-accent-02 { background-color: var(--lx-accent-02); }
+.bg-accent-02-alpha { background-color: var(--lx-accent-02-alpha); }
+.bg-accent-03 { background-color: var(--lx-accent-03); }
+.bg-accent-03-alpha { background-color: var(--lx-accent-03-alpha); }
+.bg-accent-04 { background-color: var(--lx-accent-04); }
+.bg-accent-04-alpha { background-color: var(--lx-accent-04-alpha); }
+.bg-accent-05 { background-color: var(--lx-accent-05); }
+.bg-accent-05-alpha { background-color: var(--lx-accent-05-alpha); }
+.bg-accent-06 { background-color: var(--lx-accent-06); }
+.bg-accent-06-alpha { background-color: var(--lx-accent-06-alpha); }
+.bg-accent-07 { background-color: var(--lx-accent-07); }
+.bg-accent-07-alpha { background-color: var(--lx-accent-07-alpha); }
+.bg-accent-08 { background-color: var(--lx-accent-08); }
+.bg-accent-08-alpha { background-color: var(--lx-accent-08-alpha); }
+.bg-accent-09 { background-color: var(--lx-accent-09); }
+.bg-accent-09-alpha { background-color: var(--lx-accent-09-alpha); }
+.bg-accent-10 { background-color: var(--lx-accent-10); }
+.bg-accent-10-alpha { background-color: var(--lx-accent-10-alpha); }
+.bg-accent-11 { background-color: var(--lx-accent-11); }
+.bg-accent-11-alpha { background-color: var(--lx-accent-11-alpha); }
+.bg-accent-12 { background-color: var(--lx-accent-12); }
+.bg-accent-12-alpha { background-color: var(--lx-accent-12-alpha); }
+
+.text-gray-01 { color: var(--lx-gray-01); }
+.text-gray-01-alpha { color: var(--lx-gray-01-alpha); }
+.text-gray-02 { color: var(--lx-gray-02); }
+.text-gray-02-alpha { color: var(--lx-gray-02-alpha); }
+.text-gray-03 { color: var(--lx-gray-03); }
+.text-gray-03-alpha { color: var(--lx-gray-03-alpha); }
+.text-gray-04 { color: var(--lx-gray-04); }
+.text-gray-04-alpha { color: var(--lx-gray-04-alpha); }
+.text-gray-05 { color: var(--lx-gray-05); }
+.text-gray-05-alpha { color: var(--lx-gray-05-alpha); }
+.text-gray-06 { color: var(--lx-gray-06); }
+.text-gray-06-alpha { color: var(--lx-gray-06-alpha); }
+.text-gray-07 { color: var(--lx-gray-07); }
+.text-gray-07-alpha { color: var(--lx-gray-07-alpha); }
+.text-gray-08 { color: var(--lx-gray-08); }
+.text-gray-08-alpha { color: var(--lx-gray-08-alpha); }
+.text-gray-09 { color: var(--lx-gray-09); }
+.text-gray-09-alpha { color: var(--lx-gray-09-alpha); }
+.text-gray-10 { color: var(--lx-gray-10); }
+.text-gray-10-alpha { color: var(--lx-gray-10-alpha); }
+.text-gray-11 { color: var(--lx-gray-11); }
+.text-gray-11-alpha { color: var(--lx-gray-11-alpha); }
+.text-gray-12 { color: var(--lx-gray-12); }
+.text-gray-12-alpha { color: var(--lx-gray-12-alpha); }
+.text-accent-01 { color: var(--lx-accent-01); }
+.text-accent-01-alpha { color: var(--lx-accent-01-alpha); }
+.text-accent-02 { color: var(--lx-accent-02); }
+.text-accent-02-alpha { color: var(--lx-accent-02-alpha); }
+.text-accent-03 { color: var(--lx-accent-03); }
+.text-accent-03-alpha { color: var(--lx-accent-03-alpha); }
+.text-accent-04 { color: var(--lx-accent-04); }
+.text-accent-04-alpha { color: var(--lx-accent-04-alpha); }
+.text-accent-05 { color: var(--lx-accent-05); }
+.text-accent-05-alpha { color: var(--lx-accent-05-alpha); }
+.text-accent-06 { color: var(--lx-accent-06); }
+.text-accent-06-alpha { color: var(--lx-accent-06-alpha); }
+.text-accent-07 { color: var(--lx-accent-07); }
+.text-accent-07-alpha { color: var(--lx-accent-07-alpha); }
+.text-accent-08 { color: var(--lx-accent-08); }
+.text-accent-08-alpha { color: var(--lx-accent-08-alpha); }
+.text-accent-09 { color: var(--lx-accent-09); }
+.text-accent-09-alpha { color: var(--lx-accent-09-alpha); }
+.text-accent-10 { color: var(--lx-accent-10); }
+.text-accent-10-alpha { color: var(--lx-accent-10-alpha); }
+.text-accent-11 { color: var(--lx-accent-11); }
+.text-accent-11-alpha { color: var(--lx-accent-11-alpha); }
+.text-accent-12 { color: var(--lx-accent-12); }
+.text-accent-12-alpha { color: var(--lx-accent-12-alpha); }

+ 68 - 27
resources/css/shui.css

@@ -39,28 +39,28 @@
   box-shadow: none;
 }
 
-.shui__button-theme-color {
+.shui__button-theme {
   background: or(--lx-accent-09, --rx-blue-09);
 }
 
-.shui__button-theme-color:hover {
+.shui__button-theme:hover {
   background: or(--lx-accent-10, --rx-blue-10);
 }
 
-.shui__button-theme-color:active {
+.shui__button-theme:active {
   background: or(--lx-accent-08, --rx-blue-08);
 }
 
 .shui__button-theme-gray {
-  background: or(--lx-gray-05, --ls-quaternary-background-color);
+  background: or(--lx-gray-05, --ls-quaternary-background);
 }
 
 .shui__button-theme-gray:hover {
-  background: or(--lx-gray-06, --ls-quaternary-background-color);
+  background: or(--lx-gray-06, --ls-quaternary-background);
 }
 
 .shui__button-theme-gray:active {
-  background: or(--lx-gray-04, --ls-quaternary-background-color);
+  background: or(--lx-gray-04, --ls-quaternary-background);
 }
 
 .shui__button-theme-gradient {
@@ -78,43 +78,43 @@
   --depth-shadow-to: rgba(0, 0, 0, 0);
 }
 
-.shui__button-theme-gradient.shui__button-color-,
-.shui__button-theme-gradient.shui__button-color-indigo,
-.shui__button-theme-gradient.shui__button-color-blue,
-.shui__button-theme-gradient.shui__button-color-sky,
-.shui__button-theme-gradient.shui__button-color-cyan {
+.shui__button-theme-gradient.shui__button-,
+.shui__button-theme-gradient.shui__button-indigo,
+.shui__button-theme-gradient.shui__button-blue,
+.shui__button-theme-gradient.shui__button-sky,
+.shui__button-theme-gradient.shui__button-cyan {
   background: linear-gradient(37deg, var(--depth-shadow-from) 0%, var(--depth-shadow-to) 100%),
               linear-gradient(135deg, var(--rx-indigo-09) 0%, var(--rx-blue-09) 33.85%, var(--rx-sky-09) 64.06%, var(--rx-cyan-09) 100%);
 }
 
-.shui__button-theme-gradient.shui__button-color-tomato,
-.shui__button-theme-gradient.shui__button-color-red,
-.shui__button-theme-gradient.shui__button-color-crimson,
-.shui__button-theme-gradient.shui__button-color-pink,
-.shui__button-theme-gradient.shui__button-color-plum,
-.shui__button-theme-gradient.shui__button-color-purple,
-.shui__button-theme-gradient.shui__button-color-violet {
+.shui__button-theme-gradient.shui__button-tomato,
+.shui__button-theme-gradient.shui__button-red,
+.shui__button-theme-gradient.shui__button-crimson,
+.shui__button-theme-gradient.shui__button-pink,
+.shui__button-theme-gradient.shui__button-plum,
+.shui__button-theme-gradient.shui__button-purple,
+.shui__button-theme-gradient.shui__button-violet {
   background: linear-gradient(37deg, var(--depth-shadow-from) 0%, var(--depth-shadow-to) 100%),
               linear-gradient(135deg, var(--rx-tomato-09) 0%, var(--rx-red-09) 16.66%, var(--rx-crimson-09) 33.33%, var(--rx-pink-09) 50%, var(--rx-plum-09) 66.66%, var(--rx-purple-09) 83.33%, var(--rx-violet-09) 100%);
 }
 
-.shui__button-theme-gradient.shui__button-color-green,
-.shui__button-theme-gradient.shui__button-color-mint,
-.shui__button-theme-gradient.shui__button-color-teal {
+.shui__button-theme-gradient.shui__button-green,
+.shui__button-theme-gradient.shui__button-mint,
+.shui__button-theme-gradient.shui__button-teal {
   background: linear-gradient(37deg, var(--depth-shadow-from) 0%, var(--depth-shadow-to) 100%),
               linear-gradient(135deg, var(--rx-teal-09) 0%, var(--rx-mint-09) 50%, var(--rx-green-09) 100%);
 }
 
-.shui__button-theme-gradient.shui__button-color-grass,
-.shui__button-theme-gradient.shui__button-color-lime {
+.shui__button-theme-gradient.shui__button-grass,
+.shui__button-theme-gradient.shui__button-lime {
   background: linear-gradient(37deg, var(--depth-shadow-from) 0%, var(--depth-shadow-to) 100%),
               linear-gradient(135deg, var(--rx-grass-09) 0%, var(--rx-lime-09) 100%);
 }
 
-.shui__button-theme-gradient.shui__button-color-yellow,
-.shui__button-theme-gradient.shui__button-color-amber,
-.shui__button-theme-gradient.shui__button-color-orange,
-.shui__button-theme-gradient.shui__button-color-brown {
+.shui__button-theme-gradient.shui__button-yellow,
+.shui__button-theme-gradient.shui__button-amber,
+.shui__button-theme-gradient.shui__button-orange,
+.shui__button-theme-gradient.shui__button-brown {
   background: linear-gradient(37deg, var(--depth-shadow-from) 0%, var(--depth-shadow-to) 100%),
               linear-gradient(135deg, var(--rx-yellow-09) 0%, var(--rx-amber-09) 33.33%, var(--rx-orange-09) 66.66%, var(--rx-brown-09) 100%);
 }
@@ -210,3 +210,44 @@
   -webkit-mask-composite: xor;
   mask-composite: exclude;
 }
+
+.shui__button-muted {
+  transition: opacity 200 ease-in;
+  opacity: 0.4;
+}
+
+.shui__button-muted:hover {
+  opacity: 1;
+}
+
+.shui__button-theme-gray.shui__button-color-custom  { background-color: var(--ls-tertiary-background-color); color: white; }
+.shui__button-theme-color.shui__button-color-custom  { background-color: var(--color-indigo-600); color: white; }
+
+.shui__button-theme-color.shui__button-color-lime    { background-color: var(--rx-lime-09)} 
+.shui__button-theme-color.shui__button-color-orange  { background-color: var(--rx-orange-09)} 
+.shui__button-theme-color.shui__button-color-gray    { background-color: var(--rx-gray-09)} 
+.shui__button-theme-color.shui__button-color-sand    { background-color: var(--rx-sand-09)} 
+.shui__button-theme-color.shui__button-color-crimson { background-color: var(--rx-crimson-09)} 
+.shui__button-theme-color.shui__button-color-yellow  { background-color: var(--rx-yellow-09)} 
+.shui__button-theme-color.shui__button-color-green   { background-color: var(--rx-green-09)} 
+.shui__button-theme-color.shui__button-color-indigo  { background-color: var(--rx-indigo-09)} 
+.shui__button-theme-color.shui__button-color-cyan    { background-color: var(--rx-cyan-09)} 
+.shui__button-theme-color.shui__button-color-violet  { background-color: var(--rx-violet-09)} 
+.shui__button-theme-color.shui__button-color-bronze  { background-color: var(--rx-bronze-09)} 
+.shui__button-theme-color.shui__button-color-slate   { background-color: var(--rx-slate-09)} 
+.shui__button-theme-color.shui__button-color-gold    { background-color: var(--rx-gold-09)} 
+.shui__button-theme-color.shui__button-color-sage    { background-color: var(--rx-sage-09)} 
+.shui__button-theme-color.shui__button-color-mauve   { background-color: var(--rx-mauve-09)} 
+.shui__button-theme-color.shui__button-color-mint    { background-color: var(--rx-mint-09)} 
+.shui__button-theme-color.shui__button-color-red     { background-color: var(--rx-red-09)} 
+.shui__button-theme-color.shui__button-color-blue    { background-color: var(--rx-blue-09)} 
+.shui__button-theme-color.shui__button-color-grass   { background-color: var(--rx-grass-09)} 
+.shui__button-theme-color.shui__button-color-plum    { background-color: var(--rx-plum-09)} 
+.shui__button-theme-color.shui__button-color-pink    { background-color: var(--rx-pink-09)} 
+.shui__button-theme-color.shui__button-color-teal    { background-color: var(--rx-teal-09)} 
+.shui__button-theme-color.shui__button-color-amber   { background-color: var(--rx-amber-09)} 
+.shui__button-theme-color.shui__button-color-purple  { background-color: var(--rx-purple-09)} 
+.shui__button-theme-color.shui__button-color-brown   { background-color: var(--rx-brown-09)} 
+.shui__button-theme-color.shui__button-color-sky     { background-color: var(--rx-sky-09)} 
+.shui__button-theme-color.shui__button-color-olive   { background-color: var(--rx-olive-09)} 
+.shui__button-theme-color.shui__button-color-tomato  { background-color: var(--rx-tomato-09)} 

Разница между файлами не показана из-за своего большого размера
+ 0 - 1483
src/main/frontend/colors.cljs


+ 131 - 45
src/main/frontend/components/cmdk.cljs

@@ -20,11 +20,14 @@
     [frontend.util :as util]
     [frontend.util.page :as page-util]
     [goog.functions :as gfun]
-    [logseq.shui.context :refer [make-context]]
+    [frontend.shui :refer [make-shui-context]]
     [logseq.shui.core :as shui]
     [promesa.core :as p]
     [rum.core :as rum]))
 
+(def GROUP-LIMIT 5)
+(def FILTER-ROW-HEIGHT 73)
+
 ;; When CMDK opens, we have some default search actions we make avaialbe for quick access
 (def default-search-actions 
   [{:text "Search only pages"        :info "Add filter to search" :icon-theme :gray :icon "page" :filter {:group :pages}}
@@ -36,13 +39,16 @@
    ; {:text "Generate short answer"    :info "Ask a language model"                :icon "question-mark" :icon-theme :gradient}
 
 (def default-commands 
-  [{:text "Open settings" :icon "settings"      :icon-theme :gray}])
+  [{:text "Open settings" :icon "settings"      :icon-theme :gray}
+   {:text "Open settings" :icon "settings"      :icon-theme :gray}
+   {:text "Open settings" :icon "settings"      :icon-theme :gray}])
 
 ;; The results are separated into groups, and loaded/fetched/queried separately
 (def default-results 
-  {:search-actions {:status :success :show-more false :items default-search-actions} 
-   :commands       {:status :success :show-more false :items default-commands}
-   :history        {:status :success :show-more false :items nil}
+  {:search-actions {:status :success :show-more false :items nil} 
+   :recents        {:status :success :show-more false :items nil}
+   :commands       {:status :success :show-more false :items nil}
+   :favorites      {:status :success :show-more false :items nil}
    :current-page   {:status :success :show-more false :items nil}
    :pages          {:status :success :show-more false :items nil}
    :blocks         {:status :success :show-more false :items nil} 
@@ -51,18 +57,20 @@
 ;; Take the results, decide how many items to show, and order the results appropriately
 (defn state->results-ordered [state]
   (let [results @(::results state)
+        index (volatile! -1)
         visible-items (fn [group] 
                         (let [{:keys [items show-more]} (get results group)]
                           (if show-more items (take 5 items))))
-        results [["Search actions" :search-actions (visible-items :search-actions)]
+        results [["Recents"        :recents        (visible-items :recents)]
+                 ["Search actions" :search-actions (visible-items :search-actions)]
                  ["Current page"   :current-page   (visible-items :current-page)]
                  ["Commands"       :commands       (visible-items :commands)]
                  ["Pages"          :pages          (visible-items :pages)]
                  ["Whiteboards"    :whiteboards    (visible-items :whiteboards)]
                  ["Blocks"         :blocks         (visible-items :blocks)]]]
-    results))
-    ; (for [[group-name group-key group-items] results]
-    ;   [group-name group-key (mapv #(assoc % :item-index (vswap! index inc)) group-items)])))
+    ; results
+    (for [[group-name group-key group-items] results]
+      [group-name group-key (mapv #(assoc % :item-index (vswap! index inc)) group-items)])))
 
 ;; Take the ordered results and the highlight index and determine which item is highlighted
 ; (defn state->highlighted-item 
@@ -81,6 +89,30 @@
 ;; Each result gorup has it's own load-results function
 (defmulti load-results (fn [group state] group))
 
+;; Initially we want to load the recents into the results 
+(defmethod load-results :initial [_ state]
+  (let [!results (::results state)
+        recent-searches (mapv (fn [q] {:type :search :data q}) (db/get-key-value :recent/search))
+        recent-pages (mapv (fn [page] {:type :page :data page}) (db/get-key-value :recent/pages))
+        recent-items (->> (concat recent-searches recent-pages) 
+                          (map #(hash-map :icon (if (= :page (:type %)) "page" "history")
+                                          :icon-theme :gray 
+                                          :text (:data %)
+                                          :source-recent %)))
+        command-items (->> (cp-handler/top-commands 1000) 
+                           (map #(hash-map :icon "command" 
+                                           :icon-theme :gray 
+                                           :text (cp/translate t %)
+                                           :value-label (pr-str (:id %))
+                                           :shortcut (:shortcut %)
+                                           :source-command %)))
+        favorite-pages nil
+        favorite-items nil]
+    (reset! !results (-> default-results (assoc-in [:recents :items] recent-items)
+                                         (assoc-in [:commands :items] command-items)
+                                         (assoc-in [:favorites :items] favorite-items)))))
+    
+
 ;; The search-actions are only loaded when there is no query present. It's like a quick access to filters
 (defmethod load-results :search-actions [group state]
   (let [!input (::input state)
@@ -96,7 +128,8 @@
     (swap! !results assoc-in [group :status] :loading)
     (if (empty? @!input)
       (swap! !results assoc group {:status :success :items default-commands})
-      (->> (vals (cp-handler/get-commands-unique))
+      (->> (cp-handler/top-commands 1000)
+           (map #(assoc % :t (cp/translate t %)))
            (filter #(string/includes? (string/lower-case (pr-str %)) (string/lower-case @!input)))
            (map #(hash-map :icon "command" 
                            :icon-theme :gray 
@@ -176,15 +209,37 @@
     (p/let [files (search/file-search @!input 99)]
       (js/console.log "load-results/files" (clj->js files)))))
 
+(defmethod load-results :recents [group state]
+  (let [!input (::input state)
+        !results (::results state)
+        recent-searches (mapv (fn [q] {:type :search :data q}) (db/get-key-value :recent/search))
+        recent-pages (mapv (fn [page] {:type :page :data page}) (db/get-key-value :recent/pages))]
+    (js/console.log "recents" (clj->js recent-searches) (clj->js recent-pages))
+    (swap! !results assoc-in [group :status] :loading)
+    (let [items (->> (concat recent-searches recent-pages)
+                     (filter #(string/includes? (string/lower-case (:data %)) (string/lower-case @!input)))
+                     (map #(hash-map :icon (if (= :page (:type %)) "page" "history")
+                                     :icon-theme :gray 
+                                     ; :header (when-let [page-name])
+                                     :text (:data %)
+                                     :source-recent %)))]
+      (swap! !results assoc group {:status :success :items items}))))
+      
+    ; (swap! !results assoc group {:status :success :items recent-items})))
+
 ;; The default load-results function triggers all the other load-results function
 (defmethod load-results :default [_ state]
   (js/console.log "load-results/default" @(::input state))
-  (load-results :search-actions state)
-  (load-results :commands state)
-  (load-results :blocks state)
-  (load-results :pages state)
-  ; (load-results :whiteboards state)
-  (load-results :files state))
+  (if-not (some-> state ::input deref seq)
+    (load-results :initial state)
+    (do
+      (load-results :search-actions state)
+      (load-results :commands state)
+      (load-results :blocks state)
+      (load-results :pages state)
+      ; (load-results :whiteboards state)
+      (load-results :files state)
+      (load-results :recents state))))
 
 ; (def search [query]
 ;   (load-results :search-actions state))
@@ -263,10 +318,10 @@
                                (js/console.log 
                                  "testing-capping-the-highlighted-item"
                                  (count items)
-                                 (clj->js (drop 5 items)) 
+                                 (clj->js (drop GROUP-LIMIT items)) 
                                  (clj->js highlighted-item)
                                  (.indexOf items highlighted-item))
-                               (when (< 4 (.indexOf items highlighted-item))
+                               (when (< (dec GROUP-LIMIT) (.indexOf items highlighted-item))
                                  (reset! (::highlighted-item state) (nth items 4 nil))))] 
     [:div {:class ""}
      [:div {:class "text-xs py-1.5 px-6 flex justify-between items-center gap-2" 
@@ -280,14 +335,16 @@
          (str "99+")
          (count items))]
       [:div {:class "flex-1"}]
-      (if show-more
-        [:div {:on-click (fn [] (cap-highlighted-item) (toggle-show-more))} "Show less"]
-        [:div {:on-click (fn [] (toggle-show-more))} "Show more"])]
+      (cond 
+        (<= (count items) GROUP-LIMIT) [:div]
+        show-more [:div {:class "hover:cursor-pointer" :on-click (fn [] (cap-highlighted-item) (toggle-show-more))} "Show less"]
+        :else [:div {:class "hover:cursor-pointer" :on-click (fn [] (toggle-show-more))} "Show more"])]
 
      [:div {:class ""}
       (for [item visible-items
             :let [highlighted? (= item highlighted-item)]]
        (shui/list-item (assoc item 
+                              :query @(::input state)
                               :highlighted highlighted?
                               ;; for some reason, the highlight effect does not always trigger on a 
                               ;; boolean value change so manually pass in the dep
@@ -298,7 +355,7 @@
                                               (handle-action action state item))
                                             (reset! (::highlighted-item state) item)))
                               :on-highlight (fn [ref]  
-                                              (when (and ref (.-current ref))
+                                              (when (and ref (.-current ref) (< 2 (:item-index item)))
                                                 (.. ref -current (scrollIntoView #js {:block "center" 
                                                                                       :inline "nearest"
                                                                                       :behavior "smooth"}))) 
@@ -307,7 +364,8 @@
                                                 :commands       (reset! (::actions state) [:close :trigger])
                                                 :pages          (reset! (::actions state) [:close :copy-page-ref :open-page-right :open-page])
                                                 :blocks         (reset! (::actions state) [:close :copy-block-ref :open-block-right :open-block])
-                                                nil)))))]]))
+                                                nil)))
+                       (make-shui-context)))]]))
 
 (defn move-highlight [state n]
   (let [items (mapcat last (state->results-ordered state))
@@ -317,10 +375,27 @@
       (reset! (::highlighted-item state) next-highlighted-item)
       (reset! (::highglighted-item state) nil))))
 
+(defn handle-input-change 
+  ([state e] (handle-input-change state e (.. e -target -value)))
+  ([state _ input]
+   (let [!input (::input state)
+         !load-results-throttled (::load-results-throttled state)]
+     ;; update the input value in the UI
+     (reset! !input input) 
+
+     ;; ensure that there is a throttled version of the load-results function
+     (when-not @!load-results-throttled
+       (reset! !load-results-throttled (gfun/throttle load-results 1000)))
+
+     ;; retreive the laod-results function and update all the results
+     (when-let [load-results-throttled @!load-results-throttled]
+       (load-results-throttled :default state)))))
+
 (defonce keydown-handler
   (fn [state e]
     (let [shift? (.-shiftKey e)
           alt? (.-altKey e)]
+      (js/console.log "pressing key" @(::input state) (.-key e) (boolean (seq @(::input state))))
       (reset! (::shift? state) shift?)
       (reset! (::alt? state) alt?)
       (when (#{"ArrowDown" "ArrowUp"} (.-key e))
@@ -334,6 +409,10 @@
                     (handle-action action state @(::highlighted-item state) e))
                   (when-let [action (some #{:open-block :open-page :filter :trigger} @(::actions state))]
                     (handle-action action state @(::highlighted-item state) e)))
+        "Escape" (when (seq @(::input state))
+                   (.preventDefault e)
+                   (.stopPropagation e)
+                   (handle-input-change state nil ""))
         ; "j" (when (.-metaKey e) 
         ;       (if (.-shiftKey e)
         ;         (swap! state update :current-engine prev-engine)
@@ -348,21 +427,11 @@
           alt? (.-altKey e)]
       (reset! (::shift? state) shift?)
       (reset! (::alt? state) alt?))))
-
-(defn handle-input-change [state e]
-  (let [input (.. e -target -value)
-        !input (::input state)
-        !load-results-throttled (::load-results-throttled state)]
-    ;; update the input value in the UI
-    (reset! !input input) 
-
-    ;; ensure that there is a throttled version of the load-results function
-    (when-not @!load-results-throttled
-      (reset! !load-results-throttled (gfun/throttle load-results 1000)))
-
-    ;; retreive the laod-results function and update all the results
-    (when-let [load-results-throttled @!load-results-throttled]
-      (load-results-throttled :all state))))
+      ; (when (= "Escape" (.-key e))
+      ;   (js/console.log "escape intercepted keyup")
+      ;   (.preventDefault e)
+      ;   (.stopPropagation e)
+      ;   (reset! (::input state) nil)))))
 
 (rum/defc page-preview [state highlighted]
   (let [page-name (:source-page highlighted)]
@@ -407,10 +476,14 @@
    [:div {:class "text-xs font-bold px-6"} "Filters"]
    [:div {:class "flex items-center gap-2"}
     [:div {:class "w-4 h-1"}]
-    (when-let [group (:group filter)]
-      [:div {:class "text-xs py-0.5 px-1.5 rounded bg-blue-500/20 hover:bg-blue-500/50 hover:cursor-pointer"
-             :on-click #(swap! (::filter state) dissoc :group)}
-        (print-group-name group)])]])
+    (for [group [:recents :commands :pages :whiteboards :blocks]]
+      (if (= (:group filter) group)
+        [:div {:class "text-xs py-0.5 px-1.5 rounded bg-accent-06 hover:bg-accent-07 hover:cursor-pointer"
+               :on-click #(swap! (::filter state) dissoc :group)}
+          (print-group-name group)]
+        [:div {:class "text-xs py-0.5 px-1.5 rounded bg-gray-06 hover:bg-gray-07 hover:cursor-pointer"
+               :on-click #(swap! (::filter state) assoc :group group)}
+          (print-group-name group)]))]])
 
 (rum/defc input-row 
   [state all-items]
@@ -423,6 +496,9 @@
                        (when (= -1 (.indexOf all-items highlighted-item))
                          (reset! (::highlighted-item state) nil)))
                      [all-items])
+    (rum/use-effect! (fn [] 
+                       (load-results :default state))
+                     [])
     [:div {:class ""
            :style {:background "var(--lx-gray-02)"
                    :border-bottom "1px solid var(--lx-gray-07)"}}
@@ -445,6 +521,7 @@
   (rum/local default-results ::results)
   (rum/local nil ::load-results-throttled)
   (rum/local [:close :filter] ::actions) 
+  (rum/local nil ::scroll-container-ref)
   {:did-mount (fn [state] 
                 (let [next-keydown-handler (partial keydown-handler state)
                       next-keyup-handler (partial keyup-handler state)]
@@ -454,8 +531,8 @@
                   (when-let [prev-keyup-handler @(::keyup-handler state)]
                     (js/window.removeEventListener "keyup" prev-keyup-handler))
                   ;; add new handlers
-                  (js/window.addEventListener "keydown" next-keydown-handler)
-                  (js/window.addEventListener "keyup" next-keyup-handler)
+                  (js/window.addEventListener "keydown" next-keydown-handler true)
+                  (js/window.addEventListener "keyup" next-keyup-handler true)
                   ;; save references to functions for cleanup later
                   (reset! (::keydown-handler state) next-keydown-handler)
                   (reset! (::keyup-handler state) next-keyup-handler))
@@ -470,6 +547,12 @@
                    (reset! (::keydown-handler state) nil)
                    (reset! (::keyup-handler state) nil)
                    state)}
+  {:did-mount (fn [state] 
+                (when-let [ref @(::scroll-container-ref state)]
+                  (js/console.log "scrolling")
+                  (js/setTimeout #(set! (.-scrollTop ref) FILTER-ROW-HEIGHT)))
+                state)}
+                  ; (load-results :initial state)))}
   [state {:keys []}]
   (let [input @(::input state)
         actions @(::actions state)
@@ -483,12 +566,15 @@
         preview? (or (:source-page highlighted-item) (:source-block highlighted-item))
         shift? @(::shift? state) 
         alt? @(::alt? state)]
+    ; (rum/use-effect! #(load-results :initial state) [])
     [:div.cp__cmdk {:class "-m-8 max-w-[90dvw] max-h-[90dvh] w-[60rem] h-[30.7rem] "}
      (input-row state all-items)
-     (when filter (filter-row state filter))
      [:div {:class (str "grid" (if preview? " grid-cols-2" " grid-cols-1"))}
       [:div {:class "pt-1 overflow-y-auto h-96"
+             :id "bendy"
+             :ref #(when % (some-> state ::scroll-container-ref (reset! %))) 
              :style {:background "var(--lx-gray-02)"}}
+       (filter-row state filter)
        (for [[group-name group-key group-items] results-ordered
              :when (not-empty group-items)
              :when (if-not group-filter true (= group-filter group-key))]

+ 1 - 1
src/main/frontend/components/page.css

@@ -16,7 +16,7 @@
 
     > .it {
       display: flex;
-      justify-content: center;
+      justify-content: start;
       padding-top: 5px;
       padding-bottom: 5px;
 

+ 43 - 60
src/main/frontend/components/settings.cljs

@@ -151,13 +151,16 @@
            :height 500}]]])
 
 (defn row-with-button-action
-  [{:keys [left-label action button-label href on-click desc -for stretch]}]
-  [:div.it.sm:grid.sm:grid-cols-3.sm:gap-4.sm:items-center
+  [{:keys [left-label description action button-label href on-click desc -for stretch]}]
+  [:div.it.sm:grid.sm:grid-cols-3.sm:gap-4.sm:items-start
 
    ;; left column
-   [:label.block.text-sm.font-medium.leading-5.opacity-70
-    {:for -for}
-    left-label]
+   [:div.flex.flex-col
+    [:label.block.text-sm.font-medium.leading-5.opacity-70
+     {:for -for}
+     left-label]
+    (when description 
+      [:div.text-xs.text-gray-10 description])]
 
    ;; right column
    [:div.mt-1.sm:mt-0.sm:col-span-2.flex.items-center
@@ -315,68 +318,49 @@
                              :action     pick-theme
                              :desc       (ui/render-keyboard-shortcut (shortcut-helper/gen-shortcut-seq :ui/toggle-theme))})))
 
-(defn theme-row [t dark?]
+(defn accent-color-row [t dark?]
   (let [color-accent (state/sub :ui/radix-color)
-        pick-theme [:div.grid {:style {:grid-template-columns "repeat(17, 1fr)" 
+        pick-theme [:div.grid {:style {:grid-template-columns "repeat(5, 1fr)" 
                                        :gap "0.75rem"
-                                       :overflow-x :scroll 
                                        :width "100%"
-                                       :padding-left "0.25rem"}}
-                    [:div.theme-row--color {:on-click #(state/unset-color-accent!)
-                                            :class (when (nil? color-accent) "selected")}
-                     [:div.theme-row--color-swatch {:style {;; "--background"        "#0F2A35"
-                                                            ;; "--background-hover"  "#163542"
-                                                            ;; "--background-active" "#274E5E"
-                                                            "--background"            "#0369a1"
-                                                            "--background-hover"      "#38bdf8" ;; TODO what is the hover color?
-                                                            "--background-active"      "#0ea5e9"} ;; TODO what is the hover color?
-                                                           :border-right "1px solid rgba(255,255,255,0.4)"}] 
-                     [:div.text-xs {:style {:margin "0 -0.5rem" 
-                                            :opacity 0.5 
-                                            :height "1rem" 
-                                            :padding "0 0.5rem"}}]]
-                    [:div.theme-row--color-separator]
+                                       :max-width "16rem"}}
                     (for [color colors/color-list
-                          :let [gray (get colors/gray-pairing-map color)]]
-                      [:div.theme-row--color {:on-click #(state/set-color-accent! color) 
-                                              :class (when (= color-accent color) "selected")}
-                       [:div.theme-row--color-swatch {:style {"--background"            (str "var(--rx-" (name color) "-07)")
-                                                              "--background-hover"      (str "var(--rx-" (name color) "-10)")
-                                                              "--background-active"     (str "var(--rx-" (name color) "-09) ")}}]])]
-                                                              ; "--border-hover"     (str "var(--rx-" (name color) "-08)")}}]
-        display-theme [:button {:style {:background "var(--lx-accent-03)" 
-                                        :border "1px solid var(--lx-accent-07)"
-                                        :color "var(--lx-accent-11)"}}
-                        (if color-accent (name color-accent) "default")]]
+                          :let [gray (get colors/gray-pairing-map color)
+                                active? (= color color-accent)
+                                default-classes "w-5 h-5 rounded-full flex justify-center items-center border transition ease-in duration-100 hover:cursor-pointer hover:opacity-100"
+                                bg (if active? (str "bg-" (name color) "-09 opacity-100") 
+                                               (str "bg-" (name color) "-09 opacity-50"))
+                                border (if active? (str "border-" (name color) "-07 opacity-100") 
+                                                   (str "border-" (name color) "-06 opacity-50"))]]
+                      [:div.flex.items-center {:style {:height 28}}
+                       [:div {;;:class (string/join " " [default-classes bg border]) 
+                              :class "w-5 h-5 rounded-full flex justify-center items-center transition ease-in duration-100 hover:cursor-pointer hover:opacity-100"
+                              :style {:background-color (colors/variable color :09) 
+                                      :outline-color (colors/variable color (if active? :07 :06))
+                                      :outline-width (if active? "4px" "1px")
+                                      :outline-style :solid
+                                      :opacity (if active? 1 0.5)}
+                              :on-click (fn [e] (state/set-color-accent! color))}
+                        [:div {:class "w-2 h-2 rounded-full transition ease-in duration-100" 
+                               :style {:background-color (str "var(--rx-" (name color) "-07)")
+                                       :opacity (if active? 1 0)}}]]])
+                      ; (shui/button {:text (name color) 
+                      ;               :color color 
+                      ;               :muted (not= color-accent color)}
+                      ;              (make-shui-context nil nil)))
+                    [:div.col-span-5
+                     (shui/button {:text "Use custom theme"
+                                   :theme :gray
+                                   :on-click (fn [e] (state/unset-color-accent!))}
+                                  (make-shui-context nil nil))]]] 
+                                  
     [:<>
-     (row-with-button-action {:left-label "Theme color"
+     (row-with-button-action {:left-label "Accent color"
+                              :description "Choosing an accent color will override any theme you have selected. To use a custom theme, click the button below."
                               :-for       "toggle_radix_theme"
                               :stretch    true
                               :action     pick-theme})])) 
 
-(defn theme-gradient-row [t dark? color-accent]
-  (let [color-gradient (state/sub :ui/radix-gradient)
-        pick-gradient [:div {:class "grid grid-cols-7 gap-2 overflow-x-auto"}
-                       [:div {:class (cond-> "theme-gradient-row--gradient-swatch" 
-                                       (= 1 color-gradient) (str " selected"))
-                              :style {"--background" (str "var(--rx-" (name color-accent) "-07)")
-                                      "--background-hover" (str "var(--rx-" (name color-accent) "-08)") 
-                                      "--background-active" (str "var(--rx-" (name color-accent) "-09)")}
-                              :on-click #(state/unset-color-gradient!)}]
-                       (for [n (range 2 8)
-                             :let [active? (= n color-gradient)]] 
-                        [:div {:class (cond-> "bg-white theme-gradient-row--gradient-swatch" 
-                                        active? (str " selected"))
-                               :key n 
-                               :style {"--background" (colors/linear-gradient color-accent :07 n)
-                                       "--background-hover" (colors/linear-gradient color-accent :08 n) 
-                                       "--background-active" (colors/linear-gradient color-accent :09 n)}
-                               :on-click #(state/set-color-gradient! n)}])]]
-   (row-with-button-action {:left-label "Theme gradient"
-                            :stretch true 
-                            :action pick-gradient})))
-                             
-
 (defn file-format-row [t preferred-format]
   [:div.it.sm:grid.sm:grid-cols-3.sm:gap-4.sm:items-start
    [:label.block.text-sm.font-medium.leading-5.opacity-70
@@ -715,8 +699,7 @@
      (language-row t preferred-language)
      (theme-modes-row t switch-theme system-theme? dark?)
      (when (and (util/electron?) (not util/mac?)) (native-titlebar-row t))
-     (when show-radix-themes? (theme-row t dark?))
-     (when (and show-radix-themes? color-accent) (theme-gradient-row t dark? color-accent))
+     (when show-radix-themes? (accent-color-row t dark?))
      (when (config/global-config-enabled?) (edit-global-config-edn))
      (when current-repo (edit-config-edn))
      (when current-repo (edit-custom-css))

+ 26 - 107
src/main/frontend/components/settings.css

@@ -1,5 +1,7 @@
 .cp__settings {
-  &-main {
+  &-inner {
+    @apply flex flex-col md:flex-row;
+
     > header {
       padding: 10px;
       padding-top: 0;
@@ -77,47 +79,10 @@
     }
 
     .settings-menu-link {
-      @apply px-2 py-1.5 select-none; 
-      color: or(--lx-gray-12, --ls-primary-text-color);
+      @apply px-2 py-1.5 select-none;
+      color: var(--ls-primary-text-color);
     }
 
-  }
-
-  &-inner {
-    @apply flex flex-col md:flex-row;
-
-    > aside {
-
-      ul {
-
-        > li {
-
-          > a {
-
-            > i {
-              overflow: hidden;
-              opacity: .9;
-            }
-
-            > strong {
-              font-size: 14px;
-              font-weight: normal;
-              padding-left: 5px;
-              margin-top: 2px;
-              opacity: .9;
-            }
-          }
-
-          &.active {
-            background-color: or(--lx-gray-06, --ls-quaternary-background-color);
-
-            i {
-              opacity: 1;
-            }
-          }
-        }
-      }
-    }
 
     &.no-aside {
       > article {
@@ -137,9 +102,11 @@
 
         margin-bottom: 0;
         padding-bottom: 12px;
-        align-items: center;
+        align-items: start;
 
         label {
+          height: 28px;
+          line-height: 28px;
           display: flex;
           align-items: center;
 
@@ -226,7 +193,7 @@
           cursor: inherit;
 
           > i {
-            border-color: or(--lx-accent-11, --ls-link-text-color);
+            border-color: var(--ls-link-text-color);
             border-width: 2px;
           }
         }
@@ -276,7 +243,7 @@
 
     .update-state {
       padding: 6px 10px;
-      background-color: or(--lx-gray-06, --ls-quaternary-background-color);
+      background-color: var(--ls-quaternary-background-color);
       border-radius: 4px;
       margin-top: 10px;
       width: fit-content;
@@ -334,7 +301,6 @@
       pointer-events: none;
     }
   }
-
 }
 
 .cp__assets {
@@ -345,7 +311,7 @@
       @apply m-0 list-none -mx-2;
 
       > li {
-        border-top: 1px solid or(--lx-accent-08, --ls-secondary-border-color);
+        border-top: 1px solid var(--ls-secondary-border-color);
 
         &:hover {
           .ext-label.is-plus {
@@ -362,8 +328,8 @@
     .ext-label {
       @apply rounded px-1.5 opacity-70 cursor-pointer flex items-center select-none active:opacity-50;
 
-      background-color: or(--lx-accent-08, --ls-secondary-border-color);
-      color: or(--lx-gray-11, --ls-secondary-text-color);
+      background-color: var(--ls-secondary-border-color);
+      color: var(--ls-secondary-text-color);
 
       &.is-del {
         i.ti {
@@ -387,8 +353,8 @@
       }
 
       &.is-plus {
-        background-color: or(--lx-gray-03, --ls-primary-background-color);
-        border: 1px solid or(--lx-gray-07, --ls-border-color);
+        background-color: var(--ls-primary-background-color);
+        border: 1px solid var(--ls-border-color);
       }
     }
 
@@ -415,7 +381,7 @@
         z-index: 1;
         width: 100px;
         max-height: 180px;
-        border:1px solid or(--lx-gray-07, --ls-border-color);
+        border: 1px solid var(--ls-border-color);
         border-radius: 4px;
         overflow: auto;
         overflow: overlay;
@@ -454,13 +420,13 @@
   &-alias-ext-input {
     width: 80px !important;
     padding: 1px 4px;
-    border: 2px solid or(--lx-gray-08, --ls-secondary-border-color);
+    border: 2px solid var(--ls-secondary-border-color);
     font-size: 11px;
     border-radius: 4px;
     height: 22px;
 
     &:focus {
-      border-color: var(--lx-gray-07, --ls-border-color);
+      border-color: var(--ls-border-color);
     }
   }
 }
@@ -478,6 +444,14 @@ html.is-native-iphone-without-notch {
       padding-bottom: 0;
     }
   }
+
+  .theme-row--swatch {
+    @apply w-5 h-5 rounded-full flex justify-center items-center;
+  }
+
+  .theme-row--swatch-active {
+    @apply w-5 h-5 rounded-full flex justify-center items-center;
+  }
 }
 
 svg.git {
@@ -489,61 +463,6 @@ svg.cmd {
   margin-left: -1px;
 }
 
-.cp__settings-main .theme-row--color {
-  @apply flex flex-col items-center; 
-  width: 2rem; 
-  padding-top: 1rem;
-}
-
-.cp__settings-main .theme-row--color-separator {
-  @apply relative;
-  width: 1rem;
-}
-
-.cp__settings-main .theme-row--color-separator::before {
-  @apply absolute inset-1/2 h-6 -translate-y-3 -translate-x-px;
-  content: "";
-  width: 2px;
-  background-color: or(--logseq-og-color-theme-separator, --lx-gray-09, --ls-quaternary-background-color);
-}
-
-.cp__settings-main .theme-row--color-swatch {
-  @apply rounded-full;
-  width: 2rem;
-  height: 2rem;
-  background: var(--background);
-  /* border: 4px solid var(--border); */
-  /* border: 3px solid orange; */
-}
-
-.cp__settings-main .theme-row--color-swatch:hover {
-  background: var(--background-hover);
-  border-color: var(--border-hover);
-}
-
-.cp__settings-main .selected .theme-row--color-swatch,
-.cp__settings-main .selected .theme-row--color-swatch:hover {
-  background: var(--background-active);
-  border-color: var(--border-active);
-}
-
-.cp__settings-main .theme-gradient-row--gradient-swatch {
-  @apply rounded-full;
-  width: 2rem;
-  height: 2rem;
-
-  background: var(--background);
-}
-
-.cp__settings-main .theme-gradient-row--gradient-swatch:hover {
-  background: var(--background-hover);
-}
-
-.cp__settings-main .selected.theme-gradient-row--gradient-swatch,
-.cp__settings-main .selected.theme-gradient-row--gradient-swatch:hover {
-  background: var(--background-active);
-}
- 
 body[data-settings-tab=keymap] {
   .cp__settings-inner {
     > article {

+ 3 - 3
src/main/frontend/components/shortcut.css

@@ -179,15 +179,15 @@
 .cp__shortcut-conflicts-list {
   &-wrap {
     > section {
-      @apply bg-gray-3 border-[2px] mb-3 dark:bg-transparent;
+      @apply bg-gray-03 border-[2px] mb-3 dark:bg-transparent;
 
       > ul {
         @apply px-2 pb-2 m-0 list-none;
       }
 
       > h2 {
-        @apply flex items-center p-2 text-red-9 text-sm space-x-1 font-extrabold;
+        @apply flex items-center p-2 text-red-600 text-sm space-x-1 font-extrabold;
       }
     }
   }
-}
+}

+ 1 - 1
src/main/frontend/handler.cljs

@@ -213,7 +213,7 @@
   (state/set-online! js/navigator.onLine)
   (set-network-watcher!)
   (when-let [radix-color (state/get-color-accent)]
-    (colors/set-radix radix-color (state/get-color-gradient)))
+    (colors/set-radix radix-color))
 
   (util/indexeddb-check?
    (fn [_error]

+ 2 - 7
src/main/frontend/modules/shortcut/config.cljs

@@ -528,9 +528,6 @@
    :ui/cycle-color                          {:binding "c c" 
                                              :fn      state/cycle-color!}
 
-   :ui/cycle-gradient                       {:binding "c g" 
-                                             :fn      state/cycle-gradient!}
-
    :ui/toggle-cards                         {:binding "t c"
                                              :fn      ui-handler/toggle-cards!}
 
@@ -559,7 +556,7 @@
        ::dicts/commands dicts/abbreviated-commands}]
   (assert (= (::commands keyboard-commands) (::dicts/commands keyboard-commands))
           (str "Keyboard commands must have an english label"
-               (data/diff (::commands keyboard-commands) (::commands keyboard-commands)))))
+               (data/diff (::commands keyboard-commands) (::dicts/commands keyboard-commands)))))
 
 (defn- resolve-fn
   "Converts a keyword fn to the actual fn. The fn to be resolved needs to be
@@ -727,7 +724,6 @@
            :ui/clear-all-notifications
            :ui/cycle-color
            :ui/cycle-color-off
-           :ui/cycle-gradient
            :ui/goto-plugins
            :ui/install-plugins-from-file
            :ui/select-theme-color
@@ -854,8 +850,7 @@
  :ui/toggle-settings
  :ui/toggle-contents
  :ui/cycle-color-off
- :ui/cycle-color 
- :ui/cycle-gradient]
+ :ui/cycle-color] 
 
 :shortcut.category/whiteboard
 [:editor/new-whiteboard

+ 4 - 4
src/main/frontend/modules/shortcut/data_helper.cljs

@@ -236,15 +236,15 @@
                                                             (and (set? handler-ids) (contains? handler-ids handler-id'))
                                                             (and global? (contains? global-handlers handler-id'))))
                                                     (assoc r id handler-id')
-                                                    r)
-                                                  ) {} refs)]]))]
+                                                    r))
+                                                {} refs)]]))]
 
                      [k' (->> ks-bindings
                               (filterv same-leading-key?)
                               (mapv into-conflict-refs)
                               (remove #(empty? (second (second %1))))
-                              (into {}))]
-                     ))))
+                              (into {}))]))))
+                     
           (remove #(empty? (vals (second %1))))
           (into {})))))
 

+ 24 - 9
src/main/frontend/shui.cljs

@@ -1,10 +1,13 @@
 (ns frontend.shui
   "Glue between frontend code and deps/shui for convenience"
   (:require 
+    [frontend.colors :as colors]
     [frontend.date :refer [int->local-time-2]]
+    [frontend.db :as db]
+    [frontend.db.utils :as db-utils]
+    [frontend.handler.search :as search-handler]
     [frontend.state :as state]
-    [logseq.shui.context :refer [make-context]]
-    [frontend.handler.search :as search-handler]))
+    [logseq.shui.context :refer [make-context]]))
 
 (def default-versions {:logseq.table.version 1})
 
@@ -19,10 +22,22 @@
           (get-in default-versions [version-key])
           1))))
 
-(defn make-shui-context [block-config inline]
-  (make-context {:block-config block-config 
-                 :app-config (state/get-config) 
-                 :inline inline 
-                 :int->local-time-2 int->local-time-2 
-                 :state state/state 
-                 :search search-handler/search}))
+(defn make-shui-context 
+  ([] (make-shui-context nil nil))
+  ([block-config inline]
+   (make-context {:block-config block-config 
+                  :config (state/get-config) 
+                  :inline inline 
+                  :int->local-time-2 int->local-time-2 
+                  :search search-handler/search
+                  ;; We need some variable from the state to carry over 
+                  :state state/state
+                  :get-current-repo state/get-current-repo
+                  :color-accent (state/get-color-accent) 
+                  ;; Pass over ability to look up entities 
+                  :entity db-utils/entity
+                  :get-block-and-children db/get-block-and-children
+                  :get-block-children db/get-block-children
+                  :get-page-blocks-no-cache db/get-page-blocks-no-cache
+                  :get-page db/get-page})))
+  

+ 1 - 38
src/main/frontend/state.cljs

@@ -84,7 +84,6 @@
      :ui/custom-theme                       (or (storage/get :ui/custom-theme) {:light {:mode "light"} :dark {:mode "dark"}})
      :ui/wide-mode?                         (storage/get :ui/wide-mode)
      :ui/radix-color                        (storage/get :ui/radix-color)
-     :ui/radix-gradient                     (storage/get :ui/radix-gradient)
 
      ;; ui/collapsed-blocks is to separate the collapse/expand state from db for:
      ;; 1. right sidebar
@@ -2192,28 +2191,16 @@ Similar to re-frame subscriptions"
 (defn get-color-accent []
   (get @state :ui/radix-color))
 
-(defn get-color-gradient []
-  (get @state :ui/radix-gradient 1))
-
 (defn set-color-accent! [color]
   (swap! state assoc :ui/radix-color color)
   (storage/set :ui/radix-color color)
-  (colors/set-radix color (get-color-gradient)))
-
-(defn set-color-gradient! [steps]
-  (swap! state assoc :ui/radix-gradient steps)
-  (storage/set :ui/radix-gradient steps)
-  (colors/set-radix (get-color-accent) steps))
+  (colors/set-radix color))
 
 (defn unset-color-accent! []
   (swap! state assoc :ui/radix-color nil)
   (storage/remove :ui/radix-color)
   (colors/unset-radix))
 
-(defn unset-color-gradient! []
-  (swap! state assoc :ui/radix-gradient nil)
-  (storage/remove :ui/radix-gradient))
-
 (defn cycle-color! []
   (let [current-color (get-color-accent)
         next-color (->> (cons nil colors/color-list) 
@@ -2223,30 +2210,6 @@ Similar to re-frame subscriptions"
       (set-color-accent! next-color) 
       (unset-color-accent!))))
 
-(defn cycle-gradient! []
-  (let [current-gradient (get-color-gradient)]
-    (case current-gradient  
-      nil (set-color-gradient! 2)
-      6 (unset-color-gradient!)
-      (set-color-gradient! (inc current-gradient)))))
-  
-
-(defn sub-color-gradient-bg-styles [step]
-  (let [color (sub :ui/radix-color)
-        stops (sub :ui/radix-gradient)]
-    {:background-image (colors/linear-gradient color step stops)
-     :background-attachment :fixed 
-     :background-position "0 0"
-     :background-size "100% 100%"}))
-     ; :transform "translate3d(0,0,0) "}))
-
-(defn sub-color-gradient-text-styles [step]
-  (assoc (sub-color-gradient-bg-styles step)
-        :background-clip "text"
-        "-webkit-background-clip" "text"
-        :color :transparent))
-  ; (sub-color-gradient-bg-styles step))
-
 (defn set-page-properties-changed!
   [page-name]
   (when-not (string/blank? page-name)

+ 0 - 1
src/resources/dicts/en.edn

@@ -810,7 +810,6 @@
   :ui/toggle-contents             "Toggle Contents in sidebar"
   :ui/cycle-color-off             "Cycle color off"
   :ui/cycle-color                 "Cycle color"
-  :ui/cycle-gradient              "Cycle gradient"
    ;;  :ui/open-new-window             "Open another window"
   :command/toggle-favorite        "Add to/remove from favorites"
   :editor/open-file-in-default-app "Open file in default app"

+ 142 - 69
tailwind.config.js

@@ -1,6 +1,57 @@
 const colors = require('tailwindcss/colors')
 const radix = require('@radix-ui/colors')
 
+const lx = {
+  'accent-01': 'var(--lx-accent-01)',
+  'accent-02': 'var(--lx-accent-02)',
+  'accent-03': 'var(--lx-accent-03)',
+  'accent-04': 'var(--lx-accent-04)',
+  'accent-05': 'var(--lx-accent-05)',
+  'accent-06': 'var(--lx-accent-06)',
+  'accent-07': 'var(--lx-accent-07)',
+  'accent-08': 'var(--lx-accent-08)',
+  'accent-09': 'var(--lx-accent-09)',
+  'accent-10': 'var(--lx-accent-10)',
+  'accent-11': 'var(--lx-accent-11)',
+  'accent-12': 'var(--lx-accent-12)',
+  'accent-01-alpha': 'var(--lx-accent-01-alpha)',
+  'accent-02-alpha': 'var(--lx-accent-02-alpha)',
+  'accent-03-alpha': 'var(--lx-accent-03-alpha)',
+  'accent-04-alpha': 'var(--lx-accent-04-alpha)',
+  'accent-05-alpha': 'var(--lx-accent-05-alpha)',
+  'accent-06-alpha': 'var(--lx-accent-06-alpha)',
+  'accent-07-alpha': 'var(--lx-accent-07-alpha)',
+  'accent-08-alpha': 'var(--lx-accent-08-alpha)',
+  'accent-09-alpha': 'var(--lx-accent-09-alpha)',
+  'accent-10-alpha': 'var(--lx-accent-10-alpha)',
+  'accent-11-alpha': 'var(--lx-accent-11-alpha)',
+  'accent-12-alpha': 'var(--lx-accent-12-alpha)',
+  'gray-01': 'var(--lx-gray-01)',
+  'gray-02': 'var(--lx-gray-02)',
+  'gray-03': 'var(--lx-gray-03)',
+  'gray-04': 'var(--lx-gray-04)',
+  'gray-05': 'var(--lx-gray-05)',
+  'gray-06': 'var(--lx-gray-06)',
+  'gray-07': 'var(--lx-gray-07)',
+  'gray-08': 'var(--lx-gray-08)',
+  'gray-09': 'var(--lx-gray-09)',
+  'gray-10': 'var(--lx-gray-10)',
+  'gray-11': 'var(--lx-gray-11)',
+  'gray-12': 'var(--lx-gray-12)',
+  'gray-01-alpha': 'var(--lx-gray-01-alpha)',
+  'gray-02-alpha': 'var(--lx-gray-02-alpha)',
+  'gray-03-alpha': 'var(--lx-gray-03-alpha)',
+  'gray-04-alpha': 'var(--lx-gray-04-alpha)',
+  'gray-05-alpha': 'var(--lx-gray-05-alpha)',
+  'gray-06-alpha': 'var(--lx-gray-06-alpha)',
+  'gray-07-alpha': 'var(--lx-gray-07-alpha)',
+  'gray-08-alpha': 'var(--lx-gray-08-alpha)',
+  'gray-09-alpha': 'var(--lx-gray-09-alpha)',
+  'gray-10-alpha': 'var(--lx-gray-10-alpha)',
+  'gray-11-alpha': 'var(--lx-gray-11-alpha)',
+  'gray-12-alpha': 'var(--lx-gray-12-alpha)',
+}
+
 function exposeColorsToCssVars ({ addBase, theme }) {
   function extractColorVars (colorObj, colorGroup = '') {
     return Object.keys(colorObj).reduce((vars, colorKey) => {
@@ -94,6 +145,18 @@ module.exports = {
   ],
   theme: {
     extend: {
+      backgroundColor: {
+        ...lx,
+      },
+      borderColor: {
+        ...lx,
+      },
+      outlineColor: {
+        ...lx,
+      },
+      textColor: {
+        ...lx,
+      },
       backgroundImage: {
         'gradient-conic': 'conic-gradient(var(--tw-gradient-stops))',
         'gradient-conic-bounce': 'conic-gradient(var(--tw-gradient-from), var(--tw-gradient-via), var(--tw-gradient-to), var(--tw-gradient-via), var(--tw-gradient-from))',
@@ -123,83 +186,93 @@ module.exports = {
     },
     colors: {
       // Tailwind colors
+      gray: colors.gray,
+      red: colors.red,
+      green: colors.green,
+      blue: colors.blue,
       black: colors.black,
-      current: 'currentColor',
+      orange: colors.orange,
+      indigo: colors.indigo,
       rose: colors.rose,
+      purple: colors.purple,
+      pink: colors.pink,
+      yellow: colors.yellow,
+
+      current: 'currentColor',
       transparent: 'transparent',
       white: colors.white,
 
       // Radix colors
-      amber: buildColor("amber"),
-      blue: buildColor("blue"),
-      bronze: buildColor("bronze"),
-      brown: buildColor("brown"),
-      crimson: buildColor("crimson"),
-      cyan: buildColor("cyan"),
-      gold: buildColor("gold"),
-      grass: buildColor("grass"),
-      green: buildColor("green"),
-      lime: buildColor("lime"),
-      mauve: buildColor("mauve"),
-      mint: buildColor("mint"),
-      olive: buildColor("olive"),
-      orange: buildColor("orange"),
-      pink: buildColor("pink"),
-      plum: buildColor("plum"),
-      purple: buildColor("purple"),
-      red: buildColor("red"),
-      sage: buildColor("sage"),
-      sand: buildColor("sand"),
-      sky: buildColor("sky"),
-      slate: buildColor("slate"),
-      teal: buildColor("teal"),
-      tomato: buildColor("tomato"),
-      violet: buildColor("violet"),
+      // amber: buildColor("amber"),
+      // blue: buildColor("blue"),
+      // bronze: buildColor("bronze"),
+      // brown: buildColor("brown"),
+      // crimson: buildColor("crimson"),
+      // cyan: buildColor("cyan"),
+      // gold: buildColor("gold"),
+      // grass: buildColor("grass"),
+      // green: buildColor("green"),
+      // lime: buildColor("lime"),
+      // mauve: buildColor("mauve"),
+      // mint: buildColor("mint"),
+      // olive: buildColor("olive"),
+      // orange: buildColor("orange"),
+      // pink: buildColor("pink"),
+      // plum: buildColor("plum"),
+      // purple: buildColor("purple"),
+      // red: buildColor("red"),
+      // sage: buildColor("sage"),
+      // sand: buildColor("sand"),
+      // sky: buildColor("sky"),
+      // slate: buildColor("slate"),
+      // teal: buildColor("teal"),
+      // tomato: buildColor("tomato"),
+      // violet: buildColor("violet"),
         
       // Custom colors
-      gray: buildColor("gray", colors.neutral),
-      yellow: buildColor("yellow", colors.amber),
-      indigo: buildColor("indigo", {
-        50: '#f0f9ff',
-        100: '#e0f2fe',
-        200: '#bae6fd',
-        300: '#7dd3fc',
-        400: '#38bdf8',
-        500: '#0ea5e9',
-        600: '#0284c7',
-        700: '#005b8a',
-        800: '#075985',
-        900: '#0c4a6e',
-      }),
-
-      tomatodark: buildColor("tomatoDark"),
-      reddark: buildColor("redDark"),
-      crimsondark: buildColor("crimsonDark"),
-      pinkdark: buildColor("pinkDark"),
-      plumdark: buildColor("plumDark"),
-      purpledark: buildColor("purpleDark"),
-      violetdark: buildColor("violetDark"),
-      skydark: buildColor("skyDark"),
-      indigodark: buildColor("indigoDark"),
-      bluedark: buildColor("blueDark"),
-      cyandark: buildColor("cyanDark"),
-      mintdark: buildColor("mintDark"),
-      tealdark: buildColor("tealDark"),
-      greendark: buildColor("greenDark"),
-      limedark: buildColor("limeDark"),
-      grassdark: buildColor("grassDark"),
-      yellowdark: buildColor("yellowDark"),
-      amberdark: buildColor("amberDark"),
-      orangedark: buildColor("orangeDark"),
-      browndark: buildColor("brownDark"),
-      graydark: buildColor("grayDark"),
-      mauvedark: buildColor("mauveDark"),
-      slatedark: buildColor("slateDark"),
-      sagedark: buildColor("sageDark"),
-      olivedark: buildColor("oliveDark"),
-      sanddark: buildColor("sandDark"),
-      golddark: buildColor("goldDark"),
-      bronzedark: buildColor("bronzeDark"),
+      // gray: buildColor("gray", colors.neutral),
+      // yellow: buildColor("yellow", colors.amber),
+      // indigo: buildColor("indigo", {
+      //   50: '#f0f9ff',
+      //   100: '#e0f2fe',
+      //   200: '#bae6fd',
+      //   300: '#7dd3fc',
+      //   400: '#38bdf8',
+      //   500: '#0ea5e9',
+      //   600: '#0284c7',
+      //   700: '#005b8a',
+      //   800: '#075985',
+      //   900: '#0c4a6e',
+      // }),
+
+      // tomatodark: buildColor("tomatoDark"),
+      // reddark: buildColor("redDark"),
+      // crimsondark: buildColor("crimsonDark"),
+      // pinkdark: buildColor("pinkDark"),
+      // plumdark: buildColor("plumDark"),
+      // purpledark: buildColor("purpleDark"),
+      // violetdark: buildColor("violetDark"),
+      // skydark: buildColor("skyDark"),
+      // indigodark: buildColor("indigoDark"),
+      // bluedark: buildColor("blueDark"),
+      // cyandark: buildColor("cyanDark"),
+      // mintdark: buildColor("mintDark"),
+      // tealdark: buildColor("tealDark"),
+      // greendark: buildColor("greenDark"),
+      // limedark: buildColor("limeDark"),
+      // grassdark: buildColor("grassDark"),
+      // yellowdark: buildColor("yellowDark"),
+      // amberdark: buildColor("amberDark"),
+      // orangedark: buildColor("orangeDark"),
+      // browndark: buildColor("brownDark"),
+      // graydark: buildColor("grayDark"),
+      // mauvedark: buildColor("mauveDark"),
+      // slatedark: buildColor("slateDark"),
+      // sagedark: buildColor("sageDark"),
+      // olivedark: buildColor("oliveDark"),
+      // sanddark: buildColor("sandDark"),
+      // golddark: buildColor("goldDark"),
+      // bronzedark: buildColor("bronzeDark"),
     }
   }
 }

Некоторые файлы не были показаны из-за большого количества измененных файлов