فهرست منبع

wip: add action bar for selected blocks

New UI component: ButtonGroup.
Tienson Qin 8 ماه پیش
والد
کامیت
82ca4bc9e5

+ 9 - 8
deps/shui/src/logseq/shui/ui.cljs

@@ -1,21 +1,22 @@
 (ns logseq.shui.ui
-  (:require [logseq.shui.util :as util]
+  (:require [logseq.shui.base.core :as base-core]
+            [logseq.shui.dialog.core :as dialog-core]
+            [logseq.shui.form.core :as form-core]
             [logseq.shui.icon.v2 :as icon-v2]
-            [logseq.shui.shortcut.v1 :as shui.shortcut.v1]
-            [logseq.shui.toaster.core :as toaster-core]
+            [logseq.shui.popup.core :as popup-core]
             [logseq.shui.select.core :as select-core]
             [logseq.shui.select.multi :as select-multi]
-            [logseq.shui.dialog.core :as dialog-core]
-            [logseq.shui.popup.core :as popup-core]
-            [logseq.shui.base.core :as base-core]
-            [logseq.shui.form.core :as form-core]
-            [logseq.shui.table.core :as table-core]))
+            [logseq.shui.shortcut.v1 :as shui.shortcut.v1]
+            [logseq.shui.table.core :as table-core]
+            [logseq.shui.toaster.core :as toaster-core]
+            [logseq.shui.util :as util]))
 
 (def button base-core/button)
 (def button-icon base-core/button-icon)
 (def button-ghost-icon base-core/button-ghost-icon)
 (def button-outline-icon base-core/button-outline-icon)
 (def button-secondary-icon base-core/button-secondary-icon)
+(def button-group (util/lsui-wrap "ButtonGroup"))
 (def link base-core/link)
 (def trigger-as base-core/trigger-as)
 (def trigger-child-wrap base-core/trigger-child-wrap)

+ 53 - 0
packages/ui/@/components/ui/button-group.tsx

@@ -0,0 +1,53 @@
+import { Children, ReactElement, cloneElement } from 'react';
+
+import { ButtonProps } from '@/components/ui/button';
+import { cn } from '@/lib/utils';
+
+interface ButtonGroupProps {
+  className?: string;
+  orientation?: 'horizontal' | 'vertical';
+  children: ReactElement<ButtonProps>[];
+}
+
+export const ButtonGroup = ({
+  className,
+  orientation = 'horizontal',
+  children,
+}: ButtonGroupProps) => {
+  const totalButtons = Children.count(children);
+  const isHorizontal = orientation === 'horizontal';
+  const isVertical = orientation === 'vertical';
+
+  return (
+    <div
+      className={cn(
+        'flex',
+        {
+          'flex-col': isVertical,
+          'w-fit': isVertical,
+        },
+        className
+      )}
+    >
+      {Children.map(children, (child, index) => {
+        const isFirst = index === 0;
+        const isLast = index === totalButtons - 1;
+
+        return cloneElement(child, {
+          className: cn(
+            {
+              'rounded-l-none': isHorizontal && !isFirst,
+              'rounded-r-none': isHorizontal && !isLast,
+              'border-l-0': isHorizontal && !isFirst,
+
+              'rounded-t-none': isVertical && !isFirst,
+              'rounded-b-none': isVertical && !isLast,
+              'border-t-0': isVertical && !isFirst,
+            },
+            child.props.className
+          ),
+        });
+      })}
+    </div>
+  );
+};

+ 2 - 1
packages/ui/src/ui.ts

@@ -1,4 +1,5 @@
 import { Button } from '@/components/ui/button'
+import { ButtonGroup } from '@/components/ui/button-group'
 import { Slider, SliderTrack, SliderRange, SliderThumb } from '@/components/ui/slider'
 import {
   DropdownMenu,
@@ -99,7 +100,7 @@ declare global {
 }
 
 const shadui = {
-  Link, Button,
+  Link, Button, ButtonGroup,
   Slider, SliderTrack, SliderRange, SliderThumb,
   DropdownMenu,
   DropdownMenuContent,

+ 43 - 0
src/main/frontend/components/selection.cljs

@@ -0,0 +1,43 @@
+(ns frontend.components.selection
+  "Block selection"
+  (:require [frontend.handler.editor :as editor-handler]
+            [frontend.state :as state]
+            [frontend.ui :as ui]
+            [frontend.util :as util]
+            [logseq.shui.ui :as shui]
+            [rum.core :as rum]))
+
+(rum/defc action-bar
+  []
+  (let [button-opts {:variant :outline
+                     :size :sm
+                     :class "px-2 py-0 text-xs text-muted-foreground"}]
+    [:div.selection-action-bar
+     (shui/button-group
+      ;; set tag
+      (shui/button
+       (assoc button-opts
+              :on-pointer-down (fn [e]
+                                 (util/stop e)
+                                 (state/pub-event! [:editor/new-property {:target (.-target e)
+                                                                          :property-key "Tags"}])))
+       (ui/icon "hash" {:size 14}))
+     ;; set propertyo
+      (shui/button
+       (assoc button-opts
+              :on-pointer-down (fn [e]
+                                 (util/stop e)
+                                 (state/pub-event! [:editor/new-property {:target (.-target e)}])))
+       "Set property")
+      (shui/button
+       (assoc button-opts
+              :on-pointer-down (fn [e]
+                                 (util/stop e)
+                                 (editor-handler/copy-selection-blocks true)))
+       "Copy")
+      (shui/button
+       (assoc button-opts
+              :on-pointer-down (fn [e]
+                                 (util/stop e)
+                                 (editor-handler/cut-selection-blocks true)))
+       "Cut"))]))