(themeFile: string)
| 510 | } |
| 511 | |
| 512 | function scopeGeneratedThemeStateClasses(themeFile: string): string { |
| 513 | if ( |
| 514 | !themeFile.includes('return classes[memoKey] ?? { [semanticKey]: true }') || |
| 515 | // Both anchors must exist — rewriting the call site without injecting the |
| 516 | // helper would emit a theme that throws ReferenceError on every lookup. |
| 517 | !themeFile.includes('\n/**\n * These classes have already been merged') || |
| 518 | themeFile.includes('function stateScopedClasses') |
| 519 | ) { |
| 520 | return themeFile |
| 521 | } |
| 522 | const isTS = themeFile.includes("import type { FormKitNode }") |
| 523 | const helper = `function stateScopedClasses (node${ |
| 524 | isTS ? ': FormKitNode' : '' |
| 525 | }, sectionClasses${ |
| 526 | isTS ? ': Record<string, boolean>' : '' |
| 527 | })${isTS ? ': Record<string, boolean>' : ''} { |
| 528 | const invalid = node.context?.state.invalid |
| 529 | const errors = node.context?.state.errors |
| 530 | const shouldFilterInvalid = invalid === false |
| 531 | const shouldFilterErrors = errors === false |
| 532 | if (!shouldFilterInvalid && !shouldFilterErrors) return sectionClasses |
| 533 | const filteredClasses = { ...sectionClasses } |
| 534 | for (const className of Object.keys(filteredClasses)) { |
| 535 | if (shouldFilterInvalid && isStateClass(className, 'invalid')) { |
| 536 | filteredClasses[className] = false |
| 537 | } |
| 538 | if (shouldFilterErrors && isStateClass(className, 'errors')) { |
| 539 | filteredClasses[className] = false |
| 540 | } |
| 541 | } |
| 542 | return filteredClasses |
| 543 | } |
| 544 | |
| 545 | function isStateClass (className${isTS ? ': string' : ''}, state${ |
| 546 | isTS ? ': string' : '' |
| 547 | })${isTS ? ': boolean' : ''} { |
| 548 | return ( |
| 549 | className.includes('group-data-[' + state) || |
| 550 | className.includes('formkit-' + state) |
| 551 | ) |
| 552 | } |
| 553 | ` |
| 554 | const scopedTheme = themeFile |
| 555 | .replace( |
| 556 | 'return classes[memoKey] ?? { [semanticKey]: true }', |
| 557 | 'return stateScopedClasses(node, classes[memoKey] ?? { [semanticKey]: true })' |
| 558 | ) |
| 559 | .replace( |
| 560 | '\n/**\n * These classes have already been merged', |
| 561 | `\n${helper}\n/**\n * These classes have already been merged` |
| 562 | ) |
| 563 | return addThemeChecksum(scopedTheme) |
| 564 | } |
| 565 | |
| 566 | function parseVariables(variables?: string): Record<string, string> { |
| 567 | if (!variables) return {} |
no test coverage detected