@krizaka/charts 0.0.0-stage → 0.2.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/LICENSE +202 -0
- package/README.md +59 -2
- package/dist/bar.d.ts +17 -0
- package/dist/bar.js +17 -0
- package/dist/bar.js.map +1 -0
- package/dist/candlestick-IG626XL4.js +13 -0
- package/dist/candlestick-IG626XL4.js.map +1 -0
- package/dist/candlestick.d.ts +42 -0
- package/dist/candlestick.js +13 -0
- package/dist/candlestick.js.map +1 -0
- package/dist/canvas-4MSYDVFO.js +14 -0
- package/dist/canvas-4MSYDVFO.js.map +1 -0
- package/dist/cartesian-BRhNQ3ib.d.ts +34 -0
- package/dist/chart.d.ts +58 -0
- package/dist/chart.js +11 -0
- package/dist/chart.js.map +1 -0
- package/dist/chunk-3CJHBJXA.js +186 -0
- package/dist/chunk-3CJHBJXA.js.map +1 -0
- package/dist/chunk-4LBXEAGC.js +133 -0
- package/dist/chunk-4LBXEAGC.js.map +1 -0
- package/dist/chunk-6FINSUOS.js +49 -0
- package/dist/chunk-6FINSUOS.js.map +1 -0
- package/dist/chunk-AA5EWWYV.js +38 -0
- package/dist/chunk-AA5EWWYV.js.map +1 -0
- package/dist/chunk-ANUCSRUN.js +43 -0
- package/dist/chunk-ANUCSRUN.js.map +1 -0
- package/dist/chunk-ARARFMNE.js +88 -0
- package/dist/chunk-ARARFMNE.js.map +1 -0
- package/dist/chunk-BISL7DYW.js +66 -0
- package/dist/chunk-BISL7DYW.js.map +1 -0
- package/dist/chunk-BV4DBGN7.js +178 -0
- package/dist/chunk-BV4DBGN7.js.map +1 -0
- package/dist/chunk-C4MFZLJM.js +19 -0
- package/dist/chunk-C4MFZLJM.js.map +1 -0
- package/dist/chunk-CSSZLFLO.js +116 -0
- package/dist/chunk-CSSZLFLO.js.map +1 -0
- package/dist/chunk-CVWSMUUB.js +378 -0
- package/dist/chunk-CVWSMUUB.js.map +1 -0
- package/dist/chunk-E5DKBSWX.js +2 -0
- package/dist/chunk-E5DKBSWX.js.map +1 -0
- package/dist/chunk-EEP7PS2L.js +54 -0
- package/dist/chunk-EEP7PS2L.js.map +1 -0
- package/dist/chunk-EQLC2QVN.js +73 -0
- package/dist/chunk-EQLC2QVN.js.map +1 -0
- package/dist/chunk-FINOPIDN.js +2 -0
- package/dist/chunk-FINOPIDN.js.map +1 -0
- package/dist/chunk-G2KF2WL4.js +2 -0
- package/dist/chunk-G2KF2WL4.js.map +1 -0
- package/dist/chunk-I3D7KUGN.js +205 -0
- package/dist/chunk-I3D7KUGN.js.map +1 -0
- package/dist/chunk-IKQV3NSL.js +76 -0
- package/dist/chunk-IKQV3NSL.js.map +1 -0
- package/dist/chunk-JTKR7ZWP.js +468 -0
- package/dist/chunk-JTKR7ZWP.js.map +1 -0
- package/dist/chunk-KNDHO67X.js +78 -0
- package/dist/chunk-KNDHO67X.js.map +1 -0
- package/dist/chunk-L2EKYWVI.js +94 -0
- package/dist/chunk-L2EKYWVI.js.map +1 -0
- package/dist/chunk-MXLITIGU.js +92 -0
- package/dist/chunk-MXLITIGU.js.map +1 -0
- package/dist/chunk-NCIQMRV3.js +155 -0
- package/dist/chunk-NCIQMRV3.js.map +1 -0
- package/dist/chunk-OB5EFDDH.js +118 -0
- package/dist/chunk-OB5EFDDH.js.map +1 -0
- package/dist/chunk-OIRHLJBC.js +83 -0
- package/dist/chunk-OIRHLJBC.js.map +1 -0
- package/dist/chunk-PBQV3B6O.js +145 -0
- package/dist/chunk-PBQV3B6O.js.map +1 -0
- package/dist/chunk-POQIHFAZ.js +2 -0
- package/dist/chunk-POQIHFAZ.js.map +1 -0
- package/dist/chunk-PWMMXRMC.js +234 -0
- package/dist/chunk-PWMMXRMC.js.map +1 -0
- package/dist/chunk-SLEJDQ3A.js +81 -0
- package/dist/chunk-SLEJDQ3A.js.map +1 -0
- package/dist/chunk-TPJDOB7R.js +15 -0
- package/dist/chunk-TPJDOB7R.js.map +1 -0
- package/dist/chunk-VKZZY2QD.js +103 -0
- package/dist/chunk-VKZZY2QD.js.map +1 -0
- package/dist/chunk-W5FX4TU3.js +102 -0
- package/dist/chunk-W5FX4TU3.js.map +1 -0
- package/dist/chunk-W5ILLSPK.js +107 -0
- package/dist/chunk-W5ILLSPK.js.map +1 -0
- package/dist/chunk-WBHFVBSK.js +25 -0
- package/dist/chunk-WBHFVBSK.js.map +1 -0
- package/dist/chunk-WNUFGMS7.js +113 -0
- package/dist/chunk-WNUFGMS7.js.map +1 -0
- package/dist/chunk-WVTIKOII.js +15 -0
- package/dist/chunk-WVTIKOII.js.map +1 -0
- package/dist/chunk-XDDALY4C.js +166 -0
- package/dist/chunk-XDDALY4C.js.map +1 -0
- package/dist/chunk-XLLYNNC6.js +89 -0
- package/dist/chunk-XLLYNNC6.js.map +1 -0
- package/dist/context-BgYUymEO.d.ts +163 -0
- package/dist/credits.d.ts +42 -0
- package/dist/credits.js +21 -0
- package/dist/credits.js.map +1 -0
- package/dist/earnings.d.ts +29 -0
- package/dist/earnings.js +22 -0
- package/dist/earnings.js.map +1 -0
- package/dist/frame-I7_xYGy5.d.ts +45 -0
- package/dist/full-S2MBPEEP.js +11 -0
- package/dist/full-S2MBPEEP.js.map +1 -0
- package/dist/funnel-QU5ZPC52.js +13 -0
- package/dist/funnel-QU5ZPC52.js.map +1 -0
- package/dist/funnel.d.ts +26 -0
- package/dist/funnel.js +13 -0
- package/dist/funnel.js.map +1 -0
- package/dist/gauge.d.ts +38 -0
- package/dist/gauge.js +13 -0
- package/dist/gauge.js.map +1 -0
- package/dist/geo.d.ts +37 -0
- package/dist/geo.js +13 -0
- package/dist/geo.js.map +1 -0
- package/dist/globe.d.ts +36 -0
- package/dist/globe.js +12 -0
- package/dist/globe.js.map +1 -0
- package/dist/goal.d.ts +26 -0
- package/dist/goal.js +17 -0
- package/dist/goal.js.map +1 -0
- package/dist/heatmap-JWQOKUGM.js +13 -0
- package/dist/heatmap-JWQOKUGM.js.map +1 -0
- package/dist/heatmap.d.ts +47 -0
- package/dist/heatmap.js +15 -0
- package/dist/heatmap.js.map +1 -0
- package/dist/host-_F8RgiIz.d.ts +15 -0
- package/dist/index.d.ts +29 -0
- package/dist/index.js +148 -0
- package/dist/index.js.map +1 -0
- package/dist/labels-DE_743fQ.d.ts +72 -0
- package/dist/latency.d.ts +33 -0
- package/dist/latency.js +24 -0
- package/dist/latency.js.map +1 -0
- package/dist/line.d.ts +25 -0
- package/dist/line.js +19 -0
- package/dist/line.js.map +1 -0
- package/dist/native.d.ts +494 -0
- package/dist/native.js +1244 -0
- package/dist/native.js.map +1 -0
- package/dist/pie.d.ts +37 -0
- package/dist/pie.js +16 -0
- package/dist/pie.js.map +1 -0
- package/dist/provider.d.ts +73 -0
- package/dist/provider.js +24 -0
- package/dist/provider.js.map +1 -0
- package/dist/radar-75GRJ2IK.js +13 -0
- package/dist/radar-75GRJ2IK.js.map +1 -0
- package/dist/radar.d.ts +22 -0
- package/dist/radar.js +13 -0
- package/dist/radar.js.map +1 -0
- package/dist/sankey-XQTX2EG6.js +13 -0
- package/dist/sankey-XQTX2EG6.js.map +1 -0
- package/dist/sankey.d.ts +28 -0
- package/dist/sankey.js +13 -0
- package/dist/sankey.js.map +1 -0
- package/dist/scatter-XSNG4OKD.js +13 -0
- package/dist/scatter-XSNG4OKD.js.map +1 -0
- package/dist/scatter.d.ts +41 -0
- package/dist/scatter.js +15 -0
- package/dist/scatter.js.map +1 -0
- package/dist/sparkline.d.ts +26 -0
- package/dist/sparkline.js +16 -0
- package/dist/sparkline.js.map +1 -0
- package/dist/svg-BJUHYX3B.js +14 -0
- package/dist/svg-BJUHYX3B.js.map +1 -0
- package/dist/throughput.d.ts +37 -0
- package/dist/throughput.js +24 -0
- package/dist/throughput.js.map +1 -0
- package/dist/ticker.d.ts +38 -0
- package/dist/ticker.js +22 -0
- package/dist/ticker.js.map +1 -0
- package/dist/treemap-OMGGGB5U.js +13 -0
- package/dist/treemap-OMGGGB5U.js.map +1 -0
- package/dist/treemap.d.ts +24 -0
- package/dist/treemap.js +14 -0
- package/dist/treemap.js.map +1 -0
- package/dist/world-110m-DVFWXS42.js +18 -0
- package/dist/world-110m-DVFWXS42.js.map +1 -0
- package/package.json +614 -3
- package/registry/area-chart.json +785 -0
- package/registry/bar-chart.json +784 -0
- package/registry/calendar-heatmap.json +460 -0
- package/registry/candlestick.json +553 -0
- package/registry/chart.json +441 -0
- package/registry/charts-provider.json +191 -0
- package/registry/credit-usage.json +473 -0
- package/registry/earnings-chart.json +703 -0
- package/registry/examples/area-chart/credits-usage.d.ts +4 -0
- package/registry/examples/area-chart/credits-usage.js +38 -0
- package/registry/examples/area-chart/credits-usage.tsx +32 -0
- package/registry/examples/area-chart/native/credits-usage.d.ts +4 -0
- package/registry/examples/area-chart/native/credits-usage.dark.png +0 -0
- package/registry/examples/area-chart/native/credits-usage.js +33 -0
- package/registry/examples/area-chart/native/credits-usage.light.png +0 -0
- package/registry/examples/area-chart/native/credits-usage.tsx +27 -0
- package/registry/examples/area-chart/storage.d.ts +4 -0
- package/registry/examples/area-chart/storage.js +27 -0
- package/registry/examples/area-chart/storage.tsx +21 -0
- package/registry/examples/bar-chart/jobs-by-status.d.ts +4 -0
- package/registry/examples/bar-chart/jobs-by-status.js +37 -0
- package/registry/examples/bar-chart/jobs-by-status.tsx +31 -0
- package/registry/examples/bar-chart/native/jobs-by-status.d.ts +4 -0
- package/registry/examples/bar-chart/native/jobs-by-status.dark.png +0 -0
- package/registry/examples/bar-chart/native/jobs-by-status.js +32 -0
- package/registry/examples/bar-chart/native/jobs-by-status.light.png +0 -0
- package/registry/examples/bar-chart/native/jobs-by-status.tsx +26 -0
- package/registry/examples/bar-chart/plans-by-quarter.d.ts +4 -0
- package/registry/examples/bar-chart/plans-by-quarter.js +31 -0
- package/registry/examples/bar-chart/plans-by-quarter.tsx +26 -0
- package/registry/examples/bar-chart/top-supporters.d.ts +4 -0
- package/registry/examples/bar-chart/top-supporters.js +32 -0
- package/registry/examples/bar-chart/top-supporters.tsx +27 -0
- package/registry/examples/calendar-heatmap/publishing.d.ts +4 -0
- package/registry/examples/calendar-heatmap/publishing.js +28 -0
- package/registry/examples/calendar-heatmap/publishing.tsx +23 -0
- package/registry/examples/candlestick/auction-bids.d.ts +4 -0
- package/registry/examples/candlestick/auction-bids.js +37 -0
- package/registry/examples/candlestick/auction-bids.tsx +32 -0
- package/registry/examples/chart/polar-uploads.d.ts +4 -0
- package/registry/examples/chart/polar-uploads.js +34 -0
- package/registry/examples/chart/polar-uploads.tsx +30 -0
- package/registry/examples/charts-provider/french-orazaka.d.ts +4 -0
- package/registry/examples/charts-provider/french-orazaka.js +26 -0
- package/registry/examples/charts-provider/french-orazaka.tsx +22 -0
- package/registry/examples/charts-provider/native/french-orazaka.d.ts +4 -0
- package/registry/examples/charts-provider/native/french-orazaka.dark.png +0 -0
- package/registry/examples/charts-provider/native/french-orazaka.js +17 -0
- package/registry/examples/charts-provider/native/french-orazaka.light.png +0 -0
- package/registry/examples/charts-provider/native/french-orazaka.tsx +17 -0
- package/registry/examples/credit-usage/monthly-credits.d.ts +4 -0
- package/registry/examples/credit-usage/monthly-credits.js +24 -0
- package/registry/examples/credit-usage/monthly-credits.tsx +19 -0
- package/registry/examples/credit-usage/native/monthly-credits.d.ts +4 -0
- package/registry/examples/credit-usage/native/monthly-credits.dark.png +0 -0
- package/registry/examples/credit-usage/native/monthly-credits.js +23 -0
- package/registry/examples/credit-usage/native/monthly-credits.light.png +0 -0
- package/registry/examples/credit-usage/native/monthly-credits.tsx +18 -0
- package/registry/examples/credit-usage/storage-plan.d.ts +4 -0
- package/registry/examples/credit-usage/storage-plan.js +21 -0
- package/registry/examples/credit-usage/storage-plan.tsx +15 -0
- package/registry/examples/earnings-chart/creator-month.d.ts +4 -0
- package/registry/examples/earnings-chart/creator-month.js +29 -0
- package/registry/examples/earnings-chart/creator-month.tsx +24 -0
- package/registry/examples/earnings-chart/gross-and-net.d.ts +4 -0
- package/registry/examples/earnings-chart/gross-and-net.js +29 -0
- package/registry/examples/earnings-chart/gross-and-net.tsx +24 -0
- package/registry/examples/earnings-chart/native/creator-month.d.ts +4 -0
- package/registry/examples/earnings-chart/native/creator-month.dark.png +0 -0
- package/registry/examples/earnings-chart/native/creator-month.js +29 -0
- package/registry/examples/earnings-chart/native/creator-month.light.png +0 -0
- package/registry/examples/earnings-chart/native/creator-month.tsx +24 -0
- package/registry/examples/funnel/signup.d.ts +4 -0
- package/registry/examples/funnel/signup.js +30 -0
- package/registry/examples/funnel/signup.tsx +24 -0
- package/registry/examples/gauge/challenge-goal.d.ts +4 -0
- package/registry/examples/gauge/challenge-goal.js +24 -0
- package/registry/examples/gauge/challenge-goal.tsx +18 -0
- package/registry/examples/gauge/credits-quota.d.ts +4 -0
- package/registry/examples/gauge/credits-quota.js +26 -0
- package/registry/examples/gauge/credits-quota.tsx +19 -0
- package/registry/examples/gauge/native/credits-quota.d.ts +4 -0
- package/registry/examples/gauge/native/credits-quota.dark.png +0 -0
- package/registry/examples/gauge/native/credits-quota.js +25 -0
- package/registry/examples/gauge/native/credits-quota.light.png +0 -0
- package/registry/examples/gauge/native/credits-quota.tsx +18 -0
- package/registry/examples/geo-map/viewers.d.ts +4 -0
- package/registry/examples/geo-map/viewers.js +43 -0
- package/registry/examples/geo-map/viewers.tsx +29 -0
- package/registry/examples/globe/deployment-regions.d.ts +4 -0
- package/registry/examples/globe/deployment-regions.js +36 -0
- package/registry/examples/globe/deployment-regions.tsx +30 -0
- package/registry/examples/goal-progress/challenge-pot.d.ts +4 -0
- package/registry/examples/goal-progress/challenge-pot.js +22 -0
- package/registry/examples/goal-progress/challenge-pot.tsx +16 -0
- package/registry/examples/goal-progress/goal-reached.d.ts +4 -0
- package/registry/examples/goal-progress/goal-reached.js +11 -0
- package/registry/examples/goal-progress/goal-reached.tsx +6 -0
- package/registry/examples/goal-progress/native/challenge-pot.d.ts +4 -0
- package/registry/examples/goal-progress/native/challenge-pot.dark.png +0 -0
- package/registry/examples/goal-progress/native/challenge-pot.js +11 -0
- package/registry/examples/goal-progress/native/challenge-pot.light.png +0 -0
- package/registry/examples/goal-progress/native/challenge-pot.tsx +6 -0
- package/registry/examples/heatmap/upload-activity.d.ts +4 -0
- package/registry/examples/heatmap/upload-activity.js +30 -0
- package/registry/examples/heatmap/upload-activity.tsx +25 -0
- package/registry/examples/job-throughput/live-hours.d.ts +4 -0
- package/registry/examples/job-throughput/live-hours.js +33 -0
- package/registry/examples/job-throughput/live-hours.tsx +28 -0
- package/registry/examples/job-throughput/native/week-of-jobs.d.ts +4 -0
- package/registry/examples/job-throughput/native/week-of-jobs.dark.png +0 -0
- package/registry/examples/job-throughput/native/week-of-jobs.js +20 -0
- package/registry/examples/job-throughput/native/week-of-jobs.light.png +0 -0
- package/registry/examples/job-throughput/native/week-of-jobs.tsx +16 -0
- package/registry/examples/job-throughput/week-of-jobs.d.ts +4 -0
- package/registry/examples/job-throughput/week-of-jobs.js +20 -0
- package/registry/examples/job-throughput/week-of-jobs.tsx +16 -0
- package/registry/examples/latency-chart/by-capability.d.ts +4 -0
- package/registry/examples/latency-chart/by-capability.js +26 -0
- package/registry/examples/latency-chart/by-capability.tsx +21 -0
- package/registry/examples/latency-chart/native/by-capability.d.ts +4 -0
- package/registry/examples/latency-chart/native/by-capability.dark.png +0 -0
- package/registry/examples/latency-chart/native/by-capability.js +17 -0
- package/registry/examples/latency-chart/native/by-capability.light.png +0 -0
- package/registry/examples/latency-chart/native/by-capability.tsx +13 -0
- package/registry/examples/latency-chart/time-to-result.d.ts +4 -0
- package/registry/examples/latency-chart/time-to-result.js +27 -0
- package/registry/examples/latency-chart/time-to-result.tsx +22 -0
- package/registry/examples/line-chart/creator-earnings.d.ts +4 -0
- package/registry/examples/line-chart/creator-earnings.js +35 -0
- package/registry/examples/line-chart/creator-earnings.tsx +30 -0
- package/registry/examples/line-chart/forecast.d.ts +4 -0
- package/registry/examples/line-chart/forecast.js +36 -0
- package/registry/examples/line-chart/forecast.tsx +30 -0
- package/registry/examples/line-chart/live-jobs.d.ts +4 -0
- package/registry/examples/line-chart/live-jobs.js +21 -0
- package/registry/examples/line-chart/live-jobs.tsx +23 -0
- package/registry/examples/line-chart/native/creator-earnings.d.ts +4 -0
- package/registry/examples/line-chart/native/creator-earnings.dark.png +0 -0
- package/registry/examples/line-chart/native/creator-earnings.js +32 -0
- package/registry/examples/line-chart/native/creator-earnings.light.png +0 -0
- package/registry/examples/line-chart/native/creator-earnings.tsx +26 -0
- package/registry/examples/line-chart/states.d.ts +4 -0
- package/registry/examples/line-chart/states.js +16 -0
- package/registry/examples/line-chart/states.tsx +13 -0
- package/registry/examples/pie-chart/credit-spend.d.ts +4 -0
- package/registry/examples/pie-chart/credit-spend.js +30 -0
- package/registry/examples/pie-chart/credit-spend.tsx +24 -0
- package/registry/examples/pie-chart/native/credit-spend.d.ts +4 -0
- package/registry/examples/pie-chart/native/credit-spend.dark.png +0 -0
- package/registry/examples/pie-chart/native/credit-spend.js +17 -0
- package/registry/examples/pie-chart/native/credit-spend.light.png +0 -0
- package/registry/examples/pie-chart/native/credit-spend.tsx +12 -0
- package/registry/examples/pie-chart/storage-by-kind.d.ts +4 -0
- package/registry/examples/pie-chart/storage-by-kind.js +31 -0
- package/registry/examples/pie-chart/storage-by-kind.tsx +26 -0
- package/registry/examples/price-ticker/auction-room.d.ts +4 -0
- package/registry/examples/price-ticker/auction-room.js +21 -0
- package/registry/examples/price-ticker/auction-room.tsx +17 -0
- package/registry/examples/price-ticker/native/auction-room.d.ts +4 -0
- package/registry/examples/price-ticker/native/auction-room.dark.png +0 -0
- package/registry/examples/price-ticker/native/auction-room.js +19 -0
- package/registry/examples/price-ticker/native/auction-room.light.png +0 -0
- package/registry/examples/price-ticker/native/auction-room.tsx +15 -0
- package/registry/examples/price-ticker/no-bid-yet.d.ts +4 -0
- package/registry/examples/price-ticker/no-bid-yet.js +11 -0
- package/registry/examples/price-ticker/no-bid-yet.tsx +6 -0
- package/registry/examples/radar-chart/model-comparison.d.ts +4 -0
- package/registry/examples/radar-chart/model-comparison.js +33 -0
- package/registry/examples/radar-chart/model-comparison.tsx +28 -0
- package/registry/examples/sankey/credit-flow.d.ts +4 -0
- package/registry/examples/sankey/credit-flow.js +37 -0
- package/registry/examples/sankey/credit-flow.tsx +32 -0
- package/registry/examples/scatter-chart/watch-time.d.ts +4 -0
- package/registry/examples/scatter-chart/watch-time.js +36 -0
- package/registry/examples/scatter-chart/watch-time.tsx +31 -0
- package/registry/examples/sparkline/bars.d.ts +4 -0
- package/registry/examples/sparkline/bars.js +12 -0
- package/registry/examples/sparkline/bars.tsx +7 -0
- package/registry/examples/sparkline/native/stat-trend.d.ts +4 -0
- package/registry/examples/sparkline/native/stat-trend.dark.png +0 -0
- package/registry/examples/sparkline/native/stat-trend.js +12 -0
- package/registry/examples/sparkline/native/stat-trend.light.png +0 -0
- package/registry/examples/sparkline/native/stat-trend.tsx +7 -0
- package/registry/examples/sparkline/stat-trend.d.ts +4 -0
- package/registry/examples/sparkline/stat-trend.js +18 -0
- package/registry/examples/sparkline/stat-trend.tsx +15 -0
- package/registry/examples/sparkline/table-rows.d.ts +4 -0
- package/registry/examples/sparkline/table-rows.js +23 -0
- package/registry/examples/sparkline/table-rows.tsx +26 -0
- package/registry/examples/treemap/storage.d.ts +4 -0
- package/registry/examples/treemap/storage.js +17 -0
- package/registry/examples/treemap/storage.tsx +13 -0
- package/registry/funnel.json +487 -0
- package/registry/gauge.json +600 -0
- package/registry/geo-map.json +484 -0
- package/registry/globe.json +469 -0
- package/registry/goal-progress.json +520 -0
- package/registry/heatmap.json +531 -0
- package/registry/index.json +582 -0
- package/registry/job-throughput.json +654 -0
- package/registry/latency-chart.json +671 -0
- package/registry/line-chart.json +793 -0
- package/registry/pie-chart.json +1288 -0
- package/registry/price-ticker.json +684 -0
- package/registry/radar-chart.json +459 -0
- package/registry/sankey.json +503 -0
- package/registry/scatter-chart.json +559 -0
- package/registry/sparkline.json +563 -0
- package/registry/treemap.json +432 -0
package/dist/native.js
ADDED
|
@@ -0,0 +1,1244 @@
|
|
|
1
|
+
// src/core/labels.ts
|
|
2
|
+
var DEFAULT_LABELS = {
|
|
3
|
+
showData: "Show data",
|
|
4
|
+
hideData: "Hide data",
|
|
5
|
+
tableCaption: "{title} \u2014 data",
|
|
6
|
+
exportPng: "PNG",
|
|
7
|
+
exportSvg: "SVG",
|
|
8
|
+
exportCsv: "CSV",
|
|
9
|
+
loading: "Loading chart\u2026",
|
|
10
|
+
empty: "No data for this period yet.",
|
|
11
|
+
error: "The chart could not be loaded.",
|
|
12
|
+
keyboardHint: "Use the arrow keys to move between points, Home and End to jump to the ends.",
|
|
13
|
+
roleDescription: "chart",
|
|
14
|
+
summaryIntro: "{kind}, {count}.",
|
|
15
|
+
summarySeries: "{label}: from {first} to {last}",
|
|
16
|
+
summaryRange: "lowest {min} ({minAt}), highest {max} ({maxAt})",
|
|
17
|
+
summaryTrendUp: "up {change}",
|
|
18
|
+
summaryTrendDown: "down {change}",
|
|
19
|
+
summaryTrendFlat: "stable",
|
|
20
|
+
summaryTotal: "total {total}",
|
|
21
|
+
summaryThreshold: "{label} at {value}",
|
|
22
|
+
summaryShare: "{label} {value} ({share})",
|
|
23
|
+
summaryCorrelation: "correlation {r}",
|
|
24
|
+
summaryConversion: "{from} \u2192 {to} {rate}",
|
|
25
|
+
summaryOverall: "overall {rate}",
|
|
26
|
+
summaryPeak: "peak {value} ({at})",
|
|
27
|
+
summaryActive: "{count} with a value",
|
|
28
|
+
summaryOhlc: "opened at {open}, closed at {close}, low {low}, high {high}",
|
|
29
|
+
kinds: {
|
|
30
|
+
line: "Line chart",
|
|
31
|
+
area: "Area chart",
|
|
32
|
+
bar: "Bar chart",
|
|
33
|
+
pie: "Pie chart",
|
|
34
|
+
donut: "Donut chart",
|
|
35
|
+
gauge: "Gauge",
|
|
36
|
+
sparkline: "Sparkline",
|
|
37
|
+
radar: "Radar chart",
|
|
38
|
+
heatmap: "Heatmap",
|
|
39
|
+
calendar: "Calendar heatmap",
|
|
40
|
+
sankey: "Flow diagram",
|
|
41
|
+
funnel: "Funnel",
|
|
42
|
+
candlestick: "Candlestick chart",
|
|
43
|
+
treemap: "Treemap",
|
|
44
|
+
scatter: "Scatter chart",
|
|
45
|
+
map: "Map",
|
|
46
|
+
globe: "Globe",
|
|
47
|
+
chart: "Chart"
|
|
48
|
+
},
|
|
49
|
+
category: "Category",
|
|
50
|
+
value: "Value",
|
|
51
|
+
total: "Total",
|
|
52
|
+
noValue: "\u2014"
|
|
53
|
+
};
|
|
54
|
+
function mergeLabels(...layers) {
|
|
55
|
+
let out = DEFAULT_LABELS;
|
|
56
|
+
for (const layer of layers) {
|
|
57
|
+
if (!layer) continue;
|
|
58
|
+
out = { ...out, ...layer, kinds: { ...out.kinds, ...layer.kinds } };
|
|
59
|
+
}
|
|
60
|
+
return out;
|
|
61
|
+
}
|
|
62
|
+
function capitalize(text) {
|
|
63
|
+
return text.charAt(0).toLocaleUpperCase() + text.slice(1);
|
|
64
|
+
}
|
|
65
|
+
function fill(template, values) {
|
|
66
|
+
return template.replace(/\{(\w+)\}/g, (match, name) => name in values ? String(values[name]) : match);
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
// src/needs/statuses.ts
|
|
70
|
+
var DEFAULT_STATUSES = [
|
|
71
|
+
{ key: "completed", label: "Completed", tone: "success", outcome: "succeeded" },
|
|
72
|
+
{ key: "failed", label: "Failed", tone: "danger", outcome: "failed" },
|
|
73
|
+
{ key: "running", label: "Running", tone: "info" },
|
|
74
|
+
{ key: "queued", label: "Queued", tone: "neutral" }
|
|
75
|
+
];
|
|
76
|
+
|
|
77
|
+
// src/native/cartesian.tsx
|
|
78
|
+
import { useMemo as useMemo2, useState as useState2 } from "react";
|
|
79
|
+
import Svg, { Circle, G, Line, Path, Text as SvgText } from "react-native-svg";
|
|
80
|
+
|
|
81
|
+
// src/core/data.ts
|
|
82
|
+
function read(accessor, datum, index) {
|
|
83
|
+
return typeof accessor === "function" ? accessor(datum, index) : datum[accessor];
|
|
84
|
+
}
|
|
85
|
+
var toNumber = (value) => typeof value === "number" && Number.isFinite(value) ? value : null;
|
|
86
|
+
function normalizeSeries(series, y, label) {
|
|
87
|
+
if (series?.length) return series;
|
|
88
|
+
if (y !== void 0) return [{ key: y, label: label ?? (typeof y === "string" ? y : "") }];
|
|
89
|
+
return [];
|
|
90
|
+
}
|
|
91
|
+
function tabulate(data, x, series) {
|
|
92
|
+
return {
|
|
93
|
+
categories: data.map((datum, i) => x === void 0 ? i + 1 : read(x, datum, i)),
|
|
94
|
+
series: series.map((spec, s) => ({
|
|
95
|
+
id: typeof spec.key === "string" ? spec.key : `series-${s}`,
|
|
96
|
+
label: spec.label,
|
|
97
|
+
values: data.map((datum, i) => toNumber(read(spec.key, datum, i))),
|
|
98
|
+
color: spec.color,
|
|
99
|
+
dashed: spec.dashed,
|
|
100
|
+
slot: s % 8 + 1
|
|
101
|
+
}))
|
|
102
|
+
};
|
|
103
|
+
}
|
|
104
|
+
function extent(series, stacked = false) {
|
|
105
|
+
let min = Number.POSITIVE_INFINITY;
|
|
106
|
+
let max = Number.NEGATIVE_INFINITY;
|
|
107
|
+
const count = series[0]?.values.length ?? 0;
|
|
108
|
+
if (stacked) {
|
|
109
|
+
for (let i = 0; i < count; i += 1) {
|
|
110
|
+
let pos = 0;
|
|
111
|
+
let neg = 0;
|
|
112
|
+
for (const s of series) {
|
|
113
|
+
const v = s.values[i] ?? 0;
|
|
114
|
+
if (v >= 0) pos += v;
|
|
115
|
+
else neg += v;
|
|
116
|
+
}
|
|
117
|
+
min = Math.min(min, neg);
|
|
118
|
+
max = Math.max(max, pos);
|
|
119
|
+
}
|
|
120
|
+
} else {
|
|
121
|
+
for (const s of series) {
|
|
122
|
+
for (const v of s.values) {
|
|
123
|
+
if (v == null) continue;
|
|
124
|
+
min = Math.min(min, v);
|
|
125
|
+
max = Math.max(max, v);
|
|
126
|
+
}
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
if (min === Number.POSITIVE_INFINITY) return [0, 0];
|
|
130
|
+
return [min, max];
|
|
131
|
+
}
|
|
132
|
+
function stack(series) {
|
|
133
|
+
const count = series[0]?.values.length ?? 0;
|
|
134
|
+
const out = series.map(() => []);
|
|
135
|
+
for (let i = 0; i < count; i += 1) {
|
|
136
|
+
let pos = 0;
|
|
137
|
+
let neg = 0;
|
|
138
|
+
series.forEach((s, k) => {
|
|
139
|
+
const v = s.values[i] ?? 0;
|
|
140
|
+
if (v >= 0) {
|
|
141
|
+
out[k].push({ base: pos, top: pos + v });
|
|
142
|
+
pos += v;
|
|
143
|
+
} else {
|
|
144
|
+
out[k].push({ base: neg, top: neg + v });
|
|
145
|
+
neg += v;
|
|
146
|
+
}
|
|
147
|
+
});
|
|
148
|
+
}
|
|
149
|
+
return out;
|
|
150
|
+
}
|
|
151
|
+
function summarize(series, categories, writeCategory) {
|
|
152
|
+
let min = null;
|
|
153
|
+
let max = null;
|
|
154
|
+
let first = null;
|
|
155
|
+
let last = null;
|
|
156
|
+
let total2 = 0;
|
|
157
|
+
let count = 0;
|
|
158
|
+
series.values.forEach((v, i) => {
|
|
159
|
+
if (v == null) return;
|
|
160
|
+
count += 1;
|
|
161
|
+
total2 += v;
|
|
162
|
+
if (first === null) first = v;
|
|
163
|
+
last = v;
|
|
164
|
+
if (!min || v < min.value) min = { value: v, category: writeCategory(categories[i]) };
|
|
165
|
+
if (!max || v > max.value) max = { value: v, category: writeCategory(categories[i]) };
|
|
166
|
+
});
|
|
167
|
+
const change = first !== null && last !== null && first !== 0 && count > 1 ? last / first - 1 : null;
|
|
168
|
+
const trend = count < 2 || change === null ? count < 2 ? "none" : last > first ? "up" : last < first ? "down" : "flat" : Math.abs(change) < 0.01 ? "flat" : change > 0 ? "up" : "down";
|
|
169
|
+
return { label: series.label, count, min, max, first, last, total: total2, change, trend };
|
|
170
|
+
}
|
|
171
|
+
|
|
172
|
+
// src/core/describe.ts
|
|
173
|
+
function describeSeries(table, { kind, labels, value, category, share, thresholds = [] }) {
|
|
174
|
+
const points = table.categories.length;
|
|
175
|
+
const first = points ? category(table.categories[0]) : "";
|
|
176
|
+
const last = points ? category(table.categories[points - 1]) : "";
|
|
177
|
+
const count = table.series.length > 1 ? `${table.series.length} \xD7 ${points}` : String(points);
|
|
178
|
+
const intro = fill(labels.summaryIntro, { kind: labels.kinds[kind], count: points > 1 ? `${count} (${first} \u2013 ${last})` : count });
|
|
179
|
+
const sentences = table.series.map((series) => {
|
|
180
|
+
const s = summarize(series, table.categories, category);
|
|
181
|
+
if (!s.count) return `${s.label}: ${labels.noValue}.`;
|
|
182
|
+
const parts = [fill(labels.summarySeries, { label: s.label, first: value(s.first), last: value(s.last) })];
|
|
183
|
+
if (s.min && s.max && s.count > 2) parts.push(fill(labels.summaryRange, { min: value(s.min.value), minAt: s.min.category, max: value(s.max.value), maxAt: s.max.category }));
|
|
184
|
+
if (s.trend === "up" || s.trend === "down") {
|
|
185
|
+
const template = s.trend === "up" ? labels.summaryTrendUp : labels.summaryTrendDown;
|
|
186
|
+
if (s.change !== null) parts.push(fill(template, { change: share(Math.abs(s.change)) }));
|
|
187
|
+
} else if (s.trend === "flat") parts.push(labels.summaryTrendFlat);
|
|
188
|
+
return `${parts.join(", ")}.`;
|
|
189
|
+
});
|
|
190
|
+
const marks = thresholds.map((t) => fill(labels.summaryThreshold, { label: t.label, value: value(t.value) }));
|
|
191
|
+
return [intro, ...sentences, ...marks.length ? [`${marks.join(", ")}.`] : []].join(" ");
|
|
192
|
+
}
|
|
193
|
+
function describeParts(kind, parts, { labels, value, share }) {
|
|
194
|
+
const total2 = parts.reduce((sum, p) => sum + Math.max(0, p.value), 0);
|
|
195
|
+
const intro = fill(labels.summaryIntro, { kind: labels.kinds[kind], count: parts.length });
|
|
196
|
+
const sorted = [...parts].sort((a, b) => b.value - a.value);
|
|
197
|
+
const items = sorted.map((p) => fill(labels.summaryShare, { label: p.label, value: value(p.value), share: share(total2 ? p.value / total2 : 0) }));
|
|
198
|
+
return `${intro} ${items.join(", ")}. ${capitalize(fill(labels.summaryTotal, { total: value(total2) }))}.`;
|
|
199
|
+
}
|
|
200
|
+
|
|
201
|
+
// src/core/format.ts
|
|
202
|
+
import { currencyDigits, formatCompact, formatDate, formatMoney, formatNumber, formatPercent, getDateTimeFormat, getNumberFormat } from "@krizaka/intl";
|
|
203
|
+
function valueFormatter(format = "number", locale, noValue = "\u2014", axis = false) {
|
|
204
|
+
const write = writerOf(format, locale, axis);
|
|
205
|
+
return (value) => value == null || Number.isNaN(value) ? noValue : write(value);
|
|
206
|
+
}
|
|
207
|
+
function writerOf(format, locale, axis) {
|
|
208
|
+
if (typeof format === "function") return (value) => format(value, locale);
|
|
209
|
+
if (format === "integer") return (value) => formatNumber(Math.round(value), { locale, maximumFractionDigits: 0 });
|
|
210
|
+
if (format === "compact") return (value) => formatCompact(value, { locale });
|
|
211
|
+
if (format === "percent") return (value) => formatPercent(value, { locale, maximumFractionDigits: axis ? 0 : 1 });
|
|
212
|
+
if (format === "number") {
|
|
213
|
+
return (value) => axis && Math.abs(value) >= 1e4 ? formatCompact(value, { locale }) : formatNumber(value, { locale, maximumFractionDigits: 2 });
|
|
214
|
+
}
|
|
215
|
+
if (format.style === "money") {
|
|
216
|
+
const { currency } = format;
|
|
217
|
+
const digits = currencyDigits(currency);
|
|
218
|
+
return (value) => {
|
|
219
|
+
const minor = Math.round(value);
|
|
220
|
+
if ((axis || format.compact) && Math.abs(minor) >= 1e6) {
|
|
221
|
+
const options2 = { style: "currency", currency, currencyDisplay: "narrowSymbol", notation: "compact", minimumFractionDigits: 0, maximumFractionDigits: 1 };
|
|
222
|
+
return getNumberFormat(locale, options2).format(minor / 10 ** digits);
|
|
223
|
+
}
|
|
224
|
+
if (axis && minor % 10 ** digits === 0) {
|
|
225
|
+
return getNumberFormat(locale, { style: "currency", currency, minimumFractionDigits: 0, maximumFractionDigits: 0 }).format(minor / 10 ** digits);
|
|
226
|
+
}
|
|
227
|
+
return formatMoney(minor, { currency, locale });
|
|
228
|
+
};
|
|
229
|
+
}
|
|
230
|
+
if (format.style === "unit") {
|
|
231
|
+
const { unit } = format;
|
|
232
|
+
const compact = axis || format.compact;
|
|
233
|
+
const options2 = { style: "unit", unit, unitDisplay: "short", ...compact ? { notation: "compact" } : {}, maximumFractionDigits: compact ? 1 : 2 };
|
|
234
|
+
return (value) => getNumberFormat(locale, options2).format(value);
|
|
235
|
+
}
|
|
236
|
+
const { options } = format;
|
|
237
|
+
return (value) => formatNumber(value, { locale, ...options });
|
|
238
|
+
}
|
|
239
|
+
function asDate(value) {
|
|
240
|
+
if (value instanceof Date) return Number.isNaN(value.getTime()) ? null : value;
|
|
241
|
+
if (typeof value === "number" && value > 1e10) return new Date(value);
|
|
242
|
+
if (typeof value === "string" && /^\d{4}-\d{2}(-\d{2})?([T ][\d:.]+(Z|[+-]\d{2}:?\d{2})?)?$/.test(value)) {
|
|
243
|
+
const iso = value.length === 7 ? `${value}-01T00:00:00Z` : value.length === 10 ? `${value}T00:00:00Z` : value;
|
|
244
|
+
const date = new Date(iso);
|
|
245
|
+
return Number.isNaN(date.getTime()) ? null : date;
|
|
246
|
+
}
|
|
247
|
+
return null;
|
|
248
|
+
}
|
|
249
|
+
var DATE_OPTIONS = {
|
|
250
|
+
year: { year: "numeric", timeZone: "UTC" },
|
|
251
|
+
month: { month: "short", year: "numeric", timeZone: "UTC" },
|
|
252
|
+
day: { month: "short", day: "numeric", timeZone: "UTC" },
|
|
253
|
+
date: { dateStyle: "medium", timeZone: "UTC" },
|
|
254
|
+
time: { timeStyle: "short", timeZone: "UTC" },
|
|
255
|
+
datetime: { dateStyle: "medium", timeStyle: "short", timeZone: "UTC" }
|
|
256
|
+
};
|
|
257
|
+
function categoryFormatter(format, locale) {
|
|
258
|
+
if (typeof format === "function") return (category) => format(category, locale);
|
|
259
|
+
if (format === "text") return (category) => String(category ?? "");
|
|
260
|
+
return (category) => {
|
|
261
|
+
const date = asDate(category);
|
|
262
|
+
if (!date) return String(category ?? "");
|
|
263
|
+
const kind = format ?? guessPrecision(category);
|
|
264
|
+
if (kind === "date") return formatDate(date, { locale, style: "medium", timeZone: "UTC" });
|
|
265
|
+
return getDateTimeFormat(locale, DATE_OPTIONS[kind]).format(date);
|
|
266
|
+
};
|
|
267
|
+
}
|
|
268
|
+
function guessPrecision(category) {
|
|
269
|
+
if (typeof category === "string") {
|
|
270
|
+
if (category.length === 7) return "month";
|
|
271
|
+
if (category.length === 10) return "date";
|
|
272
|
+
return "datetime";
|
|
273
|
+
}
|
|
274
|
+
const date = asDate(category);
|
|
275
|
+
return date && date.getUTCHours() === 0 && date.getUTCMinutes() === 0 ? "date" : "datetime";
|
|
276
|
+
}
|
|
277
|
+
function shareFormatter(locale) {
|
|
278
|
+
return (ratio) => formatPercent(ratio, { locale, maximumFractionDigits: Math.abs(ratio) < 0.1 ? 1 : 0 });
|
|
279
|
+
}
|
|
280
|
+
|
|
281
|
+
// src/core/scale.ts
|
|
282
|
+
function niceStep(span, count) {
|
|
283
|
+
if (!(span > 0) || !(count > 0)) return 1;
|
|
284
|
+
const raw = span / count;
|
|
285
|
+
const power = 10 ** Math.floor(Math.log10(raw));
|
|
286
|
+
const fraction = raw / power;
|
|
287
|
+
const nice = fraction <= 1 ? 1 : fraction <= 2 ? 2 : fraction <= 2.5 ? 2.5 : fraction <= 5 ? 5 : 10;
|
|
288
|
+
return nice * power;
|
|
289
|
+
}
|
|
290
|
+
function niceDomain(min, max, count = 5) {
|
|
291
|
+
if (!Number.isFinite(min) || !Number.isFinite(max)) return { domain: [0, 1], ticks: [0, 1] };
|
|
292
|
+
if (min === max) {
|
|
293
|
+
if (min === 0) return { domain: [0, 1], ticks: [0, 0.5, 1] };
|
|
294
|
+
const pad = Math.abs(min) * 0.5;
|
|
295
|
+
[min, max] = min > 0 ? [0, max + pad] : [min - pad, 0];
|
|
296
|
+
}
|
|
297
|
+
const step = niceStep(max - min, count);
|
|
298
|
+
const lo = Math.floor(min / step) * step;
|
|
299
|
+
const hi = Math.ceil(max / step) * step;
|
|
300
|
+
const ticks = [];
|
|
301
|
+
const digits = Math.max(0, -Math.floor(Math.log10(step)) + 2);
|
|
302
|
+
for (let v = lo; v <= hi + step / 2; v += step) ticks.push(Number(v.toFixed(digits)));
|
|
303
|
+
return { domain: [lo, hi], ticks };
|
|
304
|
+
}
|
|
305
|
+
function linearScale(domain, range, ticks = domain) {
|
|
306
|
+
const [d0, d1] = domain;
|
|
307
|
+
const [r0, r1] = range;
|
|
308
|
+
const k = d1 === d0 ? 0 : (r1 - r0) / (d1 - d0);
|
|
309
|
+
const scale = ((value) => r0 + (value - d0) * k);
|
|
310
|
+
return Object.assign(scale, { domain, range, ticks });
|
|
311
|
+
}
|
|
312
|
+
function bandScale(count, range, padding = 0.3) {
|
|
313
|
+
const [r0, r1] = range;
|
|
314
|
+
const step = count > 0 ? (r1 - r0) / count : 0;
|
|
315
|
+
const bandwidth = step * (1 - padding);
|
|
316
|
+
const scale = ((index) => r0 + index * step + (step - bandwidth) / 2);
|
|
317
|
+
return Object.assign(scale, { bandwidth, step, count });
|
|
318
|
+
}
|
|
319
|
+
function pointScale(count, range) {
|
|
320
|
+
const [r0, r1] = range;
|
|
321
|
+
if (count <= 1) return () => (r0 + r1) / 2;
|
|
322
|
+
const step = (r1 - r0) / (count - 1);
|
|
323
|
+
return (index) => r0 + index * step;
|
|
324
|
+
}
|
|
325
|
+
function thinLabels(count, max) {
|
|
326
|
+
if (count <= max) return Array.from({ length: count }, (_, i) => i);
|
|
327
|
+
const every = Math.ceil(count / Math.max(1, max));
|
|
328
|
+
const out = [];
|
|
329
|
+
for (let i = 0; i < count; i += every) out.push(i);
|
|
330
|
+
if (out[out.length - 1] !== count - 1) {
|
|
331
|
+
if (count - 1 - out[out.length - 1] < every) out.pop();
|
|
332
|
+
out.push(count - 1);
|
|
333
|
+
}
|
|
334
|
+
return out;
|
|
335
|
+
}
|
|
336
|
+
|
|
337
|
+
// src/core/shape.ts
|
|
338
|
+
var r = (n) => Math.round(n * 100) / 100;
|
|
339
|
+
function segments(points) {
|
|
340
|
+
const out = [];
|
|
341
|
+
let current = [];
|
|
342
|
+
for (const point of points) {
|
|
343
|
+
if (point) current.push(point);
|
|
344
|
+
else if (current.length) {
|
|
345
|
+
out.push(current);
|
|
346
|
+
current = [];
|
|
347
|
+
}
|
|
348
|
+
}
|
|
349
|
+
if (current.length) out.push(current);
|
|
350
|
+
return out;
|
|
351
|
+
}
|
|
352
|
+
function linePath(points, curve = "monotone") {
|
|
353
|
+
if (points.length === 0) return "";
|
|
354
|
+
const [x0, y0] = points[0];
|
|
355
|
+
if (points.length === 1) return `M${r(x0)},${r(y0)}`;
|
|
356
|
+
if (curve === "step") {
|
|
357
|
+
let d2 = `M${r(x0)},${r(y0)}`;
|
|
358
|
+
for (let i = 1; i < points.length; i += 1) {
|
|
359
|
+
const [px] = points[i - 1];
|
|
360
|
+
const [x, y] = points[i];
|
|
361
|
+
const mid = (px + x) / 2;
|
|
362
|
+
d2 += `H${r(mid)}V${r(y)}H${r(x)}`;
|
|
363
|
+
}
|
|
364
|
+
return d2;
|
|
365
|
+
}
|
|
366
|
+
if (curve === "linear" || points.length === 2) return points.map(([x, y], i) => `${i ? "L" : "M"}${r(x)},${r(y)}`).join("");
|
|
367
|
+
const tangents = monotoneTangents(points);
|
|
368
|
+
let d = `M${r(x0)},${r(y0)}`;
|
|
369
|
+
for (let i = 1; i < points.length; i += 1) {
|
|
370
|
+
const [xa, ya] = points[i - 1];
|
|
371
|
+
const [xb, yb] = points[i];
|
|
372
|
+
const h = (xb - xa) / 3;
|
|
373
|
+
d += `C${r(xa + h)},${r(ya + h * tangents[i - 1])} ${r(xb - h)},${r(yb - h * tangents[i])} ${r(xb)},${r(yb)}`;
|
|
374
|
+
}
|
|
375
|
+
return d;
|
|
376
|
+
}
|
|
377
|
+
function monotoneTangents(points) {
|
|
378
|
+
const n = points.length;
|
|
379
|
+
const slopes = [];
|
|
380
|
+
for (let i = 0; i < n - 1; i += 1) {
|
|
381
|
+
const [xa, ya] = points[i];
|
|
382
|
+
const [xb, yb] = points[i + 1];
|
|
383
|
+
slopes.push(xb === xa ? 0 : (yb - ya) / (xb - xa));
|
|
384
|
+
}
|
|
385
|
+
const tangents = [slopes[0]];
|
|
386
|
+
for (let i = 1; i < n - 1; i += 1) {
|
|
387
|
+
const a = slopes[i - 1];
|
|
388
|
+
const b = slopes[i];
|
|
389
|
+
tangents.push(a * b <= 0 ? 0 : 3 * a * b / (Math.max(a, b) * 2 + Math.min(a, b)) || 0);
|
|
390
|
+
}
|
|
391
|
+
tangents.push(slopes[n - 2]);
|
|
392
|
+
return tangents;
|
|
393
|
+
}
|
|
394
|
+
function areaPath(top, base, curve = "monotone") {
|
|
395
|
+
if (top.length === 0) return "";
|
|
396
|
+
const line = linePath(top, curve);
|
|
397
|
+
const bottom = typeof base === "number" ? [top[top.length - 1], top[0]].map(([x]) => [x, base]) : [...base].reverse();
|
|
398
|
+
if (typeof base === "number") return `${line}L${r(bottom[0][0])},${r(base)}L${r(bottom[1][0])},${r(base)}Z`;
|
|
399
|
+
return `${line}L${linePath(bottom, curve).slice(1)}Z`;
|
|
400
|
+
}
|
|
401
|
+
function barPath(x, y, width, height, radius = 4, horizontal = false, negative = false) {
|
|
402
|
+
if (width <= 0 || height <= 0) return "";
|
|
403
|
+
const rad = Math.min(radius, horizontal ? height / 2 : width / 2, horizontal ? width : height);
|
|
404
|
+
if (!horizontal) {
|
|
405
|
+
if (!negative) {
|
|
406
|
+
return `M${r(x)},${r(y + height)}V${r(y + rad)}Q${r(x)},${r(y)} ${r(x + rad)},${r(y)}H${r(x + width - rad)}Q${r(x + width)},${r(y)} ${r(x + width)},${r(y + rad)}V${r(y + height)}Z`;
|
|
407
|
+
}
|
|
408
|
+
return `M${r(x)},${r(y)}V${r(y + height - rad)}Q${r(x)},${r(y + height)} ${r(x + rad)},${r(y + height)}H${r(x + width - rad)}Q${r(x + width)},${r(y + height)} ${r(x + width)},${r(y + height - rad)}V${r(y)}Z`;
|
|
409
|
+
}
|
|
410
|
+
if (!negative) {
|
|
411
|
+
return `M${r(x)},${r(y)}H${r(x + width - rad)}Q${r(x + width)},${r(y)} ${r(x + width)},${r(y + rad)}V${r(y + height - rad)}Q${r(x + width)},${r(y + height)} ${r(x + width - rad)},${r(y + height)}H${r(x)}Z`;
|
|
412
|
+
}
|
|
413
|
+
return `M${r(x + width)},${r(y)}H${r(x + rad)}Q${r(x)},${r(y)} ${r(x)},${r(y + rad)}V${r(y + height - rad)}Q${r(x)},${r(y + height)} ${r(x + rad)},${r(y + height)}H${r(x + width)}Z`;
|
|
414
|
+
}
|
|
415
|
+
function polar(cx, cy, radius, angle) {
|
|
416
|
+
return [cx + radius * Math.sin(angle), cy - radius * Math.cos(angle)];
|
|
417
|
+
}
|
|
418
|
+
function arcPath(cx, cy, inner, outer, start, end) {
|
|
419
|
+
const sweep = end - start;
|
|
420
|
+
if (sweep <= 0 || outer <= 0) return "";
|
|
421
|
+
if (sweep >= Math.PI * 2 - 1e-6) {
|
|
422
|
+
const mid = start + Math.PI;
|
|
423
|
+
return `${arcPath(cx, cy, inner, outer, start, mid)}${arcPath(cx, cy, inner, outer, mid, start + Math.PI * 2)}`;
|
|
424
|
+
}
|
|
425
|
+
const large = sweep > Math.PI ? 1 : 0;
|
|
426
|
+
const [ox0, oy0] = polar(cx, cy, outer, start);
|
|
427
|
+
const [ox1, oy1] = polar(cx, cy, outer, end);
|
|
428
|
+
let d = `M${r(ox0)},${r(oy0)}A${r(outer)},${r(outer)} 0 ${large} 1 ${r(ox1)},${r(oy1)}`;
|
|
429
|
+
if (inner > 0) {
|
|
430
|
+
const [ix1, iy1] = polar(cx, cy, inner, end);
|
|
431
|
+
const [ix0, iy0] = polar(cx, cy, inner, start);
|
|
432
|
+
d += `L${r(ix1)},${r(iy1)}A${r(inner)},${r(inner)} 0 ${large} 0 ${r(ix0)},${r(iy0)}Z`;
|
|
433
|
+
} else d += `L${r(cx)},${r(cy)}Z`;
|
|
434
|
+
return d;
|
|
435
|
+
}
|
|
436
|
+
function strokeArcPath(cx, cy, radius, start, end) {
|
|
437
|
+
if (end - start <= 0) return "";
|
|
438
|
+
const [x0, y0] = polar(cx, cy, radius, start);
|
|
439
|
+
const [x1, y1] = polar(cx, cy, radius, end);
|
|
440
|
+
return `M${r(x0)},${r(y0)}A${r(radius)},${r(radius)} 0 ${end - start > Math.PI ? 1 : 0} 1 ${r(x1)},${r(y1)}`;
|
|
441
|
+
}
|
|
442
|
+
|
|
443
|
+
// ../tokens/dist/native.js
|
|
444
|
+
var themes = /* @__PURE__ */ Object.freeze({ dark: /* @__PURE__ */ Object.freeze({
|
|
445
|
+
"surface0": "#0c0c0e",
|
|
446
|
+
"surface1": "#161618",
|
|
447
|
+
"surface2": "#1f1f23",
|
|
448
|
+
"surface3": "#2a2a2d",
|
|
449
|
+
"media": "#1b1b1d",
|
|
450
|
+
"borderSubtle": "rgba(255,255,255,0.06)",
|
|
451
|
+
"borderDefault": "rgba(255,255,255,0.1)",
|
|
452
|
+
"borderStrong": "rgba(255,255,255,0.16)",
|
|
453
|
+
"textPrimary": "#f5f5f5",
|
|
454
|
+
"textSecondary": "#a0a0a7",
|
|
455
|
+
"textMuted": "#73737d",
|
|
456
|
+
"textOnMedia": "#ffffff",
|
|
457
|
+
"accent": "#196df5",
|
|
458
|
+
"accentHover": "#0e5bd8",
|
|
459
|
+
"accentSoft": "rgba(25,109,245,0.1)",
|
|
460
|
+
"accentText": "#629cf8",
|
|
461
|
+
"accent2": "#196df5",
|
|
462
|
+
"onAccent": "#ffffff",
|
|
463
|
+
"ring": "#196df5",
|
|
464
|
+
"brandGradientFrom": "#0e1525",
|
|
465
|
+
"brandGradientVia": "#0e0f16",
|
|
466
|
+
"brandGradientTo": "#0c0c0e",
|
|
467
|
+
"success": "#10b77f",
|
|
468
|
+
"successText": "#36d399",
|
|
469
|
+
"successSoft": "rgba(16,183,127,0.14)",
|
|
470
|
+
"warning": "#f59f0a",
|
|
471
|
+
"warningText": "#f6a823",
|
|
472
|
+
"warningSoft": "rgba(245,159,10,0.14)",
|
|
473
|
+
"danger": "#ef4343",
|
|
474
|
+
"dangerText": "#f87272",
|
|
475
|
+
"dangerSoft": "rgba(239,67,67,0.14)",
|
|
476
|
+
"info": "#196df5",
|
|
477
|
+
"infoText": "#629cf8",
|
|
478
|
+
"scrim": "rgba(0,0,0,0.6)",
|
|
479
|
+
"scrimStrong": "rgba(0,0,0,0.8)",
|
|
480
|
+
"overlay": "rgba(0,0,0,0.7)",
|
|
481
|
+
"surfaceSheen": "rgba(255,255,255,0.045)",
|
|
482
|
+
"fillShade": "rgba(0,0,0,0.12)",
|
|
483
|
+
"edgeLight": "rgba(255,255,255,0.07)",
|
|
484
|
+
"edgeOnFill": "rgba(255,255,255,0.22)",
|
|
485
|
+
"edgeWell": "rgba(4,4,7,0.5)",
|
|
486
|
+
"glassBg": "rgba(29,29,32,0.88)",
|
|
487
|
+
"glassBorder": "rgba(255,255,255,0.1)"
|
|
488
|
+
}), light: /* @__PURE__ */ Object.freeze({
|
|
489
|
+
"surface0": "#fafafa",
|
|
490
|
+
"surface1": "#ffffff",
|
|
491
|
+
"surface2": "#f1f1f3",
|
|
492
|
+
"surface3": "#e4e4e7",
|
|
493
|
+
"media": "#e9e9ec",
|
|
494
|
+
"borderSubtle": "rgba(0,0,0,0.06)",
|
|
495
|
+
"borderDefault": "rgba(0,0,0,0.1)",
|
|
496
|
+
"borderStrong": "rgba(0,0,0,0.16)",
|
|
497
|
+
"textPrimary": "#18181b",
|
|
498
|
+
"textSecondary": "#64646d",
|
|
499
|
+
"textMuted": "#808089",
|
|
500
|
+
"textOnMedia": "#ffffff",
|
|
501
|
+
"accent": "#0a64f5",
|
|
502
|
+
"accentHover": "#0d55c9",
|
|
503
|
+
"accentSoft": "rgba(10,100,245,0.08)",
|
|
504
|
+
"accentText": "#0954ce",
|
|
505
|
+
"accent2": "#0a64f5",
|
|
506
|
+
"onAccent": "#ffffff",
|
|
507
|
+
"ring": "#0a64f5",
|
|
508
|
+
"brandGradientFrom": "#dcebfe",
|
|
509
|
+
"brandGradientVia": "#f3f6fc",
|
|
510
|
+
"brandGradientTo": "#fafafa",
|
|
511
|
+
"success": "#10b77f",
|
|
512
|
+
"successText": "#0a714e",
|
|
513
|
+
"successSoft": "rgba(16,183,127,0.1)",
|
|
514
|
+
"warning": "#f59f0a",
|
|
515
|
+
"warningText": "#955104",
|
|
516
|
+
"warningSoft": "rgba(245,159,10,0.12)",
|
|
517
|
+
"danger": "#ef4343",
|
|
518
|
+
"dangerText": "#af1d1d",
|
|
519
|
+
"dangerSoft": "rgba(239,67,67,0.1)",
|
|
520
|
+
"info": "#0a64f5",
|
|
521
|
+
"infoText": "#0954ce",
|
|
522
|
+
"scrim": "rgba(0,0,0,0.6)",
|
|
523
|
+
"scrimStrong": "rgba(0,0,0,0.8)",
|
|
524
|
+
"overlay": "rgba(0,0,0,0.7)",
|
|
525
|
+
"surfaceSheen": "rgba(255,255,255,0.7)",
|
|
526
|
+
"fillShade": "rgba(0,0,0,0.12)",
|
|
527
|
+
"edgeLight": "rgba(255,255,255,0.9)",
|
|
528
|
+
"edgeOnFill": "rgba(255,255,255,0.22)",
|
|
529
|
+
"edgeWell": "rgba(48,52,80,0.08)",
|
|
530
|
+
"glassBg": "rgba(255,255,255,0.88)",
|
|
531
|
+
"glassBorder": "rgba(0,0,0,0.08)"
|
|
532
|
+
}) });
|
|
533
|
+
|
|
534
|
+
// src/native/frame.tsx
|
|
535
|
+
import { createContext, useContext, useMemo, useState } from "react";
|
|
536
|
+
import { Pressable, StyleSheet, Text, useColorScheme, View } from "react-native";
|
|
537
|
+
|
|
538
|
+
// src/core/palette.ts
|
|
539
|
+
var HUES = {
|
|
540
|
+
blue: { light: "#2a78d6", dark: "#3987e5" },
|
|
541
|
+
orange: { light: "#eb6834", dark: "#d95926" },
|
|
542
|
+
aqua: { light: "#1baf7a", dark: "#199e70" },
|
|
543
|
+
yellow: { light: "#eda100", dark: "#c98500" },
|
|
544
|
+
magenta: { light: "#e87ba4", dark: "#d55181" },
|
|
545
|
+
green: { light: "#008300", dark: "#008300" },
|
|
546
|
+
violet: { light: "#6250d6", dark: "#9085e9" },
|
|
547
|
+
red: { light: "#e34948", dark: "#e66767" }
|
|
548
|
+
};
|
|
549
|
+
var ORDERS = {
|
|
550
|
+
krizaka: ["blue", "green", "magenta", "yellow", "aqua", "orange", "violet", "red"],
|
|
551
|
+
orazaka: ["orange", "aqua", "blue", "yellow", "magenta", "green", "violet", "red"],
|
|
552
|
+
orochia: ["violet", "magenta", "yellow", "aqua", "orange", "blue", "green", "red"]
|
|
553
|
+
};
|
|
554
|
+
function palette(brand, mode) {
|
|
555
|
+
return ORDERS[brand].map((hue) => HUES[hue][mode]);
|
|
556
|
+
}
|
|
557
|
+
var DIVERGING = {
|
|
558
|
+
light: { low: HUES.blue.light, high: HUES.red.light },
|
|
559
|
+
dark: { low: HUES.blue.dark, high: HUES.red.dark }
|
|
560
|
+
};
|
|
561
|
+
|
|
562
|
+
// src/native/frame.tsx
|
|
563
|
+
import { jsx, jsxs } from "react/jsx-runtime";
|
|
564
|
+
var THEMES = themes;
|
|
565
|
+
var Context = createContext({});
|
|
566
|
+
function ChartsProvider({ children, ...settings }) {
|
|
567
|
+
const parent = useContext(Context);
|
|
568
|
+
const value = useMemo(() => ({ ...parent, ...Object.fromEntries(Object.entries(settings).filter(([, v]) => v !== void 0)) }), [parent, settings]);
|
|
569
|
+
return /* @__PURE__ */ jsx(Context.Provider, { value, children });
|
|
570
|
+
}
|
|
571
|
+
function useNativeSettings(own) {
|
|
572
|
+
const shared = useContext(Context);
|
|
573
|
+
const device = useColorScheme();
|
|
574
|
+
const scheme = own.scheme ?? shared.scheme ?? (device === "light" ? "light" : "dark");
|
|
575
|
+
const brand = own.brand ?? shared.brand ?? "krizaka";
|
|
576
|
+
return useMemo(() => {
|
|
577
|
+
const theme = { ...THEMES[scheme], ...shared.theme, ...own.theme };
|
|
578
|
+
const colors = palette(brand, scheme);
|
|
579
|
+
const tones = { neutral: theme.textSecondary, accent: theme.accent, success: theme.success, warning: theme.warning, danger: theme.danger, info: theme.info };
|
|
580
|
+
return {
|
|
581
|
+
locale: own.locale ?? shared.locale ?? "en-US",
|
|
582
|
+
labels: mergeLabels(shared.labels, own.labels),
|
|
583
|
+
theme,
|
|
584
|
+
palette: colors,
|
|
585
|
+
color: (color, slot) => color === void 0 ? colors[(slot - 1) % 8] : typeof color === "number" ? colors[color - 1] : color in tones ? tones[color] : color
|
|
586
|
+
};
|
|
587
|
+
}, [scheme, brand, shared, own.locale, own.labels, own.theme]);
|
|
588
|
+
}
|
|
589
|
+
function NativeFrame({ frame, defaultHeight, resolved, summary, isEmpty, points, active, onActive, indexAt, legend, children }) {
|
|
590
|
+
const { title, hideTitle, height = defaultHeight, loading, empty, style } = frame;
|
|
591
|
+
const { theme, labels } = resolved;
|
|
592
|
+
const [width, setWidth] = useState(0);
|
|
593
|
+
const onLayout = (event) => setWidth(Math.round(event.nativeEvent.layout.width));
|
|
594
|
+
const readout = active !== null ? points[active] : null;
|
|
595
|
+
const n = points.length;
|
|
596
|
+
let body;
|
|
597
|
+
if (loading) body = /* @__PURE__ */ jsx(View, { style: [styles.state, { backgroundColor: theme.surface2 }], role: "progressbar", "aria-label": labels.loading });
|
|
598
|
+
else if (isEmpty)
|
|
599
|
+
body = empty ?? /* @__PURE__ */ jsx(View, { style: [styles.state, { borderColor: theme.borderDefault, borderWidth: StyleSheet.hairlineWidth, borderStyle: "dashed" }], children: /* @__PURE__ */ jsx(Text, { style: [styles.small, { color: theme.textSecondary }], children: labels.empty }) });
|
|
600
|
+
else body = width > 0 ? children(width, height) : null;
|
|
601
|
+
return /* @__PURE__ */ jsxs(View, { style: [styles.root, style], children: [
|
|
602
|
+
!hideTitle && /* @__PURE__ */ jsx(Text, { style: [styles.title, { color: theme.textPrimary }], role: "heading", children: title }),
|
|
603
|
+
legend,
|
|
604
|
+
/* @__PURE__ */ jsx(
|
|
605
|
+
Pressable,
|
|
606
|
+
{
|
|
607
|
+
onLayout,
|
|
608
|
+
style: { height },
|
|
609
|
+
disabled: isEmpty || loading,
|
|
610
|
+
onPress: (event) => indexAt && onActive(indexAt(event.nativeEvent.locationX, width)),
|
|
611
|
+
accessible: true,
|
|
612
|
+
accessibilityRole: n ? "adjustable" : "image",
|
|
613
|
+
accessibilityLabel: `${title}. ${summary}`,
|
|
614
|
+
accessibilityValue: n ? { min: 0, max: n - 1, now: active ?? 0, ...readout ? { text: readout } : {} } : void 0,
|
|
615
|
+
"aria-valuemin": n ? 0 : void 0,
|
|
616
|
+
"aria-valuemax": n ? n - 1 : void 0,
|
|
617
|
+
"aria-valuenow": n ? active ?? 0 : void 0,
|
|
618
|
+
"aria-valuetext": readout ?? void 0,
|
|
619
|
+
accessibilityActions: n ? [{ name: "increment" }, { name: "decrement" }] : [],
|
|
620
|
+
onAccessibilityAction: (event) => {
|
|
621
|
+
if (!n) return;
|
|
622
|
+
if (event.nativeEvent.actionName === "increment") onActive(Math.min(n - 1, (active ?? -1) + 1));
|
|
623
|
+
if (event.nativeEvent.actionName === "decrement") onActive(Math.max(0, (active ?? n) - 1));
|
|
624
|
+
},
|
|
625
|
+
children: body
|
|
626
|
+
}
|
|
627
|
+
),
|
|
628
|
+
readout ? /* @__PURE__ */ jsx(Text, { style: [styles.small, { color: theme.textSecondary }], "aria-hidden": true, children: readout }) : null
|
|
629
|
+
] });
|
|
630
|
+
}
|
|
631
|
+
function NativeLegend({ items, theme }) {
|
|
632
|
+
if (items.length < 2) return null;
|
|
633
|
+
return /* @__PURE__ */ jsx(View, { style: styles.legend, "aria-hidden": true, children: items.map((item) => /* @__PURE__ */ jsxs(View, { style: styles.legendItem, children: [
|
|
634
|
+
/* @__PURE__ */ jsx(View, { style: [styles.key, { backgroundColor: item.color }] }),
|
|
635
|
+
/* @__PURE__ */ jsx(Text, { style: [styles.small, { color: theme.textSecondary }], children: item.label })
|
|
636
|
+
] }, item.label)) });
|
|
637
|
+
}
|
|
638
|
+
var styles = StyleSheet.create({
|
|
639
|
+
root: { gap: 8 },
|
|
640
|
+
title: { fontSize: 14, fontWeight: "600", lineHeight: 20 },
|
|
641
|
+
small: { fontSize: 12, lineHeight: 16, fontVariant: ["tabular-nums"] },
|
|
642
|
+
state: { flex: 1, borderRadius: 10, alignItems: "center", justifyContent: "center", padding: 16 },
|
|
643
|
+
legend: { flexDirection: "row", flexWrap: "wrap", columnGap: 14, rowGap: 4 },
|
|
644
|
+
legendItem: { flexDirection: "row", alignItems: "center", gap: 6 },
|
|
645
|
+
key: { width: 10, height: 10, borderRadius: 3 }
|
|
646
|
+
});
|
|
647
|
+
|
|
648
|
+
// src/native/cartesian.tsx
|
|
649
|
+
import { jsx as jsx2, jsxs as jsxs2 } from "react/jsx-runtime";
|
|
650
|
+
var textWidth = (text) => Math.ceil(text.length * 6.4);
|
|
651
|
+
function NativeCartesian({ props, mode }) {
|
|
652
|
+
const { data, x, y, yLabel, series: seriesProp, format, xFormat, thresholds = [] } = props;
|
|
653
|
+
const resolved = useNativeSettings(props);
|
|
654
|
+
const { locale, labels, theme, color } = resolved;
|
|
655
|
+
const specs = useMemo2(() => normalizeSeries(seriesProp, y, yLabel), [seriesProp, y, yLabel]);
|
|
656
|
+
const table = useMemo2(() => tabulate(data, x, specs), [data, x, specs]);
|
|
657
|
+
const fmt = useMemo2(
|
|
658
|
+
() => ({ value: valueFormatter(format, locale, labels.noValue), axis: valueFormatter(format, locale, labels.noValue, true), category: categoryFormatter(xFormat, locale), share: shareFormatter(locale) }),
|
|
659
|
+
[format, xFormat, locale, labels.noValue]
|
|
660
|
+
);
|
|
661
|
+
const isEmpty = table.series.length === 0 || table.series.every((s) => s.values.every((v) => v == null));
|
|
662
|
+
const summary = isEmpty ? labels.empty : describeSeries(table, { kind: mode.kind, labels, value: fmt.value, category: fmt.category, share: fmt.share, thresholds });
|
|
663
|
+
const points = table.categories.map((c, i) => `${fmt.category(c)}: ${table.series.map((s) => `${s.label} ${fmt.value(s.values[i])}`).join(", ")}`);
|
|
664
|
+
const [active, setActive] = useState2(null);
|
|
665
|
+
const colors = table.series.map((s) => color(s.color, s.slot));
|
|
666
|
+
const count = table.categories.length;
|
|
667
|
+
const stacked = Boolean(mode.stacked);
|
|
668
|
+
return /* @__PURE__ */ jsx2(
|
|
669
|
+
NativeFrame,
|
|
670
|
+
{
|
|
671
|
+
frame: props,
|
|
672
|
+
defaultHeight: 220,
|
|
673
|
+
resolved,
|
|
674
|
+
summary,
|
|
675
|
+
isEmpty,
|
|
676
|
+
points,
|
|
677
|
+
active,
|
|
678
|
+
onActive: setActive,
|
|
679
|
+
legend: /* @__PURE__ */ jsx2(NativeLegend, { theme, items: table.series.map((s, i) => ({ label: s.label, color: colors[i] })) }),
|
|
680
|
+
indexAt: (px, width) => {
|
|
681
|
+
if (!count) return null;
|
|
682
|
+
const left = 44;
|
|
683
|
+
return Math.max(0, Math.min(count - 1, mode.kind === "bar" ? Math.floor((px - left) / (width - left - 8) * count) : Math.round((px - left) / (width - left - 8) * (count - 1))));
|
|
684
|
+
},
|
|
685
|
+
children: (width, height) => {
|
|
686
|
+
let [lo, hi] = extent(table.series, stacked);
|
|
687
|
+
for (const t of thresholds) {
|
|
688
|
+
lo = Math.min(lo, t.value);
|
|
689
|
+
hi = Math.max(hi, t.value);
|
|
690
|
+
}
|
|
691
|
+
lo = Math.min(0, lo);
|
|
692
|
+
hi = Math.max(0, hi);
|
|
693
|
+
const nice = niceDomain(lo, hi, 4);
|
|
694
|
+
const ticks = nice.ticks.map((t) => fmt.axis(t));
|
|
695
|
+
const x0 = Math.max(...ticks.map(textWidth)) + 8;
|
|
696
|
+
const x1 = width - 8;
|
|
697
|
+
const y0 = 8;
|
|
698
|
+
const y1 = height - 22;
|
|
699
|
+
const value = linearScale(nice.domain, [y1, y0], nice.ticks);
|
|
700
|
+
const band = bandScale(count, [x0, x1], 0.3);
|
|
701
|
+
const at = mode.kind === "bar" ? (i) => band(i) + band.bandwidth / 2 : pointScale(count, [x0, x1]);
|
|
702
|
+
const stacks = stacked ? stack(table.series) : null;
|
|
703
|
+
const widest = Math.max(...table.categories.map((c) => textWidth(fmt.category(c))));
|
|
704
|
+
const labelsAt = thinLabels(count, Math.max(2, Math.floor((x1 - x0) / (widest + 16))));
|
|
705
|
+
const groups = stacked ? 1 : table.series.length;
|
|
706
|
+
const thickness = Math.min(20, Math.max(2, (band.bandwidth - (groups - 1) * 2) / groups));
|
|
707
|
+
return /* @__PURE__ */ jsxs2(Svg, { width, height, children: [
|
|
708
|
+
nice.ticks.map((t, i) => /* @__PURE__ */ jsxs2(G, { children: [
|
|
709
|
+
/* @__PURE__ */ jsx2(Line, { x1: x0, x2: x1, y1: value(t), y2: value(t), stroke: t === 0 ? theme.borderDefault : theme.borderSubtle, strokeWidth: 1 }),
|
|
710
|
+
/* @__PURE__ */ jsx2(SvgText, { x: x0 - 6, y: value(t) + 4, fontSize: 11, fill: theme.textSecondary, textAnchor: "end", children: ticks[i] })
|
|
711
|
+
] }, t)),
|
|
712
|
+
labelsAt.map((i) => /* @__PURE__ */ jsx2(SvgText, { x: at(i), y: y1 + 16, fontSize: 11, fill: theme.textSecondary, textAnchor: mode.kind !== "bar" && i === 0 ? "start" : mode.kind !== "bar" && i === count - 1 ? "end" : "middle", children: fmt.category(table.categories[i]) }, i)),
|
|
713
|
+
active !== null && /* @__PURE__ */ jsx2(Line, { x1: at(active), x2: at(active), y1: y0, y2: y1, stroke: theme.borderDefault, strokeWidth: 1 }),
|
|
714
|
+
table.series.map((s, k) => {
|
|
715
|
+
if (mode.kind === "bar") {
|
|
716
|
+
return s.values.map((v, i) => {
|
|
717
|
+
const seg = stacks?.[k]?.[i];
|
|
718
|
+
const from = seg ? seg.base : 0;
|
|
719
|
+
const to = seg ? seg.top : v ?? 0;
|
|
720
|
+
if (from === to) return null;
|
|
721
|
+
const isTop = !stacked || k === table.series.length - 1;
|
|
722
|
+
const top = Math.min(value(from), value(to));
|
|
723
|
+
const size = Math.abs(value(to) - value(from)) - (isTop ? 0 : 2);
|
|
724
|
+
const left = band(i) + (band.bandwidth - (thickness * groups + (groups - 1) * 2)) / 2 + (stacked ? 0 : k * (thickness + 2));
|
|
725
|
+
return /* @__PURE__ */ jsx2(Path, { d: barPath(left, isTop ? top : top + 2, thickness, Math.max(0, size), isTop ? 4 : 0, false, to < from), fill: colors[k], opacity: active !== null && active !== i ? 0.4 : 1 }, `${k}-${i}`);
|
|
726
|
+
});
|
|
727
|
+
}
|
|
728
|
+
const pts = s.values.map((v, i) => v == null ? null : [at(i), value(stacks ? stacks[k][i].top : v)]);
|
|
729
|
+
return segments(pts).map((seg) => /* @__PURE__ */ jsxs2(G, { children: [
|
|
730
|
+
mode.kind === "area" && /* @__PURE__ */ jsx2(Path, { d: areaPath(seg, stacks && k > 0 ? seg.map(([px]) => [px, value(stacks[k][Math.round((px - x0) / (x1 - x0) * (count - 1))].base)]) : value(0), mode.curve), fill: colors[k], opacity: stacked ? 0.5 : 0.14 }),
|
|
731
|
+
/* @__PURE__ */ jsx2(Path, { d: linePath(seg, mode.curve), stroke: colors[k], strokeWidth: 2, fill: "none", strokeLinecap: "round", strokeLinejoin: "round", strokeDasharray: s.dashed ? "6 4" : void 0 })
|
|
732
|
+
] }, `${k}-${seg[0][0]}`));
|
|
733
|
+
}),
|
|
734
|
+
thresholds.map((t, i) => /* @__PURE__ */ jsxs2(G, { children: [
|
|
735
|
+
/* @__PURE__ */ jsx2(Line, { x1: x0, x2: x1, y1: value(t.value), y2: value(t.value), stroke: color(t.tone ?? "neutral", 1), strokeWidth: 1.5, strokeDasharray: "6 4" }),
|
|
736
|
+
/* @__PURE__ */ jsx2(SvgText, { x: x1, y: value(t.value) - 6, fontSize: 11, fontWeight: "600", fill: theme.textPrimary, textAnchor: "end", children: t.label })
|
|
737
|
+
] }, `t-${i}`)),
|
|
738
|
+
active !== null && mode.kind !== "bar" && table.series.map((s, k) => {
|
|
739
|
+
const v = s.values[active];
|
|
740
|
+
if (v == null) return null;
|
|
741
|
+
return /* @__PURE__ */ jsx2(Circle, { cx: at(active), cy: value(stacks ? stacks[k][active].top : v), r: 5, fill: colors[k], stroke: theme.surface1, strokeWidth: 2 }, k);
|
|
742
|
+
})
|
|
743
|
+
] });
|
|
744
|
+
}
|
|
745
|
+
}
|
|
746
|
+
);
|
|
747
|
+
}
|
|
748
|
+
function LineChart({ curve = "monotone", ...props }) {
|
|
749
|
+
return /* @__PURE__ */ jsx2(NativeCartesian, { props, mode: { kind: "line", curve } });
|
|
750
|
+
}
|
|
751
|
+
function AreaChart({ curve = "monotone", stacked, ...props }) {
|
|
752
|
+
return /* @__PURE__ */ jsx2(NativeCartesian, { props, mode: { kind: "area", curve, stacked } });
|
|
753
|
+
}
|
|
754
|
+
function BarChart({ stacked, ...props }) {
|
|
755
|
+
return /* @__PURE__ */ jsx2(NativeCartesian, { props, mode: { kind: "bar", stacked } });
|
|
756
|
+
}
|
|
757
|
+
|
|
758
|
+
// src/native/needs.tsx
|
|
759
|
+
import { StyleSheet as StyleSheet2, Text as Text2, View as View2 } from "react-native";
|
|
760
|
+
import Svg3, { Path as Path3 } from "react-native-svg";
|
|
761
|
+
|
|
762
|
+
// src/needs/labels.ts
|
|
763
|
+
var EARNINGS_LABELS = {
|
|
764
|
+
total: "earned over {count} periods",
|
|
765
|
+
change: "{change} vs the previous period",
|
|
766
|
+
gross: "Gross",
|
|
767
|
+
net: "Net"
|
|
768
|
+
};
|
|
769
|
+
var THROUGHPUT_LABELS = { total: "jobs over {count} periods", success: "{rate} succeeded" };
|
|
770
|
+
var LATENCY_LABELS = {
|
|
771
|
+
p50: "Median (p50)",
|
|
772
|
+
p95: "p95",
|
|
773
|
+
slowest: "p95 of {name}, the slowest",
|
|
774
|
+
over: "{count} over the objective",
|
|
775
|
+
within: "all within the objective"
|
|
776
|
+
};
|
|
777
|
+
var CREDIT_LABELS = {
|
|
778
|
+
remaining: "left of {limit}",
|
|
779
|
+
used: "{used} used ({percent})",
|
|
780
|
+
runsOut: "At this pace, runs out on {date}",
|
|
781
|
+
steady: "No use lately",
|
|
782
|
+
renews: "Renews on {date}",
|
|
783
|
+
daily: "Use per day"
|
|
784
|
+
};
|
|
785
|
+
var GOAL_LABELS = { raised: "raised of {goal}", reached: "Goal reached", supporters: "{count} supporters", left: "{time} left" };
|
|
786
|
+
var TICKER_LABELS = {
|
|
787
|
+
current: "current bid",
|
|
788
|
+
change: "{change} since the opening \xB7 {count} bids",
|
|
789
|
+
opening: "opening price, no bid yet",
|
|
790
|
+
reserve: "Reserve price",
|
|
791
|
+
price: "Price"
|
|
792
|
+
};
|
|
793
|
+
|
|
794
|
+
// src/needs/model.ts
|
|
795
|
+
import { currencyDigits as currencyDigits2, getNumberFormat as getNumberFormat2 } from "@krizaka/intl";
|
|
796
|
+
function numberOf(row, accessor, index) {
|
|
797
|
+
const value = typeof accessor === "function" ? accessor(row, index) : row[accessor];
|
|
798
|
+
return typeof value === "number" && Number.isFinite(value) ? value : null;
|
|
799
|
+
}
|
|
800
|
+
function total(rows, accessor) {
|
|
801
|
+
return rows.reduce((sum, row, i) => sum + (numberOf(row, accessor, i) ?? 0), 0);
|
|
802
|
+
}
|
|
803
|
+
function lastChange(values) {
|
|
804
|
+
if (values.length < 2) return null;
|
|
805
|
+
const last = values[values.length - 1];
|
|
806
|
+
const previous = values[values.length - 2];
|
|
807
|
+
if (last == null || previous == null || previous === 0) return null;
|
|
808
|
+
return last / previous - 1;
|
|
809
|
+
}
|
|
810
|
+
function direction(change) {
|
|
811
|
+
if (change == null) return null;
|
|
812
|
+
return Math.abs(change) < 5e-3 ? "flat" : change > 0 ? "up" : "down";
|
|
813
|
+
}
|
|
814
|
+
function successRate(succeeded, failed) {
|
|
815
|
+
const finished = succeeded + failed;
|
|
816
|
+
return finished > 0 ? succeeded / finished : null;
|
|
817
|
+
}
|
|
818
|
+
function daysLeft(remaining, daily, days = 7) {
|
|
819
|
+
const recent = daily.slice(-days).filter((v) => v != null && v >= 0);
|
|
820
|
+
if (recent.length === 0) return null;
|
|
821
|
+
const pace = recent.reduce((a, b) => a + b, 0) / recent.length;
|
|
822
|
+
if (pace <= 0) return null;
|
|
823
|
+
return Math.max(0, Math.floor(remaining / pace));
|
|
824
|
+
}
|
|
825
|
+
var addDays = (from, days) => new Date(from.getTime() + days * 864e5);
|
|
826
|
+
function quotaLevel(ratio, warning = 0.8, danger = 0.95) {
|
|
827
|
+
return ratio >= danger ? "danger" : ratio >= warning ? "warning" : "ok";
|
|
828
|
+
}
|
|
829
|
+
function fillIn(template, values) {
|
|
830
|
+
return template.replace(/\{(\w+)\}/g, (match, key) => key in values ? String(values[key]) : match);
|
|
831
|
+
}
|
|
832
|
+
function signedPercent(change, locale) {
|
|
833
|
+
return getNumberFormat2(locale, { style: "percent", signDisplay: "exceptZero", maximumFractionDigits: Math.abs(change) < 0.1 ? 1 : 0 }).format(change);
|
|
834
|
+
}
|
|
835
|
+
function formatDuration(ms, locale) {
|
|
836
|
+
const unit = (value, name, digits) => getNumberFormat2(locale, { style: "unit", unit: name, unitDisplay: "short", maximumFractionDigits: digits }).format(value);
|
|
837
|
+
const abs = Math.abs(ms);
|
|
838
|
+
if (abs < 1e3) return unit(Math.round(ms), "millisecond", 0);
|
|
839
|
+
if (abs < 6e4) return unit(ms / 1e3, "second", abs < 1e4 ? 1 : 0);
|
|
840
|
+
if (abs < 36e5) return unit(ms / 6e4, "minute", 1);
|
|
841
|
+
return unit(ms / 36e5, "hour", 1);
|
|
842
|
+
}
|
|
843
|
+
function roundMoney(currency) {
|
|
844
|
+
const digits = currencyDigits2(currency);
|
|
845
|
+
return (value, locale) => {
|
|
846
|
+
const minor = Math.round(value);
|
|
847
|
+
const whole = minor % 10 ** digits === 0;
|
|
848
|
+
return getNumberFormat2(locale, { style: "currency", currency, minimumFractionDigits: whole ? 0 : digits, maximumFractionDigits: whole ? 0 : digits }).format(minor / 10 ** digits);
|
|
849
|
+
};
|
|
850
|
+
}
|
|
851
|
+
|
|
852
|
+
// src/needs/ticker.ts
|
|
853
|
+
function tickerModel(bids, opening, openedAt) {
|
|
854
|
+
const sorted = [...bids].sort((a, b) => new Date(a.at).getTime() - new Date(b.at).getTime());
|
|
855
|
+
const points = [...openedAt ? [{ at: openedAt, amount: opening }] : [], ...sorted];
|
|
856
|
+
const current = sorted.length > 0 ? sorted[sorted.length - 1].amount : opening;
|
|
857
|
+
return { points, current, change: current - opening, ratio: opening > 0 ? current / opening - 1 : null, count: sorted.length };
|
|
858
|
+
}
|
|
859
|
+
|
|
860
|
+
// src/native/round.tsx
|
|
861
|
+
import { useMemo as useMemo3, useState as useState3 } from "react";
|
|
862
|
+
import Svg2, { Circle as Circle2, Line as Line2, Path as Path2, Text as SvgText2 } from "react-native-svg";
|
|
863
|
+
import { jsx as jsx3, jsxs as jsxs3 } from "react/jsx-runtime";
|
|
864
|
+
function PieChart(props) {
|
|
865
|
+
const { data, label, value, format, donut, centerLabel, maxSlices = 6, otherLabel = "Other" } = props;
|
|
866
|
+
const resolved = useNativeSettings(props);
|
|
867
|
+
const { locale, labels, theme, color } = resolved;
|
|
868
|
+
const fmt = useMemo3(() => ({ value: valueFormatter(format, locale, labels.noValue), share: shareFormatter(locale) }), [format, locale, labels.noValue]);
|
|
869
|
+
const slices = useMemo3(() => {
|
|
870
|
+
const rows = data.map((d, i) => ({ label: read(label, d, i), value: Math.max(0, Number(read(value, d, i)) || 0) })).sort((a, b) => b.value - a.value);
|
|
871
|
+
const kept = rows.length > maxSlices ? rows.slice(0, maxSlices - 1) : rows;
|
|
872
|
+
const out = kept.map((r2, i) => ({ ...r2, color: color(void 0, i + 1) }));
|
|
873
|
+
if (rows.length > maxSlices) out.push({ label: otherLabel, value: rows.slice(maxSlices - 1).reduce((s, r2) => s + r2.value, 0), color: theme.textMuted });
|
|
874
|
+
return out;
|
|
875
|
+
}, [data, label, value, maxSlices, otherLabel, color, theme.textMuted]);
|
|
876
|
+
const total2 = slices.reduce((s, x) => s + x.value, 0);
|
|
877
|
+
const [active, setActive] = useState3(null);
|
|
878
|
+
const isEmpty = total2 <= 0;
|
|
879
|
+
const summary = isEmpty ? labels.empty : describeParts(donut ? "donut" : "pie", slices, { labels, value: fmt.value, share: fmt.share });
|
|
880
|
+
return /* @__PURE__ */ jsx3(
|
|
881
|
+
NativeFrame,
|
|
882
|
+
{
|
|
883
|
+
frame: props,
|
|
884
|
+
defaultHeight: 200,
|
|
885
|
+
resolved,
|
|
886
|
+
summary,
|
|
887
|
+
isEmpty,
|
|
888
|
+
points: slices.map((s) => `${s.label}: ${fmt.value(s.value)} (${fmt.share(total2 ? s.value / total2 : 0)})`),
|
|
889
|
+
active,
|
|
890
|
+
onActive: setActive,
|
|
891
|
+
legend: /* @__PURE__ */ jsx3(NativeLegend, { theme, items: slices.map((s) => ({ label: `${s.label} \xB7 ${fmt.share(total2 ? s.value / total2 : 0)}`, color: s.color })) }),
|
|
892
|
+
children: (width, height) => {
|
|
893
|
+
const radius = Math.max(10, Math.min(width, height) / 2 - 6);
|
|
894
|
+
const inner = donut ? radius * 0.64 : 0;
|
|
895
|
+
let angle = 0;
|
|
896
|
+
return /* @__PURE__ */ jsxs3(Svg2, { width, height, children: [
|
|
897
|
+
slices.map((s, i) => {
|
|
898
|
+
const start = angle;
|
|
899
|
+
angle += total2 ? s.value / total2 * Math.PI * 2 : 0;
|
|
900
|
+
return /* @__PURE__ */ jsx3(Path2, { d: arcPath(width / 2, height / 2, inner, radius, start, angle), fill: s.color, stroke: theme.surface1, strokeWidth: slices.length > 1 ? 2 : 0, opacity: active !== null && active !== i ? 0.4 : 1 }, s.label);
|
|
901
|
+
}),
|
|
902
|
+
donut && /* @__PURE__ */ jsx3(SvgText2, { x: width / 2, y: height / 2 + (centerLabel ? 0 : 7), fontSize: Math.max(14, Math.min(24, inner / 3)), fontWeight: "600", fill: theme.textPrimary, textAnchor: "middle", children: fmt.value(total2) }),
|
|
903
|
+
donut && centerLabel ? /* @__PURE__ */ jsx3(SvgText2, { x: width / 2, y: height / 2 + 18, fontSize: 11, fill: theme.textSecondary, textAnchor: "middle", children: centerLabel }) : null
|
|
904
|
+
] });
|
|
905
|
+
}
|
|
906
|
+
}
|
|
907
|
+
);
|
|
908
|
+
}
|
|
909
|
+
function DonutChart(props) {
|
|
910
|
+
return /* @__PURE__ */ jsx3(PieChart, { ...props, donut: true });
|
|
911
|
+
}
|
|
912
|
+
var START = -120 * Math.PI / 180;
|
|
913
|
+
var END = 120 * Math.PI / 180;
|
|
914
|
+
function Gauge(props) {
|
|
915
|
+
const { value, min = 0, max = 100, format, caption, target, zones = [], tone = "accent" } = props;
|
|
916
|
+
const resolved = useNativeSettings(props);
|
|
917
|
+
const { locale, labels, theme, color } = resolved;
|
|
918
|
+
const fmt = valueFormatter(format, locale, labels.noValue);
|
|
919
|
+
const clamped = Math.min(max, Math.max(min, value));
|
|
920
|
+
const zone = zones.find((z) => clamped <= z.to) ?? zones[zones.length - 1];
|
|
921
|
+
const at = (v) => START + (Math.min(max, Math.max(min, v)) - min) / (max - min || 1) * (END - START);
|
|
922
|
+
const text = fmt(value);
|
|
923
|
+
return /* @__PURE__ */ jsx3(
|
|
924
|
+
NativeFrame,
|
|
925
|
+
{
|
|
926
|
+
frame: props,
|
|
927
|
+
defaultHeight: 170,
|
|
928
|
+
resolved,
|
|
929
|
+
summary: `${labels.kinds.gauge}: ${text} / ${fmt(max)}${zone?.label ? `, ${zone.label}` : ""}.`,
|
|
930
|
+
isEmpty: false,
|
|
931
|
+
points: [],
|
|
932
|
+
active: null,
|
|
933
|
+
onActive: () => {
|
|
934
|
+
},
|
|
935
|
+
children: (width, height) => {
|
|
936
|
+
const radius = Math.max(20, Math.min(width / 2 - 12, (height - 16) / 1.58));
|
|
937
|
+
const cx = width / 2;
|
|
938
|
+
const cy = 8 + radius;
|
|
939
|
+
const stroke = Math.max(8, radius * 0.16);
|
|
940
|
+
const [tx0, ty0] = target ? polar(cx, cy, radius - stroke, at(target.value)) : [0, 0];
|
|
941
|
+
const [tx1, ty1] = target ? polar(cx, cy, radius + stroke, at(target.value)) : [0, 0];
|
|
942
|
+
return /* @__PURE__ */ jsxs3(Svg2, { width, height, children: [
|
|
943
|
+
/* @__PURE__ */ jsx3(Path2, { d: strokeArcPath(cx, cy, radius, START, END), stroke: theme.surface3, strokeWidth: stroke, strokeLinecap: "round", fill: "none" }),
|
|
944
|
+
clamped > min && /* @__PURE__ */ jsx3(Path2, { d: strokeArcPath(cx, cy, radius, START, at(clamped)), stroke: color(zone?.tone ?? tone, 1), strokeWidth: stroke, strokeLinecap: "round", fill: "none" }),
|
|
945
|
+
target && /* @__PURE__ */ jsx3(Line2, { x1: tx0, y1: ty0, x2: tx1, y2: ty1, stroke: theme.textPrimary, strokeWidth: 2, strokeLinecap: "round" }),
|
|
946
|
+
/* @__PURE__ */ jsx3(SvgText2, { x: cx, y: cy + 8, fontSize: Math.max(12, Math.min(30, radius / 2.6, radius * 1.45 / (text.length * 0.58))), fontWeight: "600", fill: theme.textPrimary, textAnchor: "middle", children: text }),
|
|
947
|
+
caption ? /* @__PURE__ */ jsx3(SvgText2, { x: cx, y: cy + Math.max(26, radius / 2.4), fontSize: 11, fill: theme.textSecondary, textAnchor: "middle", children: caption }) : null
|
|
948
|
+
] });
|
|
949
|
+
}
|
|
950
|
+
}
|
|
951
|
+
);
|
|
952
|
+
}
|
|
953
|
+
function Sparkline(props) {
|
|
954
|
+
const { data, categories, variant = "line", color: own, trendTone, format, width: fixed, height = 32 } = props;
|
|
955
|
+
const resolved = useNativeSettings(props);
|
|
956
|
+
const { locale, labels, color } = resolved;
|
|
957
|
+
const fmt = useMemo3(() => ({ value: valueFormatter(format, locale, labels.noValue), category: categoryFormatter(void 0, locale), share: shareFormatter(locale) }), [format, locale, labels.noValue]);
|
|
958
|
+
const values = data.filter((v) => v != null);
|
|
959
|
+
const table = { categories: categories ?? data.map((_, i) => i + 1), series: [{ id: "v", label: props.title, values: data, slot: 1 }] };
|
|
960
|
+
const isEmpty = values.length === 0;
|
|
961
|
+
const up = (values[values.length - 1] ?? 0) >= (values[0] ?? 0);
|
|
962
|
+
const stroke = color(own ?? (trendTone ? (trendTone === "inverse" ? !up : up) ? "success" : "danger" : void 0), 1);
|
|
963
|
+
return /* @__PURE__ */ jsx3(
|
|
964
|
+
NativeFrame,
|
|
965
|
+
{
|
|
966
|
+
frame: { ...props, hideTitle: true, height, style: { ...fixed ? { width: fixed } : {}, ...props.style } },
|
|
967
|
+
defaultHeight: 32,
|
|
968
|
+
resolved,
|
|
969
|
+
summary: isEmpty ? labels.empty : describeSeries(table, { kind: "sparkline", labels, value: fmt.value, category: fmt.category, share: fmt.share }),
|
|
970
|
+
isEmpty,
|
|
971
|
+
points: [],
|
|
972
|
+
active: null,
|
|
973
|
+
onActive: () => {
|
|
974
|
+
},
|
|
975
|
+
children: (width, h) => {
|
|
976
|
+
const lo = variant === "bar" ? Math.min(0, ...values) : Math.min(...values);
|
|
977
|
+
const hi = variant === "bar" ? Math.max(0, ...values) : Math.max(...values);
|
|
978
|
+
const yOf = (v) => 3 + (1 - (v - lo) / (hi - lo || 1)) * (h - 6);
|
|
979
|
+
const n = data.length;
|
|
980
|
+
const xOf = (i) => variant === "bar" ? (i + 0.5) * (width / n) : n > 1 ? 3 + i / (n - 1) * (width - 6) : width / 2;
|
|
981
|
+
const pts = data.map((v, i) => v == null ? null : [xOf(i), yOf(v)]);
|
|
982
|
+
const last = [...pts].reverse().find(Boolean);
|
|
983
|
+
return /* @__PURE__ */ jsxs3(Svg2, { width, height: h, children: [
|
|
984
|
+
variant === "bar" ? data.map((v, i) => v == null || v === 0 ? null : /* @__PURE__ */ jsx3(Path2, { d: barPath(xOf(i) - Math.min(4, width / n / 3), Math.min(yOf(v), yOf(0)), Math.min(8, width / n * 0.7), Math.abs(yOf(v) - yOf(0)), 1.5), fill: stroke }, i)) : segments(pts).map((seg) => [
|
|
985
|
+
variant === "area" ? /* @__PURE__ */ jsx3(Path2, { d: areaPath(seg, h), fill: stroke, opacity: 0.14 }, `a${seg[0][0]}`) : null,
|
|
986
|
+
/* @__PURE__ */ jsx3(Path2, { d: linePath(seg), stroke, strokeWidth: 1.75, fill: "none", strokeLinecap: "round" }, `l${seg[0][0]}`)
|
|
987
|
+
]),
|
|
988
|
+
variant !== "bar" && last ? /* @__PURE__ */ jsx3(Circle2, { cx: last[0], cy: last[1], r: 2.75, fill: stroke }) : null
|
|
989
|
+
] });
|
|
990
|
+
}
|
|
991
|
+
}
|
|
992
|
+
);
|
|
993
|
+
}
|
|
994
|
+
|
|
995
|
+
// src/native/needs.tsx
|
|
996
|
+
import { jsx as jsx4, jsxs as jsxs4 } from "react/jsx-runtime";
|
|
997
|
+
var ARROW = { up: "M7 17 17 7M8 7h9v9", down: "M7 7l10 10M17 8v9H8", flat: "M5 12h14M13 6l6 6-6 6" };
|
|
998
|
+
function toneColor(resolved, tone) {
|
|
999
|
+
return resolved.color(tone, 1);
|
|
1000
|
+
}
|
|
1001
|
+
function Headline({
|
|
1002
|
+
resolved,
|
|
1003
|
+
title,
|
|
1004
|
+
hideTitle,
|
|
1005
|
+
value,
|
|
1006
|
+
label,
|
|
1007
|
+
delta,
|
|
1008
|
+
way,
|
|
1009
|
+
tone = "neutral"
|
|
1010
|
+
}) {
|
|
1011
|
+
const { theme } = resolved;
|
|
1012
|
+
return /* @__PURE__ */ jsxs4(View2, { style: styles2.head, children: [
|
|
1013
|
+
!hideTitle ? /* @__PURE__ */ jsx4(Text2, { role: "heading", style: [styles2.title, { color: theme.textPrimary }], children: title }) : null,
|
|
1014
|
+
/* @__PURE__ */ jsxs4(View2, { style: styles2.kpi, children: [
|
|
1015
|
+
/* @__PURE__ */ jsx4(Text2, { style: [styles2.value, { color: theme.textPrimary }], children: value }),
|
|
1016
|
+
label ? /* @__PURE__ */ jsx4(Text2, { style: [styles2.small, { color: theme.textSecondary }], children: label }) : null
|
|
1017
|
+
] }),
|
|
1018
|
+
delta ? /* @__PURE__ */ jsxs4(View2, { style: styles2.delta, children: [
|
|
1019
|
+
way ? /* @__PURE__ */ jsx4(Svg3, { width: 12, height: 12, viewBox: "0 0 24 24", "aria-hidden": true, children: /* @__PURE__ */ jsx4(Path3, { d: ARROW[way], fill: "none", stroke: toneColor(resolved, tone), strokeWidth: 2.5, strokeLinecap: "round", strokeLinejoin: "round" }) }) : null,
|
|
1020
|
+
/* @__PURE__ */ jsx4(Text2, { style: [styles2.small, styles2.strong, { color: theme.textPrimary }], children: delta })
|
|
1021
|
+
] }) : null
|
|
1022
|
+
] });
|
|
1023
|
+
}
|
|
1024
|
+
var good = (way, up) => !way || way === "flat" ? "neutral" : way === "up" === up ? "success" : "danger";
|
|
1025
|
+
function EarningsChart({ x = "month", net, gross, currency, period = "month", payoutThreshold, labels: given, title, hideTitle, data, ...props }) {
|
|
1026
|
+
const words = { ...EARNINGS_LABELS, ...given };
|
|
1027
|
+
const resolved = useNativeSettings(props);
|
|
1028
|
+
const format = { style: "money", currency };
|
|
1029
|
+
const change = lastChange(data.map((row, i) => numberOf(row, net, i)));
|
|
1030
|
+
const way = direction(change);
|
|
1031
|
+
const series = gross ? [{ key: gross, label: words.gross, color: 2 }, { key: net, label: words.net, color: 1 }] : [{ key: net, label: words.net, color: 1 }];
|
|
1032
|
+
return /* @__PURE__ */ jsxs4(View2, { style: styles2.root, children: [
|
|
1033
|
+
/* @__PURE__ */ jsx4(
|
|
1034
|
+
Headline,
|
|
1035
|
+
{
|
|
1036
|
+
resolved,
|
|
1037
|
+
title,
|
|
1038
|
+
hideTitle,
|
|
1039
|
+
value: valueFormatter(format, resolved.locale)(total(data, net)),
|
|
1040
|
+
label: fillIn(words.total, { count: data.length }),
|
|
1041
|
+
delta: change == null ? null : fillIn(words.change, { change: signedPercent(change, resolved.locale) }),
|
|
1042
|
+
way,
|
|
1043
|
+
tone: good(way, true)
|
|
1044
|
+
}
|
|
1045
|
+
),
|
|
1046
|
+
/* @__PURE__ */ jsx4(BarChart, { ...props, title, hideTitle: true, data, x, series, format, xFormat: period, thresholds: payoutThreshold ? [{ tone: "success", ...payoutThreshold }] : void 0 })
|
|
1047
|
+
] });
|
|
1048
|
+
}
|
|
1049
|
+
function JobThroughput({ x = "day", period = "day", statuses = DEFAULT_STATUSES, labels: given, title, hideTitle, data, ...props }) {
|
|
1050
|
+
const words = { ...THROUGHPUT_LABELS, ...given };
|
|
1051
|
+
const resolved = useNativeSettings(props);
|
|
1052
|
+
const sum = (outcome) => statuses.filter((s) => outcome === void 0 || s.outcome === outcome).reduce((n, s) => n + total(data, s.key), 0);
|
|
1053
|
+
const rate = successRate(sum("succeeded"), sum("failed"));
|
|
1054
|
+
const series = statuses.map((s) => ({ key: s.key, label: s.label, color: s.tone }));
|
|
1055
|
+
return /* @__PURE__ */ jsxs4(View2, { style: styles2.root, children: [
|
|
1056
|
+
/* @__PURE__ */ jsx4(
|
|
1057
|
+
Headline,
|
|
1058
|
+
{
|
|
1059
|
+
resolved,
|
|
1060
|
+
title,
|
|
1061
|
+
hideTitle,
|
|
1062
|
+
value: valueFormatter("integer", resolved.locale)(sum()),
|
|
1063
|
+
label: fillIn(words.total, { count: data.length }),
|
|
1064
|
+
delta: rate == null ? null : fillIn(words.success, { rate: valueFormatter("percent", resolved.locale)(rate) })
|
|
1065
|
+
}
|
|
1066
|
+
),
|
|
1067
|
+
/* @__PURE__ */ jsx4(BarChart, { ...props, title, hideTitle: true, data, x, xFormat: period, series, format: "integer", stacked: true })
|
|
1068
|
+
] });
|
|
1069
|
+
}
|
|
1070
|
+
function LatencyChart({
|
|
1071
|
+
x = "name",
|
|
1072
|
+
p50 = "p50",
|
|
1073
|
+
p95 = "p95",
|
|
1074
|
+
objective,
|
|
1075
|
+
labels: given,
|
|
1076
|
+
title,
|
|
1077
|
+
hideTitle,
|
|
1078
|
+
data,
|
|
1079
|
+
...props
|
|
1080
|
+
}) {
|
|
1081
|
+
const words = { ...LATENCY_LABELS, ...given };
|
|
1082
|
+
const resolved = useNativeSettings(props);
|
|
1083
|
+
const tail = p95 ?? p50;
|
|
1084
|
+
const measured = data.map((row, i) => ({ row, i, value: numberOf(row, tail, i) ?? 0 }));
|
|
1085
|
+
const slowest = measured.reduce((a, m) => !a || m.value > a.value ? m : a, null);
|
|
1086
|
+
const over = objective ? measured.filter((m) => m.value > objective.value).length : 0;
|
|
1087
|
+
const nameOf = (row, i) => String(typeof x === "function" ? x(row, i) : row[x]);
|
|
1088
|
+
const series = [{ key: p50, label: words.p50, color: "neutral" }, ...p95 ? [{ key: p95, label: words.p95, color: 1 }] : []];
|
|
1089
|
+
return /* @__PURE__ */ jsxs4(View2, { style: styles2.root, children: [
|
|
1090
|
+
/* @__PURE__ */ jsx4(
|
|
1091
|
+
Headline,
|
|
1092
|
+
{
|
|
1093
|
+
resolved,
|
|
1094
|
+
title,
|
|
1095
|
+
hideTitle,
|
|
1096
|
+
value: slowest ? formatDuration(slowest.value, resolved.locale) : "\u2014",
|
|
1097
|
+
label: slowest ? fillIn(words.slowest, { name: nameOf(slowest.row, slowest.i) }) : void 0,
|
|
1098
|
+
delta: objective ? over > 0 ? fillIn(words.over, { count: over }) : words.within : null,
|
|
1099
|
+
way: objective ? over > 0 ? "up" : "flat" : null,
|
|
1100
|
+
tone: over > 0 ? "danger" : "success"
|
|
1101
|
+
}
|
|
1102
|
+
),
|
|
1103
|
+
/* @__PURE__ */ jsx4(
|
|
1104
|
+
BarChart,
|
|
1105
|
+
{
|
|
1106
|
+
...props,
|
|
1107
|
+
title,
|
|
1108
|
+
hideTitle: true,
|
|
1109
|
+
data,
|
|
1110
|
+
x,
|
|
1111
|
+
series,
|
|
1112
|
+
format: (value, l) => formatDuration(value, l),
|
|
1113
|
+
thresholds: objective ? [{ ...objective, tone: "danger" }] : void 0
|
|
1114
|
+
}
|
|
1115
|
+
)
|
|
1116
|
+
] });
|
|
1117
|
+
}
|
|
1118
|
+
function CreditUsage({ title, hideTitle, used, limit, format = "integer", daily, renewsAt, now, levels = [0.8, 0.95], labels: given, style, ...settings }) {
|
|
1119
|
+
const words = { ...CREDIT_LABELS, ...given };
|
|
1120
|
+
const resolved = useNativeSettings(settings);
|
|
1121
|
+
const { theme, locale } = resolved;
|
|
1122
|
+
const write = valueFormatter(format, locale);
|
|
1123
|
+
const date = categoryFormatter("date", locale);
|
|
1124
|
+
const ratio = limit > 0 ? Math.min(1, Math.max(0, used / limit)) : 0;
|
|
1125
|
+
const level = quotaLevel(ratio, levels[0], levels[1]);
|
|
1126
|
+
const remaining = Math.max(0, limit - used);
|
|
1127
|
+
const usedText = fillIn(words.used, { used: write(used), percent: valueFormatter("percent", locale)(ratio) });
|
|
1128
|
+
const left = daily ? daysLeft(remaining, daily) : null;
|
|
1129
|
+
const runOut = left == null ? null : addDays(now ?? /* @__PURE__ */ new Date(), left);
|
|
1130
|
+
const renews = renewsAt ? new Date(renewsAt) : null;
|
|
1131
|
+
const projection = daily ? runOut && (!renews || runOut < renews) ? fillIn(words.runsOut, { date: date(runOut) }) : left == null ? words.steady : null : null;
|
|
1132
|
+
const fill2 = level === "danger" ? theme.danger : level === "warning" ? theme.warning : theme.accent;
|
|
1133
|
+
return /* @__PURE__ */ jsxs4(View2, { style: [styles2.root, style], children: [
|
|
1134
|
+
/* @__PURE__ */ jsx4(Headline, { resolved, title, hideTitle, value: write(remaining), label: fillIn(words.remaining, { limit: write(limit) }) }),
|
|
1135
|
+
/* @__PURE__ */ jsx4(
|
|
1136
|
+
View2,
|
|
1137
|
+
{
|
|
1138
|
+
role: "meter",
|
|
1139
|
+
"aria-label": title,
|
|
1140
|
+
"aria-valuemin": 0,
|
|
1141
|
+
"aria-valuemax": limit,
|
|
1142
|
+
"aria-valuenow": Math.min(limit, Math.max(0, used)),
|
|
1143
|
+
"aria-valuetext": usedText,
|
|
1144
|
+
accessible: true,
|
|
1145
|
+
style: [styles2.meter, { backgroundColor: theme.surface3 }],
|
|
1146
|
+
children: /* @__PURE__ */ jsx4(View2, { style: [styles2.meterFill, { width: `${ratio * 100}%`, backgroundColor: fill2 }] })
|
|
1147
|
+
}
|
|
1148
|
+
),
|
|
1149
|
+
/* @__PURE__ */ jsxs4(View2, { style: styles2.row, children: [
|
|
1150
|
+
/* @__PURE__ */ jsx4(Text2, { style: [styles2.small, { color: theme.textSecondary }], children: usedText }),
|
|
1151
|
+
renews ? /* @__PURE__ */ jsx4(Text2, { style: [styles2.small, { color: theme.textSecondary }], children: fillIn(words.renews, { date: date(renews) }) }) : null
|
|
1152
|
+
] }),
|
|
1153
|
+
daily && daily.length > 1 ? /* @__PURE__ */ jsx4(Sparkline, { ...settings, title: words.daily, data: daily, variant: "bar", format, height: 36 }) : null,
|
|
1154
|
+
projection ? /* @__PURE__ */ jsx4(Text2, { style: [styles2.small, styles2.strong, { color: theme.textPrimary }], children: projection }) : null
|
|
1155
|
+
] });
|
|
1156
|
+
}
|
|
1157
|
+
function GoalProgress({ raised, goal, currency, supporters, timeLeft, labels: given, ...props }) {
|
|
1158
|
+
const words = { ...GOAL_LABELS, ...given };
|
|
1159
|
+
const resolved = useNativeSettings(props);
|
|
1160
|
+
const format = roundMoney(currency);
|
|
1161
|
+
const reached = goal > 0 && raised >= goal;
|
|
1162
|
+
const facts = [
|
|
1163
|
+
supporters != null ? fillIn(words.supporters, { count: valueFormatter("integer", resolved.locale)(supporters) }) : null,
|
|
1164
|
+
reached ? words.reached : null,
|
|
1165
|
+
timeLeft ? fillIn(words.left, { time: timeLeft }) : null
|
|
1166
|
+
].filter(Boolean);
|
|
1167
|
+
return /* @__PURE__ */ jsxs4(View2, { style: styles2.root, children: [
|
|
1168
|
+
/* @__PURE__ */ jsx4(Gauge, { ...props, value: raised, max: goal, format, caption: fillIn(words.raised, { goal: valueFormatter(format, resolved.locale)(goal) }), tone: reached ? "success" : "accent" }),
|
|
1169
|
+
facts.length > 0 ? /* @__PURE__ */ jsx4(Text2, { style: [styles2.small, { color: resolved.theme.textSecondary, textAlign: "center" }], children: facts.join(" \xB7 ") }) : null
|
|
1170
|
+
] });
|
|
1171
|
+
}
|
|
1172
|
+
function PriceTicker({ bids, opening, openedAt, currency, reserve, timeFormat = "time", labels: given, title, hideTitle, ...props }) {
|
|
1173
|
+
const words = { ...TICKER_LABELS, ...given };
|
|
1174
|
+
const resolved = useNativeSettings(props);
|
|
1175
|
+
const format = { style: "money", currency };
|
|
1176
|
+
const write = valueFormatter(format, resolved.locale);
|
|
1177
|
+
const model = tickerModel(bids, opening, openedAt);
|
|
1178
|
+
const way = model.count > 0 ? direction(model.ratio) : null;
|
|
1179
|
+
const signed = `${model.change > 0 ? "+" : ""}${write(model.change)}`;
|
|
1180
|
+
const change = model.ratio == null ? signed : `${signed} (${signedPercent(model.ratio, resolved.locale)})`;
|
|
1181
|
+
return /* @__PURE__ */ jsxs4(View2, { style: styles2.root, children: [
|
|
1182
|
+
/* @__PURE__ */ jsx4(
|
|
1183
|
+
Headline,
|
|
1184
|
+
{
|
|
1185
|
+
resolved,
|
|
1186
|
+
title,
|
|
1187
|
+
hideTitle,
|
|
1188
|
+
value: write(model.current),
|
|
1189
|
+
label: model.count > 0 ? words.current : words.opening,
|
|
1190
|
+
delta: model.count > 0 ? fillIn(words.change, { change, count: model.count }) : null,
|
|
1191
|
+
way,
|
|
1192
|
+
tone: good(way, true)
|
|
1193
|
+
}
|
|
1194
|
+
),
|
|
1195
|
+
/* @__PURE__ */ jsx4(
|
|
1196
|
+
LineChart,
|
|
1197
|
+
{
|
|
1198
|
+
...props,
|
|
1199
|
+
title,
|
|
1200
|
+
hideTitle: true,
|
|
1201
|
+
data: model.points,
|
|
1202
|
+
x: "at",
|
|
1203
|
+
y: "amount",
|
|
1204
|
+
yLabel: words.price,
|
|
1205
|
+
xFormat: timeFormat,
|
|
1206
|
+
format,
|
|
1207
|
+
curve: "step",
|
|
1208
|
+
thresholds: reserve != null && model.current < reserve ? [{ value: reserve, label: words.reserve, tone: "warning" }] : void 0
|
|
1209
|
+
}
|
|
1210
|
+
)
|
|
1211
|
+
] });
|
|
1212
|
+
}
|
|
1213
|
+
var styles2 = StyleSheet2.create({
|
|
1214
|
+
root: { gap: 8 },
|
|
1215
|
+
head: { gap: 2 },
|
|
1216
|
+
title: { fontSize: 14, fontWeight: "600", lineHeight: 20 },
|
|
1217
|
+
kpi: { flexDirection: "row", flexWrap: "wrap", alignItems: "baseline", columnGap: 8 },
|
|
1218
|
+
value: { fontSize: 24, lineHeight: 30, fontWeight: "800", fontVariant: ["tabular-nums"] },
|
|
1219
|
+
delta: { flexDirection: "row", alignItems: "center", gap: 4 },
|
|
1220
|
+
small: { fontSize: 12, lineHeight: 16, fontVariant: ["tabular-nums"] },
|
|
1221
|
+
strong: { fontWeight: "600" },
|
|
1222
|
+
meter: { height: 10, borderRadius: 999, overflow: "hidden" },
|
|
1223
|
+
meterFill: { height: "100%", borderRadius: 999 },
|
|
1224
|
+
row: { flexDirection: "row", flexWrap: "wrap", justifyContent: "space-between", columnGap: 12 }
|
|
1225
|
+
});
|
|
1226
|
+
export {
|
|
1227
|
+
AreaChart,
|
|
1228
|
+
BarChart,
|
|
1229
|
+
ChartsProvider,
|
|
1230
|
+
CreditUsage,
|
|
1231
|
+
DEFAULT_LABELS,
|
|
1232
|
+
DEFAULT_STATUSES,
|
|
1233
|
+
DonutChart,
|
|
1234
|
+
EarningsChart,
|
|
1235
|
+
Gauge,
|
|
1236
|
+
GoalProgress,
|
|
1237
|
+
JobThroughput,
|
|
1238
|
+
LatencyChart,
|
|
1239
|
+
LineChart,
|
|
1240
|
+
PieChart,
|
|
1241
|
+
PriceTicker,
|
|
1242
|
+
Sparkline
|
|
1243
|
+
};
|
|
1244
|
+
//# sourceMappingURL=native.js.map
|