@iyulab/modern-app 0.2.5 → 0.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (36) hide show
  1. package/CHANGELOG.md +45 -0
  2. package/README.md +18 -0
  3. package/dist/App.d.ts +9 -6
  4. package/dist/App.js +30 -28
  5. package/dist/components/SidebarButton.d.ts +4 -5
  6. package/dist/components/SidebarButton.js +12 -14
  7. package/dist/components/SidebarButton.styles.js +15 -18
  8. package/dist/components/SidebarGroup.d.ts +7 -6
  9. package/dist/components/SidebarGroup.js +45 -46
  10. package/dist/components/SidebarGroup.styles.js +39 -44
  11. package/dist/components/SidebarLink.d.ts +5 -10
  12. package/dist/components/SidebarLink.js +29 -39
  13. package/dist/components/SidebarLink.styles.js +9 -9
  14. package/dist/components/SidebarSection.d.ts +6 -7
  15. package/dist/components/SidebarSection.js +18 -22
  16. package/dist/components/SidebarSection.styles.js +9 -14
  17. package/dist/index.d.ts +2 -3
  18. package/dist/internals/ScreenObserver.d.ts +43 -0
  19. package/dist/internals/ScreenObserver.js +37 -0
  20. package/dist/internals/StyledElement.d.ts +24 -0
  21. package/dist/internals/{ExtendedBaseElement.js → StyledElement.js} +13 -14
  22. package/dist/layouts/SidebarLayout.d.ts +29 -21
  23. package/dist/layouts/SidebarLayout.js +143 -111
  24. package/dist/layouts/SidebarLayout.styles.js +82 -42
  25. package/dist/layouts/SidebarLayout.types.d.ts +14 -12
  26. package/dist/types/AppConfigs.d.ts +12 -7
  27. package/dist/types/AppOptions.d.ts +1 -1
  28. package/package.json +9 -11
  29. package/dist/components/SidebarLogo.d.ts +0 -33
  30. package/dist/components/SidebarLogo.js +0 -60
  31. package/dist/components/SidebarLogo.styles.d.ts +0 -1
  32. package/dist/components/SidebarLogo.styles.js +0 -57
  33. package/dist/internals/ExtendedBaseElement.d.ts +0 -22
  34. package/dist/internals/observables.d.ts +0 -7
  35. package/dist/internals/observables.js +0 -5
  36. package/dist/types/AppTypes.d.ts +0 -4
package/CHANGELOG.md CHANGED
@@ -1,5 +1,50 @@
1
1
  # Changelog
2
2
 
3
+ ## 0.3.1 (2026-03-05)
4
+
5
+ ### Breaking Changes
6
+ - **Slot 기반 Outlet 구조**: `SidebarLayout` 내부의 `<u-outlet>`을 `<slot>`으로 변경하고, `App`에서 Light DOM에 `<u-outlet>`을 추가하는 방식으로 전환. 이를 통해 React 라우팅 시 외부 CSS가 정상적으로 적용됨
7
+
8
+ ### Changes
9
+ - **BaseElement → UElement 마이그레이션**: 모든 컴포넌트의 기반 클래스를 `BaseElement`에서 `UElement`로 변경
10
+ - **SidebarLinkConfig**: `type` 속성을 optional에서 required로 변경
11
+ - **import 경로 수정**: `Theme.js`, `Notifier.js` 등 대소문자 교정
12
+
13
+ ### Dependencies
14
+ - `@iyulab/components` ^0.2.0 → ^0.4.0
15
+ - `@iyulab/router` ^0.6.2 → ^0.7.2
16
+ - `i18next` ^25.8.0 → ^25.8.13
17
+ - `@types/node` ^25.0.9 → ^25.3.2
18
+
19
+ ### Fixes
20
+ - `SidebarButton.styles.ts`에서 중복된 `color` 속성 제거
21
+ - `repeat` 디렉티브의 미사용 콜백 파라미터 정리
22
+
23
+ ## 0.3.0 (2026-01-21)
24
+
25
+ ### Breaking Changes
26
+ - **Configuration Updates**:
27
+ - Renamed `localization` to `i18n`
28
+ - Renamed `layout.menu` to `layout.main`
29
+ - Changed `logo` type to string (icon name)
30
+ - Added `title` property for app title
31
+ - Added `iconBasepath` option
32
+ - **Mobile layout support**: New mobile states (`mobile`, `mobile-open`) with dedicated mobile header
33
+
34
+ ### Removals
35
+ - Removed `SidebarLogo` component: Logo is now rendered using `u-icon` component
36
+ - Removed `observables.ts`: Replaced MobX observables with native `ScreenObserver` class
37
+ - Removed `AppTypes.ts`: Type definitions moved to their respective modules
38
+
39
+ ### Improvements
40
+ - Improved responsive behavior with screen size observer
41
+ - Added route context tracking and active link highlighting
42
+ - Improved color scheme and typography
43
+ - Enhanced transition animations
44
+ - Cleaner layout spacing and gaps
45
+ - Improved event handling for route changes and screen resizing
46
+ - Enhanced pattern matching for active link detection
47
+
3
48
  ## 0.2.5 (2026-01-06)
4
49
  - Updated `@iyulab/components` to v0.1.11
5
50
 
package/README.md CHANGED
@@ -10,6 +10,24 @@ For complete examples and documentation, visit our demo site: [https://modern-ap
10
10
  npm install @iyulab/modern-app
11
11
  ```
12
12
 
13
+ ## Architecture
14
+
15
+ `@iyulab/modern-app` is a **client-side SPA framework** built on Lit Element. It is designed for:
16
+
17
+ ✅ **Suitable for:**
18
+ - Single Page Applications (SPA)
19
+ - Admin dashboards and internal tools
20
+ - Progressive Web Apps (PWA)
21
+ - Projects where SEO is not a primary concern
22
+
23
+ ❌ **Not suitable for:**
24
+ - Server-Side Rendering (SSR) frameworks (Next.js, Nuxt, SvelteKit, etc.)
25
+ - Static Site Generation (SSG)
26
+ - SEO-critical public-facing pages
27
+ - Projects requiring initial HTML content for search engines
28
+
29
+ This is by design — Lit components render on the client side. If you need SSR capabilities, consider using Lit's experimental SSR support separately or choose a framework designed for SSR from the start.
30
+
13
31
  ## Quick Start
14
32
 
15
33
  ```typescript
package/dist/App.d.ts CHANGED
@@ -1,6 +1,8 @@
1
1
  import { Router } from '@iyulab/router';
2
- import { AppConfig } from './types/AppConfigs.js';
3
- import { NotificationOptions } from './types/AppOptions.js';
2
+ import { Theme } from '@iyulab/components/dist/utilities/Theme.js';
3
+ import { ScreenSize } from './internals/ScreenObserver';
4
+ import { AppConfig } from './types/AppConfigs';
5
+ import { NotificationOptions } from './types/AppOptions';
4
6
  /**
5
7
  * 애플리케이션 전역 상태 및 설정 관리 클래스
6
8
  */
@@ -9,6 +11,7 @@ declare class App {
9
11
  private _config?;
10
12
  private _layout?;
11
13
  private _router?;
14
+ private _screen?;
12
15
  private constructor();
13
16
  /** 싱글톤 인스턴스 반환 */
14
17
  static get instance(): App;
@@ -16,10 +19,12 @@ declare class App {
16
19
  get config(): AppConfig | undefined;
17
20
  /** 라우터 인스턴스 반환 */
18
21
  get router(): Router | undefined;
22
+ /** 화면 크기 반환 */
23
+ get screen(): ScreenSize | undefined;
19
24
  /** 스타일 테마 관리 유틸리티 객체 반환 */
20
- get theme(): import('@iyulab/components/dist/utilities/theme.js').Theme;
25
+ get theme(): typeof Theme;
21
26
  /** 다국어 로컬라이저(i18next) 반환 */
22
- get localizer(): import('i18next').i18n;
27
+ get i18n(): import('i18next').i18n;
23
28
  /** 앱 로드 및 초기화 */
24
29
  load(config: AppConfig): Promise<void>;
25
30
  /** 앱 언로드 */
@@ -40,8 +45,6 @@ declare class App {
40
45
  private notify;
41
46
  /** 레이아웃 생성 */
42
47
  private createLayout;
43
- /** 화면 크기 변경 핸들러 */
44
- private handleWindowResize;
45
48
  }
46
49
  /**
47
50
  * 전역 어플리케이션 설정 및 관리 인스턴스
package/dist/App.js CHANGED
@@ -1,18 +1,12 @@
1
- import { runInAction as l } from "mobx";
2
- import n from "i18next";
3
- import { Router as d } from "@iyulab/router";
4
- import { theme as u } from "@iyulab/components/dist/utilities/theme.js";
5
- import { notifier as h } from "@iyulab/components/dist/utilities/notifier.js";
6
- import { screen as s } from "./internals/observables.js";
1
+ import r from "i18next";
2
+ import { Router as u } from "@iyulab/router";
3
+ import { setDefaultBaseUrl as h } from "@iyulab/components/dist/utilities/IconRegistry.js";
4
+ import { Theme as n } from "@iyulab/components/dist/utilities/Theme.js";
5
+ import { Notifier as c } from "@iyulab/components/dist/utilities/Notifier.js";
6
+ import { ScreenObserver as y } from "./internals/ScreenObserver.js";
7
7
  class o {
8
8
  // private 생성자로 외부에서 인스턴스 생성 방지
9
9
  constructor() {
10
- this.handleWindowResize = (t) => {
11
- const e = window.innerWidth, [i, a] = this._config?.layout.breakpoints || [768, 1024];
12
- l(() => {
13
- e < i ? s.set("small") : e < a ? s.set("medium") : s.set("large");
14
- });
15
- };
16
10
  }
17
11
  /** 싱글톤 인스턴스 반환 */
18
12
  static get instance() {
@@ -26,24 +20,32 @@ class o {
26
20
  get router() {
27
21
  return this._router;
28
22
  }
23
+ /** 화면 크기 반환 */
24
+ get screen() {
25
+ return this._screen?.get();
26
+ }
29
27
  /** 스타일 테마 관리 유틸리티 객체 반환 */
30
28
  get theme() {
31
- return u;
29
+ return n;
32
30
  }
33
31
  /** 다국어 로컬라이저(i18next) 반환 */
34
- get localizer() {
35
- return n;
32
+ get i18n() {
33
+ return r;
36
34
  }
37
35
  /** 앱 로드 및 초기화 */
38
36
  async load(t) {
39
- if (this.unload(), this._config = t, await u.init(t.theme), t.localization) {
40
- for (const i of t.localization.plugins || [])
41
- n.use(i);
42
- await n.init(t.localization);
37
+ if (this.unload(), this._config = t, await n.init(t.theme), t.iconBasepath && h(t.iconBasepath), t.i18n) {
38
+ for (const a of t.i18n.plugins || [])
39
+ r.use(a);
40
+ await r.init(t.i18n);
43
41
  }
44
- window.addEventListener("resize", this.handleWindowResize), this.handleWindowResize(new Event("resize"));
45
42
  const e = t.root || document.body;
46
- this._layout = await this.createLayout(e, t.layout), this._router = new d({
43
+ this._layout = await this.createLayout(e, t.layout), this._screen = new y({
44
+ element: e,
45
+ breakpoints: t.layout.breakpoints || [768, 1024]
46
+ });
47
+ const i = document.createElement("u-outlet");
48
+ this._layout.appendChild(i), this._router = new u({
47
49
  root: this._layout,
48
50
  basepath: t.basepath,
49
51
  routes: t.routes,
@@ -52,7 +54,7 @@ class o {
52
54
  }
53
55
  /** 앱 언로드 */
54
56
  unload() {
55
- window.removeEventListener("resize", this.handleWindowResize), this._layout && (this._layout.remove(), this._layout = void 0), this._router && (this._router.destroy(), this._router = void 0), this._config && (this._config = void 0);
57
+ this._screen && (this._screen.destroy(), this._screen = void 0), this._layout && (this._layout.remove(), this._layout = void 0), this._router && (this._router.destroy(), this._router = void 0), this._config && (this._config = void 0);
56
58
  }
57
59
  /** 페이지 이동 */
58
60
  navigate(t) {
@@ -80,7 +82,7 @@ class o {
80
82
  }
81
83
  /** 알림 표시 */
82
84
  async notify(t, e, i) {
83
- await h.toast({
85
+ await c.toast({
84
86
  type: t,
85
87
  content: e,
86
88
  heading: i?.title,
@@ -91,13 +93,13 @@ class o {
91
93
  /** 레이아웃 생성 */
92
94
  async createLayout(t, e) {
93
95
  t === document.body && (document.body.style.margin = "0", document.body.style.width = "100vw", document.body.style.height = "100vh");
94
- let i = t.querySelector("[data-layout]");
95
- if (i && t.removeChild(i), e.type === "sidebar") {
96
- const { SidebarLayout: a } = await import("./layouts/SidebarLayout.js"), r = new a();
97
- r.config = e, i = r;
96
+ let i;
97
+ if (e.type === "sidebar") {
98
+ const { SidebarLayout: a } = await import("./layouts/SidebarLayout.js"), s = new a();
99
+ s.config = e, i = s;
98
100
  } else
99
101
  throw new Error(`Unsupported layout type: ${e.type}`);
100
- return i.setAttribute("data-layout", "true"), t.appendChild(i), "updateComplete" in i && await i.updateComplete, i;
102
+ return t.appendChild(i), "updateComplete" in i && await i.updateComplete, i;
101
103
  }
102
104
  }
103
105
  const _ = o.instance;
@@ -1,7 +1,6 @@
1
1
  import { DirectiveResult } from 'lit/directive.js';
2
- import { BaseElement } from '@iyulab/components/dist/components/BaseElement.js';
3
- import { ExtendedBaseElement } from '../internals/ExtendedBaseElement.js';
4
- import { StyleMap } from '../types/AppTypes.js';
2
+ import { UElement } from '@iyulab/components/dist/components/UElement.js';
3
+ import { StyledElement, StyleMap } from '../internals/StyledElement.js';
5
4
  /** 버튼 항목 부분 */
6
5
  type ElementParts = 'host' | 'base' | 'icon' | 'label';
7
6
  /** 버튼 항목 구성 */
@@ -15,9 +14,9 @@ export interface SidebarButtonConfig {
15
14
  /**
16
15
  * SidebarButton 컴포넌트는 사이드바 내의 버튼을 표시합니다.
17
16
  */
18
- export declare class SidebarButton extends ExtendedBaseElement<ElementParts> {
17
+ export declare class SidebarButton extends StyledElement<ElementParts> {
19
18
  static styles: import('lit').CSSResultGroup[];
20
- static dependencies: Record<string, typeof BaseElement>;
19
+ static dependencies: Record<string, typeof UElement>;
21
20
  /** 콤팩트 모드 여부 */
22
21
  compact: boolean;
23
22
  /** 기본 u-icon 경로의 아이콘 이름 */
@@ -1,19 +1,19 @@
1
1
  import { html as c } from "lit";
2
2
  import { property as o } from "lit/decorators.js";
3
3
  import { UIcon as l } from "@iyulab/components/dist/components/icon/UIcon.component.js";
4
- import { ExtendedBaseElement as m } from "../internals/ExtendedBaseElement.js";
5
- import { styles as d } from "./SidebarButton.styles.js";
6
- var u = Object.defineProperty, n = (e, p, s, f) => {
4
+ import { StyledElement as m } from "../internals/StyledElement.js";
5
+ import { styles as u } from "./SidebarButton.styles.js";
6
+ var d = Object.defineProperty, p = (e, n, s, f) => {
7
7
  for (var t = void 0, r = e.length - 1, a; r >= 0; r--)
8
- (a = e[r]) && (t = a(p, s, t) || t);
9
- return t && u(p, s, t), t;
8
+ (a = e[r]) && (t = a(n, s, t) || t);
9
+ return t && d(n, s, t), t;
10
10
  };
11
11
  class i extends m {
12
12
  constructor() {
13
13
  super(...arguments), this.compact = !1;
14
14
  }
15
15
  static {
16
- this.styles = [super.styles, d];
16
+ this.styles = [super.styles, u];
17
17
  }
18
18
  static {
19
19
  this.dependencies = {
@@ -22,26 +22,24 @@ class i extends m {
22
22
  }
23
23
  render() {
24
24
  return c`
25
- <button part="base">
26
- <u-icon part="icon"
27
- ?hidden=${!this.icon}
25
+ <button part="base" ?compact=${this.compact}>
26
+ <u-icon part="icon" ?hidden=${!this.icon}
28
27
  .name=${this.icon}
29
28
  ></u-icon>
30
- <span part="label"
31
- ?hidden=${this.compact}>
29
+ <span part="label" ?hidden=${this.compact}>
32
30
  ${this.label}
33
31
  </span>
34
32
  </button>
35
33
  `;
36
34
  }
37
35
  }
38
- n([
36
+ p([
39
37
  o({ type: Boolean, reflect: !0 })
40
38
  ], i.prototype, "compact");
41
- n([
39
+ p([
42
40
  o({ type: String })
43
41
  ], i.prototype, "icon");
44
- n([
42
+ p([
45
43
  o({ type: String })
46
44
  ], i.prototype, "label");
47
45
  export {
@@ -1,25 +1,15 @@
1
1
  import { css as o } from "lit";
2
- const r = o`
2
+ const e = o`
3
3
  :host {
4
4
  display: block;
5
5
  width: 100%;
6
- padding: 8px 12px;
7
- font-size: 14px;
8
6
  color: var(--u-txt-color);
9
- background: transparent;
7
+ background-color: transparent;
10
8
  border: none;
11
9
  border-radius: 8px;
12
10
  transition: all 0.2s ease;
13
11
  cursor: pointer;
14
12
  }
15
- :host([comact]) {
16
- padding: 8px;
17
- }
18
- :host([compact]) button {
19
- width: 100%;
20
- justify-content: center;
21
- gap: 0;
22
- }
23
13
  :host(:hover) {
24
14
  color: var(--u-txt-color-hover);
25
15
  background-color: var(--u-bg-color-hover);
@@ -29,13 +19,19 @@ const r = o`
29
19
  }
30
20
 
31
21
  button {
32
- width: 100%;
33
22
  all: unset;
23
+ width: 100%;
34
24
  display: flex;
35
25
  flex-direction: row;
36
26
  align-items: center;
37
27
  justify-content: flex-start;
38
28
  gap: 12px;
29
+ padding: 8px 12px;
30
+ }
31
+ button[compact] {
32
+ justify-content: center;
33
+ gap: 0;
34
+ padding: 8px;
39
35
  }
40
36
  button:focus-visible {
41
37
  outline: 2px solid #6666ff;
@@ -43,20 +39,21 @@ const r = o`
43
39
  }
44
40
 
45
41
  u-icon {
46
- font-size: 20px;
47
- color: inherit;
48
42
  flex-shrink: 0;
43
+ color: inherit;
44
+ font-size: 20px;
49
45
  }
50
46
 
51
47
  span {
52
48
  flex: 1;
49
+ font-size: 14px;
53
50
  font-weight: 500;
54
- color: inherit;
55
- overflow: hidden;
51
+ line-height: 20px;
56
52
  white-space: nowrap;
53
+ overflow: hidden;
57
54
  text-overflow: ellipsis;
58
55
  }
59
56
  `;
60
57
  export {
61
- r as styles
58
+ e as styles
62
59
  };
@@ -1,9 +1,8 @@
1
1
  import { DirectiveResult } from 'lit/directive.js';
2
- import { BaseElement } from '@iyulab/components/dist/components/BaseElement.js';
3
- import { StyleMap } from '../types/AppTypes.js';
4
- import { ExtendedBaseElement } from '../internals/ExtendedBaseElement.js';
2
+ import { UElement } from '@iyulab/components/dist/components/UElement.js';
3
+ import { StyledElement, StyleMap } from '../internals/StyledElement.js';
5
4
  import { SidebarLinkConfig } from './SidebarLink.js';
6
- type ElementParts = 'host' | 'container' | 'base' | 'icon' | 'label' | 'toggler' | 'items';
5
+ type ElementParts = 'host' | 'header' | 'icon' | 'label' | 'caret' | 'items';
7
6
  /** 그룹: 하위 링크들 묶음 */
8
7
  export interface SidebarGroupConfig {
9
8
  type: 'group';
@@ -17,11 +16,13 @@ export interface SidebarGroupConfig {
17
16
  /**
18
17
  * SidebarGroup 컴포넌트는 네비게이션 그룹 아이템을 표시합니다.
19
18
  */
20
- export declare class SidebarGroup extends ExtendedBaseElement<ElementParts> {
19
+ export declare class SidebarGroup extends StyledElement<ElementParts> {
21
20
  static styles: import('lit').CSSResultGroup[];
22
- static dependencies: Record<string, typeof BaseElement>;
21
+ static dependencies: Record<string, typeof UElement>;
23
22
  /** 콤팩트 모드 여부 */
24
23
  compact: boolean;
24
+ /** 선택된 상태 */
25
+ selected: boolean;
25
26
  /** collapsed 상태 */
26
27
  collapsed: boolean;
27
28
  /** 네비게이션 아이템 데이터 */
@@ -1,27 +1,22 @@
1
- import { html as c } from "lit";
2
- import { property as o } from "lit/decorators.js";
1
+ import { html as p } from "lit";
2
+ import { property as e } from "lit/decorators.js";
3
3
  import { UIcon as d } from "@iyulab/components/dist/components/icon/UIcon.component.js";
4
- import { app as m } from "../App.js";
5
- import { ExtendedBaseElement as u } from "../internals/ExtendedBaseElement.js";
6
- import { SidebarLink as h } from "./SidebarLink.js";
7
- import { styles as f } from "./SidebarGroup.styles.js";
8
- var y = Object.defineProperty, r = (i, n, e, l) => {
9
- for (var t = void 0, a = i.length - 1, p; a >= 0; a--)
10
- (p = i[a]) && (t = p(n, e, t) || t);
11
- return t && y(n, e, t), t;
4
+ import { StyledElement as h } from "../internals/StyledElement.js";
5
+ import { SidebarLink as m } from "./SidebarLink.js";
6
+ import { styles as u } from "./SidebarGroup.styles.js";
7
+ var f = Object.defineProperty, o = (i, l, c, a) => {
8
+ for (var t = void 0, r = i.length - 1, n; r >= 0; r--)
9
+ (n = i[r]) && (t = n(l, c, t) || t);
10
+ return t && f(l, c, t), t;
12
11
  };
13
- class s extends u {
12
+ class s extends h {
14
13
  constructor() {
15
- super(...arguments), this.compact = !1, this.collapsed = !0, this.handleButtonClick = (n) => {
16
- if (this.compact) {
17
- const e = this.shadowRoot?.querySelector("slot")?.assignedElements({ flatten: !0 }).find((l) => l instanceof h);
18
- m.navigate(e?.href || "/");
19
- } else
20
- this.collapsed = !this.collapsed;
14
+ super(...arguments), this.compact = !1, this.selected = !1, this.collapsed = !0, this.handleButtonClick = (l) => {
15
+ this.compact ? this.shadowRoot?.querySelector("slot")?.assignedElements({ flatten: !0 }).find((t) => t instanceof m)?.renderRoot.querySelector("u-link")?.click() : this.collapsed = !this.collapsed;
21
16
  };
22
17
  }
23
18
  static {
24
- this.styles = [super.styles, f];
19
+ this.styles = [super.styles, u];
25
20
  }
26
21
  static {
27
22
  this.dependencies = {
@@ -29,41 +24,45 @@ class s extends u {
29
24
  };
30
25
  }
31
26
  render() {
32
- return c`
33
- <div class="container" part="container">
34
- <button part="base"
35
- @click=${this.handleButtonClick}>
36
- <u-icon class="icon" part="icon"
37
- ?hidden=${!this.icon}
38
- .name=${this.icon}
39
- ></u-icon>
40
- <span class="label" part="label">
41
- ${this.label}
42
- </span>
43
- <u-icon class="toggler" part="toggler"
44
- lib="internal"
45
- name="chevron-down"
46
- ></u-icon>
47
- </button>
48
-
49
- <div class="items" part="items">
50
- <slot></slot>
51
- </div>
27
+ return p`
28
+ <button part="header"
29
+ ?compact=${this.compact}
30
+ ?selected=${this.selected}
31
+ @click=${this.handleButtonClick}>
32
+ <u-icon class="icon" part="icon" ?hidden=${!this.icon}
33
+ .name=${this.icon}
34
+ ></u-icon>
35
+ <span class="label" part="label" ?hidden=${this.compact}>
36
+ ${this.label}
37
+ </span>
38
+ <u-icon class="caret" part="caret" ?hidden=${this.compact}
39
+ ?collapsed=${this.collapsed}
40
+ lib="internal"
41
+ name="chevron-down"
42
+ ></u-icon>
43
+ </button>
44
+
45
+ <div class="items" part="items" ?hidden=${this.compact}
46
+ ?collapsed=${this.collapsed}>
47
+ <slot></slot>
52
48
  </div>
53
49
  `;
54
50
  }
55
51
  }
56
- r([
57
- o({ type: Boolean, reflect: !0 })
52
+ o([
53
+ e({ type: Boolean, reflect: !0 })
58
54
  ], s.prototype, "compact");
59
- r([
60
- o({ type: Boolean, reflect: !0 })
55
+ o([
56
+ e({ type: Boolean, reflect: !0 })
57
+ ], s.prototype, "selected");
58
+ o([
59
+ e({ type: Boolean, reflect: !0 })
61
60
  ], s.prototype, "collapsed");
62
- r([
63
- o({ type: String })
61
+ o([
62
+ e({ type: String })
64
63
  ], s.prototype, "icon");
65
- r([
66
- o({ type: String })
64
+ o([
65
+ e({ type: String })
67
66
  ], s.prototype, "label");
68
67
  export {
69
68
  s as SidebarGroup
@@ -1,93 +1,88 @@
1
1
  import { css as o } from "lit";
2
- const e = o`
2
+ const t = o`
3
3
  :host {
4
- display: block;
5
- }
6
- :host([compact]) button {
7
- justify-content: center;
8
- padding: 8px;
9
- }
10
- :host([compact]) .label {
11
- display: none;
12
- }
13
- :host([compact]) .toggler {
14
- display: none;
15
- }
16
- :host([compact]) .items {
17
- display: none;
18
- }
19
- :host(:not([compact])[collapsed]) .toggler {
20
- transform: rotate(-90deg);
21
- }
22
- :host(:not([compact])[collapsed]) .items {
23
- height: 0;
24
- margin-top: 0;
25
- opacity: 0;
26
- }
27
-
28
- .container {
29
4
  display: flex;
30
5
  flex-direction: column;
6
+ color: var(--u-neutral-800);
31
7
  }
32
8
 
33
9
  button {
34
10
  all: unset;
35
- position: relative;
11
+ width: 100%;
36
12
  display: flex;
37
13
  flex-direction: row;
38
- justify-content: space-between;
39
14
  align-items: center;
15
+ justify-content: space-between;
40
16
  gap: 12px;
41
- width: 100%;
42
17
  padding: 8px 12px;
43
- color: var(--u-txt-color);
44
- font-family: inherit;
45
- background: transparent;
18
+ background-color: transparent;
46
19
  border: none;
47
20
  border-radius: 8px;
48
21
  transition: all 0.2s ease;
49
22
  cursor: pointer;
50
23
  }
24
+ button[compact] {
25
+ justify-content: center;
26
+ gap: 0;
27
+ padding: 8px;
28
+ }
29
+ button[selected] {
30
+ color: var(--u-blue-700);
31
+ }
51
32
  button:hover {
52
- background-color: var(--u-bg-color-hover);
53
33
  color: var(--u-txt-color-hover);
34
+ background-color: var(--u-bg-color-hover);
35
+ }
36
+ button:active {
37
+ background-color: var(--u-bg-color-active);
38
+ }
39
+ button:focus-visible {
40
+ outline: 2px solid #6666ff;
41
+ outline-offset: 2px;
54
42
  }
55
43
 
56
44
  .icon {
57
- font-size: 20px;
58
- color: inherit;
59
45
  flex-shrink: 0;
46
+ color: inherit;
47
+ font-size: 20px;
60
48
  }
61
49
 
62
50
  .label {
63
51
  flex: 1;
64
- color: inherit;
65
52
  font-size: 14px;
66
- font-weight: 600;
67
53
  line-height: 20px;
68
- text-align: left;
54
+ font-weight: 600;
69
55
  overflow: hidden;
70
56
  white-space: nowrap;
71
57
  text-overflow: ellipsis;
72
58
  }
73
59
 
74
- .toggler {
60
+ .caret {
61
+ color: inherit;
75
62
  font-size: 16px !important;
76
63
  transition: transform 0.2s ease;
77
64
  }
65
+ .caret[collapsed] {
66
+ transform: rotate(-90deg);
67
+ }
78
68
 
79
69
  .items {
80
70
  display: flex;
81
71
  flex-direction: column;
82
- margin-left: 32px;
83
- margin-top: 4px;
84
72
  gap: 4px;
85
- overflow: hidden;
86
- transition: all 0.3s ease;
73
+ margin-top: 4px;
74
+ margin-left: 32px;
87
75
  border-left: 2px solid var(--u-border-color-weak);
88
76
  padding-left: 8px;
77
+ overflow: hidden;
78
+ transition: all 0.3s ease;
79
+ }
80
+ .items[collapsed] {
81
+ margin-top: 0;
82
+ height: 0;
83
+ opacity: 0;
89
84
  }
90
85
  `;
91
86
  export {
92
- e as styles
87
+ t as styles
93
88
  };