Browse Source

enhance: left/right arrow to navigate between code and text blocks

Tienson Qin 1 year ago
parent
commit
5aaa3c111d

+ 5 - 4
src/main/frontend/components/block.cljs

@@ -2760,7 +2760,8 @@
                      (count (:block/_refs block))
                      (rum/react *refs-count))
         table? (:table? config)
-        type-block-editor? (contains? #{:code} (:logseq.property.node/display-type block))]
+        type-block-editor? (contains? #{:code} (:logseq.property.node/display-type block))
+        config (assoc config :block-parent-id block-id)]
     [:div.block-content-or-editor-wrap
      {:class (when (:page-title? config) "ls-page-title-container")
       :data-node-type (some-> (:logseq.property.node/display-type block) name)}
@@ -4053,7 +4054,7 @@
      (fn []
        (case (:logseq.property.node/display-type editing-block)
          :code
-         (let [_cursor-pos (some-> (:editor/cursor-range @state/state) (deref) (count))
+         (let [cursor-pos (some-> (:editor/cursor-range @state/state) (deref) (count))
                direction (:block.editing/direction editing-block)
                pos (:block.editing/pos editing-block)
                target (js/document.querySelector
@@ -4064,10 +4065,10 @@
                              (case pos
                                :max (.lastLine cm)
                                0))]
-                ;; move to friendly cursor
+               ;; move to friendly cursor
                (doto cm
                  (.focus)
-                 (.setCursor to-line (or _cursor-pos 0))))))
+                 (.setCursor to-line (or cursor-pos 0))))))
          :dune))
      [editing-block]))
   nil)

+ 32 - 11
src/main/frontend/extensions/code.cljs

@@ -157,7 +157,7 @@
 (defn- block-render-type-is-code?
   [block]
   (some-> block :logseq.property.node/display-type
-    (= :code)))
+          (= :code)))
 
 (defn- all-tokens-by-cursor
   "All tokens from the beginning of the document to the cursor(inclusive)."
@@ -407,8 +407,8 @@
 (defn ^:large-vars/cleanup-todo render!
   [state]
   (let [[config id attr _code theme user-options] (:rum/args state)
+        edit-block (:block config)
         config-file? (= (:file-path config) "logseq/config.edn")
-        edit-block (state/get-edit-block)
         default-open? (and (:editor/code-mode? @state/state)
                            (= (:block/uuid edit-block)
                               (get-in config [:block :block/uuid])))
@@ -481,6 +481,7 @@
                              (vreset! *cursor-curr nil)
                              (vreset! *cursor-prev nil)))
         (.on editor "focus" (fn [_e]
+                              (state/set-editing-block-dom-id! (:block-parent-id config))
                               (state/set-block-component-editing-mode! true)
                               (state/set-state! :editor/code-block-context
                                                 {:editor editor
@@ -492,16 +493,36 @@
                                                      meta-or-ctrl-pressed? (or (.-ctrlKey e) (.-metaKey e))
                                                      shifted? (.-shiftKey e)]
                                                  (cond
+                                                   (contains? #{"ArrowLeft" "ArrowRight"} key-code)
+                                                   (let [direction (if (= "ArrowLeft" key-code) :left :right)
+                                                         line (when-let [line (:line @*cursor-curr)]
+                                                                (.getLine (.-doc editor) line))]
+                                                     (when (and (= @*cursor-prev @*cursor-curr)
+                                                                (or (and direction (nil? @*cursor-curr))
+                                                                    (case direction
+                                                                      :left (and (zero? (:line @*cursor-curr))
+                                                                                 (zero? (:ch  @*cursor-curr)))
+                                                                      :right (and (= (:line @*cursor-curr) (.lastLine editor))
+                                                                                  (= (count line) (:ch @*cursor-curr)))
+                                                                      false)))
+                                                       (editor-handler/move-to-block-when-cross-boundary direction {}))
+                                                     (update-cursor-state!))
+
                                                    (contains? #{"ArrowUp" "ArrowDown"} key-code)
-                                                   (let [direction (if (= "ArrowUp" key-code) :up :down)]
+                                                   (let [direction (if (= "ArrowUp" key-code) :up :down)
+                                                         line (when-let [line (:line @*cursor-curr)]
+                                                                (.getLine (.-doc editor) line))]
                                                      (when (and (= @*cursor-prev @*cursor-curr)
-                                                             (case direction
-                                                               :up (zero? (:line @*cursor-curr))
-                                                               :down (= (:line @*cursor-curr) (.lastLine editor))
-                                                               false))
+                                                                (or (and direction (nil? @*cursor-curr))
+                                                                    (case direction
+                                                                      :up (and (zero? (:line @*cursor-curr))
+                                                                               (zero? (:ch  @*cursor-curr)))
+                                                                      :down (and (= (:line @*cursor-curr) (.lastLine editor))
+                                                                                 (= (count line) (:ch @*cursor-curr)))
+                                                                      false)))
                                                        (editor-handler/move-cross-boundary-up-down
-                                                         direction {:input textarea
-                                                                    :pos [direction 0]}))
+                                                        direction {:input textarea
+                                                                   :pos [direction 0]}))
                                                      (update-cursor-state!))
                                                    meta-or-ctrl-pressed?
                                                    ;; prevent default behavior of browser
@@ -520,8 +541,8 @@
                                                        (when-let [blockid (some-> (.-target e) (.closest "[blockid]") (.getAttribute "blockid"))]
                                                          (code-handler/save-code-editor!)
                                                          (util/schedule #(editor-handler/api-insert-new-block! ""
-                                                                           {:block-uuid (uuid blockid)
-                                                                            :sibling? true}))))
+                                                                                                               {:block-uuid (uuid blockid)
+                                                                                                                :sibling? true}))))
                                                      nil)))))
         (.addEventListener element "pointerdown"
                            (fn [e]

+ 4 - 4
src/main/frontend/handler/editor.cljs

@@ -2614,11 +2614,11 @@
         (cursor/move-cursor-up input)
         (cursor/move-cursor-down input)))))
 
-(defn- move-to-block-when-cross-boundary
-  [direction]
+(defn move-to-block-when-cross-boundary
+  [direction {:keys [block]}]
   (let [up? (= :left direction)
         pos (if up? :max 0)
-        {:block/keys [format uuid] :as block} (state/get-edit-block)
+        {:block/keys [format uuid] :as block} (or block (state/get-edit-block))
         repo (state/get-current-repo)
         editing-block (gdom/getElement (state/get-editing-block-dom-id))
         f (if up? util/get-prev-block-non-collapsed util/get-next-block-non-collapsed)
@@ -2664,7 +2664,7 @@
 
         (or (and left? (cursor/start? input))
             (and right? (cursor/end? input)))
-        (move-to-block-when-cross-boundary direction)
+        (move-to-block-when-cross-boundary direction {})
 
         :else
         (if left?