@barocss/browser 0.0.3 → 0.5.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.
package/dist/index.d.ts CHANGED
@@ -1,5 +1,330 @@
1
- export * from './browser-runtime';
2
- export * from './change-detector';
3
- export * from './style-partition-manager';
4
- export * from './utils';
5
- export * from './baro-boot';
1
+ import { Config } from '@barocss/kit';
2
+ import { GenerateCssRulesResult } from '@barocss/kit';
3
+ import { IncrementalParser } from '@barocss/kit';
4
+
5
+ export declare function baroBoot({ loadingClassName, ...options }?: BaroBootOptions): void;
6
+
7
+ declare type BaroBootOptions = BrowserRuntimeOptions & {
8
+ loadingClassName?: string;
9
+ };
10
+
11
+ export declare const baroStart: typeof baroBoot;
12
+
13
+ export declare class BrowserRuntime {
14
+ private cache;
15
+ private rootCache;
16
+ private context;
17
+ private options;
18
+ private isDestroyed;
19
+ private existing;
20
+ private existingSheetCount;
21
+ private incrementalParser;
22
+ private changeDetector;
23
+ private stylePartitionManager;
24
+ private getCategory;
25
+ constructor(options?: BrowserRuntimeOptions);
26
+ /**
27
+ * Add debug logs (by level)
28
+ */
29
+ private debugLog;
30
+ private init;
31
+ private injectPreflightCSS;
32
+ private ensureCssVars;
33
+ private getInsertionPoint;
34
+ /**
35
+ * Dynamically add one or more class names and generate/insert CSS
36
+ */
37
+ addClass(classes: string | string[]): void;
38
+ /**
39
+ * Process classes
40
+ */
41
+ private processClasses;
42
+ /**
43
+ * Process classes using incremental parsing
44
+ */
45
+ private processClassesIncremental;
46
+ /**
47
+ * Public method to apply parser results, update internal caches, and inject CSS
48
+ */
49
+ applyParseResults(results: Array<GenerateCssRulesResult>, _opts?: {
50
+ isBrowser?: boolean;
51
+ }): void;
52
+ /** Class names defined by the page's own stylesheets (BaroCSS's sheets and cross-origin sheets excluded). */
53
+ getExistingClasses(): Set<string>;
54
+ /**
55
+ * MutationObserver instance method to automatically call addClass when class attributes change in DOM
56
+ */
57
+ observe(root?: HTMLElement, options?: {
58
+ scan?: boolean;
59
+ onReady?: () => void;
60
+ }): MutationObserver;
61
+ private normalizeClasses;
62
+ has(cls: string): boolean;
63
+ getCss(cls: string): string | undefined;
64
+ getAllCss(): string;
65
+ getClasses(): string[];
66
+ /**
67
+ * Get comprehensive cache statistics
68
+ */
69
+ getCacheStats(): {
70
+ runtime: {
71
+ cachedClasses: number;
72
+ rootCacheSize: number;
73
+ };
74
+ ast: {
75
+ size: number;
76
+ maxSize: number;
77
+ hitRate: number;
78
+ };
79
+ incremental: {
80
+ processedClasses: number;
81
+ pendingClasses: number;
82
+ cacheStats: {
83
+ ast: {
84
+ size: number;
85
+ maxSize: number;
86
+ hitRate: number;
87
+ };
88
+ css: {};
89
+ };
90
+ };
91
+ };
92
+ /**
93
+ * Clear all caches (useful for debugging or memory management)
94
+ */
95
+ clearCaches(): void;
96
+ reset(): void;
97
+ updateConfig(newConfig: Config): void;
98
+ removeClass(classes: string | string[]): void;
99
+ destroy(): void;
100
+ getStats(): {
101
+ cachedClasses: number;
102
+ styleElementId: string;
103
+ isDestroyed: boolean;
104
+ config: Config;
105
+ cacheStats: {
106
+ runtime: {
107
+ cachedClasses: number;
108
+ rootCacheSize: number;
109
+ };
110
+ ast: {
111
+ size: number;
112
+ maxSize: number;
113
+ hitRate: number;
114
+ };
115
+ incremental: {
116
+ processedClasses: number;
117
+ pendingClasses: number;
118
+ cacheStats: {
119
+ ast: {
120
+ size: number;
121
+ maxSize: number;
122
+ hitRate: number;
123
+ };
124
+ css: {};
125
+ };
126
+ };
127
+ };
128
+ };
129
+ }
130
+
131
+ export declare interface BrowserRuntimeOptions {
132
+ config?: Config;
133
+ styleId?: string;
134
+ insertionPoint?: 'head' | 'body' | HTMLElement;
135
+ maxRulesPerPartition?: number;
136
+ /**
137
+ * #210: skip classes the page's existing (non-BaroCSS, same-origin) stylesheets already define,
138
+ * so a built app plus the runtime injects only what the build is missing. Opt-in. A class counts
139
+ * as covered only when a rule's selector starts with it (e.g. `.p-4`, `.md\:p-4` inside @media,
140
+ * `.hover\:x:hover`), so a class seen only as a descendant (`.group:hover .x`) is not skipped.
141
+ * The index is rebuilt when `document.styleSheets.length` changes. A page class that leads a selector
142
+ * with the same name is treated as covered, and rules added later to an already-indexed sheet aren't seen.
143
+ */
144
+ skipExisting?: boolean;
145
+ }
146
+
147
+ /**
148
+ * Change detection system for DOM mutations
149
+ *
150
+ * ⚠️ BROWSER-ONLY: This class is designed for browser environments only.
151
+ * It uses MutationObserver and DOM APIs that are not available in Node.js.
152
+ *
153
+ * This class monitors DOM changes and automatically processes new CSS classes
154
+ * that are added to elements. It uses MutationObserver to detect:
155
+ * - Class attribute changes on existing elements
156
+ * - New elements being added to the DOM
157
+ * - Changes in child elements
158
+ *
159
+ * For server-side usage, use IncrementalParser directly with processClassesSync()
160
+ * or processClasses() methods.
161
+ */
162
+ export declare class ChangeDetector {
163
+ /** MutationObserver instance for DOM change detection */
164
+ private observer;
165
+ /** Reference to IncrementalParser for class processing */
166
+ private incrementalParser;
167
+ /** Reference to BrowserRuntime for CSS injection (optional) */
168
+ private BrowserRuntime?;
169
+ private getCategory;
170
+ /**
171
+ * Create a new ChangeDetector instance
172
+ *
173
+ * @param incrementalParser - IncrementalParser instance for class processing
174
+ * @param BrowserRuntime - Optional BrowserRuntime instance for CSS injection
175
+ */
176
+ constructor(incrementalParser: IncrementalParser, BrowserRuntime?: BrowserRuntime, getCategory?: (cls: string) => string | undefined);
177
+ setParser(parser: IncrementalParser): void;
178
+ /**
179
+ * Starts observing DOM changes for new CSS classes
180
+ *
181
+ * This method sets up a MutationObserver that monitors:
182
+ * - Attribute changes (specifically class attribute modifications)
183
+ * - Child list changes (new elements being added)
184
+ * - Subtree changes (changes in descendant elements)
185
+ *
186
+ * The observer automatically processes any new classes it discovers
187
+ * by adding them to the IncrementalParser's pending queue.
188
+ *
189
+ * @param root - The root element to observe (defaults to document.body)
190
+ * @param options - Configuration options including initial scan and onReady callback
191
+ * @returns The MutationObserver instance for external control
192
+ */
193
+ observe(root?: HTMLElement, options?: {
194
+ scan?: boolean;
195
+ onReady?: () => void;
196
+ }): MutationObserver;
197
+ /**
198
+ * Scan existing classes in the DOM and process them
199
+ */
200
+ private scanExistingClasses;
201
+ /**
202
+ * Processes an individual element and extracts new classes
203
+ *
204
+ * This method is called for each element discovered during DOM mutations.
205
+ * It:
206
+ * - Extracts all class names from the element's className
207
+ * - Filters out already processed classes
208
+ * - Adds new classes to the collection for batch processing
209
+ *
210
+ * @param element - The HTML element to process
211
+ * @param newClasses - Set to collect newly discovered class names
212
+ */
213
+ private processElement;
214
+ /**
215
+ * Stops observing DOM changes and cleans up resources
216
+ *
217
+ * This method disconnects the MutationObserver and clears the
218
+ * observer reference to prevent memory leaks and allow the
219
+ * ChangeDetector to be properly garbage collected.
220
+ */
221
+ disconnect(): void;
222
+ }
223
+
224
+ /** Collect literal className tokens from a json-render Spec's flat elements map. */
225
+ export declare function collectJsonRenderClassNames(spec: unknown): string[];
226
+
227
+ /**
228
+ * Returns the shared runtime, creating it on first use. If a live runtime
229
+ * already exists and `options.config` is a different config object, it is
230
+ * applied via `updateConfig` (which replaces the whole config), so an early
231
+ * `getRuntime()` never makes a later `baroStart({ config })` lose its config.
232
+ */
233
+ export declare function getRuntime(options?: BrowserRuntimeOptions): BrowserRuntime;
234
+
235
+ /** Tailwind 4 layer order, declared by BaroCSS's first <style> in <head>. */
236
+ export declare const LAYER_ORDER = "@layer theme, base, components, utilities;";
237
+
238
+ export declare function normalizeClassName(className: any): string;
239
+
240
+ export declare function normalizeClassNameList(className: any): string[];
241
+
242
+ /** Submit literal classes synchronously before UI mount; the caller validates class support. */
243
+ export declare function preloadJsonRenderClasses(spec: unknown, runtime: Pick<BrowserRuntime, 'addClass'>): void;
244
+
245
+ /**
246
+ * Tailwind-compatible cascade order for runtime-inserted rules (#254).
247
+ *
248
+ * The runtime discovers classes in DOM order, so without sorting `lg:px-8`
249
+ * seen before `sm:px-6` would land earlier and lose at >= 1024px. Each rule
250
+ * gets a sort key derived from its leading `@media` / `@container` preludes:
251
+ *
252
+ * 0 base, state media (hover), motion/contrast, unknown
253
+ * 1 max-* breakpoints (larger width first)
254
+ * 2 min-* breakpoints (smaller width first)
255
+ * 3 @max-* container queries (larger width first)
256
+ * 4 @min-* container queries (smaller width first)
257
+ * 5 orientation, dark (prefers-color-scheme), print, forced-colors
258
+ *
259
+ * Nested at-rules (e.g. `sm:dark:`) contribute one key pair per level, so
260
+ * `sm:` < `sm:dark:` < `md:`. Equal keys keep discovery order.
261
+ */
262
+ declare type RuleKey = number[];
263
+
264
+ export declare const shadcnTheme: {
265
+ colors: Record<string, string>;
266
+ borderRadius: Record<string, string>;
267
+ };
268
+
269
+ export declare interface StylePartition {
270
+ id: string;
271
+ styles: string[];
272
+ styleElement: HTMLStyleElement;
273
+ /** Sort keys parallel to `styles` / the sheet's cssRules (#254). */
274
+ keys?: RuleKey[];
275
+ }
276
+
277
+ export declare class StylePartitionManager {
278
+ /**
279
+ * Insert `rule` at its Tailwind variant position within `partition` (#254):
280
+ * one insertRule at a binary-searched index, no sheet rewrite.
281
+ */
282
+ private insertSorted;
283
+ private partitions;
284
+ private categoryPartitions;
285
+ private partitionCounter;
286
+ private maxRulesPerPartition;
287
+ private insertionPoint;
288
+ private classToPartitionMap;
289
+ private classToCategoryPartitionMap;
290
+ private styleIdPrefix;
291
+ private getCategory;
292
+ constructor(insertionPoint: HTMLElement, maxRulesPerPartition?: number, styleIdPrefix?: string, getCategory?: (cls: string) => string | undefined);
293
+ private initializeDefaultPartition;
294
+ private createNewCategoryPartition;
295
+ private createNewPartition;
296
+ hasRule(rule: string): boolean;
297
+ hasCategoryRule(rule: string, category: string): boolean;
298
+ setRuleCache(rule: string, partitionIndex: number): void;
299
+ setCategoryRuleCache(rule: string, category: string): void;
300
+ get currentPartition(): StylePartition;
301
+ getCategoryPartition(category: string): StylePartition | undefined;
302
+ hasDetachedPartitions(): boolean;
303
+ /**
304
+ * Escape CSS rule text
305
+ * - Properly escape special characters
306
+ * - Prevent CSS syntax errors
307
+ */
308
+ private escapeCssRule;
309
+ addRule(rule: string): boolean;
310
+ addCategoryRule(rule: string, category: string): boolean;
311
+ addRootRules(rules: string[]): {
312
+ success: number;
313
+ failed: number;
314
+ };
315
+ addRules(rules: GenerateCssRulesResult[]): {
316
+ success: number;
317
+ failed: number;
318
+ };
319
+ /**
320
+ * 특정 규칙이 어느 파티션에 있는지 찾기
321
+ */
322
+ findRulePartition(rule: string): StylePartition | null;
323
+ updateRuleContent(category: string, ruleContent: string, atDocumentStart?: boolean): void;
324
+ /**
325
+ * 모든 파티션 정리
326
+ */
327
+ cleanup(): void;
328
+ }
329
+
330
+ export { }