🎉 Show source info in sidebar

This commit is contained in:
Andrés Moya 2026-07-28 14:00:07 +02:00
parent 545ec183fd
commit c925726bfc
14 changed files with 166 additions and 43 deletions

View File

@ -1030,8 +1030,8 @@
set-ids (ctos/get-active-set-ids tokens-status)
library-data (::library-data (meta changes))
prev-tokens-status (cfo/get-tokens-status library-data)
prev-theme-ids (ctos/get-active-theme-ids prev-tokens-status)
prev-set-ids (ctos/get-active-set-ids prev-tokens-status)]
prev-theme-ids (if prev-tokens-status (ctos/get-active-theme-ids prev-tokens-status) #{})
prev-set-ids (if prev-tokens-status (ctos/get-active-set-ids prev-tokens-status) #{})]
(-> changes
(update :redo-changes conj {:type :set-tokens-status :theme-ids theme-ids :set-ids set-ids})
(update :undo-changes conj {:type :set-tokens-status :theme-ids prev-theme-ids :set-ids prev-set-ids})

View File

@ -468,7 +468,7 @@
(tht/add-tokens-lib))
file-data (cfo/set-tokens-source (:data file) (uuid/next))]
(t/is (false? (cfo/tokens-provider? file-data))))))
(t/deftest test-editable-tokens?
(t/testing "returns true when file-data has no tokens-source"
(let [file (thf/sample-file :file1)

View File

@ -1616,8 +1616,7 @@
ptk/WatchEvent
(watch [_ state _]
(let [file-data (dm/get-in state [:files file-id :data])
libraries (:shared-files state)
(let [libraries (:shared-files state)
library (get libraries library-id)
variants-count (-> library :library-summary :variants count)
@ -1635,10 +1634,10 @@
(conj $ library-id)
(map #(load-library-file file-id %) $))))
(rx/catch (fn [cause]
(let [error (ex-data cause)]
(if (= (:code error) :circular-library-reference)
(rx/of (ntf/error (tr "errors.circular-library-reference")))
(rx/throw cause))))))
(let [error (ex-data cause)]
(if (= (:code error) :circular-library-reference)
(rx/of (ntf/error (tr "errors.circular-library-reference")))
(rx/throw cause))))))
(rx/of (ptk/reify ::link-file-to-library-finished))
(when (pos? variants-count)
(->> (rp/cmd! :get-library-usage {:file-id library-id})

View File

@ -523,7 +523,8 @@
(ctob/enable-set set-name))
token-status
(ctos/make-tokens-status #{} #(ctob/get-id token-set))
(ctos/make-tokens-status :active-theme-ids #{}
:active-set-ids #{(ctob/get-id token-set)})
changes
(-> (pcb/empty-changes)
@ -533,6 +534,7 @@
(pcb/set-token-theme (ctob/get-id hidden-theme)
hidden-theme)
(pcb/set-tokens-status token-status))]
(rx/of (dch/commit-changes changes)
(set-selected-token-set-id (ctob/get-id token-set)))))))

View File

@ -7,6 +7,7 @@
(ns app.main.ui.workspace.tokens.sidebar
(:require-macros [app.main.style :as stl])
(:require
[app.common.files.tokens :as cfo]
[app.common.types.tokens-lib :as ctob]
[app.config :as cf]
[app.main.data.modal :as modal]
@ -25,18 +26,21 @@
[app.main.ui.workspace.tokens.sets.context-menu :refer [token-set-context-menu*]]
[app.main.ui.workspace.tokens.sets.lists :as tsetslist]
[app.main.ui.workspace.tokens.themes :refer [themes-header*]]
[app.main.ui.workspace.tokens.tokens-source :refer [tokens-source-info*]]
[app.util.dom :as dom]
[app.util.i18n :refer [tr]]
[rumext.v2 :as mf]
[shadow.resource]
[app.common.files.tokens :as cfo]))
[shadow.resource]))
;; Components ------------------------------------------------------------------
(mf/defc token-sets-list*
{::mf/private true}
[{:keys [tokens-lib]}]
(let [token-sets
[]
(let [tokens-lib
(mf/use-ctx ctx/tokens-lib)
token-sets
(some-> tokens-lib (ctob/get-set-tree))
selected-token-set-id
@ -61,16 +65,22 @@
(mf/defc token-management-section*
{::mf/private true}
[{:keys [resize-height] :as props}]
[{:keys [resize-height current-file-data] :as props}]
(let [can-edit-tokens?
(mf/use-ctx ctx/can-edit-tokens?)]
(mf/use-ctx ctx/can-edit-tokens?)
tokens-source
(mf/with-memo [current-file-data]
(cfo/get-tokens-source current-file-data))]
[:*
[:> token-set-context-menu*]
[:section {:data-testid "token-management-sidebar"
:class (stl/css :token-management-section-wrapper)
:style {"--resize-height" (str resize-height "px")}}
[:> themes-header*]
(when (not= tokens-source (:id current-file-data))
[:> tokens-source-info* {:tokens-source tokens-source}])
[:> themes-header* {:tokens-source tokens-source}]
[:div {:class (stl/css :sidebar-header)}
[:> title-bar* {:title (tr "labels.sets")}
(when can-edit-tokens?
@ -140,7 +150,7 @@
:on-click open-settings-modal}])]))
(mf/defc tokens-sidebar-tab*
[{:keys [tokens-lib] :as props}]
[{:keys [] :as props}]
(let [{on-pointer-down-pages :on-pointer-down
on-lost-pointer-capture-pages :on-lost-pointer-capture
on-pointer-move-pages :on-pointer-move
@ -162,7 +172,7 @@
[:div {:class (stl/css :sidebar-wrapper)}
[:> token-management-section*
{:resize-height size-pages-opened
:tokens-lib tokens-lib}]
:current-file-data current-file-data}]
[:article {:class (stl/css :tokens-section-wrapper)
:data-testid "tokens-sidebar"}
[:div {:class (stl/css :resize-area-horiz)

View File

@ -26,7 +26,7 @@
overflow-y: auto;
scrollbar-gutter: stable;
position: relative;
padding-block-end: var(--sp-l);
padding-block: var(--sp-m) var(--sp-l);
}
.tokens-section-wrapper {

View File

@ -19,7 +19,7 @@
(mf/defc themes-header*
{::mf/private true}
[]
[{:keys [tokens-source]}]
(let [ordered-themes
(mf/deref refs/workspace-token-themes-no-hidden)
@ -44,7 +44,7 @@
(tr "workspace.tokens.create-one")])]
(if can-edit-tokens?
[:div {:class (stl/css :theme-selector-wrapper)}
[:> theme-selector*]
[:> theme-selector* {:tokens-source tokens-source}]
[:> button* {:variant "secondary"
:type "button"
:class (stl/css :edit-theme-button)
@ -52,4 +52,4 @@
(tr "labels.edit")]]
[:div {:title (when-not can-edit-tokens?
(tr "workspace.tokens.no-permission-themes"))}
[:> theme-selector*]]))]))
[:> theme-selector* {:tokens-source tokens-source}]]))]))

View File

@ -9,7 +9,7 @@
@use "ds/spacing.scss" as *;
.themes-wrapper {
padding: var(--sp-m) 0 0 var(--sp-m);
padding: 0 0 0 var(--sp-m);
}
.themes-header {

View File

@ -14,7 +14,7 @@
[app.common.uuid :as uuid]
[app.main.data.modal :as modal]
[app.main.data.workspace.tokens.library-edit :as dwtl]
[app.main.refs :as refs]
[app.main.router :as rt]
[app.main.store :as st]
[app.main.ui.components.dropdown :refer [dropdown]]
[app.main.ui.context :as ctx]
@ -50,15 +50,22 @@
:class (stl/css-case :check-icon true
:check-icon-visible selected?)}]])]))
(defn- open-tokens-theme-modal
[]
(modal/show! :tokens/themes {}))
(mf/defc theme-options*
[{:keys [tokens-lib tokens-status on-close]}]
[{:keys [tokens-lib tokens-status tokens-source can-edit-tokens team-id on-close]}]
(let [themes
(mf/with-memo [tokens-lib]
(ctob/get-theme-tree-no-hidden tokens-lib))]
(ctob/get-theme-tree-no-hidden tokens-lib))
edit-token-themes
(fn []
(if can-edit-tokens
(modal/show! :tokens/themes {})
(st/emit! (rt/nav :workspace
{:team-id team-id
:file-id tokens-source
:layout :tokens}
::rt/new-window true))))]
[:ul {:class (stl/css :theme-options :custom-select-dropdown)
:role "listbox"}
(for [[group themes] themes]
@ -76,15 +83,21 @@
[:li {:class (stl/css-case :checked-element true
:checked-element-button true)
:role "option"
:on-click open-tokens-theme-modal}
:on-click edit-token-themes}
[:> text* {:as "span" :typography "body-small"} (tr "workspace.tokens.edit-themes")]
[:> icon* {:icon-id i/arrow-right :aria-hidden true}]]]))
[:> icon* {:icon-id (if can-edit-tokens
i/arrow-right
i/open-link)
:aria-hidden true}]]]))
(mf/defc theme-selector*
[{:keys []}]
[{:keys [tokens-source]}]
(let [;; Store
tokens-lib (mf/use-ctx ctx/tokens-lib)
tokens-status (mf/use-ctx ctx/tokens-status)
tokens-lib (mf/use-ctx ctx/tokens-lib)
tokens-status (mf/use-ctx ctx/tokens-status)
can-edit-file? (mf/use-ctx ctx/can-edit?)
can-edit-tokens (mf/use-ctx ctx/can-edit-tokens?)
team-id (mf/use-ctx ctx/current-team-id)
active-themes
(mf/with-memo [tokens-lib tokens-status]
@ -94,8 +107,6 @@
(mf/with-memo [active-themes]
(count active-themes))
can-edit? (:can-edit (deref refs/permissions))
;; Data
current-label (cond
(> active-themes-count 1) (tr "workspace.tokens.active-themes" active-themes-count)
@ -117,9 +128,9 @@
on-open-dropdown
(mf/use-fn
(mf/deps can-edit?)
(mf/deps can-edit-file?)
(fn [event]
(when can-edit?
(when can-edit-file?
(when-let [node (dom/get-current-target event)]
(let [rect (dom/get-bounding-rect node)]
(swap! state* assoc
@ -129,14 +140,14 @@
container (hooks/use-portal-container :popup)]
[:div {:on-click on-open-dropdown
:disabled (not can-edit?)
:disabled (not can-edit-file?)
:aria-expanded is-open?
:aria-haspopup "listbox"
:tab-index "0"
:role "combobox"
:data-testid "theme-select"
:class (stl/css-case :custom-select true
:disabled-select (not can-edit?))}
:disabled-select (not can-edit-file?))}
[:> text* {:as "span" :typography "body-small" :class (stl/css :current-label)}
current-label]
[:> icon* {:icon-id i/arrow-down :class (stl/css :dropdown-button) :aria-hidden true}]
@ -154,5 +165,8 @@
:on-close on-close-dropdown}
[:> theme-options* {:tokens-lib tokens-lib
:tokens-status tokens-status
:tokens-source tokens-source
:can-edit-tokens can-edit-tokens
:team-id team-id
:on-close on-close-dropdown}]]])
container))]))

View File

@ -0,0 +1,48 @@
;; This Source Code Form is subject to the terms of the Mozilla Public
;; License, v. 2.0. If a copy of the MPL was not distributed with this
;; file, You can obtain one at http://mozilla.org/MPL/2.0/.
;;
;; Copyright (c) KALEIDOS INC Sucursal en España SL
(ns app.main.ui.workspace.tokens.tokens-source
(:require-macros [app.main.style :as stl])
(:require
[app.main.refs :as refs]
[app.main.router :as rt]
[app.main.store :as st]
[app.main.ui.context :as ctx]
[app.main.ui.ds.buttons.icon-button :refer [icon-button*]]
[app.main.ui.ds.foundations.typography.text :refer [text*]]
[app.util.i18n :refer [tr]]
[rumext.v2 :as mf]))
(mf/defc tokens-source-info*
{::mf/private true}
[{:keys [tokens-source] :as props}]
(let [files (mf/deref refs/files)
tokens-source-file (get files tokens-source)
team-id
(mf/use-ctx ctx/current-team-id)
open-library-new-window
(mf/use-fn
(fn []
(st/emit! (rt/nav :workspace
{:team-id team-id
:file-id tokens-source
:layout :tokens}
::rt/new-window true))))]
[:div {:class (stl/css :tokens-source-wrapper)}
[:div {:class (stl/css :tokens-source-header)}
[:> text* {:as "div" :typography "headline-small" :class (stl/css :tokens-source-title)}
(:name tokens-source-file)]
[:span {:class (stl/css :replace-this-by-a-badge-component)}
(tr "workspace.tokens.connected-library")]]
[:> icon-button*
{:variant "ghost"
:aria-label (tr "workspace.tokens.open-connected-library")
:on-click open-library-new-window
:icon "open-link"}]]))

View File

@ -0,0 +1,30 @@
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
//
// Copyright (c) KALEIDOS INC Sucursal en España SL
@use "ds/typography.scss" as *;
@use "ds/_sizes" as *;
@use "ds/spacing.scss" as *;
.tokens-source-wrapper {
display: flex;
padding: 0 0 0 var(--sp-m);
}
.tokens-source-header {
column-gap: var(--sp-s);
display: flex;
flex-grow: 1;
padding: var(--sp-s);
}
.tokens-source-title {
color: var(--title-foreground-color);
overflow-wrap: break-word;
}
.replace-this-by-a-badge-component {
font-size: $sz-12;
}

View File

@ -9933,6 +9933,14 @@ msgstr "Use a reference"
msgid "workspace.tokens.value-not-valid"
msgstr "The value is not valid"
#: src/app/main/ui/workspace/tokens/tokens_source.cljs:24
msgid "workspace.tokens.connected-library"
msgstr "connected library"
#: src/app/main/ui/workspace/tokens/tokens_source.cljs:25
msgid "workspace.tokens.open-connected-library"
msgstr "Open connected library"
#: src/app/main/ui/workspace/tokens/management/forms/generic_form.cljs
#, unused
msgid "workspace.tokens.warning-name-change"

View File

@ -9606,6 +9606,14 @@ msgstr "Usa una referencia"
msgid "workspace.tokens.value-not-valid"
msgstr "El valor no es válido"
#: src/app/main/ui/workspace/tokens/tokens_source.cljs:24
msgid "workspace.tokens.connected-library"
msgstr "librería conectada"
#: src/app/main/ui/workspace/tokens/tokens_source.cljs:25
msgid "workspace.tokens.open-connected-library"
msgstr "Abrir librería conectada"
#: src/app/main/ui/workspace/tokens/management/forms/generic_form.cljs
#, unused
msgid "workspace.tokens.warning-name-change"

View File

@ -60,7 +60,11 @@
<div class="panel-heading">
<p class="headline-m">SETS</p>
@if (isEditableTokens) {
<button type="button" data-appearance="secondary" (click)="addSet()">
<button
type="button"
data-appearance="secondary"
(click)="addSet()"
>
+
</button>
}