@bitforgehq/ui 0.3.0

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 (281) hide show
  1. package/CHANGELOG.md +3665 -0
  2. package/LICENSE +21 -0
  3. package/README.md +175 -0
  4. package/ai/MANIFEST.index.json +383 -0
  5. package/ai/MANIFEST.json +7528 -0
  6. package/ai/REFERENCE.index.json +1461 -0
  7. package/ai/REFERENCE.json +7213 -0
  8. package/ai/UI_GUIDE.md +1159 -0
  9. package/ai/components/action-bar.md +209 -0
  10. package/ai/components/action-sheet.md +526 -0
  11. package/ai/components/alert-dialog.md +509 -0
  12. package/ai/components/alert.md +376 -0
  13. package/ai/components/avatar.md +146 -0
  14. package/ai/components/back-button.md +286 -0
  15. package/ai/components/badge.md +171 -0
  16. package/ai/components/button.md +431 -0
  17. package/ai/components/card.md +303 -0
  18. package/ai/components/checkbox.md +418 -0
  19. package/ai/components/chip-group.md +205 -0
  20. package/ai/components/chip.md +300 -0
  21. package/ai/components/content.md +474 -0
  22. package/ai/components/desktop-toast.md +420 -0
  23. package/ai/components/dialog.md +962 -0
  24. package/ai/components/empty-state.md +146 -0
  25. package/ai/components/field.md +319 -0
  26. package/ai/components/header.md +809 -0
  27. package/ai/components/icon-button.md +221 -0
  28. package/ai/components/icon.md +176 -0
  29. package/ai/components/input.md +455 -0
  30. package/ai/components/list-item.md +326 -0
  31. package/ai/components/list.md +178 -0
  32. package/ai/components/menu-button.md +377 -0
  33. package/ai/components/menu.md +661 -0
  34. package/ai/components/modal.md +613 -0
  35. package/ai/components/number-input.md +423 -0
  36. package/ai/components/page.md +299 -0
  37. package/ai/components/progress.md +215 -0
  38. package/ai/components/radio-group.md +432 -0
  39. package/ai/components/refresher.md +377 -0
  40. package/ai/components/segmented.md +517 -0
  41. package/ai/components/select.md +510 -0
  42. package/ai/components/sheet.md +845 -0
  43. package/ai/components/spinner.md +171 -0
  44. package/ai/components/stack-outlet.md +661 -0
  45. package/ai/components/tab-bar.md +427 -0
  46. package/ai/components/tab.md +295 -0
  47. package/ai/components/tabs.md +408 -0
  48. package/ai/components/textarea.md +371 -0
  49. package/ai/components/toast.md +522 -0
  50. package/ai/components/toggle.md +387 -0
  51. package/ai/reference/bf-action-directive.md +21 -0
  52. package/ai/reference/bf-action-sheet-action-role.md +27 -0
  53. package/ai/reference/bf-action-sheet-action.md +28 -0
  54. package/ai/reference/bf-action-sheet-options.md +28 -0
  55. package/ai/reference/bf-action-sheet-service.md +33 -0
  56. package/ai/reference/bf-alert-dialog-button-role.md +27 -0
  57. package/ai/reference/bf-alert-dialog-button.md +27 -0
  58. package/ai/reference/bf-alert-dialog-options.md +29 -0
  59. package/ai/reference/bf-alert-dialog-service.md +34 -0
  60. package/ai/reference/bf-alert-variant.md +28 -0
  61. package/ai/reference/bf-autocapitalize.md +30 -0
  62. package/ai/reference/bf-avatar-size.md +27 -0
  63. package/ai/reference/bf-avatar-variant.md +28 -0
  64. package/ai/reference/bf-back-at-root.md +28 -0
  65. package/ai/reference/bf-back-button-service.md +40 -0
  66. package/ai/reference/bf-badge-variant.md +29 -0
  67. package/ai/reference/bf-button-size.md +29 -0
  68. package/ai/reference/bf-button-type.md +28 -0
  69. package/ai/reference/bf-button-variant.md +29 -0
  70. package/ai/reference/bf-card-padding.md +26 -0
  71. package/ai/reference/bf-card-variant.md +28 -0
  72. package/ai/reference/bf-chip-group-mode.md +27 -0
  73. package/ai/reference/bf-chip-variant.md +26 -0
  74. package/ai/reference/bf-compare-with.md +24 -0
  75. package/ai/reference/bf-component-overlay-ref.md +33 -0
  76. package/ai/reference/bf-confirm-button-role.md +26 -0
  77. package/ai/reference/bf-confirm-button.md +27 -0
  78. package/ai/reference/bf-confirm-options.md +31 -0
  79. package/ai/reference/bf-confirm-size.md +26 -0
  80. package/ai/reference/bf-content-scroll-event.md +21 -0
  81. package/ai/reference/bf-defaults-options.md +32 -0
  82. package/ai/reference/bf-defaults.md +28 -0
  83. package/ai/reference/bf-desktop-toast-config.md +28 -0
  84. package/ai/reference/bf-desktop-toast-harness.md +33 -0
  85. package/ai/reference/bf-desktop-toast-options.md +28 -0
  86. package/ai/reference/bf-desktop-toast-position.md +28 -0
  87. package/ai/reference/bf-desktop-toast-service.md +42 -0
  88. package/ai/reference/bf-dialog-config.md +44 -0
  89. package/ai/reference/bf-dialog-harness.md +52 -0
  90. package/ai/reference/bf-dialog-ref.md +44 -0
  91. package/ai/reference/bf-dialog-role.md +26 -0
  92. package/ai/reference/bf-dialog-service.md +55 -0
  93. package/ai/reference/bf-dialog-size.md +31 -0
  94. package/ai/reference/bf-dialog-template-context.md +32 -0
  95. package/ai/reference/bf-empty-state-heading-level.md +26 -0
  96. package/ai/reference/bf-enter-key-hint.md +31 -0
  97. package/ai/reference/bf-field-control-class.md +32 -0
  98. package/ai/reference/bf-field-control-state.md +28 -0
  99. package/ai/reference/bf-field-size.md +29 -0
  100. package/ai/reference/bf-haptics-impact-style.md +27 -0
  101. package/ai/reference/bf-haptics-notification-type.md +27 -0
  102. package/ai/reference/bf-haptics-service.md +41 -0
  103. package/ai/reference/bf-harness-filters.md +29 -0
  104. package/ai/reference/bf-horizontal-scroll-directive.md +129 -0
  105. package/ai/reference/bf-icon-button-variant.md +28 -0
  106. package/ai/reference/bf-icon-size.md +27 -0
  107. package/ai/reference/bf-input-autocapitalize.md +36 -0
  108. package/ai/reference/bf-input-enter-key-hint.md +38 -0
  109. package/ai/reference/bf-input-input-mode.md +38 -0
  110. package/ai/reference/bf-input-mode.md +32 -0
  111. package/ai/reference/bf-input-type.md +35 -0
  112. package/ai/reference/bf-jsdom-shim-options.md +22 -0
  113. package/ai/reference/bf-keyboard-assist-behavior.md +26 -0
  114. package/ai/reference/bf-keyboard-assist-directive.md +185 -0
  115. package/ai/reference/bf-keyboard-phase.md +30 -0
  116. package/ai/reference/bf-keyboard-service.md +50 -0
  117. package/ai/reference/bf-labels-overrides.md +26 -0
  118. package/ai/reference/bf-labels.md +44 -0
  119. package/ai/reference/bf-menu-button-harness.md +40 -0
  120. package/ai/reference/bf-menu-button-variant.md +27 -0
  121. package/ai/reference/bf-menu-divider-directive.md +13 -0
  122. package/ai/reference/bf-menu-group-directive.md +14 -0
  123. package/ai/reference/bf-menu-harness.md +55 -0
  124. package/ai/reference/bf-menu-item-checkbox-directive.md +31 -0
  125. package/ai/reference/bf-menu-item-directive.md +31 -0
  126. package/ai/reference/bf-menu-item-harness.md +52 -0
  127. package/ai/reference/bf-menu-item-radio-directive.md +29 -0
  128. package/ai/reference/bf-menu-placement.md +29 -0
  129. package/ai/reference/bf-menu-trigger-directive.md +46 -0
  130. package/ai/reference/bf-modal-options.md +30 -0
  131. package/ai/reference/bf-modal-presentation.md +26 -0
  132. package/ai/reference/bf-modal-service.md +38 -0
  133. package/ai/reference/bf-nav-controller.md +59 -0
  134. package/ai/reference/bf-nav-direction.md +23 -0
  135. package/ai/reference/bf-nav-target.md +21 -0
  136. package/ai/reference/bf-number-input-mode.md +28 -0
  137. package/ai/reference/bf-number-input-step.md +25 -0
  138. package/ai/reference/bf-overlay-auto-focus.md +29 -0
  139. package/ai/reference/bf-overlay-controller.md +22 -0
  140. package/ai/reference/bf-overlay-host.md +36 -0
  141. package/ai/reference/bf-overlay-options.md +53 -0
  142. package/ai/reference/bf-overlay-position.md +30 -0
  143. package/ai/reference/bf-overlay-ref.md +53 -0
  144. package/ai/reference/bf-overlay-role.md +27 -0
  145. package/ai/reference/bf-overlay-service.md +53 -0
  146. package/ai/reference/bf-overlay-stack-options.md +24 -0
  147. package/ai/reference/bf-overlay-stack.md +81 -0
  148. package/ai/reference/bf-overlay-template-context.md +24 -0
  149. package/ai/reference/bf-overscroll-stretch-directive.md +163 -0
  150. package/ai/reference/bf-page-context.md +24 -0
  151. package/ai/reference/bf-platform-service.md +53 -0
  152. package/ai/reference/bf-platform.md +28 -0
  153. package/ai/reference/bf-progress-size.md +26 -0
  154. package/ai/reference/bf-progress-tone.md +28 -0
  155. package/ai/reference/bf-radio-group-harness.md +49 -0
  156. package/ai/reference/bf-radio-group-orientation.md +26 -0
  157. package/ai/reference/bf-radio-option.md +30 -0
  158. package/ai/reference/bf-refresher-refresh-event.md +22 -0
  159. package/ai/reference/bf-segment-option.md +29 -0
  160. package/ai/reference/bf-segmented-harness.md +48 -0
  161. package/ai/reference/bf-segmented-size.md +29 -0
  162. package/ai/reference/bf-select-harness.md +70 -0
  163. package/ai/reference/bf-select-option.md +29 -0
  164. package/ai/reference/bf-sheet-auto-focus.md +29 -0
  165. package/ai/reference/bf-sheet-options.md +32 -0
  166. package/ai/reference/bf-sheet-ref.md +45 -0
  167. package/ai/reference/bf-sheet-service.md +34 -0
  168. package/ai/reference/bf-shell-config-mode.md +28 -0
  169. package/ai/reference/bf-shell-config.md +38 -0
  170. package/ai/reference/bf-shell-dynamic-type-limit.md +21 -0
  171. package/ai/reference/bf-shell-dynamic-type.md +25 -0
  172. package/ai/reference/bf-shell-mode.md +28 -0
  173. package/ai/reference/bf-shell-testing-options.md +26 -0
  174. package/ai/reference/bf-size.md +45 -0
  175. package/ai/reference/bf-spinner-size.md +27 -0
  176. package/ai/reference/bf-stack-change.md +22 -0
  177. package/ai/reference/bf-stack-reuse-strategy.md +32 -0
  178. package/ai/reference/bf-stack-transition-event.md +26 -0
  179. package/ai/reference/bf-stack-transition.md +26 -0
  180. package/ai/reference/bf-stacked-overlay.md +23 -0
  181. package/ai/reference/bf-system-bars-style.md +38 -0
  182. package/ai/reference/bf-tab-bar-controller.md +51 -0
  183. package/ai/reference/bf-tab-bar-host.md +52 -0
  184. package/ai/reference/bf-tab-context.md +32 -0
  185. package/ai/reference/bf-tab-links.md +37 -0
  186. package/ai/reference/bf-testing-options.md +27 -0
  187. package/ai/reference/bf-text-scale-service.md +35 -0
  188. package/ai/reference/bf-theme.md +27 -0
  189. package/ai/reference/bf-toast-action.md +25 -0
  190. package/ai/reference/bf-toast-controller.md +17 -0
  191. package/ai/reference/bf-toast-dismiss-reason.md +29 -0
  192. package/ai/reference/bf-toast-options.md +29 -0
  193. package/ai/reference/bf-toast-position.md +26 -0
  194. package/ai/reference/bf-toast-ref.md +41 -0
  195. package/ai/reference/bf-toast-service.md +39 -0
  196. package/ai/reference/bf-toggle-label-position.md +26 -0
  197. package/ai/reference/bf-transition-kind.md +28 -0
  198. package/ai/reference/bf-validation-message.md +31 -0
  199. package/ai/reference/bf-validation-messages.md +33 -0
  200. package/ai/reference/bf-view-event.md +28 -0
  201. package/ai/reference/bf-view-lifecycle.md +41 -0
  202. package/ai/reference/bf-view-state.md +28 -0
  203. package/ai/reference/bf_default_labels.md +21 -0
  204. package/ai/reference/bf_default_values.md +21 -0
  205. package/ai/reference/bf_defaults.md +21 -0
  206. package/ai/reference/bf_desktop_toast_defaults.md +21 -0
  207. package/ai/reference/bf_dialog_data.md +17 -0
  208. package/ai/reference/bf_labels.md +21 -0
  209. package/ai/reference/bf_overlay_data.md +19 -0
  210. package/ai/reference/bf_overlay_host.md +21 -0
  211. package/ai/reference/bf_sheet_default_snap_points.md +17 -0
  212. package/ai/reference/bf_shell_config.md +21 -0
  213. package/ai/reference/bf_shell_defaults.md +21 -0
  214. package/ai/reference/bf_tab_bar.md +21 -0
  215. package/ai/reference/bf_tab_bar_controller.md +21 -0
  216. package/ai/reference/bf_tab_context.md +21 -0
  217. package/ai/reference/bf_tab_links.md +21 -0
  218. package/ai/reference/bf_theme_storage.md +19 -0
  219. package/ai/reference/create-transition.md +36 -0
  220. package/ai/reference/duration_fast.md +17 -0
  221. package/ai/reference/duration_md.md +17 -0
  222. package/ai/reference/duration_overlay.md +17 -0
  223. package/ai/reference/duration_push.md +17 -0
  224. package/ai/reference/fade-down.md +26 -0
  225. package/ai/reference/fade-in.md +25 -0
  226. package/ai/reference/fade-out.md +25 -0
  227. package/ai/reference/fade-up.md +26 -0
  228. package/ai/reference/inject-shell-mode.md +23 -0
  229. package/ai/reference/install-bf-jsdom-shims.md +31 -0
  230. package/ai/reference/ios_duration.md +17 -0
  231. package/ai/reference/ios_easing.md +17 -0
  232. package/ai/reference/is-text-entry.md +25 -0
  233. package/ai/reference/max_complete_ms.md +17 -0
  234. package/ai/reference/md-transition.md +31 -0
  235. package/ai/reference/md_duration.md +17 -0
  236. package/ai/reference/md_easing.md +17 -0
  237. package/ai/reference/overlay_duration.md +21 -0
  238. package/ai/reference/overlay_easing.md +19 -0
  239. package/ai/reference/overlay_reduced_duration.md +17 -0
  240. package/ai/reference/pop-frames-at.md +25 -0
  241. package/ai/reference/prefers-reduced-motion.md +25 -0
  242. package/ai/reference/provide-bf-defaults.md +33 -0
  243. package/ai/reference/provide-bf-desktop-toast.md +28 -0
  244. package/ai/reference/provide-bf-labels.md +38 -0
  245. package/ai/reference/provide-bf-shell-testing.md +34 -0
  246. package/ai/reference/provide-bf-shell.md +41 -0
  247. package/ai/reference/provide-bf-testing.md +33 -0
  248. package/ai/reference/reduced-transition.md +28 -0
  249. package/ai/reference/reduced_duration.md +17 -0
  250. package/ai/reference/resolve-shell-mode.md +33 -0
  251. package/ai/reference/scale-in.md +25 -0
  252. package/ai/reference/settle-duration.md +25 -0
  253. package/ai/reference/settle-pop.md +33 -0
  254. package/ai/reference/settle_easing.md +17 -0
  255. package/ai/reference/should-complete-pop.md +26 -0
  256. package/ai/reference/slide-down.md +26 -0
  257. package/ai/reference/slide-up.md +26 -0
  258. package/ai/reference/with-bf-shell-routing.md +19 -0
  259. package/bin/bf-ui.js +81 -0
  260. package/fesm2022/bitforgehq-ui-icons.mjs +230 -0
  261. package/fesm2022/bitforgehq-ui-icons.mjs.map +1 -0
  262. package/fesm2022/bitforgehq-ui-mobile.mjs +5530 -0
  263. package/fesm2022/bitforgehq-ui-mobile.mjs.map +1 -0
  264. package/fesm2022/bitforgehq-ui-number-input.mjs +680 -0
  265. package/fesm2022/bitforgehq-ui-number-input.mjs.map +1 -0
  266. package/fesm2022/bitforgehq-ui-overlay.mjs +2675 -0
  267. package/fesm2022/bitforgehq-ui-overlay.mjs.map +1 -0
  268. package/fesm2022/bitforgehq-ui-testing.mjs +402 -0
  269. package/fesm2022/bitforgehq-ui-testing.mjs.map +1 -0
  270. package/fesm2022/bitforgehq-ui.mjs +7765 -0
  271. package/fesm2022/bitforgehq-ui.mjs.map +1 -0
  272. package/llms-full.txt +25394 -0
  273. package/llms.txt +329 -0
  274. package/package.json +94 -0
  275. package/theme.css +253 -0
  276. package/types/bitforgehq-ui-icons.d.ts +50 -0
  277. package/types/bitforgehq-ui-mobile.d.ts +2914 -0
  278. package/types/bitforgehq-ui-number-input.d.ts +282 -0
  279. package/types/bitforgehq-ui-overlay.d.ts +1514 -0
  280. package/types/bitforgehq-ui-testing.d.ts +495 -0
  281. package/types/bitforgehq-ui.d.ts +3499 -0
@@ -0,0 +1,286 @@
1
+ # bf-back-button
2
+
3
+ Header back button that pops the page stack or falls back to a default route
4
+
5
+ `BfBackButtonComponent` from `@bitforgehq/ui/mobile` · Navigation · since 0.2.0
6
+
7
+ ## Example
8
+
9
+ ```ts
10
+ import { Component, inject } from '@angular/core';
11
+ import { BfListComponent, BfListItemComponent } from '@bitforgehq/ui';
12
+ import {
13
+ BfContentComponent,
14
+ BfHeaderComponent,
15
+ BfNavController,
16
+ BfPageComponent,
17
+ } from '@bitforgehq/ui/mobile';
18
+
19
+ /**
20
+ * `bf-back-button` showcase root. The docs start on the pushed detail page
21
+ * (`showcase/back-button/detail`) with nothing under it, so its back button has nothing to pop and
22
+ * replaces the stack with its `defaultHref` — this page; from here, the detail page is pushed and
23
+ * its back button pops.
24
+ */
25
+ @Component({
26
+ selector: 'app-back-button-showcase',
27
+ imports: [
28
+ BfPageComponent,
29
+ BfHeaderComponent,
30
+ BfContentComponent,
31
+ BfListComponent,
32
+ BfListItemComponent,
33
+ ],
34
+ template: `
35
+ <bf-page data-showcase="back-button">
36
+ <bf-header title="Back button" [largeTitle]="false" />
37
+ <bf-content>
38
+ <div class="flex flex-col gap-4 p-4">
39
+ <p class="text-caption text-text-muted">
40
+ You arrived through the detail page's defaultHref. Open it again: now its back button
41
+ pops back here.
42
+ </p>
43
+ <bf-list [inset]="false">
44
+ <bf-list-item
45
+ title="Open the detail page"
46
+ [interactive]="true"
47
+ [chevron]="true"
48
+ (clicked)="open()"
49
+ />
50
+ </bf-list>
51
+ </div>
52
+ </bf-content>
53
+ </bf-page>
54
+ `,
55
+ })
56
+ export class BackButtonShowcasePage {
57
+ private readonly nav = inject(BfNavController);
58
+
59
+ open(): void {
60
+ void this.nav.forward('/showcase/back-button/detail');
61
+ }
62
+ }
63
+ ```
64
+
65
+ ## Overview
66
+
67
+ Back button for a `bf-header` start slot (or anywhere else in a page): pops the shown stack,
68
+ or replaces it with `defaultHref` when there's nothing to pop back to, e.g. a deep link that
69
+ landed on this page directly. Hidden when neither applies. Its anatomy follows the shell mode:
70
+ iOS, a chevron with the `label` as text; Material, a bare arrow icon button named by `label`.
71
+
72
+ The back control for a pushed page: pops the stack when there's a page to go back to, or replaces
73
+ it with `defaultHref` when there isn't — the case where a deep link or a tab reset landed on this
74
+ page directly, with nothing pushed underneath it. It hides itself entirely when neither applies,
75
+ and its anatomy follows the shell mode (`provideBfShell({ mode })`, the platform's for `'auto'`):
76
+
77
+ - **iOS**: a 24 px chevron-left and the `label` as text, in `primary`, as one 44 px tall control —
78
+ the UIKit back button.
79
+ - **Material**: a bare 24 px arrow-left `bf-icon-button` (`text` variant); the `label` is its
80
+ accessible name, never shown.
81
+
82
+ ## When to use
83
+
84
+ Use `bf-back-button` in the `start` slot of a pushed page's [bf-header](https://bitforge-ui.web.app/components/header) in the Capacitor shell. Use the browser's own back button and a breadcrumb instead on a desktop web page, and a [bf-button](https://bitforge-ui.web.app/components/button) link (`a[bfButton]`) for a named way back.
85
+
86
+ ## Basic usage
87
+
88
+ Put it in a `bf-header`'s `start` slot:
89
+
90
+ ```ts
91
+ import { Component } from '@angular/core';
92
+ import { BfBackButtonComponent, BfHeaderComponent } from '@bitforgehq/ui/mobile';
93
+
94
+ /**
95
+ * A back button in a detail page's header.
96
+ *
97
+ * It pops the stack, and hides itself on a page with nothing to go back to.
98
+ *
99
+ * @preview none
100
+ */
101
+ @Component({
102
+ selector: 'app-example-back-button-basic',
103
+ imports: [BfBackButtonComponent, BfHeaderComponent],
104
+ template: `
105
+ <bf-header title="Task" [largeTitle]="false">
106
+ <bf-back-button bfSlot="start" />
107
+ </bf-header>
108
+ `,
109
+ })
110
+ export class BackButtonBasicExampleComponent {}
111
+ ```
112
+
113
+ ## Default destination
114
+
115
+ Set `defaultHref` for pages that can be entered without a page underneath them, such as a
116
+ notification deep link:
117
+
118
+ ```ts
119
+ import { Component } from '@angular/core';
120
+ import { BfBackButtonComponent, BfHeaderComponent } from '@bitforgehq/ui/mobile';
121
+
122
+ /**
123
+ * A back button with a default destination.
124
+ *
125
+ * On a page opened directly (a deep link), it shows and goes to `defaultHref`.
126
+ *
127
+ * @preview none
128
+ */
129
+ @Component({
130
+ selector: 'app-example-back-button-default-href',
131
+ imports: [BfBackButtonComponent, BfHeaderComponent],
132
+ template: `
133
+ <bf-header title="Task" [largeTitle]="false">
134
+ <bf-back-button bfSlot="start" defaultHref="/tabs/today" />
135
+ </bf-header>
136
+ `,
137
+ })
138
+ export class BackButtonDefaultHrefExampleComponent {}
139
+ ```
140
+
141
+ With `defaultHref` set, the button is visible even at the bottom of the stack; clicking it calls
142
+ `nav.root(defaultHref)`, replacing the whole stack with that one page.
143
+
144
+ ## Label
145
+
146
+ Without a `label` the button reads `provideBfLabels()`'s `back` ("Back"), so translate it once
147
+ app-wide (`provideBfLabels({ back: 'Zurück' })`); pass the previous page's name when it is short (UIKit shows the previous title and falls back to "Back" when it does not fit). In iOS
148
+ mode it is the visible text beside the chevron (truncated past 192 px); in Material mode it only
149
+ names the arrow button for assistive tech.
150
+
151
+ ```ts
152
+ import { Component } from '@angular/core';
153
+ import { BfBackButtonComponent, BfHeaderComponent } from '@bitforgehq/ui/mobile';
154
+
155
+ /**
156
+ * A back button labelled with the previous page.
157
+ *
158
+ * @preview none
159
+ */
160
+ @Component({
161
+ selector: 'app-example-back-button-label',
162
+ imports: [BfBackButtonComponent, BfHeaderComponent],
163
+ template: `
164
+ <bf-header title="Atlas rebrand" [largeTitle]="false">
165
+ <bf-back-button bfSlot="start" label="Projects" />
166
+ </bf-header>
167
+ `,
168
+ })
169
+ export class BackButtonLabelExampleComponent {}
170
+ ```
171
+
172
+ ## Desktop
173
+
174
+ `bf-back-button` is part of the Capacitor shell (`provideBfShell()`). On a desktop web page the browser's back button and history already go back; add a breadcrumb or a named link instead. Inside the shell under a mouse, the iOS form darkens to `primary-strong` on hover and the Material form is a `text` icon button; both show the pointer cursor and a focus ring on keyboard focus only.
175
+
176
+ ## Theming
177
+
178
+ - iOS: `primary-text` text and chevron (`primary-strong` on hover), `text-heading` at regular weight,
179
+ the focus ring `ring` on a `rounded-field` outline, 44 px tall (`h-11`) and at least 44 px wide
180
+ (`min-w-hit`). When the bar is short of space (large text sizes, a long title and wide actions)
181
+ it shrinks inside the header's `start` slot: the text truncates and then disappears before the
182
+ chevron, down to the 44 px hit area, as UIKit drops the back title. It stays the button's name.
183
+ - Material: the `text` variant of `bf-icon-button`: `text-muted` at rest, `surface-muted` /
184
+ `text` on hover, no background otherwise; the 44 px hit area and focus ring come from
185
+ `bf-icon-button` as well.
186
+
187
+ ## Accessibility
188
+
189
+ Both modes render a native `<button>` with a 44 px minimum hit area; the glyph is decorative
190
+ (`aria-hidden`). In iOS mode the visible `label` text is the button's name; in Material mode
191
+ `label` (else the `back` label, `"Back"`) becomes the icon button's `aria-label`, since the arrow alone gives
192
+ assistive tech no name. It never moves focus itself: after a pop
193
+ `bf-stack-outlet` returns focus to the element that had it on the page below when this page was
194
+ pushed (or to that page's frame), and after the `nav.root(defaultHref)` replacement it focuses the
195
+ new page's title (`data-bf-page-title`, the `bf-header` `h1`).
196
+
197
+ ### Keyboard
198
+
199
+ | Key | Action |
200
+ | ----------------------------------- | ---------------------------------------------------------------------------- |
201
+ | <kbd>Tab</kbd> | Moves focus to the button |
202
+ | <kbd>Enter</kbd> / <kbd>Space</kbd> | Pops the stack, or replaces it with `defaultHref` when nothing is underneath |
203
+
204
+ ## Inputs
205
+
206
+ | Name | Type | Default | Description |
207
+ | ------------- | -------- | ------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
208
+ | `defaultHref` | `string` | `''` | Destination `nav.root()` navigates to when there's no page to pop back to. |
209
+ | `label` | `string` | `''` | The previous page's name: the text beside the chevron in iOS mode, the arrow button's accessible name in Material mode. Empty falls back to `provideBfLabels()`'s `back` ("Back"). |
210
+
211
+ ## Methods
212
+
213
+ ### `go(): void`
214
+
215
+ Goes back one page, or to `defaultHref` when the stack has none to go back to.
216
+
217
+ ## Notes
218
+
219
+ ### Do
220
+
221
+ - Translate `label`, or set it to the previous page's short name — in iOS mode users read it.
222
+ - Set `defaultHref` on any page that can be the first thing a user sees (deep links, tab roots).
223
+
224
+ ### Don't
225
+
226
+ - Don't pass a long sentence as `label`: iOS truncates it, and the header's centred title gives up
227
+ the same width on the other side.
228
+ - Don't wire `(clicked)` yourself; `go()` already picks `nav.back()` or `nav.root(defaultHref)`
229
+ for you.
230
+ - Don't render it on a page that is always at the bottom of a tab's stack without a `defaultHref`
231
+ — it will simply stay hidden.
232
+
233
+ ## Migration notes
234
+
235
+ ### 0.3.0
236
+
237
+ **Behaviour:** `label` defaults to `''` and falls back to `provideBfLabels()`'s `back` ("Back"),
238
+ both as the iOS text and as the Material button's name.
239
+
240
+ **Behaviour:** the iOS label and chevron use `primary-text` (was `primary`); hover stays
241
+ `primary-strong`.
242
+
243
+ JSDoc of `back-button.component.ts` for the API reference: docs for the undocumented members and
244
+ methods. No behaviour change.
245
+
246
+ JSDoc of `back-button.service.ts` for the API reference: `@summary`/`@since` on the exported
247
+ symbols; `@param` docs. No behaviour change.
248
+
249
+ **Behaviour:** large text (F-051): the host (`min-w-0 shrink`) and the iOS button (`shrink`, no
250
+ longer `shrink-0`) may shrink inside the header's `start` slot, down to the 44 px hit area: the
251
+ text truncates and then disappears before the chevron, as UIKit drops the back title when space is
252
+ short. The text stays the button's name. It carries `data-bf-back-text`, the part `bf-header`'s iOS
253
+ start-slot cap lets give way.
254
+
255
+ ### 0.3.0
256
+
257
+ **Behaviour:** when no handler claims the back press (every shown stack at its first page),
258
+ `BfBackButtonService` calls `App.minimizeApp()`, so the app moves to the background and a
259
+ relaunch resumes warm; with `provideBfShell({ backAtRoot: 'exit' })` it calls `App.exitApp()` as
260
+ before. It reads `BF_SHELL_CONFIG` (optional; `'minimize'` without it), and a failure goes to
261
+ `console.error`. See Migration 34.
262
+
263
+ ### 0.2.0
264
+
265
+ New `bf-back-button`: a `bf-icon-button` (`text` variant, chevron-left) that pops the primary
266
+ stack via `BfNavController.back()`, or replaces it with `defaultHref` via `nav.root()` when there
267
+ is nothing to pop back to (a deep link landing directly on the page). Visible when
268
+ `nav.canGoBack()` or `defaultHref` is set, hidden otherwise. `label` (default `"Back"`) is the
269
+ button's accessible name.
270
+
271
+ Changed: the anatomy follows the shell mode (resolved like `bf-stack-outlet`). iOS: a native
272
+ button with a 24 px chevron-left and `label` as visible text (`text-heading`, regular) in
273
+ `primary`, one 44 px tall control (`h-11 min-w-hit`, text truncated past 192 px), named by its
274
+ text. Material: a bare 24 px arrow-left `bf-icon-button` (`text` variant) with `label` as its
275
+ `aria-label`. `defaultHref` works the same in both.
276
+
277
+ New `BfBackButtonService` (`providedIn: 'root'`, registered and started at bootstrap by
278
+ `provideBfShell()`'s environment initializer, together with `BfPlatformService`): the hardware
279
+ back button queue. `register(priority, handler)` returns an unregister function; `dispatch()`
280
+ (public, for tests and 2c's overlays) runs the registered handlers from highest to lowest priority
281
+ until one returns true (on equal priority the newest registration runs first, so stacked overlays
282
+ close top-down), then falls back to `App.exitApp()`; `BfNavController` registers the priority-0
283
+ handler that pops the deepest active stack while any stack has more than one page. On native Android it subscribes to
284
+ `App.addListener('backButton', …)` via `await import('@capacitor/app')` in a try/catch (never a
285
+ static import, so a web or iOS bundle never loads the plugin); nothing is registered on iOS or
286
+ web, where `Escape` closes overlays instead.
@@ -0,0 +1,171 @@
1
+ # bf-badge
2
+
3
+ Small status label in semantic tones, or a compact numeric pill for counts
4
+
5
+ `BfBadgeComponent` from `@bitforgehq/ui` · Data display · since 0.1.0
6
+
7
+ ## Example
8
+
9
+ ```ts
10
+ import { Component } from '@angular/core';
11
+ import { BfBadgeComponent } from '@bitforgehq/ui';
12
+
13
+ /**
14
+ * The bf-badge overview.
15
+ *
16
+ * Live demo of `bf-badge`: four status labels and a count pill.
17
+ */
18
+ @Component({
19
+ selector: 'app-example-badge-overview',
20
+ imports: [BfBadgeComponent],
21
+ template: `
22
+ <div class="flex flex-wrap items-center gap-3">
23
+ <bf-badge variant="success">On track</bf-badge>
24
+ <bf-badge variant="warning">At risk</bf-badge>
25
+ <bf-badge variant="danger">Blocked</bf-badge>
26
+ <bf-badge>Draft</bf-badge>
27
+ <bf-badge [count]="3" />
28
+ </div>
29
+ `,
30
+ })
31
+ export class BadgeOverviewExampleComponent {}
32
+ ```
33
+
34
+ ## Overview
35
+
36
+ Status label ("On track", "At risk") or, with `count`, a compact numeric pill for unread counts.
37
+
38
+ Badges label a status ("On track", "At risk") or, as a count pill, show how many items are waiting. They are read-only; use a `bf-chip` for anything the user can toggle.
39
+
40
+ ## When to use
41
+
42
+ Use `bf-badge` for a read-only status or count next to what it describes: "At risk" on a project, "3" on an inbox row. Use [bf-chip](https://bitforge-ui.web.app/components/chip) instead when the user can toggle it, and [bf-alert](https://bitforge-ui.web.app/components/alert) when the status needs a sentence of explanation.
43
+
44
+ ## Status labels
45
+
46
+ The variant carries the meaning: `success`, `warning`, `danger`, `primary` or the default `neutral`.
47
+
48
+ ```ts
49
+ import { Component } from '@angular/core';
50
+ import { BfBadgeComponent } from '@bitforgehq/ui';
51
+
52
+ /** Status badges in the four tones. */
53
+ @Component({
54
+ selector: 'app-example-badge-status',
55
+ imports: [BfBadgeComponent],
56
+ template: `
57
+ <div class="flex flex-wrap items-center gap-2">
58
+ <bf-badge variant="success">On track</bf-badge>
59
+ <bf-badge variant="warning">At risk</bf-badge>
60
+ <bf-badge variant="danger">Blocked</bf-badge>
61
+ <bf-badge>Draft</bf-badge>
62
+ </div>
63
+ `,
64
+ })
65
+ export class BadgeStatusExampleComponent {}
66
+ ```
67
+
68
+ ## Count pill
69
+
70
+ Setting `count` switches to the compact primary pill. Values above 99 render as "99+"; zero renders as "0".
71
+
72
+ ```ts
73
+ import { Component, signal } from '@angular/core';
74
+ import { BfBadgeComponent, BfButtonComponent } from '@bitforgehq/ui';
75
+
76
+ /** A count pill that caps at 99+. */
77
+ @Component({
78
+ selector: 'app-example-badge-count',
79
+ imports: [BfBadgeComponent, BfButtonComponent],
80
+ template: `
81
+ <div class="flex items-center gap-3">
82
+ <span class="text-body">Inbox</span>
83
+ <bf-badge [count]="unread()" />
84
+ <bf-button variant="text" size="sm" (clicked)="unread.set(unread() + 50)">Add 50</bf-button>
85
+ </div>
86
+ `,
87
+ })
88
+ export class BadgeCountExampleComponent {
89
+ protected readonly unread = signal(3);
90
+ }
91
+ ```
92
+
93
+ ## Count label
94
+
95
+ A bare number means little to a screen reader. `countLabel` says what is counted: it renders visually hidden after the number, so the pill reads "99+ unread messages" while it still shows "99+". It is used only with `count`.
96
+
97
+ ```ts
98
+ import { Component } from '@angular/core';
99
+ import { BfBadgeComponent } from '@bitforgehq/ui';
100
+
101
+ /**
102
+ * A count pill that says what it counts.
103
+ *
104
+ * `countLabel` is read after the number ("99+ unread messages") without showing on screen.
105
+ */
106
+ @Component({
107
+ selector: 'app-example-badge-count-label',
108
+ imports: [BfBadgeComponent],
109
+ template: `
110
+ <div class="flex items-center gap-3">
111
+ <span class="text-body">Inbox</span>
112
+ <bf-badge [count]="120" countLabel="unread messages" />
113
+ </div>
114
+ `,
115
+ })
116
+ export class BadgeCountLabelExampleComponent {}
117
+ ```
118
+
119
+ ## Theming
120
+
121
+ Consumes tokens by variant, background then text:
122
+
123
+ - `neutral` (default): `neutral-soft` / `neutral`
124
+ - `primary`: `primary-soft` / `primary-strong`
125
+ - `success`: `success-soft` / `success`
126
+ - `warning`: `warning-soft` / `warning`
127
+ - `danger`: `danger-soft` / `danger`
128
+ - Count pill (`count` set): `primary` / `on-primary`, ignoring `variant`
129
+ - Shape (label and count pill): `rounded-control` (`--radius-control`, `9999px` by default).
130
+
131
+ ## Accessibility
132
+
133
+ A badge is a plain `<span>` with no role or ARIA attributes; its text is read as part of the surrounding content, so pair it with a label or context that says what it means rather than relying on color alone. A count pill with `countLabel` carries that context itself: a visually hidden (`sr-only`) span after the number, read as one phrase with it ("99+ unread messages").
134
+
135
+ ## Inputs
136
+
137
+ | Name | Type | Default | Description |
138
+ | ------------ | --------------------------------------------------------------------------------- | ----------- | ---------------------------------------------------------------------------------------------------------------------------------------------------- |
139
+ | `variant` | `BfBadgeVariant` (`'neutral' \| 'primary' \| 'success' \| 'warning' \| 'danger'`) | `'neutral'` | Tint for the label style. Ignored when `count` is set. |
140
+ | `count` | `number \| undefined` | `undefined` | Switches to the count pill; values above 99 render as "99+". |
141
+ | `countLabel` | `string` | `''` | What the count counts ("unread messages"), read by assistive tech after the number ("99+ unread messages"); visually hidden. Only used with `count`. |
142
+
143
+ ## Slots
144
+
145
+ - `default`: The badge text, shown when no `count` is set.
146
+
147
+ ## Notes
148
+
149
+ ### Do
150
+
151
+ - Keep labels to one or two words; badges are scanned, not read.
152
+ - Pair a count pill with a label or icon that says what is being counted, and set `countLabel` so the number is not read alone.
153
+
154
+ ### Don't
155
+
156
+ - Don't use a badge as a button; it has no interactive states.
157
+ - Don't invent new colors on it; pick the variant that matches the meaning.
158
+
159
+ ## Migration notes
160
+
161
+ ### 0.3.0
162
+
163
+ **Behaviour:** the label and the count pill use `rounded-control` (`--radius-control`, `9999px` by
164
+ default, so they render as before).
165
+
166
+ JSDoc of `badge.component.ts` for the API reference: `@summary`/`@since` on the exported symbols;
167
+ `@slot` docs for `default`. No behaviour change.
168
+
169
+ New `countLabel = input('')` (F-039): with `count` set, it renders visually hidden after the
170
+ number (`<span class="sr-only">`), so the pill reads "99+ unread messages". Ignored without
171
+ `count`.