@vc-shell/vc-app-skill 2.0.0-alpha.32 → 2.0.0-alpha.33-pr220.455e322

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 (195) hide show
  1. package/CHANGELOG.md +59 -47
  2. package/README.md +18 -12
  3. package/package.json +4 -4
  4. package/runtime/VERSION +1 -1
  5. package/runtime/agents/api-analyzer.md +31 -16
  6. package/runtime/agents/blade-enhancer.md +15 -9
  7. package/runtime/agents/details-blade-generator.md +47 -31
  8. package/runtime/agents/list-blade-generator.md +21 -37
  9. package/runtime/agents/locales-generator.md +3 -0
  10. package/runtime/agents/migration-agent.md +94 -0
  11. package/runtime/agents/module-analyzer.md +2 -0
  12. package/runtime/agents/module-assembler.md +15 -0
  13. package/runtime/agents/promote-agent.md +15 -4
  14. package/runtime/agents/type-checker.md +11 -0
  15. package/runtime/knowledge/docs/_BUILD_HASH.md +1 -1
  16. package/runtime/knowledge/docs/core/api/platform.docs.md +30 -30
  17. package/runtime/knowledge/docs/core/blade-navigation/blade-nav-composables.docs.md +41 -41
  18. package/runtime/knowledge/docs/core/composables/bladeContext/index.docs.md +12 -10
  19. package/runtime/knowledge/docs/core/composables/useApiClient/useApiClient.docs.md +11 -14
  20. package/runtime/knowledge/docs/core/composables/useAppBarMobileButtons/useAppBarMobileButtons.docs.md +35 -35
  21. package/runtime/knowledge/docs/core/composables/useAppBarWidget/useAppBarWidget.docs.md +35 -35
  22. package/runtime/knowledge/docs/core/composables/useAppInsights/useAppInsights.docs.md +15 -15
  23. package/runtime/knowledge/docs/core/composables/useAssets/useAssets.docs.md +21 -18
  24. package/runtime/knowledge/docs/core/composables/useAssetsManager/useAssetsManager.docs.md +31 -27
  25. package/runtime/knowledge/docs/core/composables/useAsync/useAsync.docs.md +90 -61
  26. package/runtime/knowledge/docs/core/composables/useBeforeUnload/useBeforeUnload.docs.md +19 -18
  27. package/runtime/knowledge/docs/core/composables/useBlade/useBlade.docs.md +89 -68
  28. package/runtime/knowledge/docs/core/composables/useBladeForm/useBladeForm.docs.md +75 -19
  29. package/runtime/knowledge/docs/core/composables/useBladeRegistry/useBladeRegistry.docs.md +15 -15
  30. package/runtime/knowledge/docs/core/composables/useBladeWidgets/index.docs.md +74 -78
  31. package/runtime/knowledge/docs/core/composables/useBreadcrumbs/useBreadcrumbs.docs.md +11 -11
  32. package/runtime/knowledge/docs/core/composables/useConnectionStatus/useConnectionStatus.docs.md +27 -15
  33. package/runtime/knowledge/docs/core/composables/useDashboard/useDashboard.docs.md +30 -30
  34. package/runtime/knowledge/docs/core/composables/useDynamicProperties/useDynamicProperties.docs.md +34 -36
  35. package/runtime/knowledge/docs/core/composables/useErrorHandler/useErrorHandler.docs.md +44 -23
  36. package/runtime/knowledge/docs/core/composables/useFunctions/useFunctions.docs.md +14 -11
  37. package/runtime/knowledge/docs/core/composables/useKeyboardNavigation/useKeyboardNavigation.docs.md +47 -38
  38. package/runtime/knowledge/docs/core/composables/useLanguages/useLanguages.docs.md +37 -28
  39. package/runtime/knowledge/docs/core/composables/useLoading/useLoading.docs.md +23 -17
  40. package/runtime/knowledge/docs/core/composables/useMenuExpanded/index.docs.md +10 -10
  41. package/runtime/knowledge/docs/core/composables/useMenuService/useMenuService.docs.md +42 -42
  42. package/runtime/knowledge/docs/core/composables/useModificationTracker/useModificationTracker.docs.md +22 -12
  43. package/runtime/knowledge/docs/core/composables/useNotifications/useNotifications.docs.md +33 -41
  44. package/runtime/knowledge/docs/core/composables/usePermissions/usePermissions.docs.md +16 -16
  45. package/runtime/knowledge/docs/core/composables/usePopup/usePopup.docs.md +32 -24
  46. package/runtime/knowledge/docs/core/composables/useResponsive/useResponsive.docs.md +32 -11
  47. package/runtime/knowledge/docs/core/composables/useSettings/useSettings.docs.md +24 -15
  48. package/runtime/knowledge/docs/core/composables/useSettingsMenu/useSettingsMenu.docs.md +7 -7
  49. package/runtime/knowledge/docs/core/composables/useSidebarState/useSidebarState.docs.md +32 -24
  50. package/runtime/knowledge/docs/core/composables/useSlowNetworkDetection/useSlowNetworkDetection.docs.md +21 -17
  51. package/runtime/knowledge/docs/core/composables/useTheme/useTheme.docs.md +24 -24
  52. package/runtime/knowledge/docs/core/composables/useToolbar/useToolbar.docs.md +28 -31
  53. package/runtime/knowledge/docs/core/composables/useUser/useUser.docs.md +43 -24
  54. package/runtime/knowledge/docs/core/composables/useUserManagement/useUserManagement.docs.md +68 -48
  55. package/runtime/knowledge/docs/core/composables/useWebVitals/useWebVitals.docs.md +19 -19
  56. package/runtime/knowledge/docs/core/composables/useWidgets/useWidgets.docs.md +42 -47
  57. package/runtime/knowledge/docs/core/directives/autofocus/autofocus.docs.md +10 -4
  58. package/runtime/knowledge/docs/core/directives/loading/loading.docs.md +35 -20
  59. package/runtime/knowledge/docs/core/notifications/notifications.docs.md +36 -35
  60. package/runtime/knowledge/docs/core/plugins/ai-agent/ai-agent.docs.md +38 -38
  61. package/runtime/knowledge/docs/core/plugins/extension-points/extension-points.docs.md +107 -91
  62. package/runtime/knowledge/docs/core/plugins/global-error-handler/global-error-handler.docs.md +10 -10
  63. package/runtime/knowledge/docs/core/plugins/i18n/i18n.docs.md +21 -23
  64. package/runtime/knowledge/docs/core/plugins/modularity/modularity.docs.md +98 -90
  65. package/runtime/knowledge/docs/core/plugins/permissions/permissions.docs.md +10 -16
  66. package/runtime/knowledge/docs/core/plugins/signalR/signalR.docs.md +9 -9
  67. package/runtime/knowledge/docs/core/plugins/validation/validation.docs.md +65 -22
  68. package/runtime/knowledge/docs/core/services/services.docs.md +19 -22
  69. package/runtime/knowledge/docs/core/types/types.docs.md +40 -40
  70. package/runtime/knowledge/docs/core/utilities/date/date-utilities.docs.md +27 -27
  71. package/runtime/knowledge/docs/core/utilities/shared-utilities.docs.md +23 -23
  72. package/runtime/knowledge/docs/core/utilities/thumbnail/thumbnail.docs.md +22 -25
  73. package/runtime/knowledge/docs/core/utilities/utilities.docs.md +64 -64
  74. package/runtime/knowledge/docs/injection-keys.docs.md +52 -51
  75. package/runtime/knowledge/docs/modules/assets-manager/assets-manager.docs.md +9 -9
  76. package/runtime/knowledge/docs/shell/_internal/popup/common/popup-common.docs.md +23 -43
  77. package/runtime/knowledge/docs/shell/auth/ChangePasswordPage/change-password-page.docs.md +102 -0
  78. package/runtime/knowledge/docs/shell/auth/ForgotPasswordPage/forgot-password-page.docs.md +5 -5
  79. package/runtime/knowledge/docs/shell/auth/InvitePage/invite-page.docs.md +8 -7
  80. package/runtime/knowledge/docs/shell/auth/LoginPage/login-page.docs.md +7 -7
  81. package/runtime/knowledge/docs/shell/auth/ResetPasswordPage/reset-password-page.docs.md +8 -7
  82. package/runtime/knowledge/docs/shell/auth/sign-in/sign-in.docs.md +29 -13
  83. package/runtime/knowledge/docs/shell/components/change-password/change-password.docs.md +13 -16
  84. package/runtime/knowledge/docs/shell/components/change-password-button/change-password-button.docs.md +1 -7
  85. package/runtime/knowledge/docs/shell/components/error-interceptor/error-interceptor.docs.md +5 -5
  86. package/runtime/knowledge/docs/shell/components/language-selector/language-selector.docs.md +1 -1
  87. package/runtime/knowledge/docs/shell/components/logout-button/logout-button.docs.md +1 -1
  88. package/runtime/knowledge/docs/shell/components/notification-template/notification-template.docs.md +17 -9
  89. package/runtime/knowledge/docs/shell/components/settings-menu/settings-menu.docs.md +12 -18
  90. package/runtime/knowledge/docs/shell/components/settings-menu-item/settings-menu-item.docs.md +34 -65
  91. package/runtime/knowledge/docs/shell/components/sidebar/sidebar.docs.md +16 -26
  92. package/runtime/knowledge/docs/shell/components/theme-selector/theme-selector.docs.md +2 -2
  93. package/runtime/knowledge/docs/shell/components/user-dropdown-button/user-dropdown-button.docs.md +7 -9
  94. package/runtime/knowledge/docs/shell/dashboard/dashboard-charts/dashboard-charts.docs.md +30 -40
  95. package/runtime/knowledge/docs/shell/dashboard/dashboard-widget-card/dashboard-widget-card.docs.md +26 -19
  96. package/runtime/knowledge/docs/shell/dashboard/draggable-dashboard/draggable-dashboard.docs.md +15 -12
  97. package/runtime/knowledge/docs/ui/components/atoms/vc-badge/vc-badge.docs.md +15 -26
  98. package/runtime/knowledge/docs/ui/components/atoms/vc-banner/vc-banner.docs.md +21 -19
  99. package/runtime/knowledge/docs/ui/components/atoms/vc-button/vc-button.docs.md +83 -67
  100. package/runtime/knowledge/docs/ui/components/atoms/vc-card/vc-card.docs.md +104 -59
  101. package/runtime/knowledge/docs/ui/components/atoms/vc-col/vc-col.docs.md +28 -11
  102. package/runtime/knowledge/docs/ui/components/atoms/vc-container/vc-container.docs.md +20 -17
  103. package/runtime/knowledge/docs/ui/components/atoms/vc-hint/vc-hint.docs.md +26 -17
  104. package/runtime/knowledge/docs/ui/components/atoms/vc-icon/vc-icon.docs.md +30 -32
  105. package/runtime/knowledge/docs/ui/components/atoms/vc-image/vc-image.docs.md +25 -48
  106. package/runtime/knowledge/docs/ui/components/atoms/vc-label/vc-label.docs.md +29 -24
  107. package/runtime/knowledge/docs/ui/components/atoms/vc-link/vc-link.docs.md +23 -15
  108. package/runtime/knowledge/docs/ui/components/atoms/vc-loading/vc-loading.docs.md +22 -13
  109. package/runtime/knowledge/docs/ui/components/atoms/vc-progress/vc-progress.docs.md +33 -18
  110. package/runtime/knowledge/docs/ui/components/atoms/vc-row/vc-row.docs.md +56 -15
  111. package/runtime/knowledge/docs/ui/components/atoms/vc-scrollable-container/vc-scrollable-container.docs.md +28 -15
  112. package/runtime/knowledge/docs/ui/components/atoms/vc-skeleton/vc-skeleton.docs.md +40 -20
  113. package/runtime/knowledge/docs/ui/components/atoms/vc-status/vc-status.docs.md +25 -14
  114. package/runtime/knowledge/docs/ui/components/atoms/vc-status-icon/vc-status-icon.docs.md +40 -14
  115. package/runtime/knowledge/docs/ui/components/atoms/vc-tooltip/vc-tooltip.docs.md +54 -42
  116. package/runtime/knowledge/docs/ui/components/atoms/vc-video/vc-video.docs.md +17 -17
  117. package/runtime/knowledge/docs/ui/components/atoms/vc-widget/vc-widget.docs.md +21 -21
  118. package/runtime/knowledge/docs/ui/components/molecules/multilanguage-selector/multilanguage-selector.docs.md +23 -10
  119. package/runtime/knowledge/docs/ui/components/molecules/vc-accordion/vc-accordion.docs.md +59 -44
  120. package/runtime/knowledge/docs/ui/components/molecules/vc-breadcrumbs/vc-breadcrumbs.docs.md +23 -20
  121. package/runtime/knowledge/docs/ui/components/molecules/vc-checkbox/vc-checkbox.docs.md +96 -64
  122. package/runtime/knowledge/docs/ui/components/molecules/vc-checkbox-group/vc-checkbox-group.docs.md +26 -35
  123. package/runtime/knowledge/docs/ui/components/molecules/vc-color-input/vc-color-input.docs.md +69 -22
  124. package/runtime/knowledge/docs/ui/components/molecules/vc-date-picker/vc-date-picker.docs.md +58 -72
  125. package/runtime/knowledge/docs/ui/components/molecules/vc-dropdown/vc-dropdown.docs.md +91 -85
  126. package/runtime/knowledge/docs/ui/components/molecules/vc-dropdown-panel/vc-dropdown-panel.docs.md +38 -42
  127. package/runtime/knowledge/docs/ui/components/molecules/vc-editor/vc-editor.docs.md +60 -72
  128. package/runtime/knowledge/docs/ui/components/molecules/vc-field/vc-field.docs.md +65 -26
  129. package/runtime/knowledge/docs/ui/components/molecules/vc-file-upload/vc-file-upload.docs.md +46 -49
  130. package/runtime/knowledge/docs/ui/components/molecules/vc-form/vc-form.docs.md +35 -64
  131. package/runtime/knowledge/docs/ui/components/molecules/vc-image-tile/vc-image-tile.docs.md +38 -41
  132. package/runtime/knowledge/docs/ui/components/molecules/vc-input/vc-input.docs.md +115 -130
  133. package/runtime/knowledge/docs/ui/components/molecules/vc-input-currency/vc-input-currency.docs.md +53 -87
  134. package/runtime/knowledge/docs/ui/components/molecules/vc-input-dropdown/vc-input-dropdown.docs.md +56 -63
  135. package/runtime/knowledge/docs/ui/components/molecules/vc-input-group/vc-input-group.docs.md +29 -24
  136. package/runtime/knowledge/docs/ui/components/molecules/vc-menu/vc-menu.docs.md +32 -28
  137. package/runtime/knowledge/docs/ui/components/molecules/vc-multivalue/vc-multivalue.docs.md +63 -64
  138. package/runtime/knowledge/docs/ui/components/molecules/vc-pagination/vc-pagination.docs.md +28 -26
  139. package/runtime/knowledge/docs/ui/components/molecules/vc-radio-button/vc-radio-button.docs.md +59 -19
  140. package/runtime/knowledge/docs/ui/components/molecules/vc-radio-group/vc-radio-group.docs.md +25 -34
  141. package/runtime/knowledge/docs/ui/components/molecules/vc-rating/vc-rating.docs.md +42 -32
  142. package/runtime/knowledge/docs/ui/components/molecules/vc-select/vc-select.docs.md +78 -82
  143. package/runtime/knowledge/docs/ui/components/molecules/vc-slider/vc-slider.docs.md +25 -15
  144. package/runtime/knowledge/docs/ui/components/molecules/vc-switch/vc-switch.docs.md +59 -63
  145. package/runtime/knowledge/docs/ui/components/molecules/vc-textarea/vc-textarea.docs.md +57 -69
  146. package/runtime/knowledge/docs/ui/components/molecules/vc-toast/vc-toast.docs.md +58 -57
  147. package/runtime/knowledge/docs/ui/components/organisms/vc-app/vc-app.docs.md +49 -26
  148. package/runtime/knowledge/docs/ui/components/organisms/vc-auth-layout/vc-auth-layout.docs.md +82 -28
  149. package/runtime/knowledge/docs/ui/components/organisms/vc-blade/vc-blade.docs.md +120 -75
  150. package/runtime/knowledge/docs/ui/components/organisms/vc-data-table/composables/table-composables.docs.md +30 -44
  151. package/runtime/knowledge/docs/ui/components/organisms/vc-data-table/vc-data-table.docs.md +536 -365
  152. package/runtime/knowledge/docs/ui/components/organisms/vc-dynamic-property/vc-dynamic-property.docs.md +35 -52
  153. package/runtime/knowledge/docs/ui/components/organisms/vc-gallery/vc-gallery.docs.md +33 -62
  154. package/runtime/knowledge/docs/ui/components/organisms/vc-image-upload/vc-image-upload.docs.md +17 -23
  155. package/runtime/knowledge/docs/ui/components/organisms/vc-popup/vc-popup.docs.md +109 -68
  156. package/runtime/knowledge/docs/ui/components/organisms/vc-sidebar/vc-sidebar.docs.md +82 -44
  157. package/runtime/knowledge/docs/ui/composables/ui-composables.docs.md +8 -8
  158. package/runtime/knowledge/docs/ui/composables/useDataTablePagination.docs.md +164 -0
  159. package/runtime/knowledge/docs/ui/composables/useDataTableSort.docs.md +34 -26
  160. package/runtime/knowledge/docs/ui/composables/useTableSelection.docs.md +48 -40
  161. package/runtime/knowledge/docs/ui/composables/useTableSort.docs.md +30 -17
  162. package/runtime/knowledge/docs/ui/types/ui-types.docs.md +40 -29
  163. package/runtime/knowledge/examples/offers-module.md +15 -13
  164. package/runtime/knowledge/examples/team-module.md +82 -119
  165. package/runtime/knowledge/examples/videos-module.md +44 -17
  166. package/runtime/knowledge/index.md +22 -0
  167. package/runtime/knowledge/migration-prompts/blade-form-migration.md +255 -0
  168. package/runtime/knowledge/migration-prompts/blade-props-migration.md +194 -0
  169. package/runtime/knowledge/migration-prompts/datatable-migration.md +801 -0
  170. package/runtime/knowledge/migration-prompts/icon-migration.md +97 -0
  171. package/runtime/knowledge/migration-prompts/manual-migration-audit.md +117 -0
  172. package/runtime/knowledge/migration-prompts/notifications-migration.md +223 -0
  173. package/runtime/knowledge/migration-prompts/nswag-migration.md +244 -0
  174. package/runtime/knowledge/migration-prompts/use-assets-migration.md +164 -0
  175. package/runtime/knowledge/migration-prompts/use-data-table-pagination-migration.md +176 -0
  176. package/runtime/knowledge/migration-prompts/widgets-migration.md +178 -0
  177. package/runtime/knowledge/patterns/assets-management.md +20 -20
  178. package/runtime/knowledge/patterns/blade-navigation.md +7 -14
  179. package/runtime/knowledge/patterns/blade-widget.md +19 -17
  180. package/runtime/knowledge/patterns/child-blade-flow.md +19 -7
  181. package/runtime/knowledge/patterns/composable-details.md +20 -50
  182. package/runtime/knowledge/patterns/composable-list.md +43 -31
  183. package/runtime/knowledge/patterns/dashboard-widget.md +14 -16
  184. package/runtime/knowledge/patterns/datatable-pattern.md +521 -0
  185. package/runtime/knowledge/patterns/details-blade-pattern.md +78 -116
  186. package/runtime/knowledge/patterns/extension-points-usage.md +53 -44
  187. package/runtime/knowledge/patterns/form-validation.md +28 -64
  188. package/runtime/knowledge/patterns/list-blade-pattern.md +33 -21
  189. package/runtime/knowledge/patterns/module-structure.md +7 -1
  190. package/runtime/knowledge/patterns/multilanguage-fields.md +8 -14
  191. package/runtime/knowledge/patterns/notification-template.md +21 -14
  192. package/runtime/knowledge/patterns/signalr-notifications.md +30 -32
  193. package/runtime/knowledge/patterns/toolbar-pattern.md +18 -20
  194. package/runtime/vc-app.md +354 -49
  195. package/runtime/knowledge/docs/core/constants/constants.docs.md +0 -185
@@ -34,30 +34,30 @@ const user = reactive({ name: "John", role: "Admin" });
34
34
 
35
35
  ## Props
36
36
 
37
- | Prop | Type | Default | Description |
38
- |------|------|---------|-------------|
39
- | `isReady` | `boolean` | *required* | When false, shows a full-screen loading spinner. |
40
- | `logo` | `string` | -- | Logo image URL for the sidebar/top bar. |
41
- | `title` | `string` | -- | Application title shown in the sidebar. |
42
- | `version` | `string` | -- | App version string (informational). |
43
- | `avatar` | `string` | -- | User avatar image URL. |
44
- | `name` | `string` | -- | Current user display name. |
45
- | `role` | `string` | -- | Current user role label. |
46
- | `disableMenu` | `boolean` | `false` | Hide navigation menu items. |
47
- | `disableAppHub` | `boolean` | `false` | Hide the Applications section inside the App Hub. |
48
- | `showSearch` | `boolean` | `false` | Show a search input in the sidebar that filters menu items by title. |
49
- | `searchPlaceholder` | `string` | `"Search keyword"` | Placeholder text for the sidebar search input. Falls back to i18n key `SHELL.SIDEBAR.SEARCH_PLACEHOLDER`. |
37
+ | Prop | Type | Default | Description |
38
+ | ------------------- | --------- | ------------------ | --------------------------------------------------------------------------------------------------------- |
39
+ | `isReady` | `boolean` | _required_ | When false, shows a full-screen loading spinner. |
40
+ | `logo` | `string` | -- | Logo image URL for the sidebar/top bar. |
41
+ | `title` | `string` | -- | Application title shown in the sidebar. |
42
+ | `version` | `string` | -- | App version string (informational). |
43
+ | `avatar` | `string` | -- | User avatar image URL. |
44
+ | `name` | `string` | -- | Current user display name. |
45
+ | `role` | `string` | -- | Current user role label. |
46
+ | `disableMenu` | `boolean` | `false` | Hide navigation menu items. |
47
+ | `disableAppHub` | `boolean` | `false` | Hide the Applications section inside the App Hub. |
48
+ | `showSearch` | `boolean` | `false` | Show a search input in the sidebar that filters menu items by title. |
49
+ | `searchPlaceholder` | `string` | `"Search keyword"` | Placeholder text for the sidebar search input. Falls back to i18n key `SHELL.SIDEBAR.SEARCH_PLACEHOLDER`. |
50
50
 
51
51
  ## Slots
52
52
 
53
- | Slot | Props | Description |
54
- |------|-------|-------------|
55
- | `layout` | `{ isMobile, sidebar, appsList, switchApp, openRoot, handleMenuItemClick }` | Override the entire layout (sidebar + navigation). |
56
- | `menu` | `{ expanded, onItemClick, searchQuery }` | Custom navigation menu. `searchQuery` contains the current search input value (empty string when search is inactive). |
57
- | `sidebar-header` | `{ logo, expanded, isMobile }` | Custom sidebar header. |
58
- | `sidebar-footer` | `{ avatar, name, role }` | Custom sidebar footer (user info). |
59
- | `workspace` | `{ isAuthenticated }` | Override the blade navigation workspace. |
60
- | `app-hub` | `{ appsList, switchApp }` | Custom content for the Applications section of the App Hub. |
53
+ | Slot | Props | Description |
54
+ | ---------------- | --------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------------- |
55
+ | `layout` | `{ isMobile, sidebar, appsList, switchApp, openRoot, handleMenuItemClick }` | Override the entire layout (sidebar + navigation). |
56
+ | `menu` | `{ expanded, onItemClick, searchQuery }` | Custom navigation menu. `searchQuery` contains the current search input value (empty string when search is inactive). |
57
+ | `sidebar-header` | `{ logo, expanded, isMobile }` | Custom sidebar header. |
58
+ | `sidebar-footer` | `{ avatar, name, role }` | Custom sidebar footer (user info). |
59
+ | `workspace` | `{ isAuthenticated }` | Override the blade navigation workspace. |
60
+ | `app-hub` | `{ appsList, switchApp }` | Custom content for the Applications section of the App Hub. |
61
61
 
62
62
  ## Architecture
63
63
 
@@ -88,7 +88,13 @@ If you use the `menu` slot to provide a custom menu, the `searchQuery` prop is p
88
88
 
89
89
  ```vue
90
90
  <template>
91
- <VcApp :is-ready="true" logo="/logo.svg" title="Admin" show-search search-placeholder="Find a module...">
91
+ <VcApp
92
+ :is-ready="true"
93
+ logo="/logo.svg"
94
+ title="Admin"
95
+ show-search
96
+ search-placeholder="Find a module..."
97
+ >
92
98
  <!-- Default menu with built-in filtering — no extra code needed -->
93
99
  </VcApp>
94
100
  </template>
@@ -98,7 +104,12 @@ If you use the `menu` slot to provide a custom menu, the `searchQuery` prop is p
98
104
 
99
105
  ```vue
100
106
  <template>
101
- <VcApp :is-ready="true" logo="/logo.svg" title="Admin" show-search>
107
+ <VcApp
108
+ :is-ready="true"
109
+ logo="/logo.svg"
110
+ title="Admin"
111
+ show-search
112
+ >
102
113
  <template #menu="{ expanded, onItemClick, searchQuery }">
103
114
  <MyCustomMenu
104
115
  :expanded="expanded"
@@ -157,15 +168,27 @@ Replace the default user info section with a custom footer:
157
168
 
158
169
  ```vue
159
170
  <template>
160
- <VcApp :is-ready="true" logo="/logo.svg" title="Admin">
171
+ <VcApp
172
+ :is-ready="true"
173
+ logo="/logo.svg"
174
+ title="Admin"
175
+ >
161
176
  <template #sidebar-footer="{ avatar, name, role }">
162
177
  <div class="tw-flex tw-items-center tw-gap-3 tw-p-3">
163
- <img :src="avatar" class="tw-w-8 tw-h-8 tw-rounded-full" />
178
+ <img
179
+ :src="avatar"
180
+ class="tw-w-8 tw-h-8 tw-rounded-full"
181
+ />
164
182
  <div>
165
183
  <div class="tw-text-sm tw-font-medium">{{ name }}</div>
166
184
  <div class="tw-text-xs tw-text-gray-500">{{ role }}</div>
167
185
  </div>
168
- <VcButton variant="ghost" size="icon" icon="lucide-log-out" @click="logout" />
186
+ <VcButton
187
+ variant="ghost"
188
+ size="icon"
189
+ icon="lucide-log-out"
190
+ @click="logout"
191
+ />
169
192
  </div>
170
193
  </template>
171
194
  </VcApp>
@@ -18,34 +18,39 @@ A full-page centered authentication layout for login, registration, password res
18
18
  subtitle="Welcome back"
19
19
  >
20
20
  <form @submit.prevent="handleLogin">
21
- <VcInput v-model="email" label="Email" />
22
- <VcInput v-model="password" label="Password" type="password" />
21
+ <VcInput
22
+ v-model="email"
23
+ label="Email"
24
+ />
25
+ <VcInput
26
+ v-model="password"
27
+ label="Password"
28
+ type="password"
29
+ />
23
30
  <button type="submit">Sign In</button>
24
31
  </form>
25
- <template #footer>
26
- <a href="/terms">Terms of Service</a> | <a href="/privacy">Privacy Policy</a>
27
- </template>
32
+ <template #footer> <a href="/terms">Terms of Service</a> | <a href="/privacy">Privacy Policy</a> </template>
28
33
  </VcAuthLayout>
29
34
  </template>
30
35
  ```
31
36
 
32
37
  ## Key Props
33
38
 
34
- | Prop | Type | Default | Description |
35
- |------|------|---------|-------------|
36
- | `logo` | `string` | - | Path or URL to the logo image |
37
- | `logoAlt` | `string` | `"Logo"` | Alt text for the logo |
38
- | `title` | `string` | - | Card heading |
39
- | `subtitle` | `string` | - | Card subheading |
40
- | `background` | `string` | - | Background image URL (preloaded) |
41
- | `bgColor` | `string` | - | Background color CSS override |
39
+ | Prop | Type | Default | Description |
40
+ | ------------ | -------- | -------- | -------------------------------- |
41
+ | `logo` | `string` | - | Path or URL to the logo image |
42
+ | `logoAlt` | `string` | `"Logo"` | Alt text for the logo |
43
+ | `title` | `string` | - | Card heading |
44
+ | `subtitle` | `string` | - | Card subheading |
45
+ | `background` | `string` | - | Background image URL (preloaded) |
46
+ | `bgColor` | `string` | - | Background color CSS override |
42
47
 
43
48
  ## Slots
44
49
 
45
- | Slot | Description |
46
- |------|-------------|
50
+ | Slot | Description |
51
+ | --------- | ----------------------------------------------------- |
47
52
  | `default` | Form content (fields, buttons, SSO providers, errors) |
48
- | `footer` | Below-card area (terms, privacy links) |
53
+ | `footer` | Below-card area (terms, privacy links) |
49
54
 
50
55
  ## Features
51
56
 
@@ -71,10 +76,27 @@ The layout uses a `<main>` element as the page landmark and an `<h2>` for the ca
71
76
  subtitle="Enter your credentials or use a social provider"
72
77
  background="/img/auth-bg.jpg"
73
78
  >
74
- <form @submit.prevent="handleLogin" class="tw-space-y-4">
75
- <VcInput v-model="email" label="Email" type="email" required />
76
- <VcInput v-model="password" label="Password" type="password" required />
77
- <VcButton type="submit" variant="primary" class="tw-w-full">
79
+ <form
80
+ @submit.prevent="handleLogin"
81
+ class="tw-space-y-4"
82
+ >
83
+ <VcInput
84
+ v-model="email"
85
+ label="Email"
86
+ type="email"
87
+ required
88
+ />
89
+ <VcInput
90
+ v-model="password"
91
+ label="Password"
92
+ type="password"
93
+ required
94
+ />
95
+ <VcButton
96
+ type="submit"
97
+ variant="primary"
98
+ class="tw-w-full"
99
+ >
78
100
  Sign In
79
101
  </VcButton>
80
102
  </form>
@@ -82,16 +104,27 @@ The layout uses a `<main>` element as the page landmark and an `<h2>` for the ca
82
104
  <div class="tw-my-4 tw-text-center tw-text-sm tw-text-gray-500">or</div>
83
105
 
84
106
  <div class="tw-space-y-2">
85
- <VcButton variant="outline" class="tw-w-full" @click="loginWithGoogle">
107
+ <VcButton
108
+ variant="outline"
109
+ class="tw-w-full"
110
+ @click="loginWithGoogle"
111
+ >
86
112
  Continue with Google
87
113
  </VcButton>
88
- <VcButton variant="outline" class="tw-w-full" @click="loginWithAzure">
114
+ <VcButton
115
+ variant="outline"
116
+ class="tw-w-full"
117
+ @click="loginWithAzure"
118
+ >
89
119
  Continue with Azure AD
90
120
  </VcButton>
91
121
  </div>
92
122
 
93
123
  <template #footer>
94
- <nav aria-label="Legal links" class="tw-text-sm tw-text-gray-500">
124
+ <nav
125
+ aria-label="Legal links"
126
+ class="tw-text-sm tw-text-gray-500"
127
+ >
95
128
  <a href="/terms">Terms</a> &middot; <a href="/privacy">Privacy</a>
96
129
  </nav>
97
130
  </template>
@@ -108,15 +141,36 @@ The layout uses a `<main>` element as the page landmark and an `<h2>` for the ca
108
141
  title="Reset Password"
109
142
  subtitle="Enter your email to receive a reset link"
110
143
  >
111
- <form @submit.prevent="sendResetLink" class="tw-space-y-4">
112
- <VcInput v-model="email" label="Email" type="email" required />
113
- <VcBanner v-if="successMessage" variant="success" icon="lucide-circle-check">
144
+ <form
145
+ @submit.prevent="sendResetLink"
146
+ class="tw-space-y-4"
147
+ >
148
+ <VcInput
149
+ v-model="email"
150
+ label="Email"
151
+ type="email"
152
+ required
153
+ />
154
+ <VcBanner
155
+ v-if="successMessage"
156
+ variant="success"
157
+ icon="lucide-circle-check"
158
+ >
114
159
  {{ successMessage }}
115
160
  </VcBanner>
116
- <VcBanner v-if="errorMessage" variant="danger" icon="lucide-circle-alert">
161
+ <VcBanner
162
+ v-if="errorMessage"
163
+ variant="danger"
164
+ icon="lucide-circle-alert"
165
+ >
117
166
  {{ errorMessage }}
118
167
  </VcBanner>
119
- <VcButton type="submit" variant="primary" class="tw-w-full" :disabled="isSending">
168
+ <VcButton
169
+ type="submit"
170
+ variant="primary"
171
+ class="tw-w-full"
172
+ :disabled="isSending"
173
+ >
120
174
  Send Reset Link
121
175
  </VcButton>
122
176
  </form>
@@ -18,21 +18,21 @@ Traditional admin panels use page-based routing: click a link, the entire viewpo
18
18
  +----------------+-------------------+---------------------+
19
19
  ```
20
20
 
21
- | Aspect | Pages/Routes | Blades |
22
- |--------|-------------|--------|
23
- | Context | Lost on navigate | Parent remains visible |
21
+ | Aspect | Pages/Routes | Blades |
22
+ | --------- | -------------------- | -------------------------------- |
23
+ | Context | Lost on navigate | Parent remains visible |
24
24
  | Data flow | Query params / store | `param`, `options`, `callParent` |
25
- | Layout | Full viewport | Side-by-side panels |
26
- | Depth | Flat (1 level) | Unlimited nesting |
25
+ | Layout | Full viewport | Side-by-side panels |
26
+ | Depth | Flat (1 level) | Unlimited nesting |
27
27
 
28
28
  ## When to Use
29
29
 
30
- | Scenario | Component |
31
- |----------|-----------|
32
- | Stacked panel with toolbar, header, and lifecycle | **VcBlade** |
33
- | One-off confirmation or input dialog | [VcPopup](../../molecules/vc-popup/) |
34
- | Full-page route without blade stack | Vue Router view |
35
- | Scrollable content section inside a blade | [VcContainer](../../molecules/vc-container/) |
30
+ | Scenario | Component |
31
+ | ------------------------------------------------- | -------------------------------------------- |
32
+ | Stacked panel with toolbar, header, and lifecycle | **VcBlade** |
33
+ | One-off confirmation or input dialog | [VcPopup](../../molecules/vc-popup/) |
34
+ | Full-page route without blade stack | Vue Router view |
35
+ | Scrollable content section inside a blade | [VcContainer](../../molecules/vc-container/) |
36
36
 
37
37
  Use VcBlade for every screen in a vc-shell application -- it is the standard container that integrates with the navigation system, toolbar, breadcrumbs, and unsaved-changes guards. **Do not use** VcBlade for transient dialogs (use `VcPopup` / `usePopup()`) or for content areas that do not need their own header and close button.
38
38
 
@@ -40,7 +40,11 @@ Use VcBlade for every screen in a vc-shell application -- it is the standard con
40
40
 
41
41
  ```vue
42
42
  <template>
43
- <VcBlade title="My First Blade" icon="lucide-box" @close="$emit('close:blade')">
43
+ <VcBlade
44
+ title="My First Blade"
45
+ icon="lucide-box"
46
+ @close="$emit('close:blade')"
47
+ >
44
48
  <div class="tw-p-4">Hello from a blade!</div>
45
49
  </VcBlade>
46
50
  </template>
@@ -105,16 +109,16 @@ import { useBlade, type IBladeToolbar } from "@vc-shell/framework";
105
109
 
106
110
  // Registration metadata
107
111
  defineOptions({
108
- name: "OfferDetails", // Required: unique blade name
109
- url: "/offer", // Optional: URL segment
110
- routable: false, // Optional: exclude from direct URL access
112
+ name: "OfferDetails", // Required: unique blade name
113
+ url: "/offer", // Optional: URL segment
114
+ routable: false, // Optional: exclude from direct URL access
111
115
  });
112
116
 
113
117
  // Standard props injected by the navigation system
114
118
  export interface Props {
115
119
  expanded: boolean;
116
120
  closable: boolean;
117
- param?: string; // Entity ID
121
+ param?: string; // Entity ID
118
122
  options?: { sellerProduct?: object };
119
123
  }
120
124
 
@@ -132,7 +136,7 @@ const emit = defineEmits<Emits>();
132
136
 
133
137
  const { openBlade, closeSelf, callParent, onBeforeClose } = useBlade();
134
138
 
135
- const title = computed(() => props.param ? "Edit Offer" : "New Offer");
139
+ const title = computed(() => (props.param ? "Edit Offer" : "New Offer"));
136
140
  const isLoading = ref(false);
137
141
  const hasChanges = ref(false);
138
142
 
@@ -153,13 +157,13 @@ defineExpose({ title });
153
157
 
154
158
  ### defineOptions Reference
155
159
 
156
- | Property | Type | Description |
157
- |----------|------|-------------|
158
- | `name` | `string` | **Required.** Unique blade identifier for `openBlade({ name: "..." })`. |
159
- | `url` | `string` | URL path segment (e.g., `"/offers"` produces `/#/.../offers`). |
160
- | `isWorkspace` | `boolean` | Marks blade as a workspace (root-level, not closable). |
161
- | `routable` | `boolean` | When `false`, blade cannot be opened via direct URL navigation. |
162
- | `menuItem` | `object` | Registers a sidebar menu entry: `{ id, title, icon, priority }`. |
160
+ | Property | Type | Description |
161
+ | ------------- | --------- | ----------------------------------------------------------------------- |
162
+ | `name` | `string` | **Required.** Unique blade identifier for `openBlade({ name: "..." })`. |
163
+ | `url` | `string` | URL path segment (e.g., `"/offers"` produces `/#/.../offers`). |
164
+ | `isWorkspace` | `boolean` | Marks blade as a workspace (root-level, not closable). |
165
+ | `routable` | `boolean` | When `false`, blade cannot be opened via direct URL navigation. |
166
+ | `menuItem` | `object` | Registers a sidebar menu entry: `{ id, title, icon, priority }`. |
163
167
 
164
168
  ### defineExpose
165
169
 
@@ -191,8 +195,12 @@ openBlade({
191
195
  openBlade({
192
196
  name: "ProductDetails",
193
197
  param: item.id,
194
- onOpen() { selectedItemId.value = item.id; },
195
- onClose() { selectedItemId.value = undefined; },
198
+ onOpen() {
199
+ selectedItemId.value = item.id;
200
+ },
201
+ onClose() {
202
+ selectedItemId.value = undefined;
203
+ },
196
204
  });
197
205
 
198
206
  // Open a workspace (replaces entire blade stack)
@@ -225,8 +233,9 @@ openBlade({ name: "OrderDetails", param: order.id });
225
233
 
226
234
  // In child blade
227
235
  onMounted(async () => {
228
- if (props.param) await loadOrder(props.param); // Existing
229
- else initNewOrder(); // New
236
+ if (props.param)
237
+ await loadOrder(props.param); // Existing
238
+ else initNewOrder(); // New
230
239
  });
231
240
  ```
232
241
 
@@ -301,8 +310,8 @@ const entityId = computed(() => ctx.value.item?.id);
301
310
  ```ts
302
311
  const { closeSelf, closeChildren } = useBlade();
303
312
 
304
- await closeSelf(); // Close this blade
305
- await closeChildren(); // Close all children, keep this blade
313
+ await closeSelf(); // Close this blade
314
+ await closeChildren(); // Close all children, keep this blade
306
315
  ```
307
316
 
308
317
  ### Preventing Close (Unsaved Changes Guard)
@@ -316,7 +325,7 @@ const { showConfirmation } = usePopup();
316
325
  onBeforeClose(async () => {
317
326
  if (hasUnsavedChanges.value) {
318
327
  const confirmed = await showConfirmation("Discard unsaved changes?");
319
- return !confirmed; // true = prevent close, false = allow
328
+ return !confirmed; // true = prevent close, false = allow
320
329
  }
321
330
  return false;
322
331
  });
@@ -340,7 +349,7 @@ const toolbar = ref<IBladeToolbar[]>([
340
349
  title: "Delete",
341
350
  icon: "lucide-trash-2",
342
351
  clickHandler: () => confirmDelete(),
343
- isVisible: computed(() => !!props.param), // Only for existing entities
352
+ isVisible: computed(() => !!props.param), // Only for existing entities
344
353
  },
345
354
  ]);
346
355
  ```
@@ -354,8 +363,7 @@ interface IBladeToolbar {
354
363
  icon?: string | (() => string);
355
364
  clickHandler?(): void;
356
365
  disabled?: boolean | ComputedRef<boolean>;
357
- isVisible?: boolean | Ref<boolean> | ComputedRef<boolean>
358
- | ((blade?: BladeDescriptor) => boolean);
366
+ isVisible?: boolean | Ref<boolean> | ComputedRef<boolean> | ((blade?: BladeDescriptor) => boolean);
359
367
  separator?: "left" | "right" | "both";
360
368
  }
361
369
  ```
@@ -396,7 +404,7 @@ Combine with `onBeforeClose` and `useBeforeUnload` for full protection:
396
404
 
397
405
  ```ts
398
406
  import { useBeforeUnload } from "@vc-shell/framework";
399
- useBeforeUnload(hasChanges); // Browser tab close warning
407
+ useBeforeUnload(hasChanges); // Browser tab close warning
400
408
  ```
401
409
 
402
410
  ## Custom Banners
@@ -441,6 +449,7 @@ On mobile, width is forced to `100%`. When `expanded` is `true`, the blade fills
441
449
  The most common vc-shell pattern. Key points from real-world usage (see `offers-list.vue` and `offers-details.vue`):
442
450
 
443
451
  **List blade** -- Opens a details blade on row click, tracks selected item:
452
+
444
453
  ```ts
445
454
  defineOptions({ name: "Offers", url: "/offers", isWorkspace: true });
446
455
 
@@ -451,8 +460,12 @@ const onItemClick = (event: { data: Offer }) => {
451
460
  openBlade({
452
461
  name: "Offer",
453
462
  param: event.data.id,
454
- onOpen() { selectedItemId.value = event.data.id; },
455
- onClose() { selectedItemId.value = undefined; },
463
+ onOpen() {
464
+ selectedItemId.value = event.data.id;
465
+ },
466
+ onClose() {
467
+ selectedItemId.value = undefined;
468
+ },
456
469
  });
457
470
  };
458
471
 
@@ -461,6 +474,7 @@ defineExpose({ title: bladeTitle, reload });
461
474
  ```
462
475
 
463
476
  **Details blade** -- Loads entity, saves, notifies parent, replaces self on create:
477
+
464
478
  ```ts
465
479
  defineOptions({ name: "Offer", url: "/offer", routable: false });
466
480
 
@@ -508,20 +522,21 @@ Using `vee-validate` with `Field` components:
508
522
  ```ts
509
523
  const { meta } = useForm({ validateOnMount: false });
510
524
 
511
- const toolbar = ref([{
512
- id: "save",
513
- title: "Save",
514
- icon: "lucide-save",
515
- clickHandler: () => meta.value.valid ? save() : showError("Fix validation errors."),
516
- disabled: computed(() => !meta.value.valid || !modified.value),
517
- }]);
525
+ const toolbar = ref([
526
+ {
527
+ id: "save",
528
+ title: "Save",
529
+ icon: "lucide-save",
530
+ clickHandler: () => (meta.value.valid ? save() : showError("Fix validation errors.")),
531
+ disabled: computed(() => !meta.value.valid || !modified.value),
532
+ },
533
+ ]);
518
534
  ```
519
535
 
520
536
  ### Blade with Data Table
521
537
 
522
538
  ```vue
523
- <VcBlade :title="$t('ORDERS.LIST.TITLE')" icon="lucide-file-text" width="50%"
524
- :expanded="expanded" :closable="closable" :toolbar-items="toolbar">
539
+ <VcBlade :title="$t('ORDERS.LIST.TITLE')" icon="lucide-file-text" width="50%" :expanded="expanded" :closable="closable" :toolbar-items="toolbar">
525
540
  <VcDataTable
526
541
  v-model:sort-field="sortField" v-model:sort-order="sortOrder"
527
542
  v-model:search-value="searchValue" v-model:active-item-id="selectedItemId"
@@ -592,31 +607,31 @@ openBlade({ name: "ProductsList" });
592
607
 
593
608
  ## Props
594
609
 
595
- | Prop | Type | Default | Description |
596
- |------|------|---------|-------------|
597
- | `title` | `string` | `undefined` | Title text in the blade header. |
598
- | `subtitle` | `string` | `undefined` | Secondary text below the title. |
599
- | `icon` | `string` | `undefined` | Icon name (e.g., `"lucide-box"`) displayed before the title. |
600
- | `width` | `number \| string` | `"30%"` | Blade width. Numbers are pixels; strings are CSS values. |
601
- | `expanded` | `boolean` | `false` | Whether the blade fills all available width. |
602
- | `closable` | `boolean` | `true` | Whether the close button is shown. |
603
- | `toolbarItems` | `IBladeToolbar[]` | `[]` | Action buttons in the toolbar zone. |
604
- | `modified` | `boolean` | `undefined` | Shows unsaved changes indicator and banner. |
605
- | `loading` | `boolean` | `false` | Shows skeleton placeholders for all blade zones. |
610
+ | Prop | Type | Default | Description |
611
+ | -------------- | ------------------ | ----------- | ------------------------------------------------------------ |
612
+ | `title` | `string` | `undefined` | Title text in the blade header. |
613
+ | `subtitle` | `string` | `undefined` | Secondary text below the title. |
614
+ | `icon` | `string` | `undefined` | Icon name (e.g., `"lucide-box"`) displayed before the title. |
615
+ | `width` | `number \| string` | `"30%"` | Blade width. Numbers are pixels; strings are CSS values. |
616
+ | `expanded` | `boolean` | `false` | Whether the blade fills all available width. |
617
+ | `closable` | `boolean` | `true` | Whether the close button is shown. |
618
+ | `toolbarItems` | `IBladeToolbar[]` | `[]` | Action buttons in the toolbar zone. |
619
+ | `modified` | `boolean` | `undefined` | Shows unsaved changes indicator and banner. |
620
+ | `loading` | `boolean` | `false` | Shows skeleton placeholders for all blade zones. |
606
621
 
607
622
  ## Events
608
623
 
609
- | Event | Payload | Description |
610
- |-------|---------|-------------|
611
- | `close` | -- | Close button clicked. Re-emit as `close:blade`. |
612
- | `expand` | -- | Blade expanded. Re-emit as `expand:blade`. |
613
- | `collapse` | -- | Blade collapsed. Re-emit as `collapse:blade`. |
624
+ | Event | Payload | Description |
625
+ | ---------- | ------- | ----------------------------------------------- |
626
+ | `close` | -- | Close button clicked. Re-emit as `close:blade`. |
627
+ | `expand` | -- | Blade expanded. Re-emit as `expand:blade`. |
628
+ | `collapse` | -- | Blade collapsed. Re-emit as `collapse:blade`. |
614
629
 
615
630
  ## Slots
616
631
 
617
- | Slot | Description |
618
- |------|-------------|
619
- | `default` | Main scrollable content area. |
632
+ | Slot | Description |
633
+ | --------- | -------------------------------------------------- |
634
+ | `default` | Main scrollable content area. |
620
635
  | `actions` | Custom elements in the header, right of the title. |
621
636
 
622
637
  ## CSS Custom Properties
@@ -649,13 +664,43 @@ openBlade({ name: "ProductsList" });
649
664
 
650
665
  ## Related
651
666
 
652
- | Resource | Description |
653
- |----------|-------------|
654
- | `useBlade()` | Unified composable: identity, navigation, communication, guards, error management. |
655
- | `defineBladeContext()` / `injectBladeContext()` | Provide/inject reactive data for widgets and extensions. |
656
- | `VcBladeNavigation` | Manages blade stack and horizontal scroll (part of `vc-app.vue`). |
657
- | `IBladeToolbar` | TypeScript interface for toolbar button definitions. |
658
- | `useBeforeUnload()` | Browser tab close warning for unsaved changes. |
659
- | `useLoading()` | Merges multiple loading refs into a single boolean. |
660
- | `usePopup()` | Confirmation dialogs and error messages. |
661
- | `useBladeWidgets()` | Register contextual widgets for the blade widget area. |
667
+ | Resource | Description |
668
+ | ----------------------------------------------- | ---------------------------------------------------------------------------------- |
669
+ | `useBlade()` | Unified composable: identity, navigation, communication, guards, error management. |
670
+ | `defineBladeContext()` / `injectBladeContext()` | Provide/inject reactive data for widgets and extensions. |
671
+ | `VcBladeNavigation` | Manages blade stack and horizontal scroll (part of `vc-app.vue`). |
672
+ | `IBladeToolbar` | TypeScript interface for toolbar button definitions. |
673
+ | `useBeforeUnload()` | Browser tab close warning for unsaved changes. |
674
+ | `useLoading()` | Merges multiple loading refs into a single boolean. |
675
+ | `usePopup()` | Confirmation dialogs and error messages. |
676
+ | `useBladeWidgets()` | Register contextual widgets for the blade widget area. |
677
+
678
+ ## Content Skeleton Mode
679
+
680
+ When `loading=true`, VcBlade provides `BladeLoadingKey` to all descendant components via Vue's provide/inject. Each framework UI component automatically renders a skeleton placeholder matching its visual footprint.
681
+
682
+ ### How It Works
683
+
684
+ 1. Set `loading` prop on VcBlade (typically bound to your data-fetching composable's loading ref)
685
+ 2. All child components (`VcInput`, `VcSelect`, `VcCard`, etc.) detect the loading state and render skeletons
686
+ 3. Layout containers (`VcContainer`, `VcRow`, `VcCol`, `VcForm`) are transparent — they preserve layout structure
687
+ 4. When loading completes, components switch to their normal rendering
688
+
689
+ ### What Shows During Loading
690
+
691
+ - **Config-gated fields** (`v-if="config.showName"`) — config is available immediately, so these fields show skeletons
692
+ - **Data-gated fields** (`v-if="item.productData"`) — data not yet loaded, so these fields don't appear in the skeleton
693
+ - **Header and toolbar** — have their own dedicated skeletons (unchanged)
694
+
695
+ No changes to existing blade pages are required.
696
+
697
+ ### Custom Components
698
+
699
+ To make custom components skeleton-aware:
700
+
701
+ ```ts
702
+ import { useBladeLoading } from "@vc-shell/framework";
703
+
704
+ const bladeLoading = useBladeLoading();
705
+ // bladeLoading.value === true when parent VcBlade is loading
706
+ ```