{"_id":"@blankparticle/yoga-layout","_rev":"2-14992b4c19c441cc3f22c571ea66144a","name":"@blankparticle/yoga-layout","dist-tags":{"rc":"0.0.1-rc.1","latest":"0.0.1-rc.2"},"versions":{"0.0.1-rc.1":{"name":"@blankparticle/yoga-layout","version":"0.0.1-rc.1","author":{"name":"Meta Open Source and contributors"},"license":"MIT","_id":"@blankparticle/yoga-layout@0.0.1-rc.1","maintainers":[{"name":"blankparticle","email":"blankparticle@gmail.com"}],"homepage":"https://github.com/BlankParticle/yoga-layout-js#readme","bugs":{"url":"https://github.com/BlankParticle/yoga-layout-js/issues"},"dist":{"shasum":"b511babd71edf9f811cc30579e005fea3242acbc","tarball":"https://registry.npmjs.org/@blankparticle/yoga-layout/-/yoga-layout-0.0.1-rc.1.tgz","fileCount":74,"integrity":"sha512-od9TXwWDPwl4Jf0HQPkJiCSE84lEyBnTfd1M6ag13YXOeS4MH5n4xW34tGShwLDiQgHWwoEMQ5PW6sro3J1ToA==","signatures":[{"sig":"MEUCIQDcneXdIhdLpowSk7tcLo/OUgWRQnTcvaI1+YQ+uGv3+AIgQL0l+JzhfANJ0KpqPAZlRdqUfhGpJsIIyq6yDphCJ/4=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":522535},"main":"./dist/index.js","type":"module","types":"./dist/index.d.ts","engines":{"node":">=18"},"exports":{".":{"types":"./dist/index.d.ts","import":"./dist/index.js","default":"./dist/index.js"},"./load":{"types":"./dist/load.d.ts","import":"./dist/load.js","default":"./dist/load.js"},"./package.json":"./package.json"},"scripts":{"test":"vitest run","build":"vp run clean && tsc -p tsconfig.build.json","clean":"node -e \"require('node:fs').rmSync('dist', {recursive: true, force: true})\"","test:ink":"vp -C integration/ink run test","benchmark":"vite-node test/bin/compare-bench.ts","typecheck":"tsc -p tsconfig.json --noEmit","test:package":"node test/package/drop-in.mjs && tsc --ignoreConfig --noEmit --strict --skipLibCheck false --target ES2022 --module NodeNext --moduleResolution NodeNext test/package/type-smoke.ts","benchmark:ink":"vite-node test/bin/compare-ink-bench.ts","prepublishOnly":"vp run typecheck && vp run test && vp run build && vp run test:package","benchmark:engine":"vite-node test/bin/run-bench.ts test/Benchmarks/YGBenchmark.test.ts","test:differential":"vitest run test/differential"},"_npmUser":{"name":"blankparticle","email":"blankparticle@gmail.com"},"devEngines":{"packageManager":{"name":"npm","onFail":"download","version":"11.17.0"}},"repository":{"url":"git+https://github.com/BlankParticle/yoga-layout-js.git","type":"git"},"_npmVersion":"11.17.0","description":"A drop-in TypeScript implementation of the Yoga layout engine","directories":{},"sideEffects":false,"_nodeVersion":"24.19.0","publishConfig":{"access":"public"},"_hasShrinkwrap":false,"devDependencies":{"tsx":"^4.23.11","vite":"^8.2.1","react":"^19.2.8","vitest":"^4.1.10","vite-node":"^6.0.0","typescript":"^7.0.2","@types/node":"^26.1.2","yoga-layout-upstream":"npm:yoga-layout@3.2.1"},"_npmOperationalInternal":{"tmp":"tmp/yoga-layout_0.0.1-rc.1_1786207246399_0.6584164537402295","host":"s3://npm-registry-packages-npm-production"}},"0.0.1-rc.2":{"name":"@blankparticle/yoga-layout","version":"0.0.1-rc.2","description":"A drop-in TypeScript implementation of the Yoga layout engine","license":"MIT","author":"BlankParticle","type":"module","sideEffects":false,"main":"./dist/index.js","types":"./dist/index.d.ts","exports":{".":{"types":"./dist/index.d.ts","import":"./dist/index.js","default":"./dist/index.js"},"./load":{"types":"./dist/load.d.ts","import":"./dist/load.js","default":"./dist/load.js"},"./package.json":"./package.json"},"devDependencies":{"@types/node":"^26.1.2","react":"^19.2.8","tsx":"^4.23.11","typescript":"^7.0.2","vite":"^8.2.1","vite-node":"^6.0.0","vitest":"^4.1.10"},"engines":{"node":">=18"},"devEngines":{"packageManager":{"name":"pnpm","version":"11.20.0","onFail":"download"}},"repository":{"type":"git","url":"https://github.com/BlankParticle/yoga-layout-js.git"},"homepage":"https://github.com/BlankParticle/yoga-layout-js#readme","bugs":{"url":"https://github.com/BlankParticle/yoga-layout-js/issues"},"publishConfig":{"access":"public"},"scripts":{"clean":"node -e \"require('node:fs').rmSync('dist', {recursive: true, force: true})\"","generate:enums":"node scripts/generate-enums.mjs","check:generated":"vp run generate:enums && git diff --exit-code -- src/generated/YGEnums.ts","build":"vp run clean && tsc -p tsconfig.build.json","typecheck":"tsc -p tsconfig.json --noEmit","build:reference":"node scripts/build-reference.mjs","test":"vp run build:reference && vitest run","test:local":"vp run build:reference && vitest run --exclude \"reference/yoga/javascript/tests/**\"","test:official":"vitest run reference/yoga/javascript/tests","test:differential":"vp run build:reference && vitest run test/differential","fuzz":"vite-node fuzz/typescript.ts","fuzz:differential":"vp run build:reference && vite-node fuzz/differential.ts","fuzz:loop":"vp run build:reference && vite-node fuzz/loop.ts","fuzz:smoke":"vite-node fuzz/typescript.ts --runs 250 --seed 12648430 && vp run build:reference && vite-node fuzz/differential.ts --runs 10 --seed 12648430","test:package":"vp run build && node test/package/drop-in.mjs && tsc --ignoreConfig --noEmit --strict --skipLibCheck false --target ES2022 --module NodeNext --moduleResolution NodeNext test/package/type-smoke.ts","test:ink":"vp run build && vp run setup:ink && node scripts/run-ink-tests.mjs","test:ink:smoke":"vp run build && vp run setup:ink && node --import tsx --import ./benchmarks/ink/register-engine.mjs test/ink.mjs","test:all":"vp run check:generated && vp run typecheck && vp run test && vp run fuzz:smoke && vp run test:package && vp run test:ink","setup:ink":"node scripts/setup-ink.mjs","benchmark":"vp run build:reference && vite-node benchmarks/engine.ts","benchmark:ink":"vp run build && vp run setup:ink && node benchmarks/ink/native.mjs","benchmark:ink:rerender":"vp run build && vp run setup:ink && vite-node benchmarks/ink/compare.ts","pprepublishOnly":"vp run test:all"},"_nodeVersion":"24.19.0","_id":"@blankparticle/yoga-layout@0.0.1-rc.2","dist":{"integrity":"sha512-WsGUjIQT3EqgoZ60SLDqhc6gRs8or895qjdlecuWKN+CTk1tK59p6Vq/vL3EYZF9Evjh8L7ztI/Yzr+a7R///A==","shasum":"ea5c6863b3d907653af64a6519abb86d5b9eebd6","tarball":"https://registry.npmjs.org/@blankparticle/yoga-layout/-/yoga-layout-0.0.1-rc.2.tgz","fileCount":76,"unpackedSize":524469,"signatures":[{"keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U","sig":"MEYCIQDgc7UN8UwcZVDzfVKG8tVX+JzoEpBuDbjpb/4+FboxWwIhANbFlb+qxNMRqcEhJeGJ0WRjEJkWJCSelv0UoxVnFcfA"}]},"_npmUser":{"name":"blankparticle","email":"blankparticle@gmail.com"},"directories":{},"maintainers":[{"name":"blankparticle","email":"blankparticle@gmail.com"}],"_npmOperationalInternal":{"host":"s3://npm-registry-packages-npm-production","tmp":"tmp/yoga-layout_0.0.1-rc.2_1786866476820_0.047893957061845516"},"_hasShrinkwrap":false}},"time":{"created":"2026-08-08T16:40:46.239Z","modified":"2026-08-16T07:47:57.104Z","0.0.1-rc.1":"2026-08-08T16:40:46.542Z","0.0.1-rc.2":"2026-08-16T07:47:56.965Z"},"bugs":{"url":"https://github.com/BlankParticle/yoga-layout-js/issues"},"author":"BlankParticle","license":"MIT","homepage":"https://github.com/BlankParticle/yoga-layout-js#readme","repository":{"type":"git","url":"https://github.com/BlankParticle/yoga-layout-js.git"},"description":"A drop-in TypeScript implementation of the Yoga layout engine","maintainers":[{"name":"blankparticle","email":"blankparticle@gmail.com"}],"readme":"# @blankparticle/yoga-layout\n\nA pure TypeScript implementation of the Yoga layout engine, optimized for JavaScript runtimes. It exposes the same ESM entry points as `yoga-layout` while avoiding the JavaScript-to-WebAssembly boundary.\n\nThe implementation is validated against the Yoga source snapshot pinned in\n`reference/yoga`. Differential tests build that snapshot with the repository's\n`patches/yoga-f64.patch`, making Yoga use the same binary64 number model as\nJavaScript instead of treating expected float32 rounding as port failures.\n\n## Using it as an override\n\nOnce published, a pnpm consumer can replace Yoga without changing application code:\n\n```json\n{\n  \"pnpm\": {\n    \"overrides\": {\n      \"yoga-layout\": \"npm:@blankparticle/yoga-layout@<version>\"\n    }\n  }\n}\n```\n\nFor local development, point the override at this directory instead:\n\n```json\n{\n  \"pnpm\": {\n    \"overrides\": {\n      \"yoga-layout\": \"file:../yoga-layout-js\"\n    }\n  }\n}\n```\n\nThe package ships compiled ESM and TypeScript declarations. Consumers do not need a TypeScript loader and do not compile the engine's source.\n\n## Development\n\n```sh\nvp install\ngit submodule update --init --recursive\nvpr typecheck\nvpr generate:enums\nvpr check:generated\nvpr test\nvpr test:official\nvpr test:local\nvpr test:differential\nvpr fuzz\nvpr fuzz:differential\nvpr fuzz:loop\nvpr fuzz:smoke\nvpr test:package\nvpr test:ink\nvpr test:ink:smoke\nvpr test:all\nvpr benchmark\nvpr setup:ink\nvpr benchmark:ink\nvpr benchmark:ink:rerender\n```\n\n`test:ink` builds this package, injects it as Ink's `yoga-layout` import, and\nruns every AVA test in the Ink source snapshot pinned in `reference/ink`. The\noverride is inherited by AVA workers and Ink's spawned terminal fixtures.\n`test:ink:smoke` remains available for a quick integration check.\n\n`benchmark:ink` runs Ink's checked-in `simple` and `static` benchmark programs\nunchanged in isolated processes, once against this engine and once against the\nYoga WASM version resolved by that Ink snapshot. It reports wall time, user and\nsystem CPU time, and peak RSS. The `simple` fixture performs 100,000 real Ink\nrerenders and can take several minutes. `benchmark:ink:rerender` is the smaller\nproject-owned rerender comparison intended for quick iteration.\n\nThe setup command installs the Ink submodule's development dependencies\nwithout changing its lockfile or running unrelated dependency lifecycle\nscripts:\n\n```sh\nvpr setup:ink\nvpr build\nvpr benchmark:ink\n```\n\nThe test layers are:\n\n- Yoga's official JavaScript and generated conformance suites, consumed\n  unchanged from `reference/yoga/javascript/tests/`;\n- additional C++-API ports and project regressions in `test/` for this\n  implementation, including JS-only API behavior;\n- focused layout and public-surface differential tests in `test/differential/`\n  and `test/PublicApiTest.test.ts`, run against the locally built reference WASM;\n- a built-package API smoke test in `test/package/`;\n- Ink's complete AVA suite with this engine substituted for `yoga-layout`.\n\n`src/generated/YGEnums.ts` is generated from the enum definitions in the pinned\nYoga source. `generate:enums` runs Yoga's canonical `enums.py` generator and\nsyncs its TypeScript output with this project's license header; `check:generated`\nguards against a stale committed file.\n\n### Fuzzing\n\nThe structured fuzzers generate bounded trees across dimensions, intrinsic\nsizes, percentages, flex properties, alignment, wrapping, gaps, box edges,\npositioning, display, overflow, aspect ratios, measure functions, direction,\nand configuration modes.\n\n```sh\n# TypeScript crash, determinism, and layout-invariant campaign (10,000 cases)\nvpr fuzz\n\n# Compare generated layouts with the f64 WASM built from pinned Yoga (1,000 cases)\nvpr fuzz:differential\n\n# Replay one failure or run a larger bounded campaign\nvpr fuzz:differential -- --seed 160575059 --runs 1\nvpr fuzz:differential -- --runs 10000 --max-nodes 40\n\n# Continuously exercise determinism and JS/f64-WASM parity until Ctrl+C\nvpr fuzz:loop -- --max-nodes 40 --report-every 1000\n```\n\nWith no `--seed`, each campaign chooses and prints a random base seed. Failures\nprint a one-case replay command and write a self-contained report under the\nignored `.reference/fuzz-failures/` directory, including the generated case,\nexception stack, runtime details, and timestamp. `fuzz:smoke` is deterministic\nand is included in `test:all`.\n\n`fuzz:loop` builds the f64 reference engine once, then continuously runs both\nTypeScript determinism/invariant checks and WASM differential checks. It keeps\ngoing after failures and stores deduplicated, self-contained records under\n`.reference/fuzz-failures/loop/`. Records include both engine outcomes, layout\nsnapshots or exception stacks, campaign position, runtime details, occurrence\ncounts, and recent seeds. `SIGINT` and `SIGTERM` flush the current record and\nprint a final campaign summary.\n\nTo leave a campaign running from a shell and keep its console log:\n\n```sh\nvpr fuzz:loop -- --max-nodes 40 --report-every 10000 > .reference/fuzz-loop.log 2>&1 &\n```\n\nLocal, aggregate, and benchmark commands build the reference WASM first.\n`build:reference` temporarily applies `patches/yoga-f64.patch`, builds Yoga,\ncopies the matching f64 runtime wrapper into ignored `.reference/yoga-f64/`,\nand restores the submodule even when the build fails. It also recovers and\nrestores the patch if an earlier build was interrupted. Generated WASM and\nwrapper files are ignored, so none are committed or published:\n\n```sh\nvpr build:reference\nvpr test:local\nvpr test:package\nvpr test:ink\nvpr test:all\n```\n\n## Reference source\n\n`reference/yoga` and `reference/ink` are clean Git submodules at rest. They pin\nthe C++ implementation, test corpus, and Ink source used for development\nwithout mixing any of them or their generated artifacts into the published\npackage. The maintained f64 delta lives outside the Yoga submodule in\n`patches/yoga-f64.patch`.\n\n```sh\ngit submodule update --init --recursive\n```\n\n## License\n\nThis project is distributed under the MIT license. Portions are derived from\nYoga; its original copyright and MIT terms are preserved in\n`THIRD_PARTY_NOTICES.md`.\n","readmeFilename":""}