@vitreajs/vitrea 0.19.0 → 0.21.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/{dist-VQPRX7BX.js → dist-N437MSRG.js} +505 -23
- package/dist/dist-N437MSRG.js.map +1 -0
- package/dist/index.d.ts +249 -1
- package/dist/index.js +1 -1
- package/package.json +1 -1
- package/dist/dist-VQPRX7BX.js.map +0 -1
package/dist/index.d.ts
CHANGED
|
@@ -1993,8 +1993,88 @@ interface MaterialRim {
|
|
|
1993
1993
|
interface MaterialOuterShadow {
|
|
1994
1994
|
/** Downward translation of the shadow's silhouette, CSS px. */
|
|
1995
1995
|
readonly offsetPx: number;
|
|
1996
|
-
/**
|
|
1996
|
+
/**
|
|
1997
|
+
* Gaussian σ the silhouette is blurred by, CSS px. A `box-shadow` blur is 2σ.
|
|
1998
|
+
*
|
|
1999
|
+
* Since W30 G2 this is the σ at the reference span rather than the σ full
|
|
2000
|
+
* stop: the three leaves below grade it with the casting span, and at their
|
|
2001
|
+
* inert defaults the law returns exactly this number for every span. The
|
|
2002
|
+
* header above records the macOS 26.5 material's own span-invariance as a
|
|
2003
|
+
* positive measurement, which is why that material can go on expressing
|
|
2004
|
+
* itself with three zeros.
|
|
2005
|
+
*/
|
|
1997
2006
|
readonly sigmaPx: number;
|
|
2007
|
+
/**
|
|
2008
|
+
* The σ law's slope: CSS px of σ per CSS px of casting span, dimensionless.
|
|
2009
|
+
*
|
|
2010
|
+
* macOS 27 blurs the outer shadow wider under a wider surface. Over spans 96
|
|
2011
|
+
* to 160 the measured σ is linear in the span on every bed of the macOS 27
|
|
2012
|
+
* capture — slope 0.128 to 0.134, holding to 2 % on the median and scale-
|
|
2013
|
+
* invariant in CSS px to 11 % at its worst cell (claims §5.156 §2) — while
|
|
2014
|
+
* the shipped single σ draws 4.2 to 7.2 times too wide below span 96 and
|
|
2015
|
+
* about a third too narrow at 128 and above. The whole law is
|
|
2016
|
+
*
|
|
2017
|
+
* σ_css(span) = sigmaPx + max(sigmaThinOffsetPx,
|
|
2018
|
+
* sigmaSlopePerSpan · (span − sigmaSpanRefPx))
|
|
2019
|
+
*
|
|
2020
|
+
* evaluated PER CASTER: the GPU tier reads the casting surface's own span per
|
|
2021
|
+
* pixel from the field pass's `shadowAux.z`, and the CSS tier writes one blur
|
|
2022
|
+
* radius per surface from `surface.spanPx`. It takes no device ratio, because
|
|
2023
|
+
* the cut rejected the device-px reading of the thin regime in both directions
|
|
2024
|
+
* (§5.156 §2's two signatures) — one function of CSS span is one mirror fewer
|
|
2025
|
+
* for the CSS tier to keep.
|
|
2026
|
+
*
|
|
2027
|
+
* **Ships at 0, which is a multiplied zero**: the whole span term is
|
|
2028
|
+
* `0 · (span − sigmaSpanRefPx)`, so the `max` sees two zeros and σ is
|
|
2029
|
+
* `sigmaPx` identically, at every span and every scale. Fitted in the macOS 27
|
|
2030
|
+
* documents by claims §5.159; the frozen macOS 26.5 material keeps the zero,
|
|
2031
|
+
* where it is the measurement.
|
|
2032
|
+
*/
|
|
2033
|
+
readonly sigmaSlopePerSpan: number;
|
|
2034
|
+
/**
|
|
2035
|
+
* The casting span, CSS px, at which σ equals `sigmaPx` — the span the line
|
|
2036
|
+
* pivots about.
|
|
2037
|
+
*
|
|
2038
|
+
* The law has one flat direction: shifting `sigmaPx`, `sigmaThinOffsetPx` and
|
|
2039
|
+
* this constant together leaves σ unchanged at every span, so a fit has to
|
|
2040
|
+
* hold one of the three. **The fit holds this one, at 96** (W30 Decision Log
|
|
2041
|
+
* 3 (c)) — the span every bed carries sixteen cells at, and the span the
|
|
2042
|
+
* amplitude's own anchor `thickOcclusionAt96` is keyed to — and fits the slope
|
|
2043
|
+
* and the offset around it, refitting `sigmaPx` as the σ at span 96.
|
|
2044
|
+
*
|
|
2045
|
+
* **Ships at 0**, which is unreachable while the slope is 0 and which the
|
|
2046
|
+
* identity does not depend on: a pivot multiplied by a zero slope contributes
|
|
2047
|
+
* nothing whatever its value. 96 is the fit's value in claims §5.159, not the
|
|
2048
|
+
* default's.
|
|
2049
|
+
*/
|
|
2050
|
+
readonly sigmaSpanRefPx: number;
|
|
2051
|
+
/**
|
|
2052
|
+
* The width the thin regime holds, CSS px, SIGNED, stated as an offset from
|
|
2053
|
+
* `sigmaPx` — the floor the line is clamped below at.
|
|
2054
|
+
*
|
|
2055
|
+
* A floor is structurally necessary rather than a fit of the thin cells: the
|
|
2056
|
+
* measured line crosses zero at a span of 23.6 to 30.4 on every bed and the
|
|
2057
|
+
* smallest declared span in the bed is 32, so without one the law emits
|
|
2058
|
+
* 0.27 CSS px on a 32 px surface and a negative σ on a 24 px one
|
|
2059
|
+
* (claims §5.156 §2).
|
|
2060
|
+
*
|
|
2061
|
+
* **Its unit is CSS px and its value is a declared reading rather than a fit**
|
|
2062
|
+
* (W30 Decision Log 2 (b)). The thin cells are a position on the instrument's
|
|
2063
|
+
* valley, not a measurement of Apple's blur: the reader's (amplitude, σ) pair
|
|
2064
|
+
* trades at a nearly constant product there, and the thin σ bifurcates on the
|
|
2065
|
+
* author's TINT — untinted cells read a 1x/2x ratio of 1.86–2.57 and their
|
|
2066
|
+
* tinted siblings 0.51–0.56 on the same geometry, which the material's blur
|
|
2067
|
+
* cannot depend on. So no order statistic over those cells is a measurement,
|
|
2068
|
+
* and §5.159 sets this by declaration with the statistic it is checked
|
|
2069
|
+
* against named.
|
|
2070
|
+
*
|
|
2071
|
+
* **Ships at 0**, an added zero under a `max` whose other arm is also zero.
|
|
2072
|
+
* The knee — where the floor gives way to the line — is DERIVED from the three
|
|
2073
|
+
* (`sigmaSpanRefPx + sigmaThinOffsetPx / sigmaSlopePerSpan`) rather than being
|
|
2074
|
+
* a fourth leaf, because a knee stated beside a slope and a floor is a third
|
|
2075
|
+
* name for a quantity two of them already fix.
|
|
2076
|
+
*/
|
|
2077
|
+
readonly sigmaThinOffsetPx: number;
|
|
1998
2078
|
/** Outward spread of the silhouette before the blur, CSS px. */
|
|
1999
2079
|
readonly spreadPx: number;
|
|
2000
2080
|
/**
|
|
@@ -2827,6 +2907,88 @@ interface MaterialProfile {
|
|
|
2827
2907
|
*/
|
|
2828
2908
|
readonly sizeHeavyTapSigma: number;
|
|
2829
2909
|
readonly sizeHeavyTapSigma2x: number;
|
|
2910
|
+
/**
|
|
2911
|
+
* The second heavy tap's Gaussian width in CSS px, per scale — candidate (i)'s
|
|
2912
|
+
* width, on `sizeHeavyTapSigma`'s own pattern and resolved by the same
|
|
2913
|
+
* `rampAtScale`.
|
|
2914
|
+
*
|
|
2915
|
+
* It is a second `PyramidResources` texture and a second separable pair, not a
|
|
2916
|
+
* uniform the optics pass evaluates, for `sizeHeavyTapSigma`'s measured
|
|
2917
|
+
* reason: a grid of taps at the fragment costs +1.1 ms on the mobile bench row
|
|
2918
|
+
* against 0.070 ms for two separable passes the chain already runs (W26
|
|
2919
|
+
* Decision Log 2 (b)). So the width, like the first one, is one per SOURCE.
|
|
2920
|
+
*
|
|
2921
|
+
* **Ships at 0, and the width is not what makes it inert** —
|
|
2922
|
+
* `sizeHeavySecondShare` is. At share 0 no texture is allocated, no pass is
|
|
2923
|
+
* encoded and the optics pass never reads one, so this width is unread
|
|
2924
|
+
* whatever it holds; 0 is chosen because it is the value at which
|
|
2925
|
+
* `heavyTapPlan` would also decline. A profile that names a width and leaves
|
|
2926
|
+
* the share at 0 gets nothing, deliberately: the share is the single gate, so
|
|
2927
|
+
* that the off path has exactly one condition.
|
|
2928
|
+
*/
|
|
2929
|
+
readonly sizeHeavySecondSigma: number;
|
|
2930
|
+
readonly sizeHeavySecondSigma2x: number;
|
|
2931
|
+
/**
|
|
2932
|
+
* The second heavy sample's weight in the deep mix — a SIGNED fraction, and
|
|
2933
|
+
* the scheme-conditioned leaf of candidate (i).
|
|
2934
|
+
*
|
|
2935
|
+
* The deep sample becomes `heavy + share · (heavy2 − heavy)`, so a positive
|
|
2936
|
+
* share widens the deep component toward the second width and a NEGATIVE one
|
|
2937
|
+
* subtracts it — an unsharp mask on the backdrop, which is a kernel that
|
|
2938
|
+
* passes the middle pitch less than both ends and is the only shape on offer
|
|
2939
|
+
* that can do what the residual asks. The sign is what the colour scheme
|
|
2940
|
+
* flips: on the gated 16 px cell vitrea passes 1.57× the native structure in
|
|
2941
|
+
* 1x light and 0.75× in 1x dark, so the light document wants structure removed
|
|
2942
|
+
* at that pitch and the dark document wants it added (claims §5.156 §3, §6).
|
|
2943
|
+
*
|
|
2944
|
+
* **It is also the GATE.** The second heavy texture is built, bound and read
|
|
2945
|
+
* only where this is non-zero, so at 0 the mechanism costs no allocation, no
|
|
2946
|
+
* pass and no sample, and the deep mix is the expression W26 left — which is
|
|
2947
|
+
* what the 34 renderer goldens prove, since they render an explicit patch over
|
|
2948
|
+
* the default and every one of them is byte-identical across this commit.
|
|
2949
|
+
*
|
|
2950
|
+
* **Ships at 0, a multiplied zero**: the lerp's second term is
|
|
2951
|
+
* `0 · (heavy2 − heavy)`, and the branch that would read `heavy2` at all is
|
|
2952
|
+
* not taken.
|
|
2953
|
+
*/
|
|
2954
|
+
readonly sizeHeavySecondShare: number;
|
|
2955
|
+
/**
|
|
2956
|
+
* The gain on `kScatter` per unit of the source's measured scale statistic
|
|
2957
|
+
* about `sizeScatterScaleRef` — candidate (ii)'s scheme-conditioned leaf, a
|
|
2958
|
+
* fraction per unit of statistic, signed.
|
|
2959
|
+
*
|
|
2960
|
+
* `kScatter` is the share of the deep component in the body's mix, and this
|
|
2961
|
+
* adds `sizeScatterScaleGain · (stat − sizeScatterScaleRef)` to it before the
|
|
2962
|
+
* clamp — so a backdrop whose structure sits at a finer scale than the
|
|
2963
|
+
* reference takes a different share of the heavy component from one whose
|
|
2964
|
+
* structure is coarser, which is a transmission that depends on the backdrop's
|
|
2965
|
+
* scale rather than only on the surface's span. The statistic is the analysis
|
|
2966
|
+
* pass's per-source EDGE DENSITY (mean luminance-gradient magnitude per texel,
|
|
2967
|
+
* a reciprocal length), resolved on the CPU where the readback is and handed
|
|
2968
|
+
* to the optics pass as one number per group.
|
|
2969
|
+
*
|
|
2970
|
+
* The sign is the scheme's, for `sizeHeavySecondShare`'s reason and read off
|
|
2971
|
+
* the same cell.
|
|
2972
|
+
*
|
|
2973
|
+
* **Ships at 0, a multiplied zero**: the added term is
|
|
2974
|
+
* `0 · (stat − sizeScatterScaleRef)` and `kScatter` is already clamped to
|
|
2975
|
+
* [0, 1], so the clamp that follows is the identity on it.
|
|
2976
|
+
*/
|
|
2977
|
+
readonly sizeScatterScaleGain: number;
|
|
2978
|
+
/**
|
|
2979
|
+
* The reference value of the per-source scale statistic the gain above is
|
|
2980
|
+
* measured about — the backdrop scale at which the operator does nothing.
|
|
2981
|
+
*
|
|
2982
|
+
* Not scheme-conditioned: a spatial scale is a property of the source raster
|
|
2983
|
+
* and the raster is the same in both schemes. Fitted in §5.159 as the edge
|
|
2984
|
+
* density of the pitch the two sides of the residual straddle, once the ladder
|
|
2985
|
+
* has a macOS 27 reading.
|
|
2986
|
+
*
|
|
2987
|
+
* **Ships at 0**, and the argument for its inertness is not a multiplied zero
|
|
2988
|
+
* but a different one and sufficient on its own: the gain that multiplies the
|
|
2989
|
+
* difference from it is 0, so no value of this constant can reach the mix.
|
|
2990
|
+
*/
|
|
2991
|
+
readonly sizeScatterScaleRef: number;
|
|
2830
2992
|
/**
|
|
2831
2993
|
* The occlusion gain — "a larger size is more opaque. A smaller size is
|
|
2832
2994
|
* clearer" (S284). The fraction of the *remaining* transparency the size law
|
|
@@ -3104,6 +3266,60 @@ interface MaterialProfile {
|
|
|
3104
3266
|
* it at every ratio and this anchor is the identity on the landed material.
|
|
3105
3267
|
*/
|
|
3106
3268
|
readonly collapseTransmission2x: number;
|
|
3269
|
+
/**
|
|
3270
|
+
* **How much of the blurred backdrop's CHROMATICITY the body restores** (W31;
|
|
3271
|
+
* claims §5.161 §5, fitted in §5.164) — a fraction in [0, 1], inert at 0.
|
|
3272
|
+
*
|
|
3273
|
+
* The body is a neutral plate composited over the blurred backdrop, so what a
|
|
3274
|
+
* photograph's hues survive the composite at is `1 − sizedAlpha` — 0.513 on the
|
|
3275
|
+
* macOS 27 light document and 0.095 on the dark one, against a reference that
|
|
3276
|
+
* reads 0.90–0.97 of its own backdrop's chroma on the same cells. Apple's body
|
|
3277
|
+
* at the same LEVEL keeps the hue, which is what a darkening acting on the
|
|
3278
|
+
* backdrop's luma while leaving its chromaticity alone does and what a plate
|
|
3279
|
+
* does not. No constant the material had could close that (W29 Decision Log
|
|
3280
|
+
* 6 (c)): it is a mechanism, and this is the one leaf that adds it.
|
|
3281
|
+
*
|
|
3282
|
+
* Applied immediately after `colour = mix(backdrop, adapted, presentAlpha)`
|
|
3283
|
+
* and before the tint composition, so an author's tint still displaces the
|
|
3284
|
+
* result. The colour is mixed toward `backdrop · (Y / Y_backdrop)` — the
|
|
3285
|
+
* backdrop's chromaticity carried to the colour's OWN linear luma — by this
|
|
3286
|
+
* fraction, so **luma is preserved by construction rather than by
|
|
3287
|
+
* correction**: both endpoints of the mix have linear luma exactly `Y`,
|
|
3288
|
+
* `dot(rgb, (0.2126, 0.7152, 0.0722))` is a linear functional, and the mix has
|
|
3289
|
+
* luma `Y` in exact arithmetic. (OKLab `L` is NOT linear luma, which is why the
|
|
3290
|
+
* formulation is in linear RGB: holding `L` while moving toward a saturated
|
|
3291
|
+
* chromaticity moves `Y` by −22 % at sRGB blue and +10 % at green.) Gamut is
|
|
3292
|
+
* taken by scaling chroma toward the neutral at fixed luma, never by clipping
|
|
3293
|
+
* per channel.
|
|
3294
|
+
*
|
|
3295
|
+
* **No `toneAdapt` gate**, and the reason is measured rather than assumed
|
|
3296
|
+
* (claims §5.161 §11, finding N1). A retention toward the backdrop's
|
|
3297
|
+
* chromaticity is the identity wherever the backdrop is achromatic, and the
|
|
3298
|
+
* only region `backdropToneAdaptation` can fire in on the macOS 27 documents
|
|
3299
|
+
* is `x < backdropToneHigh` = 1e-4 of linear light — achromatic to within the
|
|
3300
|
+
* capture's own quantisation. A future document that re-opens
|
|
3301
|
+
* `backdropToneHigh` must re-examine that, and must read it at a span at or
|
|
3302
|
+
* below `sizeSpanMin` where `backdropToneSizeBias` is not there to help.
|
|
3303
|
+
*
|
|
3304
|
+
* Conditioned by SCHEME (two values across the light and dark documents) and
|
|
3305
|
+
* by POSE: each receded document carries its own, read on the inactive cells,
|
|
3306
|
+
* because the recede's untinted body has no chroma law at all otherwise —
|
|
3307
|
+
* W27c's collapse acts on the tint SEED inside `if (tintK > 0.0)`. The
|
|
3308
|
+
* accessibility documents inherit the light value.
|
|
3309
|
+
*
|
|
3310
|
+
* **Ships at 0, a multiplied zero**: the mix's second term is `0 · (target −
|
|
3311
|
+
* colour)` and `colour` leaves the composite exactly as
|
|
3312
|
+
* `mix(backdrop, adapted, presentAlpha)` produced it, which is why the 34
|
|
3313
|
+
* renderer goldens are byte-identical across the commit that added it and why
|
|
3314
|
+
* `MATERIAL_IDENTITY_TABLE` can drop it from the fingerprint.
|
|
3315
|
+
*
|
|
3316
|
+
* One place it cannot act, declared rather than discovered: on the unsampled
|
|
3317
|
+
* layer path (`flags.x <= 0.5` and not `domMaterial`) the shader overwrites
|
|
3318
|
+
* `colour` with `adapted` and writes a layer for the browser to composite, so
|
|
3319
|
+
* there is no backdrop in hand and no chromaticity to restore toward. The
|
|
3320
|
+
* retention is silently the identity there.
|
|
3321
|
+
*/
|
|
3322
|
+
readonly bodyChromaRetention: number;
|
|
3107
3323
|
/**
|
|
3108
3324
|
* **The rim that survives the collapse (W23)** — the one mark the collapsed
|
|
3109
3325
|
* appearance keeps.
|
|
@@ -3320,6 +3536,11 @@ interface MaterialProfilePatch {
|
|
|
3320
3536
|
readonly sizeToneLevelFar?: number;
|
|
3321
3537
|
readonly sizeHeavyTapSigma?: number;
|
|
3322
3538
|
readonly sizeHeavyTapSigma2x?: number;
|
|
3539
|
+
readonly sizeHeavySecondSigma?: number;
|
|
3540
|
+
readonly sizeHeavySecondSigma2x?: number;
|
|
3541
|
+
readonly sizeHeavySecondShare?: number;
|
|
3542
|
+
readonly sizeScatterScaleGain?: number;
|
|
3543
|
+
readonly sizeScatterScaleRef?: number;
|
|
3323
3544
|
readonly sizeOcclusionGain?: number;
|
|
3324
3545
|
readonly sizeShadowGainMax?: number;
|
|
3325
3546
|
readonly lensRefractionGain?: number;
|
|
@@ -3349,6 +3570,7 @@ interface MaterialProfilePatch {
|
|
|
3349
3570
|
readonly backdropToneSizeBias?: number;
|
|
3350
3571
|
readonly collapseTransmission?: number;
|
|
3351
3572
|
readonly collapseTransmission2x?: number;
|
|
3573
|
+
readonly bodyChromaRetention?: number;
|
|
3352
3574
|
readonly rimCollapsed?: number;
|
|
3353
3575
|
readonly rimCollapsedTinted?: number;
|
|
3354
3576
|
readonly rimTintChroma?: number;
|
|
@@ -4176,6 +4398,19 @@ interface PyramidResources {
|
|
|
4176
4398
|
* says the material can afford that.
|
|
4177
4399
|
*/
|
|
4178
4400
|
readonly heavy: GPUTexture | undefined;
|
|
4401
|
+
/**
|
|
4402
|
+
* The **second** heavy blur (W30 G2; `MaterialProfile.sizeHeavySecondSigma`
|
|
4403
|
+
* gated on `sizeHeavySecondShare`) — the same construction one width along,
|
|
4404
|
+
* and `undefined` wherever the material leaves the share at 0, which is
|
|
4405
|
+
* everywhere on the landed material.
|
|
4406
|
+
*
|
|
4407
|
+
* It is a second texture and a second separable pair rather than a second tap
|
|
4408
|
+
* in the optics pass for the reason the first one is: the price of a width at
|
|
4409
|
+
* the fragment is +1.1 ms on the mobile bench row against 0.070 ms here (W26
|
|
4410
|
+
* Decision Log 2 (b)). The price of having it at all is therefore paid by the
|
|
4411
|
+
* material that names it and by nothing else.
|
|
4412
|
+
*/
|
|
4413
|
+
readonly heavy2: GPUTexture | undefined;
|
|
4179
4414
|
readonly stats: GPUBuffer;
|
|
4180
4415
|
/** Source size epoch this allocation was made for. */
|
|
4181
4416
|
readonly sizeEpoch: number;
|
|
@@ -4221,6 +4456,11 @@ interface PyramidResources {
|
|
|
4221
4456
|
* texture from the same clean source.
|
|
4222
4457
|
*/
|
|
4223
4458
|
readonly heavySigmaCss: number;
|
|
4459
|
+
/**
|
|
4460
|
+
* The SECOND heavy blur's σ in **CSS px** the build converted with (W30 G2),
|
|
4461
|
+
* on `heavySigmaCss`'s own rule and for the same staleness reason.
|
|
4462
|
+
*/
|
|
4463
|
+
readonly heavy2SigmaCss: number;
|
|
4224
4464
|
}
|
|
4225
4465
|
interface PyramidInstrumentation {
|
|
4226
4466
|
/** Successful rebuilds since the store was created. */
|
|
@@ -4256,6 +4496,14 @@ interface PyramidBuildRequest {
|
|
|
4256
4496
|
* material that names no heavy width pays for none of this.
|
|
4257
4497
|
*/
|
|
4258
4498
|
readonly heavySigmaCss: number;
|
|
4499
|
+
/**
|
|
4500
|
+
* The SECOND heavy blur's σ in **CSS px** (W30 G2), 0 where the material
|
|
4501
|
+
* leaves `sizeHeavySecondShare` at 0 — at which point nothing is allocated
|
|
4502
|
+
* and nothing is drawn, exactly as for the first one. The share is the gate
|
|
4503
|
+
* and `heavySecondTapSigmaAtScale` applies it, so this arrives already 0
|
|
4504
|
+
* rather than being re-decided here.
|
|
4505
|
+
*/
|
|
4506
|
+
readonly heavy2SigmaCss: number;
|
|
4259
4507
|
readonly viewportCss: readonly [number, number];
|
|
4260
4508
|
/**
|
|
4261
4509
|
* Where the source sits on the plane, in CSS px relative to the viewport, if
|
package/dist/index.js
CHANGED
|
@@ -1092,7 +1092,7 @@ function isHealthy(state) {
|
|
|
1092
1092
|
|
|
1093
1093
|
// src/renderer-seam.ts
|
|
1094
1094
|
async function loadWebGPURendererModule() {
|
|
1095
|
-
return import('./dist-
|
|
1095
|
+
return import('./dist-N437MSRG.js');
|
|
1096
1096
|
}
|
|
1097
1097
|
async function loadWebGPURenderer() {
|
|
1098
1098
|
const { createWebGPURenderer } = await loadWebGPURendererModule();
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@vitreajs/vitrea",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.21.0",
|
|
4
4
|
"description": "Framework-agnostic Liquid Glass material runtime: scene model, capability resolution, material policy, accessibility policy.",
|
|
5
5
|
"license": "Apache-2.0",
|
|
6
6
|
"homepage": "https://github.com/SSFSKIM/designer",
|