enhance(capacitor): blocks container for journals list

This commit is contained in:
charlie
2025-05-17 15:36:04 +08:00
parent c98603b14d
commit 1bc07f1010
4 changed files with 126 additions and 68 deletions

View File

@@ -12,6 +12,7 @@
[capacitor.state :as state]
[capacitor.handler :as handler]
[capacitor.pages.utils :as pages-util]
[capacitor.pages.blocks :as blocks]
[capacitor.components.ui :as ui]
[frontend.db.conn :as db-conn]
[frontend.db-mixins :as db-mixins]
@@ -85,37 +86,15 @@
[:ul
(for [journal-id journals]
(let [journal (db-util/entity journal-id)]
[::li.font-mono.flex.items-center.py-1.active:opacity-50.active:underline.whitespace-nowrap
[:li.flex.py-1.active:opacity-50.flex-col.w-full
{:on-click #(pages-util/nav-to-block! journal {:reload-pages! (fn [] ())})}
(ionic/tabler-icon "calendar")
[:span.pl-1 (:block/title journal)]]))]))
(rum/defc create-page-input
[{:keys [close! reload-pages!]}]
(ionic/ion-alert
{:is-open true
:header "Create new page"
:onWillDismiss (fn [^js e]
(let [^js detail (.-detail e)]
(when-let [val (and (= "confirm" (.-role detail))
(aget (.-values (.-data detail)) 0))]
(-> (handler/<create-page! val)
(p/finally reload-pages!)))
(close!)))
:onDidPresent (fn [^js e]
(let [^js target (.-target e)]
(when-let [input (.querySelector target "input")]
(js/setTimeout #(.focus input)))))
:buttons [#js {:text "Cancel"
:role "cancel"}
#js {:text "Confirm"
:role "confirm"}]
:inputs [#js {:placeholder "page name"
:auto-focus true}]}))
[:h1.text-2xl.font-semibold.opacity-90 (:block/title journal)]
;; blocks editor
(blocks/page-blocks journal)
]))]))
(rum/defc home []
(let [[reload set-reload!] (rum/use-state 0)
[page-input-open? set-page-input-open?] (rum/use-state false)]
(let [[reload set-reload!] (rum/use-state 0)]
(ionic/ion-content
(ionic/ion-refresher
@@ -130,19 +109,8 @@
1000))}
(ionic/ion-refresher-content))
(when page-input-open?
(create-page-input {:close! #(set-page-input-open? false)
:reload-pages! #(set-reload! (inc reload))}))
[:div.pt-6.px-6
[:div.flex.justify-between.items-center.mt-4
[:h1.text-3xl.font-mono.font-bold.py-2 "Journals"]
[:flex.gap-1]]
[:div.pt-4.px-4
(journals-list)
;(when journal-calendar-open?
; (journals-calendar-modal {:close! #(set-journal-calendar-open? false)}))
]
;; tabbar
@@ -231,7 +199,7 @@
[:> (.-IonApp ionic/ionic-react)
[:<>
(ionic/ion-nav {:ref nav-ref
:root root ;;settings/page
:root root ;;settings/page
:animated true
:swipeGesture false})

View File

@@ -1,5 +1,6 @@
(ns capacitor.pages.blocks
(:require [capacitor.state :as state]
[frontend.db.model :as db-model]
[promesa.core :as p]
[rum.core :as rum]
[frontend.db.async :as db-async]
@@ -79,12 +80,66 @@
(some-> @state/*nav-root
(.push #(edit-block-modal block opts))))
(rum/defc block-editor
[])
(rum/defc block-content
[])
(rum/defc block-item
[block]
(when block
[:li.text-xl.pr-1 {:on-click #()}
[:span (:block/title block)]]))
(rum/defc blocks-list
[blocks]
(when (seq blocks)
[:ul.app-blocks-list
(for [block blocks]
(block-item block))]))
(rum/defc blocks-container
[root]
[:div.app-blocks-container
(let [block? (not (db-model/page? root))
children (:block/_parent root)
blocks (if block? [root] (db-model/sort-by-order children))]
;(js/console.log "==>> blocks:" (:block/title root) (count blocks))
(blocks-list blocks))])
(rum/defc page-blocks
[page-name-or-entity]
(let [[page set-page!] (rum/use-state
(if (:db/id page-name-or-entity) page-name-or-entity
(db-model/get-page page-name-or-entity)))
[p] (state/use-app-state [:last-modified-page-uuid (:block/uuid page)])
[_loading? set-loading!] (rum/use-state false)]
(rum/use-effect!
;; sync page blocks
(fn []
(-> (db-async/<get-block (fstate/get-current-repo) (:block/uuid page))
(p/then (fn [page]
(set-page! (db-utils/entity (:db/id page)))))
(p/finally #()))
#())
[p])
(when page
[:div.app-page-blocks.mb-4
(blocks-container page)])))
(rum/defc page [block {:keys [reload-pages!]}]
(let [[^js nav] (state/use-nav-root)
[page set-page!] (rum/use-state (db-utils/entity (:db/id block)))
title (or (:block/title block) (:block.temp/cached-title block))
[loading? set-loading!] (rum/use-state true)
rerender! #(set-page! (db-utils/entity (:db/id block)))]
rerender! (fn []
(set-page! (db-utils/entity (:db/id block)))
(swap! state/*state assoc
:last-modified-page-uuid
{(:block/uuid block) (js/Date.now)}))]
(rum/use-effect!
;; sync page blocks

View File

@@ -1,17 +1,40 @@
(ns capacitor.pages.settings
(:require [capacitor.handler :as handler]
[capacitor.pages.utils :as pages-util]
[promesa.core :as p]
[rum.core :as rum]
[capacitor.state :as state]
[capacitor.ionic :as ionic]))
(rum/defc create-page-input
[{:keys [close! reload-pages!]}]
(ionic/ion-alert
{:is-open true
:header "Create new page"
:onWillDismiss (fn [^js e]
(let [^js detail (.-detail e)]
(when-let [val (and (= "confirm" (.-role detail))
(aget (.-values (.-data detail)) 0))]
(-> (handler/<create-page! val)
(p/finally reload-pages!)))
(close!)))
:onDidPresent (fn [^js e]
(let [^js target (.-target e)]
(when-let [input (.querySelector target "input")]
(js/setTimeout #(.focus input)))))
:buttons [#js {:text "Cancel"
:role "cancel"}
#js {:text "Confirm"
:role "confirm"}]
:inputs [#js {:placeholder "page name"
:auto-focus true}]}))
(rum/defc all-pages
[]
(let [[all-pages set-all-pages!] (rum/use-state [])
[filtered-pages set-filtered-pages!] (rum/use-state [])
[reload set-reload!] (rum/use-state 0)
[_page-input-open? set-page-input-open?] (rum/use-state false)
]
[page-input-open? set-page-input-open?] (rum/use-state false)]
(rum/use-effect!
(fn []
@@ -29,33 +52,37 @@
#())
[all-pages])
[:div.flex.flex-col
[:div.flex.justify-between.items-center.pt-4
[:h1.text-3xl.font-mono.font-bold.py-2
"All pages"
[:small.text-xs.pl-2.opacity-50 (count filtered-pages)]]
[:div.flex.gap-1
(ionic/ion-button {:size "small" :fill "clear" :on-click #(set-page-input-open? true)}
[:span {:slot "icon-only"} (ionic/tabler-icon "file-plus" {:size 22})])
;(ionic/ion-button {:size "small" :fill "clear" :on-click #(set-reload! (inc reload))}
; [:span {:slot "icon-only"} (ionic/tabler-icon "refresh")])
]]
[:<>
(when page-input-open?
(create-page-input {:close! #(set-page-input-open? false)
:reload-pages! #(set-reload! (inc reload))}))
[:div.flex.flex-col
[:div.flex.justify-between.items-center.pt-4
[:h1.text-3xl.font-mono.font-bold.py-2
"All pages"
[:small.text-xs.pl-2.opacity-50 (count filtered-pages)]]
[:ul.mb-24.pt-2
(for [page filtered-pages]
(let [ident (some-> (:block/tags page) first :db/ident)]
[:li.font-mono.flex.items-center.py-1.active:opacity-50.active:underline.whitespace-nowrap
{:on-click #(pages-util/nav-to-block! page {:reload-pages! (fn [] (set-reload! (inc reload)))})}
(case ident
:logseq.class/Property (ionic/tabler-icon "letter-t")
:logseq.class/Page (ionic/tabler-icon "file")
:logseq.class/Journal (ionic/tabler-icon "calendar")
(ionic/tabler-icon "hash"))
[:span.pl-1 (:block/title page)]
[:code.opacity-30.scale-75 (.toLocaleDateString (js/Date. (:block/created-at page)))]]))]
[:div.flex.gap-1
(ionic/ion-button {:size "small" :fill "clear" :on-click #(set-page-input-open? true)}
[:span {:slot "icon-only"} (ionic/tabler-icon "file-plus" {:size 22})])
;(ionic/ion-button {:size "small" :fill "clear" :on-click #(set-reload! (inc reload))}
; [:span {:slot "icon-only"} (ionic/tabler-icon "refresh")])
]]
]))
[:ul.mb-24.pt-2
(for [page filtered-pages]
(let [ident (some-> (:block/tags page) first :db/ident)]
[:li.font-mono.flex.items-center.py-1.active:opacity-50.active:underline.whitespace-nowrap
{:on-click #(pages-util/nav-to-block! page {:reload-pages! (fn [] (set-reload! (inc reload)))})}
(case ident
:logseq.class/Property (ionic/tabler-icon "letter-t")
:logseq.class/Page (ionic/tabler-icon "file")
:logseq.class/Journal (ionic/tabler-icon "calendar")
(ionic/tabler-icon "hash"))
[:span.pl-1 (:block/title page)]
[:code.opacity-30.scale-75 (.toLocaleDateString (js/Date. (:block/created-at page)))]]))]
]]))
(rum/defc page
[]

View File

@@ -2,5 +2,13 @@
(:require [frontend.rum :as r]))
(defonce *nav-root (atom nil))
(defonce *state
(atom {:version 0
:last-modified-page-uuid nil}))
(defn use-nav-root [] (r/use-atom *nav-root))
(defn use-app-state
([] (r/use-atom *state))
([ks] (r/use-atom-in *state ks)))