| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291 |
- (ns frontend.components.right-sidebar
- (:require [rum.core :as rum]
- [frontend.ui :as ui]
- [frontend.components.svg :as svg]
- [frontend.components.page :as page]
- [frontend.components.block :as block]
- [frontend.extensions.graph-2d :as graph-2d]
- [frontend.components.onboarding :as onboarding]
- [frontend.handler.route :as route-handler]
- [frontend.handler.page :as page-handler]
- [frontend.handler.graph :as graph-handler]
- [frontend.state :as state]
- [frontend.db :as db]
- [frontend.db.model :as db-model]
- [frontend.util :as util]
- [frontend.date :as date]
- [medley.core :as medley]
- [clojure.string :as string]
- [frontend.extensions.slide :as slide]
- [cljs-bean.core :as bean]
- [goog.object :as gobj]
- [frontend.graph :as graph]
- [frontend.context.i18n :as i18n]
- [reitit.frontend.easy :as rfe]
- [frontend.db-mixins :as db-mixins]
- [frontend.config :as config]))
- (rum/defc block-cp < rum/reactive
- [repo idx block]
- (let [id (:block/uuid block)]
- (page/page {:parameters {:path {:name (str id)}}
- :sidebar? true
- :sidebar/idx idx
- :repo repo})))
- (rum/defc page-cp < rum/reactive
- [repo page-name]
- (page/page {:parameters {:path {:name page-name}}
- :sidebar? true
- :repo repo}))
- (rum/defc page-graph < db-mixins/query
- [page]
- (let [theme (:ui/theme @state/state)
- dark? (= theme "dark")
- graph (if (util/uuid-string? page)
- (graph-handler/build-block-graph (uuid page) theme)
- (graph-handler/build-page-graph page theme))]
- (when (seq (:nodes graph))
- [:div.sidebar-item.flex-col.flex-1
- (graph-2d/graph
- (graph/build-graph-opts
- graph dark? false
- {:width 600
- :height 600}))])))
- (defn recent-pages
- []
- (let [pages (->> (db/get-key-value :recent/pages)
- (remove #(= (string/lower-case %) "contents")))]
- [:div.recent-pages.text-sm.flex-col.flex.ml-3.mt-2
- (if (seq pages)
- (for [page pages]
- [:a.mb-1 {:key (str "recent-page-" page)
- :href (rfe/href :page {:name page})
- :on-click (fn [e]
- (when (gobj/get e "shiftKey")
- (when-let [page (db/pull [:block/name (string/lower-case page)])]
- (state/sidebar-add-block!
- (state/get-current-repo)
- (:db/id page)
- :page
- {:page page}))
- (.preventDefault e)))}
- page]))]))
- (rum/defc contents < rum/reactive db-mixins/query
- []
- [:div.contents.flex-col.flex.ml-3
- (when-let [contents (db/entity [:block/name "contents"])]
- (page/contents-page contents))])
- (defn build-sidebar-item
- [repo idx db-id block-type block-data t]
- (case block-type
- :contents
- [[:a {:on-click (fn [e]
- (util/stop e)
- (if-not (db/entity [:block/name "contents"])
- (page-handler/create! "contents")
- (route-handler/redirect! {:to :page
- :path-params {:name "contents"}})))}
- (t :right-side-bar/contents)]
- (contents)]
- :recent
- [(t :right-side-bar/recent) (recent-pages)]
- :help
- [(t :right-side-bar/help) (onboarding/help)]
- :page-graph
- [(str (t :right-side-bar/graph-ref) (db-model/get-page-original-name block-data))
- (page-graph block-data)]
- :block-ref
- (when-let [block (db/entity repo [:block/uuid (:block/uuid (:block block-data))])]
- [(t :right-side-bar/block-ref)
- (let [block (:block block-data)
- block-id (:block/uuid block)
- format (:block/format block)]
- [[:div.ml-2.mt-1
- (block/block-parents {:id "block-parent"
- :block? true} repo block-id format)]
- [:div.ml-2
- (block-cp repo idx block)]])])
- :block
- (when-let [block (db/entity repo [:block/uuid (:block/uuid block-data)])]
- (let [block-id (:block/uuid block-data)
- format (:block/format block-data)]
- [(block/block-parents {:id "block-parent"
- :block? true} repo block-id format)
- [:div.ml-2
- (block-cp repo idx block-data)]]))
- :page
- (let [page-name (:block/name block-data)]
- [[:a {:href (rfe/href :page {:name page-name})
- :on-click (fn [e]
- (when (gobj/get e "shiftKey")
- (.preventDefault e)))}
- (db-model/get-page-original-name page-name)]
- [:div.ml-2
- (page-cp repo page-name)]])
- :page-presentation
- (let [page-name (get-in block-data [:page :block/name])
- journal? (:journal? block-data)
- blocks (db/get-page-blocks repo page-name)
- blocks (if journal?
- (rest blocks)
- blocks)
- sections (block/build-slide-sections blocks {:id "slide-reveal-js"
- :start-level 2
- :slide? true
- :sidebar? true
- :page-name page-name})]
- [[:a {:href (rfe/href :page {:name page-name})}
- (db-model/get-page-original-name page-name)]
- [:div.ml-2.slide.mt-2
- (slide/slide sections)]])
- ["" [:span]]))
- (defn close
- ([on-close]
- (close nil on-close))
- ([class on-close]
- [:a.close.opacity-50.hover:opacity-100.flex.items-center
- (cond-> {:on-click on-close}
- class
- (assoc :class class))
- svg/close]))
- (rum/defc sidebar-item < rum/reactive
- [repo idx db-id block-type block-data t]
- (let [item
- (if (= :page block-type)
- (let [page (db/query-entity-in-component db-id)]
- (when (seq page)
- (build-sidebar-item repo idx db-id block-type page t)))
- (build-sidebar-item repo idx db-id block-type block-data t))]
- (when item
- (let [collapse? (state/sub [:ui/sidebar-collapsed-blocks db-id])]
- [:div.sidebar-item.content.color-level
- (let [[title component] item]
- [:div.flex.flex-col
- [:div.flex.flex-row.justify-between
- [:div.flex.flex-row.justify-center
- [:a.opacity-50.hover:opacity-100.flex.items-center.pr-1
- {:on-click #(state/sidebar-block-toggle-collapse! db-id)}
- (if collapse?
- (svg/caret-right)
- (svg/caret-down))]
- [:div.ml-1
- title]]
- (close #(state/sidebar-remove-block! idx))]
- [:div {:class (if collapse? "hidden" "initial")}
- component]])]))))
- (defn- get-page
- [match]
- (let [route-name (get-in match [:data :name])
- page (case route-name
- :page
- (get-in match [:path-params :name])
- :file
- (get-in match [:path-params :path])
- (date/journal-name))]
- (if page
- (string/lower-case page))))
- (defn get-current-page
- []
- (let [match (:route-match @state/state)
- theme (:ui/theme @state/state)]
- (get-page match)))
- (rum/defc sidebar-resizer
- []
- (let [el-ref (rum/use-ref nil)]
- (rum/use-effect!
- (fn []
- (when-let [el (and (fn? js/window.interact) (rum/deref el-ref))]
- (-> (js/interact el)
- (.draggable
- (bean/->js
- {:listeners
- {:move
- (fn [^js/MouseEvent e]
- (let [width js/document.documentElement.clientWidth
- offset (.-left (.-rect e))
- to-val (- 1 (.toFixed (/ offset width) 6))
- to-val (cond
- (< to-val 0.2) 0.2
- (> to-val 0.7) 0.7
- :else to-val)]
- (.setProperty (.-style js/document.documentElement)
- "--ls-right-sidebar-width"
- (str (* to-val 100) "%"))))}}))
- (.styleCursor false)
- (.on "dragstart" #(.. js/document.documentElement -classList (add "is-resizing-buf")))
- (.on "dragend" #(.. js/document.documentElement -classList (remove "is-resizing-buf")))))
- #())
- [])
- [:span.resizer {:ref el-ref}]))
- (rum/defcs sidebar < rum/reactive
- [state]
- (let [blocks (state/sub :sidebar/blocks)
- blocks (if (empty? blocks)
- [[(state/get-current-repo) "contents" :contents nil]]
- blocks)
- sidebar-open? (state/sub :ui/sidebar-open?)
- repo (state/sub :git/current-repo)
- match (state/sub :route-match)
- theme (state/sub :ui/theme)
- t (i18n/use-tongue)]
- (rum/with-context [[t] i18n/*tongue-context*]
- [:div#right-sidebar.cp__right-sidebar
- {:class (if sidebar-open? "is-open")}
- (if sidebar-open?
- [:div.cp__right-sidebar-inner
- (sidebar-resizer)
- [:div.flex.flex-row.justify-between.items-center
- [:div.cp__right-sidebar-settings.hide-scrollbar {:key "right-sidebar-settings"}
- [:div.ml-4.text-sm
- [:a.cp__right-sidebar-settings-btn {:on-click (fn [e]
- (state/sidebar-add-block! repo "contents" :contents nil))}
- (t :right-side-bar/contents)]]
- [:div.ml-4.text-sm
- [:a.cp__right-sidebar-settings-btn {:on-click (fn [_e]
- (state/sidebar-add-block! repo "recent" :recent nil))}
- (t :right-side-bar/recent)]]
- [:div.ml-4.text-sm
- [:a.cp__right-sidebar-settings-btn {:on-click (fn []
- (when-let [page (get-current-page)]
- (state/sidebar-add-block!
- repo
- (str "page-graph-" page)
- :page-graph
- page)))}
- (t :right-side-bar/page)]]
- [:div.ml-4.text-sm
- [:a.cp__right-sidebar-settings-btn {:on-click (fn [_e]
- (state/sidebar-add-block! repo "help" :help nil))}
- (t :right-side-bar/help)]]]
- [:a.close-arrow.opacity-50.hover:opacity-100 {:on-click state/toggle-sidebar-open?!}
- (svg/big-arrow-right)]]
- (for [[idx [repo db-id block-type block-data]] (medley/indexed blocks)]
- (rum/with-key
- (sidebar-item repo idx db-id block-type block-data t)
- (str "sidebar-block-" idx)))])])))
|