Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
20 commits
Select commit Hold shift + click to select a range
c0ab8f4
feat(tw): add Tailwind CSS v4 module with components, services, binde…
JumpLink Apr 2, 2026
63e09ee
chore(deps): upgrade devDependencies across all packages
JumpLink Apr 13, 2026
cd1dd7d
fix(jsx): skip __self and __source dev props in renderElement
JumpLink Apr 13, 2026
f375698
docs(tw): add rv-* binder usage rules for rv-if/rv-each and rv-class
JumpLink Apr 14, 2026
3b05629
fix(tw,bs5,shopify-tda): comprehensive component binding and behavior…
JumpLink Apr 14, 2026
4dceabb
feat(demos): add tw-interactive demo and extend existing tw demos
JumpLink Apr 14, 2026
65b1d4d
fix(demos): use rel=stylesheet instead of rel=scss for main.scss links
JumpLink Apr 14, 2026
c9a451c
chore: update yarn.lock for tw-interactive demo workspace
JumpLink Apr 14, 2026
6cbe54a
refactor(demos): use @ribajs/tw package imports instead of relative p…
JumpLink Apr 14, 2026
fc2533a
fix(fuse): remove unsupported generic type argument on Fuse.search()
JumpLink Apr 14, 2026
52becde
fix(tw): move @source directives into utilities.css for automatic sca…
JumpLink Apr 14, 2026
78e8bf8
refactor: extract framework-agnostic tw parts to extras + router
JumpLink Apr 14, 2026
3072bcb
fix(tw): close listener leaks in services + tw-form
JumpLink Apr 14, 2026
df7e7b3
fix(tw): reactive rv-each updates in tw-rating and tw-pagination
JumpLink Apr 14, 2026
64d6f7f
refactor(tw): rename tw-tooltip-component -> tw-tooltip
JumpLink Apr 14, 2026
987146f
refactor(tw): extract AbstractToggleBinder + syncPassthroughControls …
JumpLink Apr 14, 2026
aafc5c3
refactor(tw): template a11y/style cleanups and computed tw-card classes
JumpLink Apr 14, 2026
8072032
fix(extras): exclude *.spec.ts from typecheck
JumpLink Apr 14, 2026
233e110
feat(tw-theme): extend demo; fix theme-aware sidebar surface
JumpLink Apr 15, 2026
d2152bb
style: apply yarn format across tw package and demos
JumpLink Apr 15, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
The table of contents is too big for display.
Diff view
Diff view
  •  
  •  
  •  
57 changes: 57 additions & 0 deletions AGENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,63 @@ Priority: higher=first | Block binders (rv-if,rv-each-*) prevent child parsing |
rv-text|textContent | rv-html|innerHTML | rv-value|two-way input | rv-if|conditional block | rv-show|display toggle
rv-each-*|iterate arrays/objects | rv-on-*|event listeners | rv-class-*|toggle CSS class | rv-style-*|inline CSS
rv-checked,rv-disabled,rv-enabled|form states | rv-template|dynamic HTML+rebind | rv-assign|merge obj into model
rv-add-class|add class string to element | rv-remove-class|remove class string from element

### rv-class vs rv-add-class — NO rv-class BINDER EXISTS

There is **no `rv-class` binder** in Riba. Only these class-related binders exist:
- `rv-class-*` (star binder) — toggles a single CSS class based on a boolean: `rv-class-active="item.active"`
- `rv-add-class` — adds class(es) from a string value while **preserving** static classes from the `class` attribute
- `rv-remove-class` — removes a class string

If you write `rv-class="someClassString"`, it falls through to the **generic attribute binder** which does `setAttribute("class", value)` — this **overwrites** the entire `class` attribute, destroying all static Tailwind classes.

```html
<!-- BAD: rv-class overwrites static classes — bg-gray-200, rounded-full etc. are lost -->
<div class="rounded-full bg-gray-200" rv-class="sizeClass"></div>

<!-- GOOD: rv-add-class preserves static classes -->
<div class="rounded-full bg-gray-200" rv-add-class="sizeClass"></div>
```

### rv-if/rv-unless inside rv-each — KNOWN BUG

`rv-if`/`rv-unless` are block binders that remove/insert DOM nodes. Inside `rv-each-*` child views, they do not reactively update when the iterated object's properties change. The initial render works, but subsequent property mutations are ignored.

The problem is that `rv-if` removes the element it's placed on. When the rv-each child view tries to update, the element is gone.

**Two workarounds:**

**1. Use `rv-show`/`rv-hide` (preferred for simple cases)**
```html
<!-- BAD -->
<div rv-each-item="items">
<span rv-if="item.active">Active</span>
</div>

<!-- GOOD: rv-show toggles display:none, element stays in DOM -->
<div rv-each-item="items">
<span rv-show="item.active">Active</span>
</div>
```
`rv-unless` → use `rv-hide`. For toggling between two elements, use `rv-show` on one and `rv-hide` on the other. Also works: `rv-class-*` to toggle CSS classes.

**2. Wrap in a child element (when rv-if is needed)**
```html
<!-- BAD: rv-if on the rv-each element's direct content -->
<li rv-each-item="items">
<a rv-if="item.href" rv-href="item.href">Link</a>
</li>

<!-- GOOD: rv-if on a wrapper child — the wrapper gets removed but the li stays -->
<li rv-each-item="items">
<div rv-if="item.href">
<a rv-href="item.href">Link</a>
</div>
</li>
```

Duplicate `rv-class` attributes on the same element are also invalid (HTML drops the second). Use a single computed class string or separate `rv-class-*` toggles.

## Formatters

Expand Down
16 changes: 8 additions & 8 deletions demos/accessibility-gamepad/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -28,23 +28,23 @@
"@ribajs/tsconfig": "workspace:^",
"@ribajs/vite-config": "workspace:^",
"@types/jest": "^30.0.0",
"@typescript-eslint/eslint-plugin": "^8.57.2",
"@typescript-eslint/eslint-plugin": "^8.58.1",
"@typescript-eslint/experimental-utils": "^5.62.0",
"@typescript-eslint/parser": "^8.57.2",
"@typescript-eslint/parser": "^8.58.1",
"@yarnpkg/pnpify": "^4.1.6",
"eslint": "^10.1.0",
"eslint": "^10.2.0",
"eslint-config-prettier": "^10.1.8",
"eslint-plugin-prettier": "^5.5.5",
"jest": "^30.3.0",
"jest-extended": "^7.0.0",
"postcss": "^8.5.8",
"postcss": "^8.5.9",
"postcss-modules": "^6.0.1",
"postcss-preset-env": "^11.2.0",
"prettier": "^3.8.1",
"sass": "^1.98.0",
"postcss-preset-env": "^11.2.1",
"prettier": "^3.8.2",
"sass": "^1.99.0",
"serve": "^14.2.6",
"typescript": "6.0.2",
"vite": "^8.0.3"
"vite": "^8.0.8"
},
"dependencies": {
"@ribajs/accessibility": "workspace:^",
Expand Down
16 changes: 8 additions & 8 deletions demos/accessibility-keyboard/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -28,23 +28,23 @@
"@ribajs/tsconfig": "workspace:^",
"@ribajs/vite-config": "workspace:^",
"@types/jest": "^30.0.0",
"@typescript-eslint/eslint-plugin": "^8.57.2",
"@typescript-eslint/eslint-plugin": "^8.58.1",
"@typescript-eslint/experimental-utils": "^5.62.0",
"@typescript-eslint/parser": "^8.57.2",
"@typescript-eslint/parser": "^8.58.1",
"@yarnpkg/pnpify": "^4.1.6",
"eslint": "^10.1.0",
"eslint": "^10.2.0",
"eslint-config-prettier": "^10.1.8",
"eslint-plugin-prettier": "^5.5.5",
"jest": "^30.3.0",
"jest-extended": "^7.0.0",
"postcss": "^8.5.8",
"postcss": "^8.5.9",
"postcss-modules": "^6.0.1",
"postcss-preset-env": "^11.2.0",
"prettier": "^3.8.1",
"sass": "^1.98.0",
"postcss-preset-env": "^11.2.1",
"prettier": "^3.8.2",
"sass": "^1.99.0",
"serve": "^14.2.6",
"typescript": "6.0.2",
"vite": "^8.0.3"
"vite": "^8.0.8"
},
"dependencies": {
"@ribajs/accessibility": "workspace:^",
Expand Down
16 changes: 8 additions & 8 deletions demos/bs5-accordion/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -31,23 +31,23 @@
"@ribajs/tsconfig": "workspace:^",
"@ribajs/vite-config": "workspace:^",
"@types/jest": "^30.0.0",
"@typescript-eslint/eslint-plugin": "^8.57.2",
"@typescript-eslint/eslint-plugin": "^8.58.1",
"@typescript-eslint/experimental-utils": "^5.62.0",
"@typescript-eslint/parser": "^8.57.2",
"@typescript-eslint/parser": "^8.58.1",
"@yarnpkg/pnpify": "^4.1.6",
"eslint": "^10.1.0",
"eslint": "^10.2.0",
"eslint-config-prettier": "^10.1.8",
"eslint-plugin-prettier": "^5.5.5",
"jest": "^30.3.0",
"jest-extended": "^7.0.0",
"postcss": "^8.5.8",
"postcss": "^8.5.9",
"postcss-modules": "^6.0.1",
"postcss-preset-env": "^11.2.0",
"prettier": "^3.8.1",
"sass": "^1.98.0",
"postcss-preset-env": "^11.2.1",
"prettier": "^3.8.2",
"sass": "^1.99.0",
"serve": "^14.2.6",
"typescript": "6.0.2",
"vite": "^8.0.3"
"vite": "^8.0.8"
},
"dependencies": {
"@ribajs/bs5": "workspace:^",
Expand Down
16 changes: 8 additions & 8 deletions demos/bs5-dropdown/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -31,23 +31,23 @@
"@ribajs/tsconfig": "workspace:^",
"@ribajs/vite-config": "workspace:^",
"@types/jest": "^30.0.0",
"@typescript-eslint/eslint-plugin": "^8.57.2",
"@typescript-eslint/eslint-plugin": "^8.58.1",
"@typescript-eslint/experimental-utils": "^5.62.0",
"@typescript-eslint/parser": "^8.57.2",
"@typescript-eslint/parser": "^8.58.1",
"@yarnpkg/pnpify": "^4.1.6",
"eslint": "^10.1.0",
"eslint": "^10.2.0",
"eslint-config-prettier": "^10.1.8",
"eslint-plugin-prettier": "^5.5.5",
"jest": "^30.3.0",
"jest-extended": "^7.0.0",
"postcss": "^8.5.8",
"postcss": "^8.5.9",
"postcss-modules": "^6.0.1",
"postcss-preset-env": "^11.2.0",
"prettier": "^3.8.1",
"sass": "^1.98.0",
"postcss-preset-env": "^11.2.1",
"prettier": "^3.8.2",
"sass": "^1.99.0",
"serve": "^14.2.6",
"typescript": "6.0.2",
"vite": "^8.0.3"
"vite": "^8.0.8"
},
"dependencies": {
"@ribajs/bs5": "workspace:^",
Expand Down
16 changes: 8 additions & 8 deletions demos/bs5-form/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -31,23 +31,23 @@
"@ribajs/tsconfig": "workspace:^",
"@ribajs/vite-config": "workspace:^",
"@types/jest": "^30.0.0",
"@typescript-eslint/eslint-plugin": "^8.57.2",
"@typescript-eslint/eslint-plugin": "^8.58.1",
"@typescript-eslint/experimental-utils": "^5.62.0",
"@typescript-eslint/parser": "^8.57.2",
"@typescript-eslint/parser": "^8.58.1",
"@yarnpkg/pnpify": "^4.1.6",
"eslint": "^10.1.0",
"eslint": "^10.2.0",
"eslint-config-prettier": "^10.1.8",
"eslint-plugin-prettier": "^5.5.5",
"jest": "^30.3.0",
"jest-extended": "^7.0.0",
"postcss": "^8.5.8",
"postcss": "^8.5.9",
"postcss-modules": "^6.0.1",
"postcss-preset-env": "^11.2.0",
"prettier": "^3.8.1",
"sass": "^1.98.0",
"postcss-preset-env": "^11.2.1",
"prettier": "^3.8.2",
"sass": "^1.99.0",
"serve": "^14.2.6",
"typescript": "6.0.2",
"vite": "^8.0.3"
"vite": "^8.0.8"
},
"dependencies": {
"@ribajs/bs5": "workspace:^",
Expand Down
14 changes: 7 additions & 7 deletions demos/bs5-notifications/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -31,22 +31,22 @@
"@ribajs/tsconfig": "workspace:^",
"@ribajs/vite-config": "workspace:^",
"@types/jest": "^30.0.0",
"@typescript-eslint/eslint-plugin": "^8.57.2",
"@typescript-eslint/eslint-plugin": "^8.58.1",
"@typescript-eslint/experimental-utils": "^5.62.0",
"@typescript-eslint/parser": "^8.57.2",
"@typescript-eslint/parser": "^8.58.1",
"@yarnpkg/pnpify": "^4.1.6",
"eslint": "^10.1.0",
"eslint": "^10.2.0",
"eslint-config-prettier": "^10.1.8",
"eslint-plugin-prettier": "^5.5.5",
"jest": "^30.3.0",
"jest-extended": "^7.0.0",
"postcss-modules": "^6.0.1",
"postcss-preset-env": "^11.2.0",
"prettier": "^3.8.1",
"sass": "^1.98.0",
"postcss-preset-env": "^11.2.1",
"prettier": "^3.8.2",
"sass": "^1.99.0",
"serve": "^14.2.6",
"typescript": "6.0.2",
"vite": "^8.0.3"
"vite": "^8.0.8"
},
"dependencies": {
"@ribajs/bs5": "workspace:^",
Expand Down
2 changes: 1 addition & 1 deletion demos/bs5-notifications/src/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
<html>
<head>
<title>Bs5 Notifications Demo</title>
<link rel="scss" href="/./scss/main.scss">
<link rel="stylesheet" href="./scss/main.scss">
<meta name="viewport" content="width=device-width, initial-scale=1">
</head>
<body>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ <h2 class="mb-2">Toast from component</h2>
</div>

<div class="col-12">
<button rv-class="'btn btn-' | append fromComponent.contextualClass" rv-on-click="showToast" type="button">Trigger component toast</button>
<button rv-add-class="'btn btn-' | append fromComponent.contextualClass" rv-on-click="showToast" type="button">Trigger component toast</button>
</div>

</div>
Expand Down Expand Up @@ -171,7 +171,7 @@ <h2 class="mb-2">Other notifications</h2>
</div>

<div class="col-12">
<button rv-class="'btn btn-' | append fromComponent.contextualClass" rv-on-click="showModal" type="button">Trigger component modal</button>
<button rv-add-class="'btn btn-' | append fromComponent.contextualClass" rv-on-click="showModal" type="button">Trigger component modal</button>
</div>

</div>
Expand Down
16 changes: 8 additions & 8 deletions demos/bs5-photoswipe/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -33,23 +33,23 @@
"@ribajs/types": "workspace:^",
"@ribajs/vite-config": "workspace:^",
"@types/jest": "^30.0.0",
"@typescript-eslint/eslint-plugin": "^8.57.2",
"@typescript-eslint/eslint-plugin": "^8.58.1",
"@typescript-eslint/experimental-utils": "^5.62.0",
"@typescript-eslint/parser": "^8.57.2",
"@typescript-eslint/parser": "^8.58.1",
"@yarnpkg/pnpify": "^4.1.6",
"eslint": "^10.1.0",
"eslint": "^10.2.0",
"eslint-config-prettier": "^10.1.8",
"eslint-plugin-prettier": "^5.5.5",
"jest": "^30.3.0",
"jest-extended": "^7.0.0",
"postcss-modules": "^6.0.1",
"postcss-preset-env": "^11.2.0",
"prettier": "^3.8.1",
"sass": "^1.98.0",
"postcss-preset-env": "^11.2.1",
"prettier": "^3.8.2",
"sass": "^1.99.0",
"serve": "^14.2.6",
"ts-jest": "^29.4.6",
"ts-jest": "^29.4.9",
"typescript": "6.0.2",
"vite": "^8.0.3"
"vite": "^8.0.8"
},
"dependencies": {
"@ribajs/bs5": "workspace:^",
Expand Down
16 changes: 8 additions & 8 deletions demos/bs5-responsive-components/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -31,23 +31,23 @@
"@ribajs/tsconfig": "workspace:^",
"@ribajs/vite-config": "workspace:^",
"@types/jest": "^30.0.0",
"@typescript-eslint/eslint-plugin": "^8.57.2",
"@typescript-eslint/eslint-plugin": "^8.58.1",
"@typescript-eslint/experimental-utils": "^5.62.0",
"@typescript-eslint/parser": "^8.57.2",
"@typescript-eslint/parser": "^8.58.1",
"@yarnpkg/pnpify": "^4.1.6",
"eslint": "^10.1.0",
"eslint": "^10.2.0",
"eslint-config-prettier": "^10.1.8",
"eslint-plugin-prettier": "^5.5.5",
"jest": "^30.3.0",
"jest-extended": "^7.0.0",
"postcss": "^8.5.8",
"postcss": "^8.5.9",
"postcss-modules": "^6.0.1",
"postcss-preset-env": "^11.2.0",
"prettier": "^3.8.1",
"sass": "^1.98.0",
"postcss-preset-env": "^11.2.1",
"prettier": "^3.8.2",
"sass": "^1.99.0",
"serve": "^14.2.6",
"typescript": "6.0.2",
"vite": "^8.0.3"
"vite": "^8.0.8"
},
"dependencies": {
"@ribajs/bs5": "workspace:^",
Expand Down
14 changes: 7 additions & 7 deletions demos/bs5-slider/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -30,22 +30,22 @@
"@ribajs/tsconfig": "workspace:^",
"@ribajs/vite-config": "workspace:^",
"@types/jest": "^30.0.0",
"@typescript-eslint/eslint-plugin": "^8.57.2",
"@typescript-eslint/eslint-plugin": "^8.58.1",
"@typescript-eslint/experimental-utils": "^5.62.0",
"@typescript-eslint/parser": "^8.57.2",
"@typescript-eslint/parser": "^8.58.1",
"@yarnpkg/pnpify": "^4.1.6",
"eslint": "^10.1.0",
"eslint": "^10.2.0",
"eslint-config-prettier": "^10.1.8",
"eslint-plugin-prettier": "^5.5.5",
"jest": "^30.3.0",
"jest-extended": "^7.0.0",
"postcss-modules": "^6.0.1",
"postcss-preset-env": "^11.2.0",
"prettier": "^3.8.1",
"sass": "^1.98.0",
"postcss-preset-env": "^11.2.1",
"prettier": "^3.8.2",
"sass": "^1.99.0",
"serve": "^14.2.6",
"typescript": "6.0.2",
"vite": "^8.0.3"
"vite": "^8.0.8"
},
"dependencies": {
"@ribajs/bs5": "workspace:^",
Expand Down
2 changes: 1 addition & 1 deletion demos/bs5-slider/src/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@

<head>
<title>Bootstrap 5 Slider Demo</title>
<link rel="scss" href="/./scss/main.scss">
<link rel="stylesheet" href="./scss/main.scss">
<meta name="viewport" content="width=device-width, initial-scale=1">
</head>

Expand Down
Loading
Loading