ranger-compiler 3.5.0 → 3.5.2
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/CHANGELOG.md +1160 -19
- package/LICENSE +3 -1
- package/README.md +124 -29
- package/dist/Lang.rgr +1188 -290
- package/dist/api.d.ts +2343 -879
- package/dist/api.js +79924 -56922
- package/dist/lib/JSON.rgr +102 -91
- package/dist/lib/Shell.rgr +4 -4
- package/dist/lib/apple/AppleToolchain.rgr +4 -4
- package/dist/lib/apple/README.md +5 -4
- package/dist/lib/apple/apple_test.rgr +1 -1
- package/dist/lib/core/README.md +1 -1
- package/dist/lib/evg/EVG.rgr +12 -0
- package/dist/lib/evg/EVGA11yFromTree.rgr +302 -0
- package/dist/lib/evg/EVGA11yTree.rgr +894 -0
- package/dist/lib/evg/EVGBox.rgr +267 -0
- package/dist/lib/evg/EVGBoxShorthandTest.rgr +220 -0
- package/dist/lib/evg/EVGCodepoint.rgr +316 -0
- package/dist/lib/evg/EVGColor.rgr +700 -0
- package/dist/lib/evg/EVGCommands.rgr +177 -0
- package/dist/lib/evg/EVGComponent.rgr +331 -0
- package/dist/lib/evg/EVGComponentTest.rgr +387 -0
- package/dist/lib/evg/EVGConnector.rgr +541 -0
- package/dist/lib/evg/EVGConnectorTest.rgr +306 -0
- package/dist/lib/evg/EVGDisplayList.rgr +4186 -0
- package/dist/lib/evg/EVGEasing.rgr +370 -0
- package/dist/lib/evg/EVGEffectTest.rgr +253 -0
- package/dist/lib/evg/EVGElement.rgr +4914 -0
- package/dist/lib/evg/EVGFixedTest.rgr +289 -0
- package/dist/lib/evg/EVGFlexRulesTest.rgr +317 -0
- package/dist/lib/evg/EVGFlexWrapTest.rgr +246 -0
- package/dist/lib/evg/EVGFling.rgr +244 -0
- package/dist/lib/evg/EVGFocus.rgr +400 -0
- package/dist/lib/evg/EVGFocusTest.rgr +399 -0
- package/dist/lib/evg/EVGGradient.rgr +322 -0
- package/dist/lib/evg/EVGGrapheme.rgr +190 -0
- package/dist/lib/evg/EVGGrid.rgr +975 -0
- package/dist/lib/evg/EVGHitTest.rgr +208 -0
- package/dist/lib/evg/EVGHoles.rgr +294 -0
- package/dist/lib/evg/EVGHostMeasurerTest.rgr +281 -0
- package/dist/lib/evg/EVGHostTextMeasurer.rgr +331 -0
- package/dist/lib/evg/EVGHostTree.rgr +834 -0
- package/dist/lib/evg/EVGHostTreeTest.rgr +447 -0
- package/dist/lib/evg/EVGImageDecode.rgr +117 -0
- package/dist/lib/evg/EVGImageMeasurer.rgr +86 -0
- package/dist/lib/evg/EVGInspect.rgr +883 -0
- package/dist/lib/evg/EVGInvalidateTest.rgr +432 -0
- package/dist/lib/evg/EVGJsonTest.rgr +535 -0
- package/dist/lib/evg/EVGLayout.rgr +4220 -0
- package/dist/lib/evg/EVGMeasure.rgr +1267 -0
- package/dist/lib/evg/EVGOverlayTest.rgr +626 -0
- package/dist/lib/evg/EVGPatch.rgr +1721 -0
- package/dist/lib/evg/EVGPatchTest.rgr +692 -0
- package/dist/lib/evg/EVGPopoverTest.rgr +395 -0
- package/dist/lib/evg/EVGReconcile.rgr +226 -0
- package/dist/lib/evg/EVGReconcileTest.rgr +421 -0
- package/dist/lib/evg/EVGReject.rgr +126 -0
- package/dist/lib/evg/EVGRelayoutTest.rgr +375 -0
- package/dist/lib/evg/EVGRtlLayoutTest.rgr +319 -0
- package/dist/lib/evg/EVGRuler.rgr +232 -0
- package/dist/lib/evg/EVGRulerTest.rgr +172 -0
- package/dist/lib/evg/EVGSelectChrome.rgr +178 -0
- package/dist/lib/evg/EVGStyleCacheTest.rgr +419 -0
- package/dist/lib/evg/EVGStyleSheet.rgr +2148 -0
- package/dist/lib/evg/EVGStyleStateTest.rgr +407 -0
- package/dist/lib/evg/EVGStyleVarTest.rgr +471 -0
- package/dist/lib/evg/EVGText.rgr +105 -0
- package/dist/lib/evg/EVGTextEngine.rgr +536 -0
- package/dist/lib/evg/EVGTextMeasurer.rgr +720 -0
- package/dist/lib/evg/EVGTimingTest.rgr +1417 -0
- package/dist/lib/evg/EVGToolbar.rgr +1369 -0
- package/dist/lib/evg/EVGTransition.rgr +728 -0
- package/dist/lib/evg/EVGTreeJson.rgr +721 -0
- package/dist/lib/evg/EVGUnit.rgr +554 -0
- package/dist/lib/evg/EVGViewportUnitTest.rgr +236 -0
- package/dist/lib/evg/EvgApp.rgr +189 -0
- package/dist/lib/evg/EvgBitmapTracer.rgr +4277 -0
- package/dist/lib/evg/EvgBitmapTracerTest.rgr +2119 -0
- package/dist/lib/evg/EvgHost.rgr +451 -0
- package/dist/lib/evg/EvgTest.rgr +91 -0
- package/dist/lib/evg/EvgTraceColor.rgr +236 -0
- package/dist/lib/evg/EvgTraceCurve.rgr +648 -0
- package/dist/lib/evg/EvgTraceFit.rgr +767 -0
- package/dist/lib/evg/EvgTracePath.rgr +435 -0
- package/dist/lib/evg/EvgTraceTypes.rgr +559 -0
- package/dist/lib/evg/EvgViewport.rgr +313 -0
- package/dist/lib/evg/FxDemoDoc.rgr +185 -0
- package/dist/lib/evg/HOSTS.md +227 -0
- package/dist/lib/evg/ISSUES.md +835 -0
- package/dist/lib/evg/PLAN_ACCESSIBILITY.md +650 -0
- package/dist/lib/evg/PLAN_CSS_LAYOUT_AND_FONTS.md +1124 -0
- package/dist/lib/evg/PLAN_EFFECTS.md +431 -0
- package/dist/lib/evg/PLAN_EVG.md +518 -0
- package/dist/lib/evg/PLAN_EVG_RENDERER.md +1674 -0
- package/dist/lib/evg/PLAN_INSPECTOR.md +788 -0
- package/dist/lib/evg/PLAN_LINKS_AND_FORMS.md +157 -0
- package/dist/lib/evg/PLAN_NATIVE_HOSTS.md +671 -0
- package/dist/lib/evg/PLAN_VECTOR_IR.md +664 -0
- package/dist/lib/evg/PLAN_VIEW_TRANSFORM.md +322 -0
- package/dist/lib/evg/PathBuilder.rgr +333 -0
- package/dist/lib/evg/README.md +1236 -0
- package/dist/lib/evg/SPEC.md +1252 -0
- package/dist/lib/evg/SVGPathParser.rgr +1199 -0
- package/dist/lib/evg/SvgParser.rgr +1736 -0
- package/dist/lib/evg/TODO_EVG_RENDERER.md +595 -0
- package/dist/lib/evg/VectorShapes.rgr +331 -0
- package/dist/lib/evg/VectorStroke.rgr +107 -0
- package/dist/lib/evg/VectorViewBox.rgr +380 -0
- package/dist/lib/evg/agent/README.md +290 -0
- package/dist/lib/evg/agent/evg_agent.rgr +899 -0
- package/dist/lib/evg/agent/fixtures/broken.evg.json +7 -0
- package/dist/lib/evg/agent/fixtures/card.evg.json +9 -0
- package/dist/lib/evg/agent/fixtures/connector.css +63 -0
- package/dist/lib/evg/agent/fixtures/connector.evg.json +14 -0
- package/dist/lib/evg/agent/fixtures/drawn.evg.json +129 -0
- package/dist/lib/evg/agent/fixtures/gradient.evg.json +4 -0
- package/dist/lib/evg/agent/fixtures/popover.css +99 -0
- package/dist/lib/evg/agent/fixtures/popover.evg.json +30 -0
- package/dist/lib/evg/agent/roundtrip.sh +74 -0
- package/dist/lib/evg/agent/smoke.sh +230 -0
- package/dist/lib/evg/android/README.md +97 -0
- package/dist/lib/evg/android/androidstubs/AndroidStubs.kt +175 -0
- package/dist/lib/evg/android/androidstubs/Annotation.kt +10 -0
- package/dist/lib/evg/android/androidstubs/App.kt +30 -0
- package/dist/lib/evg/android/androidstubs/Content.kt +41 -0
- package/dist/lib/evg/android/androidstubs/ContentRes.kt +12 -0
- package/dist/lib/evg/android/androidstubs/InputMethod.kt +46 -0
- package/dist/lib/evg/android/androidstubs/Net.kt +6 -0
- package/dist/lib/evg/android/androidstubs/Os.kt +30 -0
- package/dist/lib/evg/android/androidstubs/Util.kt +15 -0
- package/dist/lib/evg/android/androidstubs/View.kt +113 -0
- package/dist/lib/evg/android/androidstubs/Widget.kt +16 -0
- package/dist/lib/evg/android/src/android/kotlin/fi/ranger/evg/AndroidEvgSurface.kt +323 -0
- package/dist/lib/evg/android/src/android/kotlin/fi/ranger/evg/AndroidTextMeasurer.kt +56 -0
- package/dist/lib/evg/android/src/android/kotlin/fi/ranger/evg/RippleEffect.kt +262 -0
- package/dist/lib/evg/android/src/awt/kotlin/fi/ranger/evg/AwtEvgSurface.kt +238 -0
- package/dist/lib/evg/android/src/awt/kotlin/fi/ranger/evg/AwtTextMeasurer.kt +85 -0
- package/dist/lib/evg/android/src/main/kotlin/fi/ranger/evg/EvgEngineThread.kt +115 -0
- package/dist/lib/evg/android/src/main/kotlin/fi/ranger/evg/EvgPainter.kt +231 -0
- package/dist/lib/evg/android/src/main/kotlin/fi/ranger/evg/EvgSurface.kt +117 -0
- package/dist/lib/evg/android/src/main/kotlin/fi/ranger/evg/RecordingSurface.kt +94 -0
- package/dist/lib/evg/apple/README.md +128 -0
- package/dist/lib/evg/apple/Sources/CoreGraphicsEvgSurface.swift +329 -0
- package/dist/lib/evg/apple/Sources/CoreTextMeasurer.swift +70 -0
- package/dist/lib/evg/apple/Sources/EvgEngineQueue.swift +105 -0
- package/dist/lib/evg/apple/Sources/EvgPainter.swift +225 -0
- package/dist/lib/evg/apple/Sources/EvgSurface.swift +163 -0
- package/dist/lib/evg/apple/Sources/RecordingSurface.swift +110 -0
- package/dist/lib/evg/bench/EvgLayoutBench.rgr +34 -0
- package/dist/lib/evg/bench/README.md +64 -0
- package/dist/lib/evg/bench/layout-bench.mjs +316 -0
- package/dist/lib/evg/bench/layout-cases.mjs +510 -0
- package/dist/lib/evg/bench/layout-conformance.mjs +254 -0
- package/dist/lib/evg/bin/.gitignore +17 -0
- package/dist/lib/evg/evg_test.rgr +313 -0
- package/dist/lib/evg/gl/README.md +198 -0
- package/dist/lib/evg/gl/a11y-paint-check.mjs +73 -0
- package/dist/lib/evg/gl/blur-check.mjs +399 -0
- package/dist/lib/evg/gl/boxmodel.json +1 -0
- package/dist/lib/evg/gl/demo.html +46 -0
- package/dist/lib/evg/gl/effect-presets.css +285 -0
- package/dist/lib/evg/gl/effect-presets.js +63 -0
- package/dist/lib/evg/gl/effect-shots.mjs +135 -0
- package/dist/lib/evg/gl/evg-a11y.js +566 -0
- package/dist/lib/evg/gl/evg-binary.js +160 -0
- package/dist/lib/evg/gl/evg-engine.js +296 -0
- package/dist/lib/evg/gl/evg-fx.js +237 -0
- package/dist/lib/evg/gl/evg-gestures.js +209 -0
- package/dist/lib/evg/gl/evg-list.js +167 -0
- package/dist/lib/evg/gl/evg-measure.js +186 -0
- package/dist/lib/evg/gl/evg-textinput.js +303 -0
- package/dist/lib/evg/gl/evg-view.js +144 -0
- package/dist/lib/evg/gl/evg-webgl.js +3942 -0
- package/dist/lib/evg/gl/fx-check.mjs +998 -0
- package/dist/lib/evg/gl/fx-demo.html +166 -0
- package/dist/lib/evg/gl/fx-demo.js +2 -0
- package/dist/lib/evg/gl/fx-serve.mjs +47 -0
- package/dist/lib/evg/gl/gestures-check.mjs +189 -0
- package/dist/lib/evg/gl/list-binary-check.mjs +152 -0
- package/dist/lib/evg/gl/measure-check.mjs +135 -0
- package/dist/lib/evg/gl/rotation-check.mjs +207 -0
- package/dist/lib/evg/gl/shift-check.mjs +113 -0
- package/dist/lib/evg/gl/stroke-check.mjs +168 -0
- package/dist/lib/evg/gl/text-snap-check.mjs +139 -0
- package/dist/lib/evg/gl/view-check.mjs +343 -0
- package/dist/lib/evg/gl/view-policy-check.mjs +184 -0
- package/dist/lib/evg/html/evg-dom.js +318 -0
- package/dist/lib/evg/html/evg-html.js +600 -0
- package/dist/lib/evg/inspect/README.md +415 -0
- package/dist/lib/evg/inspect/browser-smoke.mjs +115 -0
- package/dist/lib/evg/inspect/evg-inspect.js +947 -0
- package/dist/lib/evg/inspect/shots/css.png +0 -0
- package/dist/lib/evg/inspect/shots/dashboard.png +0 -0
- package/dist/lib/evg/inspect/shots/pptx-slide.png +0 -0
- package/dist/lib/evg/inspect/shots/state.png +0 -0
- package/dist/lib/evg/inspect/shots.mjs +226 -0
- package/dist/lib/evg/oracle/css-blur.json +576 -0
- package/dist/lib/evg/oracle/css-box.json +157 -0
- package/dist/lib/evg/oracle/css-timing.json +709 -0
- package/dist/lib/evg/oracle/css_blur_oracle.mjs +529 -0
- package/dist/lib/evg/oracle/css_box_oracle.mjs +106 -0
- package/dist/lib/evg/oracle/css_timing_oracle.mjs +389 -0
- package/dist/lib/evg/original/EVGColor.clj +310 -0
- package/dist/lib/evg/original/EVGColorContext.rgr +178 -0
- package/dist/lib/evg/original/SVGPath.rgr +627 -0
- package/dist/lib/evg/original/Vec2.crgr +103 -0
- package/dist/lib/evg/ranger.json +9 -0
- package/dist/lib/evg/showcase/README.md +246 -0
- package/dist/lib/evg/showcase/assets/emblem.svg +30 -0
- package/dist/lib/evg/showcase/assets/rosette.svg +22 -0
- package/dist/lib/evg/showcase/build.mjs +651 -0
- package/dist/lib/evg/showcase/pages/album.tsx +30 -0
- package/dist/lib/evg/showcase/pages/boxmodel.tsx +37 -0
- package/dist/lib/evg/showcase/pages/cards.tsx +41 -0
- package/dist/lib/evg/showcase/pages/chart_api.tsx +170 -0
- package/dist/lib/evg/showcase/pages/charts.tsx +219 -0
- package/dist/lib/evg/showcase/pages/drawing.tsx +160 -0
- package/dist/lib/evg/showcase/pages/emoji.tsx +91 -0
- package/dist/lib/evg/showcase/pages/flex.tsx +46 -0
- package/dist/lib/evg/showcase/pages/more.tsx +332 -0
- package/dist/lib/evg/showcase/pages/plots.tsx +262 -0
- package/dist/lib/evg/showcase/pages/svg.tsx +63 -0
- package/dist/lib/evg/showcase/pages/tables.tsx +209 -0
- package/dist/lib/evg/showcase/pages/typography.tsx +43 -0
- package/dist/lib/evg/showcase/pages/units.tsx +35 -0
- package/dist/lib/evg/showcase/pages/variants.tsx +233 -0
- package/dist/lib/evg/showcase/pages/vector.tsx +75 -0
- package/dist/lib/evg/showcase/pages/views.tsx +223 -0
- package/dist/lib/evg/showcase/tests/chart_api_smoke.mjs +339 -0
- package/dist/lib/evg/showcase/tests/gl_smoke.mjs +125 -0
- package/dist/lib/evg/showcase/themes/chart_api-default.css +15 -0
- package/dist/lib/evg/showcase/themes/charts-default.css +29 -0
- package/dist/lib/evg/showcase/themes/drawing-default.css +35 -0
- package/dist/lib/evg/showcase/themes/more-default.css +128 -0
- package/dist/lib/evg/showcase/themes/plots-default.css +18 -0
- package/dist/lib/evg/showcase/themes/showcase.css +508 -0
- package/dist/lib/evg/showcase/themes/tables-default.css +123 -0
- package/dist/lib/evg/showcase/themes/variants-default.css +15 -0
- package/dist/lib/evg/showcase/themes/views-default.css +15 -0
- package/dist/lib/evg/tools/bench_vs_potrace.mjs +290 -0
- package/dist/lib/evg/tools/evg_image_tool.rgr +488 -0
- package/dist/lib/evg/tools/evg_trace_bench.rgr +114 -0
- package/dist/lib/evg/tools/evg_trace_cli.rgr +662 -0
- package/dist/lib/evg/tools/evg_trace_cpp_bench.rgr +83 -0
- package/dist/lib/evg/tools/run_trace_bench.sh +74 -0
- package/dist/lib/evg/tools/run_trace_cli_smoke.sh +128 -0
- package/dist/lib/evg/web/responsive/EvgResponsiveCheck.rgr +271 -0
- package/dist/lib/evg/web/responsive/EvgResponsiveDemo.rgr +531 -0
- package/dist/lib/evg/web/responsive/README.md +97 -0
- package/dist/lib/evg/web/responsive/build.mjs +90 -0
- package/dist/lib/evg/web/responsive/dom-check.mjs +169 -0
- package/dist/lib/evg/web/responsive/index.html +177 -0
- package/dist/lib/evg/web/responsive/smoke.mjs +221 -0
- package/dist/lib/evg/web/tools/assets-client.mjs +95 -0
- package/dist/lib/evg/web/tools/boot-bench.mjs +189 -0
- package/dist/lib/evg/web/tools/inline-assets.mjs +119 -0
- package/dist/lib/evg/web/tools/minify.mjs +60 -0
- package/dist/lib/evg/web/tracer/build.mjs +87 -0
- package/dist/lib/evg/web/tracer/index.html +2805 -0
- package/dist/lib/evg/web/tracer/sample.png +0 -0
- package/dist/lib/evg/web/tracer/smoke.mjs +1162 -0
- package/dist/lib/evgr/Cargo.lock +21 -0
- package/dist/lib/evgr/Cargo.toml +19 -0
- package/dist/lib/evgr/README.md +140 -0
- package/dist/lib/evgr/bench/NativeBench.rgr +246 -0
- package/dist/lib/evgr/bench/compare.mjs +252 -0
- package/dist/lib/evgr/bench/speed.mjs +277 -0
- package/dist/lib/evgr/bin/.gitignore +3 -0
- package/dist/lib/evgr/src/bin/bench.rs +106 -0
- package/dist/lib/evgr/src/bin/smoke.rs +13 -0
- package/dist/lib/evgr/src/grid.rs +730 -0
- package/dist/lib/evgr/src/lib.rs +1003 -0
- package/dist/lib/evgr/src/style.rs +468 -0
- package/dist/lib/evgr/src/text.rs +83 -0
- package/dist/lib/image/BitReader.rgr +171 -0
- package/dist/lib/image/Buffer.rgr +173 -0
- package/dist/lib/image/DCT.rgr +283 -0
- package/dist/lib/image/Deflate.rgr +339 -0
- package/dist/lib/image/HuffmanDecoder.rgr +181 -0
- package/dist/lib/image/ImageBuffer.rgr +706 -0
- package/dist/lib/image/JPEGDecoder.rgr +808 -0
- package/dist/lib/image/PNGDecoder.rgr +544 -0
- package/dist/lib/image/PNGEncoder.rgr +388 -0
- package/dist/lib/image/PPMImage.rgr +224 -0
- package/dist/lib/image/ProgressiveJPEGDecoder.rgr +1154 -0
- package/dist/lib/image/README.md +33 -0
- package/dist/lib/image/RasterBuffer.rgr +294 -0
- package/dist/lib/image/VP8BoolDecoder.rgr +163 -0
- package/dist/lib/image/WebPDecoder.rgr +433 -0
- package/dist/lib/image/WebPLossless.rgr +1035 -0
- package/dist/lib/image/WebPLossy.rgr +1929 -0
- package/dist/lib/image/ranger.json +9 -0
- package/dist/lib/image/testdata/webp/anim_2f_24x16.webp +0 -0
- package/dist/lib/image/testdata/webp/fixtures.txt +33 -0
- package/dist/lib/image/testdata/webp/gen_fixtures.py +261 -0
- package/dist/lib/image/testdata/webp/ll_1x1.webp +0 -0
- package/dist/lib/image/testdata/webp/ll_alpha_29x21.webp +0 -0
- package/dist/lib/image/testdata/webp/ll_gradient_64x64.webp +0 -0
- package/dist/lib/image/testdata/webp/ll_meta_32x32.webp +0 -0
- package/dist/lib/image/testdata/webp/ll_noise_17x9.webp +0 -0
- package/dist/lib/image/testdata/webp/ll_pal11_23x11.webp +0 -0
- package/dist/lib/image/testdata/webp/ll_pal2_19x7.webp +0 -0
- package/dist/lib/image/testdata/webp/ll_pal40_16x16.webp +0 -0
- package/dist/lib/image/testdata/webp/ll_pal4_13x5.webp +0 -0
- package/dist/lib/image/testdata/webp/ll_photo_40x30.webp +0 -0
- package/dist/lib/image/testdata/webp/ll_predictors_64x32.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_1x1.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_alph_raw_f0_21x13.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_alph_raw_f1_21x13.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_alph_raw_f2_21x13.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_alph_raw_f3_21x13.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_alph_vp8l_f0_21x13.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_alph_vp8l_f1_21x13.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_alph_vp8l_f2_21x13.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_alph_vp8l_f3_21x13.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_alpha_33x17.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_exif_15x11.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_i16_96x80.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_nofilter_24x20.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_odd_17x9.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_photo_48x40.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_q100_20x18.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_sharp_40x36.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_simple_filter_33x31.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_vpx_parts8_37x45.webp +0 -0
- package/dist/lib/image/testdata/webp/ly_vpx_skip_96x80.webp +0 -0
- package/dist/lib/image/tests/WebPDecodeTool.rgr +81 -0
- package/dist/lib/image/tests/WebPDecoderTest.rgr +1162 -0
- package/dist/lib/image/tests/run_webp_tests.sh +39 -0
- package/dist/lib/rust/RsJson.rgr +468 -0
- package/dist/lib/rust/RsPrelude.rgr +1663 -0
- package/dist/lib/shell_test.rgr +7 -7
- package/dist/lib/stdlib.rgr +21 -5
- package/dist/lib/zip/ranger.json +6 -0
- package/dist/rgrc.js +87318 -67610
- package/package.json +1010 -1040
- package/dist/README.md +0 -117
- package/dist/package.json +0 -47
|
@@ -0,0 +1,721 @@
|
|
|
1
|
+
; SPDX-License-Identifier: MIT
|
|
2
|
+
|
|
3
|
+
; ==============================================================================
|
|
4
|
+
; EVGTreeJson — a tree on disk, in exactly the set that can be edited
|
|
5
|
+
; ==============================================================================
|
|
6
|
+
;
|
|
7
|
+
; The display list has had `toJson` for a long time, because a GPU backend and
|
|
8
|
+
; a remote viewer both read it. The TREE never did: it was always built in
|
|
9
|
+
; code, laid out, drawn, and thrown away. An agent editing a document needs it
|
|
10
|
+
; to survive between two processes, so here it is.
|
|
11
|
+
;
|
|
12
|
+
; --- THE FORMAT IS THE PATCHABLE SET ------------------------------------------
|
|
13
|
+
;
|
|
14
|
+
; A node says its tag, its identity, its text, and then `props` — and `props`
|
|
15
|
+
; is exactly `EVGPatch.patchableNames()`, nothing more. That is not a shortcut,
|
|
16
|
+
; it is the invariant worth having: **what can be written down is what can be
|
|
17
|
+
; edited, and what can be edited can be undone.** A property outside that set
|
|
18
|
+
; cannot appear in a file, so no file can carry a value an edit would silently
|
|
19
|
+
; drop.
|
|
20
|
+
;
|
|
21
|
+
; The cost is stated plainly: this is not a lossless container for an arbitrary
|
|
22
|
+
; EVG tree. A `path` element's `d`, an image's `alt`, a viewBox — the engine
|
|
23
|
+
; has them and this format does not. Converting a document INTO this format
|
|
24
|
+
; (from JSX, from a `.fig`) therefore loses what the patchable set does not
|
|
25
|
+
; cover, and a converter has to say so rather than round-trip through here and
|
|
26
|
+
; call it identity.
|
|
27
|
+
;
|
|
28
|
+
; --- ONLY DEFAULTS ARE OMITTED ------------------------------------------------
|
|
29
|
+
;
|
|
30
|
+
; A property is written when it differs from what a FRESH ELEMENT OF THE SAME
|
|
31
|
+
; TAG reads — not from a fixed table of defaults, because a span and a div do
|
|
32
|
+
; not agree about all of them. `EVGPatch.readProp` answers both sides, so the
|
|
33
|
+
; comparison is between two answers from one reader and cannot drift.
|
|
34
|
+
;
|
|
35
|
+
; --- THE READER READS WHAT THIS WRITER WRITES ---------------------------------
|
|
36
|
+
;
|
|
37
|
+
; The scanner below is deliberately not a general JSON parser. It handles the
|
|
38
|
+
; escapes this file emits (quote, backslash, newline, return, tab) and no
|
|
39
|
+
; others, because a general parser here would be a second, unrelated thing to
|
|
40
|
+
; get right and to test. A file from somewhere else is not this format.
|
|
41
|
+
; ==============================================================================
|
|
42
|
+
|
|
43
|
+
Import "EVGCodepoint.rgr"
|
|
44
|
+
Import "EVGElement.rgr"
|
|
45
|
+
Import "EVGPatch.rgr"
|
|
46
|
+
|
|
47
|
+
class EVGTreeJson {
|
|
48
|
+
|
|
49
|
+
; --- writing --------------------------------------------------------------
|
|
50
|
+
|
|
51
|
+
sfn toText:string (root:EVGElement) {
|
|
52
|
+
def w (new EVGTreeJson())
|
|
53
|
+
def out:string "{\"evg\":1"
|
|
54
|
+
; The stylesheet first, because it is the document talking about
|
|
55
|
+
; itself and a reader opening the file should meet it before the tree.
|
|
56
|
+
if ((strlen root.documentCss) > 0) {
|
|
57
|
+
out = ((out + ",\"css\":") + (EVGTreeJson.str(root.documentCss)))
|
|
58
|
+
}
|
|
59
|
+
out = (out + ",\"root\":")
|
|
60
|
+
out = (out + (w.node(root 1)))
|
|
61
|
+
out = (out + "}")
|
|
62
|
+
return out
|
|
63
|
+
} doc {
|
|
64
|
+
description "Writes a tree as JSON carrying every patchable property that differs from a fresh element."
|
|
65
|
+
param root "The tree to write."
|
|
66
|
+
returns "The document text."
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
sfn withCss@(optional):EVGElement (root@(optional):EVGElement css:string) {
|
|
70
|
+
if (null? root) {
|
|
71
|
+
return root
|
|
72
|
+
}
|
|
73
|
+
if ((strlen css) == 0) {
|
|
74
|
+
return root
|
|
75
|
+
}
|
|
76
|
+
def el:EVGElement (unwrap root)
|
|
77
|
+
el.documentCss = css
|
|
78
|
+
def out@(optional):EVGElement el
|
|
79
|
+
return out
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
fn node:string (el:EVGElement depth:int) {
|
|
83
|
+
def pad:string (EVGTreeJson.indent(depth))
|
|
84
|
+
def inner:string (EVGTreeJson.indent((depth + 1)))
|
|
85
|
+
def out:string "{"
|
|
86
|
+
out = (((out + "\"tag\":") + (EVGTreeJson.str(el.tagName))))
|
|
87
|
+
if ((strlen el.id) > 0) {
|
|
88
|
+
out = (((out + ",\"id\":") + (EVGTreeJson.str(el.id))))
|
|
89
|
+
}
|
|
90
|
+
if ((strlen el.key) > 0) {
|
|
91
|
+
out = (((out + ",\"key\":") + (EVGTreeJson.str(el.key))))
|
|
92
|
+
}
|
|
93
|
+
if ((strlen el.textContent) > 0) {
|
|
94
|
+
out = (((out + ",\"text\":") + (EVGTreeJson.str(el.textContent))))
|
|
95
|
+
}
|
|
96
|
+
; WHAT THE NODE IS, not how it looks. A document that carries a real
|
|
97
|
+
; control has to be able to say so: without this a switch is a pill
|
|
98
|
+
; with a knob in it, indistinguishable from one somebody drew, and
|
|
99
|
+
; everything reading the document afterwards — the accessibility tree,
|
|
100
|
+
; the layout check that names drawn controls — has to guess.
|
|
101
|
+
if ((strlen el.role) > 0) {
|
|
102
|
+
out = (((out + ",\"role\":") + (EVGTreeJson.str(el.role))))
|
|
103
|
+
}
|
|
104
|
+
if ((strlen el.a11yLabel) > 0) {
|
|
105
|
+
out = (((out + ",\"label\":") + (EVGTreeJson.str(el.a11yLabel))))
|
|
106
|
+
}
|
|
107
|
+
if (el.a11yHidden) {
|
|
108
|
+
out = (out + ",\"hidden\":true")
|
|
109
|
+
}
|
|
110
|
+
; 0 not applicable, 1 no, 2 yes — the tri-state a checkbox needs.
|
|
111
|
+
if (el.a11yChecked > 0) {
|
|
112
|
+
out = ((out + ",\"checked\":") + (to_string el.a11yChecked))
|
|
113
|
+
}
|
|
114
|
+
def props:string (this.props(el))
|
|
115
|
+
if ((strlen props) > 0) {
|
|
116
|
+
out = ((((out + ",\"props\":{") + props) + "}"))
|
|
117
|
+
}
|
|
118
|
+
def n:int (array_length el.children)
|
|
119
|
+
if (n > 0) {
|
|
120
|
+
out = (out + ",\"children\":[")
|
|
121
|
+
def i:int 0
|
|
122
|
+
while (i < n) {
|
|
123
|
+
if (i > 0) {
|
|
124
|
+
out = (out + ",")
|
|
125
|
+
}
|
|
126
|
+
out = (out + "\n")
|
|
127
|
+
out = (out + inner)
|
|
128
|
+
def kid:EVGElement (itemAt el.children i)
|
|
129
|
+
out = (out + (this.node(kid (depth + 1))))
|
|
130
|
+
i = (i + 1)
|
|
131
|
+
}
|
|
132
|
+
out = (out + "\n")
|
|
133
|
+
out = (out + pad)
|
|
134
|
+
out = (out + "]")
|
|
135
|
+
}
|
|
136
|
+
out = (out + "}")
|
|
137
|
+
return out
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
; What this node says that a fresh one of its tag does not.
|
|
141
|
+
fn props:string (el:EVGElement) {
|
|
142
|
+
def fresh@(optional):EVGElement (EVGPatch.create(el.tagName))
|
|
143
|
+
if (null? fresh) {
|
|
144
|
+
return ""
|
|
145
|
+
}
|
|
146
|
+
def blank:EVGElement (unwrap fresh)
|
|
147
|
+
def names:[string] (EVGPatch.patchableNames())
|
|
148
|
+
def out:string ""
|
|
149
|
+
def wrote:int 0
|
|
150
|
+
def i:int 0
|
|
151
|
+
while (i < (array_length names)) {
|
|
152
|
+
def name:string (itemAt names i)
|
|
153
|
+
def mine:string (EVGPatch.readProp(el name))
|
|
154
|
+
def theirs:string (EVGPatch.readProp(blank name))
|
|
155
|
+
; A value the sheet put there belongs to the sheet. Writing it
|
|
156
|
+
; down as well would copy the rule onto every node it matched and
|
|
157
|
+
; leave the document saying the same thing twice.
|
|
158
|
+
if ((mine != theirs) && ((el.fromCss(name)) == false)) {
|
|
159
|
+
if (wrote > 0) {
|
|
160
|
+
out = (out + ",")
|
|
161
|
+
}
|
|
162
|
+
out = (out + (EVGTreeJson.str(name)))
|
|
163
|
+
out = (out + ":")
|
|
164
|
+
out = (out + (EVGTreeJson.str(mine)))
|
|
165
|
+
wrote = (wrote + 1)
|
|
166
|
+
}
|
|
167
|
+
i = (i + 1)
|
|
168
|
+
}
|
|
169
|
+
; `evg-fx-*` is a family, not a list: the names belong to whichever
|
|
170
|
+
; plugin reads them, so `patchableNames` cannot carry them and this
|
|
171
|
+
; asks the element what it has. A fresh element has none, so anything
|
|
172
|
+
; here is by definition something the document must say.
|
|
173
|
+
def fx:[string] (EVGPatch.fxNamesOf(el))
|
|
174
|
+
def k:int 0
|
|
175
|
+
while (k < (array_length fx)) {
|
|
176
|
+
def fxName:string (itemAt fx k)
|
|
177
|
+
if (el.fromCss(fxName)) {
|
|
178
|
+
k = (k + 1)
|
|
179
|
+
} {
|
|
180
|
+
if (wrote > 0) {
|
|
181
|
+
out = (out + ",")
|
|
182
|
+
}
|
|
183
|
+
out = (out + (EVGTreeJson.str(fxName)))
|
|
184
|
+
out = (out + ":")
|
|
185
|
+
out = (out + (EVGTreeJson.str((EVGPatch.readProp(el fxName)))))
|
|
186
|
+
wrote = (wrote + 1)
|
|
187
|
+
k = (k + 1)
|
|
188
|
+
}
|
|
189
|
+
}
|
|
190
|
+
return out
|
|
191
|
+
}
|
|
192
|
+
|
|
193
|
+
sfn indent:string (depth:int) {
|
|
194
|
+
def s:string ""
|
|
195
|
+
def i:int 0
|
|
196
|
+
while (i < depth) {
|
|
197
|
+
s = (s + " ")
|
|
198
|
+
i = (i + 1)
|
|
199
|
+
}
|
|
200
|
+
return s
|
|
201
|
+
}
|
|
202
|
+
|
|
203
|
+
; Quote, backslash and the three control characters a document actually
|
|
204
|
+
; contains. Everything else goes out as it came in — UTF-8 is valid JSON.
|
|
205
|
+
sfn str:string (v:string) {
|
|
206
|
+
def out:string "\""
|
|
207
|
+
def i:int 0
|
|
208
|
+
def n:int (strlen v)
|
|
209
|
+
while (i < n) {
|
|
210
|
+
def c:int (charAt v i)
|
|
211
|
+
if (c == 34) {
|
|
212
|
+
out = (out + "\\\"")
|
|
213
|
+
} {
|
|
214
|
+
if (c == 92) {
|
|
215
|
+
out = (out + "\\\\")
|
|
216
|
+
} {
|
|
217
|
+
if (c == 10) {
|
|
218
|
+
out = (out + "\\n")
|
|
219
|
+
} {
|
|
220
|
+
if (c == 13) {
|
|
221
|
+
out = (out + "\\r")
|
|
222
|
+
} {
|
|
223
|
+
if (c == 9) {
|
|
224
|
+
out = (out + "\\t")
|
|
225
|
+
} {
|
|
226
|
+
out = (out + (substring v i (i + 1)))
|
|
227
|
+
}
|
|
228
|
+
}
|
|
229
|
+
}
|
|
230
|
+
}
|
|
231
|
+
}
|
|
232
|
+
i = (i + 1)
|
|
233
|
+
}
|
|
234
|
+
return (out + "\"")
|
|
235
|
+
}
|
|
236
|
+
|
|
237
|
+
|
|
238
|
+
; One node, without its subtree — what `query` answers with.
|
|
239
|
+
;
|
|
240
|
+
; `EVGInspect.nodeJson` exists and is NOT what to use here. It reports
|
|
241
|
+
; every computed property including the resolved pixels, which is right for
|
|
242
|
+
; an inspector looking at a laid-out frame and wrong for a query: nothing
|
|
243
|
+
; has run layout, so it would report `padding-left: 0.00px` for a document
|
|
244
|
+
; that plainly says 16px. This answers with what the document says.
|
|
245
|
+
sfn brief:string (path:string el:EVGElement) {
|
|
246
|
+
def w (new EVGTreeJson())
|
|
247
|
+
def out:string "{\"at\":"
|
|
248
|
+
out = (out + (EVGTreeJson.str(path)))
|
|
249
|
+
out = ((out + ",\"tag\":") + (EVGTreeJson.str(el.tagName)))
|
|
250
|
+
if ((strlen el.id) > 0) {
|
|
251
|
+
out = ((out + ",\"id\":") + (EVGTreeJson.str(el.id)))
|
|
252
|
+
}
|
|
253
|
+
if ((strlen el.key) > 0) {
|
|
254
|
+
out = ((out + ",\"key\":") + (EVGTreeJson.str(el.key)))
|
|
255
|
+
}
|
|
256
|
+
if ((strlen el.textContent) > 0) {
|
|
257
|
+
out = ((out + ",\"text\":") + (EVGTreeJson.str(el.textContent)))
|
|
258
|
+
}
|
|
259
|
+
def props:string (w.props(el))
|
|
260
|
+
if ((strlen props) > 0) {
|
|
261
|
+
out = (((out + ",\"props\":{") + props) + "}")
|
|
262
|
+
}
|
|
263
|
+
out = ((out + ",\"children\":") + (to_string (array_length el.children)))
|
|
264
|
+
return (out + "}")
|
|
265
|
+
}
|
|
266
|
+
|
|
267
|
+
; --- reading --------------------------------------------------------------
|
|
268
|
+
|
|
269
|
+
sfn fromText@(optional):EVGElement (text:string) {
|
|
270
|
+
def c (new EVGJsonCursor())
|
|
271
|
+
c.src = text
|
|
272
|
+
c.at = 0
|
|
273
|
+
c.skipWs()
|
|
274
|
+
if ((c.take()) != 123) {
|
|
275
|
+
def bad@(optional):EVGElement
|
|
276
|
+
return bad
|
|
277
|
+
}
|
|
278
|
+
def root@(optional):EVGElement
|
|
279
|
+
; `css` may be written before or after `root`, so it is held until the
|
|
280
|
+
; object closes rather than assumed to arrive second.
|
|
281
|
+
def css:string ""
|
|
282
|
+
def guard:int 0
|
|
283
|
+
while ((c.ok) && (guard < 64)) {
|
|
284
|
+
c.skipWs()
|
|
285
|
+
def ch:int (c.peek())
|
|
286
|
+
if (ch == 125) {
|
|
287
|
+
def closing:int (c.take())
|
|
288
|
+
return (EVGTreeJson.withCss(root css))
|
|
289
|
+
}
|
|
290
|
+
if (ch == 44) {
|
|
291
|
+
def comma:int (c.take())
|
|
292
|
+
} {
|
|
293
|
+
def key:string (c.readString())
|
|
294
|
+
c.skipWs()
|
|
295
|
+
def colon:int (c.take())
|
|
296
|
+
if (key == "root") {
|
|
297
|
+
root = (c.readNode())
|
|
298
|
+
} {
|
|
299
|
+
if (key == "css") {
|
|
300
|
+
css = (c.readString())
|
|
301
|
+
} {
|
|
302
|
+
c.skipValue()
|
|
303
|
+
}
|
|
304
|
+
}
|
|
305
|
+
}
|
|
306
|
+
guard = (guard + 1)
|
|
307
|
+
}
|
|
308
|
+
return (EVGTreeJson.withCss(root css))
|
|
309
|
+
} doc {
|
|
310
|
+
description "Reads a tree back from the format `write` produces."
|
|
311
|
+
param text "The document text."
|
|
312
|
+
returns "The root element, or nothing when the text is not this format."
|
|
313
|
+
}
|
|
314
|
+
}
|
|
315
|
+
|
|
316
|
+
; A scanner over one document. `ok` goes false at the first thing the format
|
|
317
|
+
; does not allow and never goes back: a half-read tree is not a tree, and the
|
|
318
|
+
; caller gets nothing rather than something plausible.
|
|
319
|
+
class EVGJsonCursor {
|
|
320
|
+
def src:string ""
|
|
321
|
+
def at:int 0
|
|
322
|
+
def ok:boolean true
|
|
323
|
+
|
|
324
|
+
Constructor () {}
|
|
325
|
+
|
|
326
|
+
fn peek:int () {
|
|
327
|
+
if (at >= (strlen src)) {
|
|
328
|
+
return 0
|
|
329
|
+
}
|
|
330
|
+
return (charAt src at)
|
|
331
|
+
}
|
|
332
|
+
|
|
333
|
+
fn take:int () {
|
|
334
|
+
def c:int (this.peek())
|
|
335
|
+
at = (at + 1)
|
|
336
|
+
return c
|
|
337
|
+
}
|
|
338
|
+
|
|
339
|
+
fn skipWs:void () {
|
|
340
|
+
while (at < (strlen src)) {
|
|
341
|
+
def c:int (charAt src at)
|
|
342
|
+
if ((((c == 32) || (c == 10)) || (c == 13)) || (c == 9)) {
|
|
343
|
+
at = (at + 1)
|
|
344
|
+
} {
|
|
345
|
+
return
|
|
346
|
+
}
|
|
347
|
+
}
|
|
348
|
+
}
|
|
349
|
+
|
|
350
|
+
fn readString:string () {
|
|
351
|
+
this.skipWs()
|
|
352
|
+
if ((this.peek()) != 34) {
|
|
353
|
+
ok = false
|
|
354
|
+
return ""
|
|
355
|
+
}
|
|
356
|
+
def opening:int (this.take())
|
|
357
|
+
def out:string ""
|
|
358
|
+
while (at < (strlen src)) {
|
|
359
|
+
def c:int (this.take())
|
|
360
|
+
if (c == 34) {
|
|
361
|
+
return out
|
|
362
|
+
}
|
|
363
|
+
if (c == 92) {
|
|
364
|
+
def e:int (this.take())
|
|
365
|
+
if (e == 110) {
|
|
366
|
+
out = (out + "\n")
|
|
367
|
+
} {
|
|
368
|
+
if (e == 114) {
|
|
369
|
+
out = (out + "\r")
|
|
370
|
+
} {
|
|
371
|
+
if (e == 116) {
|
|
372
|
+
out = (out + "\t")
|
|
373
|
+
} {
|
|
374
|
+
; \uXXXX. Without this the backslash was dropped
|
|
375
|
+
; and the four hex digits were read as text, so a
|
|
376
|
+
; `\u00b7` written by an agent reached the screen
|
|
377
|
+
; as the literal `u00b7` — which is exactly what it
|
|
378
|
+
; looked like, and reads as a broken font rather
|
|
379
|
+
; than a broken parser.
|
|
380
|
+
if (e == 117) {
|
|
381
|
+
out = (out + (this.readEscape()))
|
|
382
|
+
} {
|
|
383
|
+
out = (out + (substring src (at - 1) at))
|
|
384
|
+
}
|
|
385
|
+
}
|
|
386
|
+
}
|
|
387
|
+
}
|
|
388
|
+
} {
|
|
389
|
+
out = (out + (substring src (at - 1) at))
|
|
390
|
+
}
|
|
391
|
+
}
|
|
392
|
+
ok = false
|
|
393
|
+
return out
|
|
394
|
+
}
|
|
395
|
+
|
|
396
|
+
|
|
397
|
+
; One `\uXXXX`, already past the `u`, as the character it names. A high
|
|
398
|
+
; surrogate takes the `\uXXXX` after it as its pair, because that is how
|
|
399
|
+
; JSON writes anything above U+FFFF — every emoji, among other things — and
|
|
400
|
+
; half a pair is not a character.
|
|
401
|
+
fn readEscape:string () {
|
|
402
|
+
def cp:int (this.hex4())
|
|
403
|
+
if (cp < 0) {
|
|
404
|
+
return "u"
|
|
405
|
+
}
|
|
406
|
+
if (EVGCodepoint.isHighSurrogate(cp)) {
|
|
407
|
+
def save:int at
|
|
408
|
+
if ((at + 1) < (strlen src)) {
|
|
409
|
+
if ((charAt src at) == 92) {
|
|
410
|
+
if ((charAt src (at + 1)) == 117) {
|
|
411
|
+
at = (at + 2)
|
|
412
|
+
def lo:int (this.hex4())
|
|
413
|
+
if (EVGCodepoint.isLowSurrogate(lo)) {
|
|
414
|
+
cp = (65536 + ((((cp - 55296) * 1024)) + (lo - 56320)))
|
|
415
|
+
} {
|
|
416
|
+
at = save
|
|
417
|
+
}
|
|
418
|
+
}
|
|
419
|
+
}
|
|
420
|
+
}
|
|
421
|
+
}
|
|
422
|
+
return (EVGCodepoint.toStr(cp))
|
|
423
|
+
}
|
|
424
|
+
|
|
425
|
+
; Four hex digits, or -1 when they are not there. `at` only moves when all
|
|
426
|
+
; four were read, so a malformed escape is left exactly as written.
|
|
427
|
+
fn hex4:int () {
|
|
428
|
+
if ((at + 4) > (strlen src)) {
|
|
429
|
+
return (0 - 1)
|
|
430
|
+
}
|
|
431
|
+
def out:int 0
|
|
432
|
+
def i:int 0
|
|
433
|
+
while (i < 4) {
|
|
434
|
+
def d:int (EVGJsonCursor.hexDigit((charAt src (at + i))))
|
|
435
|
+
if (d < 0) {
|
|
436
|
+
return (0 - 1)
|
|
437
|
+
}
|
|
438
|
+
out = ((out * 16) + d)
|
|
439
|
+
i = (i + 1)
|
|
440
|
+
}
|
|
441
|
+
at = (at + 4)
|
|
442
|
+
return out
|
|
443
|
+
}
|
|
444
|
+
|
|
445
|
+
sfn hexDigit:int (c:int) {
|
|
446
|
+
if ((c >= 48) && (c <= 57)) {
|
|
447
|
+
return (c - 48)
|
|
448
|
+
}
|
|
449
|
+
if ((c >= 97) && (c <= 102)) {
|
|
450
|
+
return ((c - 97) + 10)
|
|
451
|
+
}
|
|
452
|
+
if ((c >= 65) && (c <= 70)) {
|
|
453
|
+
return ((c - 65) + 10)
|
|
454
|
+
}
|
|
455
|
+
return (0 - 1)
|
|
456
|
+
}
|
|
457
|
+
|
|
458
|
+
; Numbers appear in an ops file (`index`), never in a document, so this is
|
|
459
|
+
; small on purpose: an optional minus and digits.
|
|
460
|
+
; `true` or `false`; anything else is stepped over and answers false.
|
|
461
|
+
fn readBool:boolean () {
|
|
462
|
+
this.skipWs()
|
|
463
|
+
if ((this.peek()) == 116) {
|
|
464
|
+
def i:int 0
|
|
465
|
+
while (i < 4) {
|
|
466
|
+
def taken:int (this.take())
|
|
467
|
+
i = (i + 1)
|
|
468
|
+
}
|
|
469
|
+
return true
|
|
470
|
+
}
|
|
471
|
+
this.skipValue()
|
|
472
|
+
return false
|
|
473
|
+
}
|
|
474
|
+
|
|
475
|
+
fn readNumber:int () {
|
|
476
|
+
this.skipWs()
|
|
477
|
+
def neg:boolean false
|
|
478
|
+
if ((this.peek()) == 45) {
|
|
479
|
+
neg = true
|
|
480
|
+
at = (at + 1)
|
|
481
|
+
}
|
|
482
|
+
def v:int 0
|
|
483
|
+
def digits:int 0
|
|
484
|
+
while (at < (strlen src)) {
|
|
485
|
+
def c:int (this.peek())
|
|
486
|
+
if ((c >= 48) && (c <= 57)) {
|
|
487
|
+
v = ((v * 10) + (c - 48))
|
|
488
|
+
digits = (digits + 1)
|
|
489
|
+
at = (at + 1)
|
|
490
|
+
} {
|
|
491
|
+
if (digits == 0) {
|
|
492
|
+
ok = false
|
|
493
|
+
}
|
|
494
|
+
if neg {
|
|
495
|
+
return (0 - v)
|
|
496
|
+
}
|
|
497
|
+
return v
|
|
498
|
+
}
|
|
499
|
+
}
|
|
500
|
+
if (digits == 0) {
|
|
501
|
+
ok = false
|
|
502
|
+
}
|
|
503
|
+
if neg {
|
|
504
|
+
return (0 - v)
|
|
505
|
+
}
|
|
506
|
+
return v
|
|
507
|
+
}
|
|
508
|
+
|
|
509
|
+
; Enough to step over a value this format does not use — a number, a
|
|
510
|
+
; boolean, null, or a nested object or array.
|
|
511
|
+
fn skipValue:void () {
|
|
512
|
+
this.skipWs()
|
|
513
|
+
def c:int (this.peek())
|
|
514
|
+
if (c == 34) {
|
|
515
|
+
def ignored:string (this.readString())
|
|
516
|
+
return
|
|
517
|
+
}
|
|
518
|
+
if ((c == 123) || (c == 91)) {
|
|
519
|
+
def depth:int 0
|
|
520
|
+
while (at < (strlen src)) {
|
|
521
|
+
def d:int (this.take())
|
|
522
|
+
if ((d == 123) || (d == 91)) {
|
|
523
|
+
depth = (depth + 1)
|
|
524
|
+
}
|
|
525
|
+
if ((d == 125) || (d == 93)) {
|
|
526
|
+
depth = (depth - 1)
|
|
527
|
+
if (depth == 0) {
|
|
528
|
+
return
|
|
529
|
+
}
|
|
530
|
+
}
|
|
531
|
+
if (d == 34) {
|
|
532
|
+
at = (at - 1)
|
|
533
|
+
def inner:string (this.readString())
|
|
534
|
+
}
|
|
535
|
+
}
|
|
536
|
+
ok = false
|
|
537
|
+
return
|
|
538
|
+
}
|
|
539
|
+
while (at < (strlen src)) {
|
|
540
|
+
def e:int (this.peek())
|
|
541
|
+
if ((((e == 44) || (e == 125)) || (e == 93)) || (e == 32)) {
|
|
542
|
+
return
|
|
543
|
+
}
|
|
544
|
+
at = (at + 1)
|
|
545
|
+
}
|
|
546
|
+
}
|
|
547
|
+
|
|
548
|
+
fn readNode@(optional):EVGElement () {
|
|
549
|
+
this.skipWs()
|
|
550
|
+
if ((this.take()) != 123) {
|
|
551
|
+
ok = false
|
|
552
|
+
def bad@(optional):EVGElement
|
|
553
|
+
return bad
|
|
554
|
+
}
|
|
555
|
+
; The tag decides which element to make, and it is not guaranteed to
|
|
556
|
+
; come first, so the node is read into locals and built at the end.
|
|
557
|
+
def tag:string "div"
|
|
558
|
+
def id:string ""
|
|
559
|
+
def key:string ""
|
|
560
|
+
def text:string ""
|
|
561
|
+
; What the node IS, read back the way it was written.
|
|
562
|
+
def role:string ""
|
|
563
|
+
def label:string ""
|
|
564
|
+
def hidden:boolean false
|
|
565
|
+
def checked:int 0
|
|
566
|
+
def propNames:[string]
|
|
567
|
+
def propValues:[string]
|
|
568
|
+
def kids:[EVGElement]
|
|
569
|
+
|
|
570
|
+
while (ok) {
|
|
571
|
+
this.skipWs()
|
|
572
|
+
def ch:int (this.peek())
|
|
573
|
+
if (ch == 125) {
|
|
574
|
+
def closing:int (this.take())
|
|
575
|
+
def made@(optional):EVGElement (EVGPatch.create(tag))
|
|
576
|
+
if (null? made) {
|
|
577
|
+
ok = false
|
|
578
|
+
def none@(optional):EVGElement
|
|
579
|
+
return none
|
|
580
|
+
}
|
|
581
|
+
def el:EVGElement (unwrap made)
|
|
582
|
+
el.id = id
|
|
583
|
+
el.key = key
|
|
584
|
+
el.textContent = text
|
|
585
|
+
el.role = role
|
|
586
|
+
el.a11yLabel = label
|
|
587
|
+
el.a11yHidden = hidden
|
|
588
|
+
el.a11yChecked = checked
|
|
589
|
+
def i:int 0
|
|
590
|
+
while (i < (array_length propNames)) {
|
|
591
|
+
def pn:string (itemAt propNames i)
|
|
592
|
+
def pv:string (itemAt propValues i)
|
|
593
|
+
el.setAttribute(pn pv)
|
|
594
|
+
el.markInline(pn)
|
|
595
|
+
i = (i + 1)
|
|
596
|
+
}
|
|
597
|
+
def k:int 0
|
|
598
|
+
while (k < (array_length kids)) {
|
|
599
|
+
el.addChild((itemAt kids k))
|
|
600
|
+
k = (k + 1)
|
|
601
|
+
}
|
|
602
|
+
def out@(optional):EVGElement el
|
|
603
|
+
return out
|
|
604
|
+
}
|
|
605
|
+
if (ch == 44) {
|
|
606
|
+
def comma:int (this.take())
|
|
607
|
+
} {
|
|
608
|
+
if (ch == 0) {
|
|
609
|
+
ok = false
|
|
610
|
+
} {
|
|
611
|
+
def field:string (this.readString())
|
|
612
|
+
this.skipWs()
|
|
613
|
+
def colon:int (this.take())
|
|
614
|
+
if (field == "tag") {
|
|
615
|
+
tag = (this.readString())
|
|
616
|
+
} {
|
|
617
|
+
if (field == "id") {
|
|
618
|
+
id = (this.readString())
|
|
619
|
+
} {
|
|
620
|
+
if (field == "key") {
|
|
621
|
+
key = (this.readString())
|
|
622
|
+
} {
|
|
623
|
+
if (field == "text") {
|
|
624
|
+
text = (this.readString())
|
|
625
|
+
} {
|
|
626
|
+
if (field == "role") {
|
|
627
|
+
role = (this.readString())
|
|
628
|
+
} {
|
|
629
|
+
if (field == "label") {
|
|
630
|
+
label = (this.readString())
|
|
631
|
+
} {
|
|
632
|
+
if (field == "hidden") {
|
|
633
|
+
hidden = (this.readBool())
|
|
634
|
+
} {
|
|
635
|
+
if (field == "checked") {
|
|
636
|
+
checked = (this.readNumber())
|
|
637
|
+
} {
|
|
638
|
+
if (field == "props") {
|
|
639
|
+
this.readProps(propNames propValues)
|
|
640
|
+
} {
|
|
641
|
+
if (field == "children") {
|
|
642
|
+
this.readChildren(kids)
|
|
643
|
+
} {
|
|
644
|
+
this.skipValue()
|
|
645
|
+
}
|
|
646
|
+
}
|
|
647
|
+
}
|
|
648
|
+
}
|
|
649
|
+
}
|
|
650
|
+
}
|
|
651
|
+
}
|
|
652
|
+
}
|
|
653
|
+
}
|
|
654
|
+
}
|
|
655
|
+
}
|
|
656
|
+
}
|
|
657
|
+
}
|
|
658
|
+
def failed@(optional):EVGElement
|
|
659
|
+
return failed
|
|
660
|
+
}
|
|
661
|
+
|
|
662
|
+
fn readProps:void (names:[string] values:[string]) {
|
|
663
|
+
this.skipWs()
|
|
664
|
+
if ((this.take()) != 123) {
|
|
665
|
+
ok = false
|
|
666
|
+
return
|
|
667
|
+
}
|
|
668
|
+
while (ok) {
|
|
669
|
+
this.skipWs()
|
|
670
|
+
def ch:int (this.peek())
|
|
671
|
+
if (ch == 125) {
|
|
672
|
+
def closing:int (this.take())
|
|
673
|
+
return
|
|
674
|
+
}
|
|
675
|
+
if (ch == 44) {
|
|
676
|
+
def comma:int (this.take())
|
|
677
|
+
} {
|
|
678
|
+
if (ch == 0) {
|
|
679
|
+
ok = false
|
|
680
|
+
return
|
|
681
|
+
}
|
|
682
|
+
def name:string (this.readString())
|
|
683
|
+
this.skipWs()
|
|
684
|
+
def colon:int (this.take())
|
|
685
|
+
def value:string (this.readString())
|
|
686
|
+
push names name
|
|
687
|
+
push values value
|
|
688
|
+
}
|
|
689
|
+
}
|
|
690
|
+
}
|
|
691
|
+
|
|
692
|
+
fn readChildren:void (kids:[EVGElement]) {
|
|
693
|
+
this.skipWs()
|
|
694
|
+
if ((this.take()) != 91) {
|
|
695
|
+
ok = false
|
|
696
|
+
return
|
|
697
|
+
}
|
|
698
|
+
while (ok) {
|
|
699
|
+
this.skipWs()
|
|
700
|
+
def ch:int (this.peek())
|
|
701
|
+
if (ch == 93) {
|
|
702
|
+
def closing:int (this.take())
|
|
703
|
+
return
|
|
704
|
+
}
|
|
705
|
+
if (ch == 44) {
|
|
706
|
+
def comma:int (this.take())
|
|
707
|
+
} {
|
|
708
|
+
if (ch == 0) {
|
|
709
|
+
ok = false
|
|
710
|
+
return
|
|
711
|
+
}
|
|
712
|
+
def kid@(optional):EVGElement (this.readNode())
|
|
713
|
+
if (null? kid) {
|
|
714
|
+
ok = false
|
|
715
|
+
return
|
|
716
|
+
}
|
|
717
|
+
push kids (unwrap kid)
|
|
718
|
+
}
|
|
719
|
+
}
|
|
720
|
+
}
|
|
721
|
+
}
|