@jax-data-science/sci-image-visualizer 0.8.2 → 0.9.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/README.md +201 -460
- package/esm2022/index.mjs +28 -15
- package/esm2022/lib/channel-histogram/channel-histogram.component.mjs +163 -91
- package/esm2022/lib/contracts/capabilities.contract.mjs +4 -3
- package/esm2022/lib/contracts/cell-segmenter.contract.mjs +1 -1
- package/esm2022/lib/contracts/channel-histogram-api.contract.mjs +5 -1
- package/esm2022/lib/contracts/color.mjs +60 -0
- package/esm2022/lib/contracts/colormap-lut.mjs +213 -57
- package/esm2022/lib/contracts/coordinate-transform.contract.mjs +1 -1
- package/esm2022/lib/contracts/display-types.mjs +11 -1
- package/esm2022/lib/contracts/instance-segmenter.contract.mjs +1 -1
- package/esm2022/lib/contracts/intensity.mjs +48 -5
- package/esm2022/lib/contracts/plot-type-contribution.contract.mjs +1 -1
- package/esm2022/lib/contracts/plot-type.mjs +134 -17
- package/esm2022/lib/contracts/ports/image-state.port.mjs +4 -1
- package/esm2022/lib/contracts/ports/preferences.port.mjs +5 -1
- package/esm2022/lib/contracts/ports/region-io.port.mjs +2 -1
- package/esm2022/lib/contracts/ports/spatial-data.port.mjs +5 -1
- package/esm2022/lib/contracts/ports/tile-access.port.mjs +2 -1
- package/esm2022/lib/contracts/region-editor-api.contract.mjs +1 -1
- package/esm2022/lib/contracts/region-overlay.contract.mjs +1 -1
- package/esm2022/lib/contracts/sam.contract.mjs +1 -1
- package/esm2022/lib/contracts/semantic-segmenter.contract.mjs +1 -1
- package/esm2022/lib/contracts/spatial-dataset.contract.mjs +3 -1
- package/esm2022/lib/contracts/toolbar-tool.contract.mjs +6 -4
- package/esm2022/lib/contracts/visualizer.contract.mjs +1 -1
- package/esm2022/lib/contracts/viz-config.mjs +2 -1
- package/esm2022/lib/geometry/contour.mjs +63 -0
- package/esm2022/lib/geometry/raster.mjs +98 -0
- package/esm2022/lib/geometry/ring.mjs +201 -0
- package/esm2022/lib/hex-color-picker/hex-color-picker.component.mjs +202 -102
- package/esm2022/lib/implementations/base-store-visualizer.mjs +201 -48
- package/esm2022/lib/implementations/napari-js/napari-axes-gizmo.mjs +65 -0
- package/esm2022/lib/implementations/napari-js/napari-display-state.mjs +136 -0
- package/esm2022/lib/implementations/napari-js/napari-helpers.mjs +199 -0
- package/esm2022/lib/implementations/napari-js/napari-image-2d-scene.mjs +602 -0
- package/esm2022/lib/implementations/napari-js/napari-loading-badge.mjs +3 -4
- package/esm2022/lib/implementations/napari-js/napari-loading-state.mjs +66 -0
- package/esm2022/lib/implementations/napari-js/napari-region-overlay.mjs +157 -591
- package/esm2022/lib/implementations/napari-js/napari-scene.mjs +2 -0
- package/esm2022/lib/implementations/napari-js/napari-spatial-2d-scene.mjs +614 -0
- package/esm2022/lib/implementations/napari-js/napari-spatial-3d-scene.mjs +769 -0
- package/esm2022/lib/implementations/napari-js/napari-spatial-encoding.mjs +199 -0
- package/esm2022/lib/implementations/napari-js/napari-spatial-hover.mjs +263 -0
- package/esm2022/lib/implementations/napari-js/napari-spatial-scene.mjs +159 -0
- package/esm2022/lib/implementations/napari-js/napari-spatial-tiles.mjs +106 -1408
- package/esm2022/lib/implementations/napari-js/napari-spatial-tooltip.mjs +2 -2
- package/esm2022/lib/implementations/napari-js/napari-surface-scene.mjs +271 -0
- package/esm2022/lib/implementations/napari-js/napari-tile-client.mjs +562 -0
- package/esm2022/lib/implementations/napari-js/napari-tool-bridge.mjs +344 -0
- package/esm2022/lib/implementations/napari-js/napari-visualizer.service.mjs +361 -4184
- package/esm2022/lib/implementations/napari-js/napari-volume-scene.mjs +439 -0
- package/esm2022/lib/implementations/napari-js/napari-volume-z-handle.mjs +6 -6
- package/esm2022/lib/implementations/napari-js/region-overlay/overlay-projection.mjs +96 -0
- package/esm2022/lib/implementations/napari-js/region-overlay/region-edit.mjs +35 -0
- package/esm2022/lib/implementations/napari-js/region-overlay/region-svg-renderer.mjs +182 -0
- package/esm2022/lib/implementations/napari-js/spatial-tiles/categorical-lookup.mjs +30 -0
- package/esm2022/lib/implementations/napari-js/spatial-tiles/cell-layers.mjs +274 -0
- package/esm2022/lib/implementations/napari-js/spatial-tiles/density-layer.mjs +144 -0
- package/esm2022/lib/implementations/napari-js/spatial-tiles/layer-groups.mjs +165 -0
- package/esm2022/lib/implementations/napari-js/spatial-tiles/plan-context.mjs +78 -0
- package/esm2022/lib/implementations/napari-js/spatial-tiles/transcript-hover.mjs +182 -0
- package/esm2022/lib/implementations/napari-js/spatial-tiles/transcript-jobs.mjs +369 -0
- package/esm2022/lib/implementations/napari-js/spatial-tiles/transcript-layers.mjs +306 -0
- package/esm2022/lib/implementations/osd/display-pipeline.mjs +102 -40
- package/esm2022/lib/implementations/osd/histogram-sampler.mjs +56 -31
- package/esm2022/lib/implementations/osd/openseadragon-viewer-options.mjs +128 -0
- package/esm2022/lib/implementations/osd/openseadragon-visualizer.service.mjs +333 -1685
- package/esm2022/lib/implementations/osd/osd-coordinate-transform.mjs +1 -1
- package/esm2022/lib/implementations/osd/osd-coords.mjs +5 -6
- package/esm2022/lib/implementations/osd/osd-export.mjs +122 -0
- package/esm2022/lib/implementations/osd/osd-lib.mjs +15 -1
- package/esm2022/lib/implementations/osd/osd-navigator-chrome.mjs +205 -0
- package/esm2022/lib/implementations/osd/osd-pixel-readback.mjs +68 -0
- package/esm2022/lib/implementations/osd/osd-region-overlay-draw.mjs +153 -0
- package/esm2022/lib/implementations/osd/osd-region-overlay.mjs +185 -718
- package/esm2022/lib/implementations/osd/osd-scale-bar.mjs +52 -60
- package/esm2022/lib/implementations/osd/osd-tile-source.mjs +105 -0
- package/esm2022/lib/implementations/osd/osd-viewer-like.mjs +2 -0
- package/esm2022/lib/implementations/osd/osd-viewer-mount.mjs +44 -0
- package/esm2022/lib/implementations/osd/osd-viewport.mjs +184 -0
- package/esm2022/lib/implementations/osd/osd-zoom.mjs +7 -1
- package/esm2022/lib/implementations/osd/simple-source.mjs +395 -0
- package/esm2022/lib/implementations/osd/slice-cache.mjs +53 -48
- package/esm2022/lib/implementations/osd/tile-client.mjs +32 -11
- package/esm2022/lib/implementations/osd/tile-recolor.mjs +330 -0
- package/esm2022/lib/implementations/plotly/omics-trace-builders.mjs +161 -73
- package/esm2022/lib/implementations/plotly/plotly-coordinate-transform.mjs +1 -1
- package/esm2022/lib/implementations/plotly/plotly-image-loader.mjs +112 -0
- package/esm2022/lib/implementations/plotly/plotly-image-recolor.mjs +178 -0
- package/esm2022/lib/implementations/plotly/plotly-intensity-inset.mjs +33 -0
- package/esm2022/lib/implementations/plotly/plotly-isosurface-controls.mjs +83 -0
- package/esm2022/lib/implementations/plotly/plotly-layouts.mjs +121 -0
- package/esm2022/lib/implementations/plotly/plotly-readback.mjs +117 -0
- package/esm2022/lib/implementations/plotly/plotly-region-overlay.mjs +19 -10
- package/esm2022/lib/implementations/plotly/plotly-shape-projection.mjs +223 -0
- package/esm2022/lib/implementations/plotly/plotly-trace-builders.mjs +79 -19
- package/esm2022/lib/implementations/plotly/plotly-zoom-controller.mjs +223 -0
- package/esm2022/lib/implementations/plotly/plotly.service.mjs +439 -1655
- package/esm2022/lib/implementations/region-centroids.mjs +47 -0
- package/esm2022/lib/implementations/simple-slice-access.service.mjs +22 -12
- package/esm2022/lib/implementations/spatial-data-http/spatial-data-http.service.mjs +172 -92
- package/esm2022/lib/implementations/spatial-data-http/spatial-wire.mjs +103 -22
- package/esm2022/lib/implementations/tile-server/index.mjs +6 -0
- package/esm2022/lib/implementations/tile-server/native-histogram.mjs +30 -0
- package/esm2022/lib/implementations/tile-server/poll-descriptor.mjs +65 -0
- package/esm2022/lib/implementations/tile-server/tile-protocol.mjs +42 -0
- package/esm2022/lib/implementations/tile-server/transport.mjs +135 -0
- package/esm2022/lib/intensity/intensity-profile.mjs +107 -0
- package/esm2022/lib/intensity/intensity-profile.service.mjs +223 -0
- package/esm2022/lib/intensity-inset/intensity-inset.component.mjs +133 -0
- package/esm2022/lib/models/bezier.mjs +1 -11
- package/esm2022/lib/models/class-preset.mjs +41 -3
- package/esm2022/lib/models/geometry.mjs +27 -164
- package/esm2022/lib/models/polygon-edit.mjs +254 -0
- package/esm2022/lib/models/polygon-factory.mjs +118 -0
- package/esm2022/lib/models/region-clone.mjs +68 -0
- package/esm2022/lib/models/region-geojson.mjs +373 -0
- package/esm2022/lib/models/region.mjs +34 -33
- package/esm2022/lib/models/shape.mjs +18 -16
- package/esm2022/lib/plot-mode/contribution-host.mjs +297 -0
- package/esm2022/lib/plot-mode/plot-mode-controller.mjs +9 -6
- package/esm2022/lib/plot-mode/plot-type-menu.mjs +85 -0
- package/esm2022/lib/plot-mode/tool-params-model.mjs +87 -0
- package/esm2022/lib/plot.utilities.mjs +296 -473
- package/esm2022/lib/processing/image-crop.mjs +1 -1
- package/esm2022/lib/processing/processing-image.mjs +28 -15
- package/esm2022/lib/provide-visualization.mjs +40 -14
- package/esm2022/lib/region-editor/classes-panel/classes-panel.component.mjs +99 -0
- package/esm2022/lib/region-editor/file-stem.mjs +13 -0
- package/esm2022/lib/region-editor/manage-classes-dialog/manage-classes-dialog.component.mjs +118 -0
- package/esm2022/lib/region-editor/mask-export.service.mjs +98 -0
- package/esm2022/lib/region-editor/mask-raster.mjs +11 -5
- package/esm2022/lib/region-editor/region-color-dialog/region-color-dialog.component.mjs +56 -0
- package/esm2022/lib/region-editor/region-editor-help/region-editor-help.component.mjs +28 -0
- package/esm2022/lib/region-editor/region-editor.component.mjs +402 -651
- package/esm2022/lib/region-editor/region-metrics.mjs +68 -0
- package/esm2022/lib/region-editor/region-persistence.service.mjs +134 -0
- package/esm2022/lib/region-editor/region-table/region-table.component.mjs +153 -0
- package/esm2022/lib/region-editor/save-mask-dialog/save-mask-dialog.component.mjs +91 -0
- package/esm2022/lib/region-editor/save-regions-dialog/save-regions-dialog.component.mjs +92 -0
- package/esm2022/lib/region-ops.service.mjs +28 -70
- package/esm2022/lib/region-overlay/region-geometry.mjs +360 -0
- package/esm2022/lib/region-overlay/region-hit-test.mjs +103 -0
- package/esm2022/lib/region-overlay/svg-region-renderer.mjs +228 -0
- package/esm2022/lib/render-orchestrator.mjs +14 -11
- package/esm2022/lib/render-session.mjs +207 -0
- package/esm2022/lib/routing-visualizer.service.mjs +459 -411
- package/esm2022/lib/spatial/density-raster.mjs +14 -0
- package/esm2022/lib/spatial/embedding-compute-coordinator.mjs +239 -0
- package/esm2022/lib/spatial/embedding-compute.mjs +43 -10
- package/esm2022/lib/spatial/gene-search.mjs +1 -1
- package/esm2022/lib/spatial/glyphs.mjs +97 -0
- package/esm2022/lib/spatial/lod.mjs +187 -0
- package/esm2022/lib/spatial/spatial-controls.facade.mjs +200 -0
- package/esm2022/lib/spatial/spatial-density.mjs +25 -16
- package/esm2022/lib/spatial/spatial-encoding.mjs +26 -82
- package/esm2022/lib/spatial/spatial-expression.mjs +43 -42
- package/esm2022/lib/spatial/spatial-framing.mjs +1 -1
- package/esm2022/lib/spatial/spatial-heatmap.mjs +6 -3
- package/esm2022/lib/spatial/spatial-hover.mjs +5 -33
- package/esm2022/lib/spatial/spatial-panel-model.mjs +282 -0
- package/esm2022/lib/spatial/spatial-sections.mjs +1 -1
- package/esm2022/lib/spatial/spatial-selection.mjs +33 -46
- package/esm2022/lib/spatial/spatial-tile-merge.mjs +219 -0
- package/esm2022/lib/spatial/spatial-tiles.mjs +12 -648
- package/esm2022/lib/spatial/spatial-volume-image.mjs +2 -4
- package/esm2022/lib/spatial/stats.mjs +71 -0
- package/esm2022/lib/spatial/transcript-grouping.mjs +307 -0
- package/esm2022/lib/spatial-controls/spatial-cells-panel/spatial-cells-panel.component.mjs +150 -0
- package/esm2022/lib/spatial-controls/spatial-charts/chart-data-model.mjs +309 -0
- package/esm2022/lib/spatial-controls/spatial-charts/chart-help.mjs +145 -0
- package/esm2022/lib/spatial-controls/spatial-charts/plotly-chart-host.mjs +158 -0
- package/esm2022/lib/spatial-controls/spatial-charts/spatial-chart-window/spatial-chart-window.component.mjs +47 -0
- package/esm2022/lib/spatial-controls/spatial-charts/spatial-charts.component.mjs +297 -802
- package/esm2022/lib/spatial-controls/spatial-charts/spatial-embedding-controls/spatial-embedding-controls.component.mjs +89 -0
- package/esm2022/lib/spatial-controls/spatial-charts/spatial-heatmap-controls/spatial-heatmap-controls.component.mjs +52 -0
- package/esm2022/lib/spatial-controls/spatial-controls.component.mjs +143 -1238
- package/esm2022/lib/spatial-controls/spatial-gene-picker.mjs +153 -0
- package/esm2022/lib/spatial-controls/spatial-gene-tree/spatial-gene-tree.component.mjs +241 -0
- package/esm2022/lib/spatial-controls/spatial-groups-panel/spatial-groups-panel.component.mjs +193 -0
- package/esm2022/lib/spatial-controls/spatial-key/spatial-key.component.mjs +132 -0
- package/esm2022/lib/spatial-controls/spatial-key/spatial-key.model.mjs +67 -0
- package/esm2022/lib/spatial-controls/spatial-marker-genes-form/spatial-marker-genes-form.component.mjs +147 -0
- package/esm2022/lib/spatial-controls/spatial-observations-panel/spatial-observations-panel.component.mjs +300 -0
- package/esm2022/lib/spatial-controls/spatial-transcripts-panel/spatial-transcripts-panel.component.mjs +370 -0
- package/esm2022/lib/store/class-color.util.mjs +46 -3
- package/esm2022/lib/store/region-history.mjs +146 -0
- package/esm2022/lib/store/region-scope-cache.mjs +140 -0
- package/esm2022/lib/store/region-selection.mjs +82 -0
- package/esm2022/lib/store/region-store.service.mjs +279 -675
- package/esm2022/lib/store/spatial-selection.service.mjs +2 -2
- package/esm2022/lib/store/visualizer-store.service.mjs +49 -71
- package/esm2022/lib/toast-outlets.mjs +5 -4
- package/esm2022/lib/toolbar/brush/brush-tool.service.mjs +92 -434
- package/esm2022/lib/toolbar/canvas-tools.mjs +20 -0
- package/esm2022/lib/toolbar/crop/slide-crop.mjs +26 -42
- package/esm2022/lib/toolbar/plot-type-selector/plot-type-selector.component.mjs +85 -0
- package/esm2022/lib/toolbar/region-tools/region-tool-buttons.mjs +74 -0
- package/esm2022/lib/toolbar/region-tools/region-tools.component.mjs +114 -0
- package/esm2022/lib/toolbar/segmentation/cell-segment-tool.service.mjs +74 -78
- package/esm2022/lib/toolbar/segmentation/cellpose-segmenter.service.mjs +50 -8
- package/esm2022/lib/toolbar/segmentation/onnx-sam-session.mjs +61 -42
- package/esm2022/lib/toolbar/segmentation/pending-calls.mjs +47 -0
- package/esm2022/lib/toolbar/segmentation/sam-model-registry.mjs +12 -4
- package/esm2022/lib/toolbar/segmentation/sam-onnx-core.mjs +70 -14
- package/esm2022/lib/toolbar/segmentation/sam-point-tool.service.mjs +135 -172
- package/esm2022/lib/toolbar/segmentation/sam-prompt.mjs +9 -90
- package/esm2022/lib/toolbar/segmentation/sam-session.service.mjs +183 -0
- package/esm2022/lib/toolbar/segmentation/sam-tool.service.mjs +95 -150
- package/esm2022/lib/toolbar/segmentation/segmentation-commit.mjs +12 -0
- package/esm2022/lib/toolbar/segmentation/segmentation-runner.mjs +108 -0
- package/esm2022/lib/toolbar/segmentation-tools/segmentation-tools.component.mjs +155 -0
- package/esm2022/lib/toolbar/stack-controls/stack-controls.component.mjs +81 -0
- package/esm2022/lib/toolbar/tool-kit/async-tool-status.mjs +37 -0
- package/esm2022/lib/toolbar/tool-kit/canvas-tool-manager.mjs +63 -0
- package/esm2022/lib/toolbar/tool-kit/canvas-tool.mjs +2 -0
- package/esm2022/lib/toolbar/tool-kit/frame-pixels.mjs +108 -0
- package/esm2022/lib/toolbar/tool-kit/mask-stroke-editor.mjs +306 -0
- package/esm2022/lib/toolbar/tool-kit/matrix-frame.mjs +61 -0
- package/esm2022/lib/toolbar/tool-kit/tool-overlay.mjs +140 -0
- package/esm2022/lib/toolbar/tool-kit/undo-gesture.mjs +24 -0
- package/esm2022/lib/toolbar/tool-slider/tool-slider.component.mjs +63 -0
- package/esm2022/lib/toolbar/toolbar-help-dialog/toolbar-help-dialog.component.mjs +50 -0
- package/esm2022/lib/toolbar/toolbar.component.mjs +68 -117
- package/esm2022/lib/toolbar/vertex-eraser/vertex-eraser-tool.service.mjs +93 -115
- package/esm2022/lib/toolbar/view-controls/view-controls.component.mjs +107 -0
- package/esm2022/lib/toolbar/wand/wand-region-grow.mjs +321 -0
- package/esm2022/lib/toolbar/wand/wand-tool.service.mjs +121 -416
- package/esm2022/lib/toolbar/wand/wand.service.mjs +30 -894
- package/esm2022/lib/toolbar/zoom-to-box/zoom-to-box-tool.service.mjs +48 -90
- package/esm2022/lib/util/mark-for-check.mjs +17 -0
- package/esm2022/lib/util/supersede.mjs +56 -0
- package/esm2022/lib/visualization.module.mjs +39 -141
- package/esm2022/lib/visualizer/floating-drag.directive.mjs +58 -0
- package/esm2022/lib/visualizer/region-actions.mjs +149 -0
- package/esm2022/lib/visualizer/region-load.mjs +60 -0
- package/esm2022/lib/visualizer/spatial-dataset-binder.mjs +163 -0
- package/esm2022/lib/visualizer/tool-modes.mjs +113 -0
- package/esm2022/lib/visualizer/viewer-shortcuts.mjs +167 -0
- package/esm2022/lib/visualizer/visualizer-context-menu.mjs +119 -0
- package/esm2022/lib/visualizer.component.mjs +480 -1902
- package/esm2022/lib/workers/spatial-math-ops.mjs +43 -0
- package/esm2022/lib/workers/spatial-math-worker.mjs +10 -0
- package/esm2022/lib/workers/spatial-math.mjs +190 -0
- package/fesm2022/jax-data-science-sci-image-visualizer-jax-data-science-sci-image-visualizer-Csxlnq7I.mjs +41083 -0
- package/fesm2022/jax-data-science-sci-image-visualizer-jax-data-science-sci-image-visualizer-Csxlnq7I.mjs.map +1 -0
- package/fesm2022/jax-data-science-sci-image-visualizer-onnx-sam-session-Bkujqg7m.mjs +238 -0
- package/fesm2022/jax-data-science-sci-image-visualizer-onnx-sam-session-Bkujqg7m.mjs.map +1 -0
- package/fesm2022/jax-data-science-sci-image-visualizer-spatial-math-worker-BzVFFqGS.mjs +12 -0
- package/fesm2022/jax-data-science-sci-image-visualizer-spatial-math-worker-BzVFFqGS.mjs.map +1 -0
- package/fesm2022/jax-data-science-sci-image-visualizer.mjs +41 -34430
- package/fesm2022/jax-data-science-sci-image-visualizer.mjs.map +1 -1
- package/fesm2022/mask.worker.js +36 -917
- package/fesm2022/onnx-sam.worker.js +52 -16
- package/fesm2022/spatial-math.worker.js +471 -0
- package/fesm2022/tsne.worker.js +32 -15
- package/index.d.ts +13 -10
- package/lib/channel-histogram/channel-histogram.component.d.ts +53 -43
- package/lib/contracts/capabilities.contract.d.ts +4 -2
- package/lib/contracts/cell-segmenter.contract.d.ts +1 -0
- package/lib/contracts/channel-histogram-api.contract.d.ts +4 -0
- package/lib/contracts/color.d.ts +27 -0
- package/lib/contracts/colormap-lut.d.ts +19 -4
- package/lib/contracts/coordinate-transform.contract.d.ts +3 -3
- package/lib/contracts/display-types.d.ts +21 -0
- package/lib/contracts/instance-segmenter.contract.d.ts +5 -0
- package/lib/contracts/intensity.d.ts +13 -2
- package/lib/contracts/plot-type.d.ts +3 -1
- package/lib/contracts/ports/image-state.port.d.ts +6 -2
- package/lib/contracts/ports/preferences.port.d.ts +4 -0
- package/lib/contracts/ports/region-io.port.d.ts +1 -0
- package/lib/contracts/ports/spatial-data.port.d.ts +4 -10
- package/lib/contracts/ports/tile-access.port.d.ts +1 -0
- package/lib/contracts/region-editor-api.contract.d.ts +1 -1
- package/lib/contracts/region-overlay.contract.d.ts +5 -0
- package/lib/contracts/sam.contract.d.ts +7 -0
- package/lib/contracts/semantic-segmenter.contract.d.ts +6 -0
- package/lib/contracts/spatial-dataset.contract.d.ts +19 -6
- package/lib/contracts/toolbar-tool.contract.d.ts +1 -0
- package/lib/contracts/visualizer.contract.d.ts +221 -54
- package/lib/contracts/viz-config.d.ts +1 -0
- package/lib/geometry/contour.d.ts +24 -0
- package/lib/geometry/raster.d.ts +42 -0
- package/lib/geometry/ring.d.ts +67 -0
- package/lib/hex-color-picker/hex-color-picker.component.d.ts +61 -27
- package/lib/implementations/base-store-visualizer.d.ts +61 -15
- package/lib/implementations/napari-js/napari-axes-gizmo.d.ts +36 -0
- package/lib/implementations/napari-js/napari-display-state.d.ts +76 -0
- package/lib/implementations/napari-js/napari-helpers.d.ts +129 -0
- package/lib/implementations/napari-js/napari-image-2d-scene.d.ts +162 -0
- package/lib/implementations/napari-js/napari-loading-badge.d.ts +0 -1
- package/lib/implementations/napari-js/napari-loading-state.d.ts +30 -0
- package/lib/implementations/napari-js/napari-region-overlay.d.ts +62 -70
- package/lib/implementations/napari-js/napari-scene.d.ts +93 -0
- package/lib/implementations/napari-js/napari-spatial-2d-scene.d.ts +163 -0
- package/lib/implementations/napari-js/napari-spatial-3d-scene.d.ts +212 -0
- package/lib/implementations/napari-js/napari-spatial-encoding.d.ts +114 -0
- package/lib/implementations/napari-js/napari-spatial-hover.d.ts +89 -0
- package/lib/implementations/napari-js/napari-spatial-scene.d.ts +118 -0
- package/lib/implementations/napari-js/napari-spatial-tiles.d.ts +56 -263
- package/lib/implementations/napari-js/napari-spatial-tooltip.d.ts +1 -1
- package/lib/implementations/napari-js/napari-surface-scene.d.ts +76 -0
- package/lib/implementations/napari-js/napari-tile-client.d.ts +214 -0
- package/lib/implementations/napari-js/napari-tool-bridge.d.ts +179 -0
- package/lib/implementations/napari-js/napari-visualizer.service.d.ts +121 -878
- package/lib/implementations/napari-js/napari-volume-scene.d.ts +104 -0
- package/lib/implementations/napari-js/napari-volume-z-handle.d.ts +8 -12
- package/lib/implementations/napari-js/region-overlay/overlay-projection.d.ts +59 -0
- package/lib/implementations/napari-js/region-overlay/region-edit.d.ts +15 -0
- package/lib/implementations/napari-js/region-overlay/region-svg-renderer.d.ts +54 -0
- package/lib/implementations/napari-js/spatial-tiles/categorical-lookup.d.ts +26 -0
- package/lib/implementations/napari-js/spatial-tiles/cell-layers.d.ts +70 -0
- package/lib/implementations/napari-js/spatial-tiles/density-layer.d.ts +61 -0
- package/lib/implementations/napari-js/spatial-tiles/layer-groups.d.ts +67 -0
- package/lib/implementations/napari-js/spatial-tiles/plan-context.d.ts +38 -0
- package/lib/implementations/napari-js/spatial-tiles/transcript-hover.d.ts +71 -0
- package/lib/implementations/napari-js/spatial-tiles/transcript-jobs.d.ts +105 -0
- package/lib/implementations/napari-js/spatial-tiles/transcript-layers.d.ts +56 -0
- package/lib/implementations/osd/display-pipeline.d.ts +38 -9
- package/lib/implementations/osd/histogram-sampler.d.ts +22 -12
- package/lib/implementations/osd/openseadragon-viewer-options.d.ts +35 -0
- package/lib/implementations/osd/openseadragon-visualizer.service.d.ts +78 -354
- package/lib/implementations/osd/osd-coordinate-transform.d.ts +2 -1
- package/lib/implementations/osd/osd-coords.d.ts +6 -4
- package/lib/implementations/osd/osd-export.d.ts +36 -0
- package/lib/implementations/osd/osd-lib.d.ts +7 -0
- package/lib/implementations/osd/osd-navigator-chrome.d.ts +69 -0
- package/lib/implementations/osd/osd-pixel-readback.d.ts +22 -0
- package/lib/implementations/osd/osd-region-overlay-draw.d.ts +37 -0
- package/lib/implementations/osd/osd-region-overlay.d.ts +36 -48
- package/lib/implementations/osd/osd-scale-bar.d.ts +8 -6
- package/lib/implementations/osd/osd-tile-source.d.ts +49 -0
- package/lib/implementations/osd/osd-viewer-like.d.ts +100 -0
- package/lib/implementations/osd/osd-viewer-mount.d.ts +14 -0
- package/lib/implementations/osd/osd-viewport.d.ts +77 -0
- package/lib/implementations/osd/osd-zoom.d.ts +6 -0
- package/lib/implementations/osd/simple-source.d.ts +161 -0
- package/lib/implementations/osd/slice-cache.d.ts +12 -3
- package/lib/implementations/osd/tile-client.d.ts +11 -14
- package/lib/implementations/osd/tile-recolor.d.ts +141 -0
- package/lib/implementations/plotly/omics-trace-builders.d.ts +32 -20
- package/lib/implementations/plotly/plotly-image-loader.d.ts +49 -0
- package/lib/implementations/plotly/plotly-image-recolor.d.ts +75 -0
- package/lib/implementations/plotly/plotly-intensity-inset.d.ts +8 -0
- package/lib/implementations/plotly/plotly-isosurface-controls.d.ts +38 -0
- package/lib/implementations/plotly/plotly-layouts.d.ts +188 -0
- package/lib/implementations/plotly/plotly-readback.d.ts +41 -0
- package/lib/implementations/plotly/plotly-region-overlay.d.ts +2 -2
- package/lib/implementations/plotly/plotly-shape-projection.d.ts +92 -0
- package/lib/implementations/plotly/plotly-trace-builders.d.ts +23 -12
- package/lib/implementations/plotly/plotly-zoom-controller.d.ts +86 -0
- package/lib/implementations/plotly/plotly.service.d.ts +136 -401
- package/lib/implementations/region-centroids.d.ts +14 -0
- package/lib/implementations/simple-slice-access.service.d.ts +7 -4
- package/lib/implementations/spatial-data-http/spatial-data-http.service.d.ts +42 -18
- package/lib/implementations/spatial-data-http/spatial-wire.d.ts +34 -9
- package/lib/implementations/tile-server/index.d.ts +5 -0
- package/lib/implementations/tile-server/native-histogram.d.ts +25 -0
- package/lib/implementations/tile-server/poll-descriptor.d.ts +39 -0
- package/lib/implementations/tile-server/tile-protocol.d.ts +80 -0
- package/lib/implementations/tile-server/transport.d.ts +62 -0
- package/lib/intensity/intensity-profile.d.ts +66 -0
- package/lib/intensity/intensity-profile.service.d.ts +108 -0
- package/lib/intensity-inset/intensity-inset.component.d.ts +58 -0
- package/lib/models/bezier.d.ts +0 -5
- package/lib/models/class-preset.d.ts +18 -0
- package/lib/models/geometry.d.ts +14 -48
- package/lib/models/polygon-edit.d.ts +72 -0
- package/lib/models/polygon-factory.d.ts +40 -0
- package/lib/models/region-clone.d.ts +20 -0
- package/lib/models/region-geojson.d.ts +17 -0
- package/lib/models/region.d.ts +40 -4
- package/lib/models/shape.d.ts +8 -0
- package/lib/plot-mode/contribution-host.d.ts +125 -0
- package/lib/plot-mode/plot-type-menu.d.ts +60 -0
- package/lib/plot-mode/tool-params-model.d.ts +49 -0
- package/lib/plot.utilities.d.ts +19 -30
- package/lib/processing/processing-image.d.ts +5 -2
- package/lib/provide-visualization.d.ts +19 -2
- package/lib/region-editor/classes-panel/classes-panel.component.d.ts +56 -0
- package/lib/region-editor/file-stem.d.ts +7 -0
- package/lib/region-editor/manage-classes-dialog/manage-classes-dialog.component.d.ts +45 -0
- package/lib/region-editor/mask-export.service.d.ts +54 -0
- package/lib/region-editor/mask-raster.d.ts +2 -8
- package/lib/region-editor/region-color-dialog/region-color-dialog.component.d.ts +29 -0
- package/lib/region-editor/region-editor-help/region-editor-help.component.d.ts +11 -0
- package/lib/region-editor/region-editor.component.d.ts +166 -199
- package/lib/region-editor/region-metrics.d.ts +26 -0
- package/lib/region-editor/region-persistence.service.d.ts +69 -0
- package/lib/region-editor/region-table/region-table.component.d.ts +83 -0
- package/lib/region-editor/save-mask-dialog/save-mask-dialog.component.d.ts +36 -0
- package/lib/region-editor/save-regions-dialog/save-regions-dialog.component.d.ts +37 -0
- package/lib/region-ops.service.d.ts +1 -7
- package/lib/region-overlay/region-geometry.d.ts +157 -0
- package/lib/region-overlay/region-hit-test.d.ts +38 -0
- package/lib/region-overlay/svg-region-renderer.d.ts +110 -0
- package/lib/render-orchestrator.d.ts +6 -2
- package/lib/render-session.d.ts +75 -0
- package/lib/routing-visualizer.service.d.ts +110 -58
- package/lib/spatial/density-raster.d.ts +6 -0
- package/lib/spatial/embedding-compute-coordinator.d.ts +123 -0
- package/lib/spatial/embedding-compute.d.ts +21 -2
- package/lib/spatial/glyphs.d.ts +16 -0
- package/lib/spatial/lod.d.ts +94 -0
- package/lib/spatial/spatial-controls.facade.d.ts +64 -0
- package/lib/spatial/spatial-density.d.ts +15 -5
- package/lib/spatial/spatial-encoding.d.ts +11 -44
- package/lib/spatial/spatial-expression.d.ts +40 -22
- package/lib/spatial/spatial-framing.d.ts +1 -0
- package/lib/spatial/spatial-heatmap.d.ts +2 -0
- package/lib/spatial/spatial-hover.d.ts +4 -16
- package/lib/spatial/spatial-panel-model.d.ts +135 -0
- package/lib/spatial/spatial-selection.d.ts +21 -26
- package/lib/spatial/spatial-tile-merge.d.ts +41 -0
- package/lib/spatial/spatial-tiles.d.ts +9 -256
- package/lib/spatial/stats.d.ts +38 -0
- package/lib/spatial/transcript-grouping.d.ts +119 -0
- package/lib/spatial-controls/spatial-cells-panel/spatial-cells-panel.component.d.ts +64 -0
- package/lib/spatial-controls/spatial-charts/chart-data-model.d.ts +153 -0
- package/lib/spatial-controls/spatial-charts/chart-help.d.ts +69 -0
- package/lib/spatial-controls/spatial-charts/plotly-chart-host.d.ts +98 -0
- package/lib/spatial-controls/spatial-charts/spatial-chart-window/spatial-chart-window.component.d.ts +26 -0
- package/lib/spatial-controls/spatial-charts/spatial-charts.component.d.ts +101 -260
- package/lib/spatial-controls/spatial-charts/spatial-embedding-controls/spatial-embedding-controls.component.d.ts +43 -0
- package/lib/spatial-controls/spatial-charts/spatial-heatmap-controls/spatial-heatmap-controls.component.d.ts +27 -0
- package/lib/spatial-controls/spatial-controls.component.d.ts +68 -448
- package/lib/spatial-controls/spatial-gene-picker.d.ts +86 -0
- package/lib/spatial-controls/spatial-gene-tree/spatial-gene-tree.component.d.ts +102 -0
- package/lib/spatial-controls/spatial-groups-panel/spatial-groups-panel.component.d.ts +72 -0
- package/lib/spatial-controls/spatial-key/spatial-key.component.d.ts +66 -0
- package/lib/spatial-controls/spatial-key/spatial-key.model.d.ts +33 -0
- package/lib/spatial-controls/spatial-marker-genes-form/spatial-marker-genes-form.component.d.ts +64 -0
- package/lib/spatial-controls/spatial-observations-panel/spatial-observations-panel.component.d.ts +117 -0
- package/lib/spatial-controls/spatial-transcripts-panel/spatial-transcripts-panel.component.d.ts +142 -0
- package/lib/store/class-color.util.d.ts +35 -1
- package/lib/store/region-history.d.ts +66 -0
- package/lib/store/region-scope-cache.d.ts +63 -0
- package/lib/store/region-selection.d.ts +36 -0
- package/lib/store/region-store.service.d.ts +104 -112
- package/lib/store/visualizer-store.service.d.ts +22 -33
- package/lib/toast-outlets.d.ts +4 -3
- package/lib/toolbar/brush/brush-tool.service.d.ts +31 -98
- package/lib/toolbar/canvas-tools.d.ts +20 -0
- package/lib/toolbar/crop/slide-crop.d.ts +10 -4
- package/lib/toolbar/plot-type-selector/plot-type-selector.component.d.ts +38 -0
- package/lib/toolbar/region-tools/region-tool-buttons.d.ts +21 -0
- package/lib/toolbar/region-tools/region-tools.component.d.ts +60 -0
- package/lib/toolbar/segmentation/cell-segment-tool.service.d.ts +10 -14
- package/lib/toolbar/segmentation/cellpose-segmenter.service.d.ts +12 -2
- package/lib/toolbar/segmentation/onnx-sam-session.d.ts +22 -3
- package/lib/toolbar/segmentation/pending-calls.d.ts +31 -0
- package/lib/toolbar/segmentation/sam-model-registry.d.ts +9 -3
- package/lib/toolbar/segmentation/sam-onnx-core.d.ts +18 -5
- package/lib/toolbar/segmentation/sam-point-tool.service.d.ts +46 -32
- package/lib/toolbar/segmentation/sam-prompt.d.ts +7 -31
- package/lib/toolbar/segmentation/sam-session.service.d.ts +74 -0
- package/lib/toolbar/segmentation/sam-tool.service.d.ts +23 -30
- package/lib/toolbar/segmentation/segmentation-commit.d.ts +8 -0
- package/lib/toolbar/segmentation/segmentation-runner.d.ts +52 -0
- package/lib/toolbar/segmentation-tools/segmentation-tools.component.d.ts +87 -0
- package/lib/toolbar/stack-controls/stack-controls.component.d.ts +40 -0
- package/lib/toolbar/tool-kit/async-tool-status.d.ts +21 -0
- package/lib/toolbar/tool-kit/canvas-tool-manager.d.ts +36 -0
- package/lib/toolbar/tool-kit/canvas-tool.d.ts +86 -0
- package/lib/toolbar/tool-kit/frame-pixels.d.ts +45 -0
- package/lib/toolbar/tool-kit/mask-stroke-editor.d.ts +125 -0
- package/lib/toolbar/tool-kit/matrix-frame.d.ts +40 -0
- package/lib/toolbar/tool-kit/tool-overlay.d.ts +60 -0
- package/lib/toolbar/tool-kit/undo-gesture.d.ts +17 -0
- package/lib/toolbar/tool-slider/tool-slider.component.d.ts +33 -0
- package/lib/toolbar/toolbar-help-dialog/toolbar-help-dialog.component.d.ts +24 -0
- package/lib/toolbar/toolbar.component.d.ts +47 -83
- package/lib/toolbar/vertex-eraser/vertex-eraser-tool.service.d.ts +33 -40
- package/lib/toolbar/view-controls/view-controls.component.d.ts +54 -0
- package/lib/toolbar/wand/wand-region-grow.d.ts +49 -0
- package/lib/toolbar/wand/wand-tool.service.d.ts +39 -124
- package/lib/toolbar/wand/wand.service.d.ts +22 -116
- package/lib/toolbar/zoom-to-box/zoom-to-box-tool.service.d.ts +17 -37
- package/lib/util/mark-for-check.d.ts +11 -0
- package/lib/util/supersede.d.ts +53 -0
- package/lib/visualization.module.d.ts +18 -39
- package/lib/visualizer/floating-drag.directive.d.ts +30 -0
- package/lib/visualizer/region-actions.d.ts +54 -0
- package/lib/visualizer/region-load.d.ts +27 -0
- package/lib/visualizer/spatial-dataset-binder.d.ts +74 -0
- package/lib/visualizer/tool-modes.d.ts +49 -0
- package/lib/visualizer/viewer-shortcuts.d.ts +71 -0
- package/lib/visualizer/visualizer-context-menu.d.ts +55 -0
- package/lib/visualizer.component.d.ts +201 -447
- package/lib/workers/spatial-math-ops.d.ts +65 -0
- package/lib/workers/spatial-math-worker.d.ts +7 -0
- package/lib/workers/spatial-math.d.ts +74 -0
- package/package.json +12 -3
- package/src/lib/styles/_viz-icons-rules.scss +73 -0
- package/src/lib/styles/viz-icons.scss +14 -0
- package/esm2022/lib/implementations/napari-js/napari-axes-labels.mjs +0 -97
- package/esm2022/lib/implementations/napari-js/napari-navigator.mjs +0 -195
- package/esm2022/lib/implementations/napari-js/napari-scale-bar.mjs +0 -92
- package/fesm2022/jax-data-science-sci-image-visualizer-onnx-sam-session-BwP-A11m.mjs +0 -329
- package/fesm2022/jax-data-science-sci-image-visualizer-onnx-sam-session-BwP-A11m.mjs.map +0 -1
- package/lib/implementations/napari-js/napari-axes-labels.d.ts +0 -49
- package/lib/implementations/napari-js/napari-navigator.d.ts +0 -72
- package/lib/implementations/napari-js/napari-scale-bar.d.ts +0 -35
- package/src/lib/assets/cell-detection.svg +0 -37
- package/src/lib/assets/click.svg +0 -1
- package/src/lib/assets/colormap-luts.json +0 -1
- package/src/lib/assets/edit-selection-white.svg +0 -47
- package/src/lib/assets/icons/colormap-earth.png +0 -0
- package/src/lib/assets/icons/colormap-placeholder.png +0 -0
- package/src/lib/assets/icons/colormap-pubu.png +0 -0
- package/src/lib/assets/interactive-segmentation-cursor.svg +0 -1
- package/src/lib/assets/picture-segmentation.svg +0 -43
- package/src/lib/assets/test/download-379.svg +0 -1
- package/src/lib/assets/test/download-98.svg +0 -1
- package/src/lib/assets/test/json-1.svg +0 -1
- package/src/lib/assets/test/load-53.svg +0 -1
- package/src/lib/assets/test/mask-44.svg +0 -1
- package/src/lib/assets/test/mask-download-44.svg +0 -15
- package/src/lib/assets/test/mask-save-44.svg +0 -11
- package/src/lib/assets/test/overlay-1.svg +0 -1
- package/src/lib/assets/test/overlay-4.svg +0 -1
- package/src/lib/assets/test/region-26.svg +0 -1
- package/src/lib/assets/test/save-56.svg +0 -1
- package/src/lib/assets/test/upload-43.svg +0 -1
|
@@ -1,16 +1,15 @@
|
|
|
1
1
|
import { OSD } from './osd-lib';
|
|
2
2
|
import { Subscription } from 'rxjs';
|
|
3
3
|
import { Region, Rectangle, Polygon, MultiPolygon } from '../../models/region';
|
|
4
|
-
import { resolveHandles } from '../../models/bezier';
|
|
5
4
|
import { elementToImage, imageToElement } from './osd-coords';
|
|
6
5
|
import { OSD_ZOOM_PER_SCROLL } from './osd-zoom';
|
|
6
|
+
import { translateBounds } from '../../models/polygon-edit';
|
|
7
|
+
import { makePolygon } from '../../models/polygon-factory';
|
|
8
|
+
import { OPEN_PATH_TOL_PX, hitHandle, nearestEdge, regionContains, regionsInRect, topmostRegionAt, } from '../../region-overlay/region-geometry';
|
|
9
|
+
import { SvgRegionRenderer, affineFromProjection } from '../../region-overlay/svg-region-renderer';
|
|
10
|
+
import { drawDraftPath, drawDraftRect, drawRegionLabel, drawSelectionBand, drawSelectionHandles, styleRegionShape, vertexMarker, } from './osd-region-overlay-draw';
|
|
11
|
+
import { EDIT_TOL_PX, ZONE_CURSOR, rectZone, resizeRect } from '../../region-overlay/region-hit-test';
|
|
7
12
|
const SVGNS = 'http://www.w3.org/2000/svg';
|
|
8
|
-
const ZONE_CURSOR = {
|
|
9
|
-
move: 'move', n: 'ns-resize', s: 'ns-resize', e: 'ew-resize', w: 'ew-resize',
|
|
10
|
-
ne: 'nesw-resize', sw: 'nesw-resize', nw: 'nwse-resize', se: 'nwse-resize',
|
|
11
|
-
};
|
|
12
|
-
/** Screen-pixel tolerance for grabbing an edge/corner handle. */
|
|
13
|
-
const EDIT_TOL = 8;
|
|
14
13
|
/**
|
|
15
14
|
* OpenSeadragon implementation of {@link IRegionOverlay}.
|
|
16
15
|
*
|
|
@@ -30,7 +29,6 @@ export class OsdRegionOverlay {
|
|
|
30
29
|
this.viewer = viewer;
|
|
31
30
|
this.store = store;
|
|
32
31
|
this.subs = new Subscription();
|
|
33
|
-
this.osd = OSD;
|
|
34
32
|
this.selected = [];
|
|
35
33
|
this.mode = 'none';
|
|
36
34
|
this.rectStart = null; // image coords
|
|
@@ -55,6 +53,19 @@ export class OsdRegionOverlay {
|
|
|
55
53
|
this.bandCurrent = null;
|
|
56
54
|
this.bandDragged = false;
|
|
57
55
|
this.redrawHandler = () => this.redraw();
|
|
56
|
+
/** A camera move ('update-viewport', raised on every redrawn frame, animated ones
|
|
57
|
+
* included; 'resize'; 'rotate'). The regions are drawn in image coordinates, so
|
|
58
|
+
* only the renderer's transform and its few screen-space elements follow; nothing
|
|
59
|
+
* is rebuilt (OSD-PLOTLY-11). A tile-only frame (loading, recolor) leaves the
|
|
60
|
+
* projection, and so the DOM, untouched. */
|
|
61
|
+
this.cameraHandler = () => this.updateCamera();
|
|
62
|
+
/** OSD's MouseTracker drops a cancelled pointer (touch interrupted, pointer
|
|
63
|
+
* capture lost to the browser) without calling releaseHandler, so the
|
|
64
|
+
* gesture is ended here instead. */
|
|
65
|
+
this.pointerCancelHandler = () => {
|
|
66
|
+
this.endGesture();
|
|
67
|
+
this.redraw();
|
|
68
|
+
};
|
|
58
69
|
/** Drive OSD zoom from the wheel while any tool owns the pointer.
|
|
59
70
|
*
|
|
60
71
|
* OSD's native scroll-zoom is part of mouse-nav, so `setMouseNavEnabled(false)`
|
|
@@ -72,24 +83,43 @@ export class OsdRegionOverlay {
|
|
|
72
83
|
return;
|
|
73
84
|
e.preventDefault();
|
|
74
85
|
const rect = el.getBoundingClientRect();
|
|
75
|
-
const refPoint = vp.pointFromPixel(new
|
|
86
|
+
const refPoint = vp.pointFromPixel(new OSD.Point(e.clientX - rect.left, e.clientY - rect.top));
|
|
76
87
|
vp.zoomBy(e.deltaY < 0 ? OSD_ZOOM_PER_SCROLL : 1 / OSD_ZOOM_PER_SCROLL, refPoint);
|
|
77
88
|
vp.applyConstraints();
|
|
78
89
|
};
|
|
90
|
+
/** Image point -> element px, as the shared region geometry wants it. */
|
|
91
|
+
this.toScreen = (x, y) => {
|
|
92
|
+
const q = this.toPx(x, y);
|
|
93
|
+
return [q.x, q.y];
|
|
94
|
+
};
|
|
79
95
|
this.svg = document.createElementNS(SVGNS, 'svg');
|
|
80
96
|
Object.assign(this.svg.style, {
|
|
81
|
-
position: 'absolute',
|
|
97
|
+
position: 'absolute',
|
|
98
|
+
left: '0',
|
|
99
|
+
top: '0',
|
|
100
|
+
width: '100%',
|
|
101
|
+
height: '100%',
|
|
82
102
|
pointerEvents: 'none', // OSD handles navigation unless we're drawing
|
|
83
103
|
});
|
|
84
104
|
this.viewer.canvas.appendChild(this.svg);
|
|
85
|
-
this.
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
105
|
+
this.renderer = new SvgRegionRenderer(this.svg, {
|
|
106
|
+
rectElement: 'polygon',
|
|
107
|
+
styleShape: (el, region, selected) => styleRegionShape(el, region, selected, this.store.getShapeColor()),
|
|
108
|
+
// The class label, when the Region Editor's "show labels" is on.
|
|
109
|
+
decorate: (region, _i, _selected, layer) => {
|
|
110
|
+
if (this.store.getShowShapeLabel())
|
|
111
|
+
drawRegionLabel(layer, region, this.store.getShapeColor());
|
|
112
|
+
},
|
|
113
|
+
});
|
|
114
|
+
this.viewer.canvas.addEventListener('pointercancel', this.pointerCancelHandler);
|
|
115
|
+
// 'update-viewport' fires on every redrawn frame, animated ones included —
|
|
116
|
+
// also listening to 'animation' rebuilt the whole SVG twice per frame.
|
|
117
|
+
this.viewer.addHandler('update-viewport', this.cameraHandler);
|
|
118
|
+
this.viewer.addHandler('resize', this.cameraHandler);
|
|
119
|
+
this.viewer.addHandler('rotate', this.cameraHandler);
|
|
89
120
|
// Keep wheel-zoom alive while a tool has mouse-nav disabled (see handler).
|
|
90
|
-
this.viewer.element
|
|
91
|
-
|
|
92
|
-
this.tracker = new this.osd.MouseTracker({
|
|
121
|
+
this.viewer.element?.addEventListener('wheel', this.wheelZoomHandler, { passive: false });
|
|
122
|
+
this.tracker = new OSD.MouseTracker({
|
|
93
123
|
element: this.viewer.canvas,
|
|
94
124
|
pressHandler: (e) => this.onPress(e),
|
|
95
125
|
dragHandler: (e) => this.onDrag(e),
|
|
@@ -99,7 +129,7 @@ export class OsdRegionOverlay {
|
|
|
99
129
|
});
|
|
100
130
|
this.tracker.setTracking(false);
|
|
101
131
|
this.subs.add(this.store.getRegionUpdateEvent().subscribe(this.redrawHandler));
|
|
102
|
-
this.subs.add(this.store.getSelectedShapeIndices$().subscribe(idx => {
|
|
132
|
+
this.subs.add(this.store.getSelectedShapeIndices$().subscribe((idx) => {
|
|
103
133
|
this.selected = idx || [];
|
|
104
134
|
this.redraw();
|
|
105
135
|
}));
|
|
@@ -115,14 +145,18 @@ export class OsdRegionOverlay {
|
|
|
115
145
|
this.viewer.setMouseNavEnabled(mode === 'none');
|
|
116
146
|
this.tracker.setTracking(mode !== 'none');
|
|
117
147
|
this.updateCursor(false);
|
|
118
|
-
this.
|
|
148
|
+
this.renderOverlay();
|
|
119
149
|
}
|
|
120
150
|
/** Cursor feedback per mode (crosshair while drawing; pointer over a region
|
|
121
151
|
* in select mode). */
|
|
122
152
|
updateCursor(overRegion) {
|
|
123
153
|
const canvas = this.viewer.canvas;
|
|
124
|
-
if (this.mode === 'drawrect' ||
|
|
125
|
-
|
|
154
|
+
if (this.mode === 'drawrect' ||
|
|
155
|
+
this.mode === 'drawclosedpath' ||
|
|
156
|
+
this.mode === 'drawopenpath' ||
|
|
157
|
+
this.mode === 'drawpolygon' ||
|
|
158
|
+
this.mode === 'addpoint' ||
|
|
159
|
+
this.mode === 'deletepoint') {
|
|
126
160
|
canvas.style.cursor = 'crosshair';
|
|
127
161
|
}
|
|
128
162
|
else if (this.mode === 'move') {
|
|
@@ -141,17 +175,21 @@ export class OsdRegionOverlay {
|
|
|
141
175
|
* its vertices. Suppressed only while actively drawing a brand-new shape,
|
|
142
176
|
* where stray handles would be noise. */
|
|
143
177
|
get showsSelectedVertices() {
|
|
144
|
-
return this.mode !== 'drawrect' &&
|
|
145
|
-
|
|
178
|
+
return (this.mode !== 'drawrect' &&
|
|
179
|
+
this.mode !== 'drawpolygon' &&
|
|
180
|
+
this.mode !== 'drawclosedpath' &&
|
|
181
|
+
this.mode !== 'drawopenpath');
|
|
146
182
|
}
|
|
147
183
|
destroy() {
|
|
184
|
+
// Close a gesture in flight first: a drag's open store batch would
|
|
185
|
+
// otherwise suppress every later region-update emission app-wide.
|
|
186
|
+
this.endGesture();
|
|
187
|
+
this.viewer.canvas.removeEventListener('pointercancel', this.pointerCancelHandler);
|
|
148
188
|
this.subs.unsubscribe();
|
|
149
|
-
this.viewer.element
|
|
150
|
-
|
|
151
|
-
this.viewer.removeHandler('
|
|
152
|
-
this.viewer.removeHandler('
|
|
153
|
-
this.viewer.removeHandler('resize', this.redrawHandler);
|
|
154
|
-
this.viewer.removeHandler('rotate', this.redrawHandler);
|
|
189
|
+
this.viewer.element?.removeEventListener('wheel', this.wheelZoomHandler);
|
|
190
|
+
this.viewer.removeHandler('update-viewport', this.cameraHandler);
|
|
191
|
+
this.viewer.removeHandler('resize', this.cameraHandler);
|
|
192
|
+
this.viewer.removeHandler('rotate', this.cameraHandler);
|
|
155
193
|
if (this.tracker)
|
|
156
194
|
this.tracker.destroy();
|
|
157
195
|
if (this.svg.parentNode)
|
|
@@ -162,346 +200,59 @@ export class OsdRegionOverlay {
|
|
|
162
200
|
toPx(imgX, imgY) {
|
|
163
201
|
return imageToElement(this.viewer, imgX, imgY);
|
|
164
202
|
}
|
|
165
|
-
/** Element pixel point (from a MouseTracker event) -> image-pixel point
|
|
203
|
+
/** Element pixel point (from a MouseTracker event) -> image-pixel point, rounded
|
|
204
|
+
* to whole pixels (where a drawn vertex lands). */
|
|
166
205
|
toImage(pos) {
|
|
167
206
|
const p = elementToImage(this.viewer, pos.x, pos.y);
|
|
168
207
|
return { x: Math.round(p.x), y: Math.round(p.y) };
|
|
169
208
|
}
|
|
209
|
+
/** Element pixel point -> exact image point, for hit tests. */
|
|
210
|
+
toWorld(pos) {
|
|
211
|
+
return elementToImage(this.viewer, pos.x, pos.y);
|
|
212
|
+
}
|
|
170
213
|
// ── rendering ────────────────────────────────────────────────────────
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
regions.forEach((r, i) => {
|
|
176
|
-
const el = this.buildRegionEl(r, this.selected.includes(i));
|
|
177
|
-
if (el)
|
|
178
|
-
this.svg.appendChild(el);
|
|
179
|
-
});
|
|
180
|
-
// Handles on the selected polygon, so the user can grab/insert/delete
|
|
181
|
-
// vertices. Bezier regions also get their cubic
|
|
182
|
-
// control handles (tangent lines + control points), mirroring paper.js's
|
|
183
|
-
// fullySelected rendering.
|
|
184
|
-
if (this.showsSelectedVertices) {
|
|
185
|
-
const sel = this.selectedRegionInfo();
|
|
186
|
-
const b = sel?.region.bounds;
|
|
187
|
-
// Handles/vertices take the region's own colour (not the global shape
|
|
188
|
-
// colour) so they match the shape they belong to.
|
|
189
|
-
const color = sel ? sel.region.color || this.store.getShapeColor() : '';
|
|
190
|
-
if (b instanceof Polygon) {
|
|
191
|
-
if (b.bezier) {
|
|
192
|
-
this.drawBezierHandles(b, color);
|
|
193
|
-
}
|
|
194
|
-
else {
|
|
195
|
-
for (let i = 0; i < b.xpoints.length; i++) {
|
|
196
|
-
const q = this.toPx(b.xpoints[i], b.ypoints[i]);
|
|
197
|
-
this.svg.appendChild(this.vertexMarker(q.x, q.y, false, color));
|
|
198
|
-
}
|
|
199
|
-
// Interior-ring (hole) vertices too, so a donut's inner outline shows
|
|
200
|
-
// its vertices when selected (jit-ui#85).
|
|
201
|
-
if (b.holes) {
|
|
202
|
-
for (const ring of b.holes) {
|
|
203
|
-
for (const [hx, hy] of ring) {
|
|
204
|
-
const q = this.toPx(hx, hy);
|
|
205
|
-
this.svg.appendChild(this.vertexMarker(q.x, q.y, false, color));
|
|
206
|
-
}
|
|
207
|
-
}
|
|
208
|
-
}
|
|
209
|
-
}
|
|
210
|
-
}
|
|
211
|
-
else if (b instanceof Rectangle) {
|
|
212
|
-
// The four corners as grab/resize handles.
|
|
213
|
-
const corners = [
|
|
214
|
-
[b.x, b.y], [b.x + b.width, b.y],
|
|
215
|
-
[b.x + b.width, b.y + b.height], [b.x, b.y + b.height],
|
|
216
|
-
];
|
|
217
|
-
for (const [cx, cy] of corners) {
|
|
218
|
-
const q = this.toPx(cx, cy);
|
|
219
|
-
this.svg.appendChild(this.vertexMarker(q.x, q.y, false, color));
|
|
220
|
-
}
|
|
221
|
-
}
|
|
222
|
-
}
|
|
223
|
-
// Rubber-band (marquee) selection preview.
|
|
224
|
-
if (this.mode === 'select' && this.bandStart && this.bandCurrent) {
|
|
225
|
-
this.svg.appendChild(this.selectionBand(this.bandStart, this.bandCurrent));
|
|
226
|
-
}
|
|
227
|
-
// In-progress drawing preview.
|
|
228
|
-
if (this.mode === 'drawrect' && this.rectStart && this.rectCurrent) {
|
|
229
|
-
this.svg.appendChild(this.rectPreview(this.rectStart, this.rectCurrent));
|
|
230
|
-
}
|
|
231
|
-
if ((this.mode === 'drawclosedpath' || this.mode === 'drawopenpath') && this.polyPoints.length) {
|
|
232
|
-
this.svg.appendChild(this.polyPreview(this.polyPoints));
|
|
233
|
-
}
|
|
234
|
-
// Click-to-place polygon preview: the polyline so far + a marker on the
|
|
235
|
-
// first vertex (click it to close).
|
|
236
|
-
if (this.mode === 'drawpolygon' && this.polyPoints.length) {
|
|
237
|
-
this.svg.appendChild(this.polyPreview(this.polyPoints));
|
|
238
|
-
const f = this.toPx(this.polyPoints[0].x, this.polyPoints[0].y);
|
|
239
|
-
this.svg.appendChild(this.vertexMarker(f.x, f.y, true));
|
|
240
|
-
}
|
|
214
|
+
/** Follow the current image→element projection: the renderer rewrites one transform
|
|
215
|
+
* and re-positions its screen-space elements, or does nothing when it did not move. */
|
|
216
|
+
updateCamera() {
|
|
217
|
+
this.renderer.setCamera(affineFromProjection(this.toScreen));
|
|
241
218
|
}
|
|
242
|
-
/**
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
c.setAttribute('cx', `${x}`);
|
|
248
|
-
c.setAttribute('cy', `${y}`);
|
|
249
|
-
c.setAttribute('r', emphasised ? '5' : '4');
|
|
250
|
-
c.setAttribute('fill', emphasised ? color : '#ffffff');
|
|
251
|
-
c.setAttribute('stroke', color);
|
|
252
|
-
c.setAttribute('stroke-width', '2');
|
|
253
|
-
return c;
|
|
219
|
+
/** Rebuild everything: the regions (in image coordinates), their labels and the overlay. */
|
|
220
|
+
redraw() {
|
|
221
|
+
this.updateCamera();
|
|
222
|
+
this.renderer.render(this.store.getRegions(), this.selected);
|
|
223
|
+
this.renderOverlay();
|
|
254
224
|
}
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
//
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
pts.push(...ext);
|
|
272
|
-
d += (d ? ' ' : '') + this.straightPathD(ext, true);
|
|
273
|
-
if (part.holes) {
|
|
274
|
-
for (const ring of part.holes) {
|
|
275
|
-
d += ' ' + this.straightPathD(ring.map(([x, y]) => ({ x, y })), true);
|
|
276
|
-
}
|
|
277
|
-
}
|
|
225
|
+
/**
|
|
226
|
+
* Rebuild the screen-space overlay only: the selected region's handles, the rubber band
|
|
227
|
+
* and any in-progress drawing. Drawing and marquee drags call this rather than
|
|
228
|
+
* {@link redraw}, so the regions are not rebuilt per pointer move.
|
|
229
|
+
*/
|
|
230
|
+
renderOverlay() {
|
|
231
|
+
const shapeColor = this.store.getShapeColor();
|
|
232
|
+
this.renderer.renderOverlay((layer) => {
|
|
233
|
+
// Handles on the selected region, so the user can grab/insert/delete
|
|
234
|
+
// vertices — in the region's own colour, so they match the shape.
|
|
235
|
+
const sel = this.showsSelectedVertices ? this.selectedRegionInfo() : null;
|
|
236
|
+
if (sel)
|
|
237
|
+
drawSelectionHandles(layer, sel.region, sel.region.color || shapeColor);
|
|
238
|
+
// Rubber-band (marquee) selection preview.
|
|
239
|
+
if (this.mode === 'select' && this.bandStart && this.bandCurrent) {
|
|
240
|
+
drawSelectionBand(layer, this.bandStart, this.bandCurrent);
|
|
278
241
|
}
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
}
|
|
283
|
-
else if (bounds instanceof Rectangle) {
|
|
284
|
-
pts = [
|
|
285
|
-
{ x: bounds.x, y: bounds.y },
|
|
286
|
-
{ x: bounds.x + bounds.width, y: bounds.y },
|
|
287
|
-
{ x: bounds.x + bounds.width, y: bounds.y + bounds.height },
|
|
288
|
-
{ x: bounds.x, y: bounds.y + bounds.height },
|
|
289
|
-
];
|
|
290
|
-
}
|
|
291
|
-
else if (bounds instanceof Polygon) {
|
|
292
|
-
closed = bounds.closed !== false;
|
|
293
|
-
// The anchors drive the label bbox and (for non-bezier) the rendered shape.
|
|
294
|
-
pts = bounds.xpoints.map((x, i) => ({ x, y: bounds.ypoints[i] }));
|
|
295
|
-
}
|
|
296
|
-
if (!pts || pts.length === 0)
|
|
297
|
-
return null;
|
|
298
|
-
if (!el) {
|
|
299
|
-
// Bezier regions render as a true cubic-bezier path through the anchors
|
|
300
|
-
// (paper.js-equivalent smooth curve); everything else as a straight
|
|
301
|
-
// polygon/polyline.
|
|
302
|
-
const isBezier = bounds instanceof Polygon && bounds.bezier && pts.length >= 2;
|
|
303
|
-
// Interior rings (holes) — punch through with even-odd fill (jit-ui#85).
|
|
304
|
-
const holes = (closed && bounds instanceof Polygon && bounds.holes?.length)
|
|
305
|
-
? bounds.holes : null;
|
|
306
|
-
if (isBezier || holes) {
|
|
307
|
-
el = document.createElementNS(SVGNS, 'path');
|
|
308
|
-
// Exterior subpath (smooth for bezier, straight otherwise) followed by a
|
|
309
|
-
// straight subpath per hole.
|
|
310
|
-
let d = isBezier ? this.bezierPathD(bounds) : this.straightPathD(pts, closed);
|
|
311
|
-
if (holes) {
|
|
312
|
-
const poly = bounds;
|
|
313
|
-
holes.forEach((ring, hi) => {
|
|
314
|
-
const xs = ring.map((p) => p[0]);
|
|
315
|
-
const ys = ring.map((p) => p[1]);
|
|
316
|
-
// When the donut is a bezier, smooth its holes too (jit-ui#102) — using stored hole
|
|
317
|
-
// handles when present, else the Catmull-Rom default (via resolveHandles).
|
|
318
|
-
d +=
|
|
319
|
-
' ' +
|
|
320
|
-
(isBezier
|
|
321
|
-
? this.ringBezierPathD(xs, ys, poly.holeHandlesIn?.[hi], poly.holeHandlesOut?.[hi], true)
|
|
322
|
-
: this.straightPathD(ring.map(([x, y]) => ({ x, y })), true));
|
|
323
|
-
});
|
|
324
|
-
el.setAttribute('fill-rule', 'evenodd');
|
|
325
|
-
}
|
|
326
|
-
el.setAttribute('d', d);
|
|
242
|
+
// In-progress drawing preview.
|
|
243
|
+
if (this.mode === 'drawrect' && this.rectStart && this.rectCurrent) {
|
|
244
|
+
drawDraftRect(layer, this.rectStart, this.rectCurrent, shapeColor);
|
|
327
245
|
}
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
el.setAttribute('points', pts.map(p => { const q = this.toPx(p.x, p.y); return `${q.x},${q.y}`; }).join(' '));
|
|
246
|
+
if ((this.mode === 'drawclosedpath' || this.mode === 'drawopenpath') && this.polyPoints.length) {
|
|
247
|
+
drawDraftPath(layer, this.polyPoints, shapeColor);
|
|
331
248
|
}
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
// on — mirrors Plotly's per-shape label (top-left, drawn in the region's
|
|
338
|
-
// colour). Without this OSD showed regions with no label even though Plotly
|
|
339
|
-
// did. region.label is restored from the shape's legend in getRegion().
|
|
340
|
-
const label = region.label;
|
|
341
|
-
if (this.store.getShowShapeLabel() && label != null && `${label}`.length > 0) {
|
|
342
|
-
const g = document.createElementNS(SVGNS, 'g');
|
|
343
|
-
g.appendChild(el);
|
|
344
|
-
const minX = Math.min(...pts.map(p => p.x));
|
|
345
|
-
const minY = Math.min(...pts.map(p => p.y));
|
|
346
|
-
const q = this.toPx(minX, minY);
|
|
347
|
-
const text = document.createElementNS(SVGNS, 'text');
|
|
348
|
-
text.setAttribute('x', `${q.x}`);
|
|
349
|
-
text.setAttribute('y', `${q.y - 4}`); // just above the top-left corner
|
|
350
|
-
text.setAttribute('fill', color);
|
|
351
|
-
text.setAttribute('font-size', '13');
|
|
352
|
-
text.setAttribute('font-family', 'sans-serif');
|
|
353
|
-
// Dark halo so the label stays legible over both bright and dark tiles.
|
|
354
|
-
text.setAttribute('paint-order', 'stroke');
|
|
355
|
-
text.setAttribute('stroke', 'rgba(0,0,0,0.65)');
|
|
356
|
-
text.setAttribute('stroke-width', '2');
|
|
357
|
-
text.textContent = `${label}`;
|
|
358
|
-
g.appendChild(text);
|
|
359
|
-
return g;
|
|
360
|
-
}
|
|
361
|
-
return el;
|
|
362
|
-
}
|
|
363
|
-
/** Marquee rectangle for rubber-band multi-select (dashed outline + faint fill). */
|
|
364
|
-
selectionBand(a, b) {
|
|
365
|
-
const corners = [
|
|
366
|
-
{ x: a.x, y: a.y }, { x: b.x, y: a.y }, { x: b.x, y: b.y }, { x: a.x, y: b.y },
|
|
367
|
-
];
|
|
368
|
-
const el = document.createElementNS(SVGNS, 'polygon');
|
|
369
|
-
el.setAttribute('points', corners.map(p => { const q = this.toPx(p.x, p.y); return `${q.x},${q.y}`; }).join(' '));
|
|
370
|
-
el.setAttribute('fill', 'rgba(120,170,255,0.15)');
|
|
371
|
-
el.setAttribute('stroke', '#4a90e2');
|
|
372
|
-
el.setAttribute('stroke-dasharray', '4 3');
|
|
373
|
-
el.setAttribute('stroke-width', '1');
|
|
374
|
-
return el;
|
|
375
|
-
}
|
|
376
|
-
rectPreview(a, b) {
|
|
377
|
-
const corners = [
|
|
378
|
-
{ x: a.x, y: a.y }, { x: b.x, y: a.y }, { x: b.x, y: b.y }, { x: a.x, y: b.y },
|
|
379
|
-
];
|
|
380
|
-
const el = document.createElementNS(SVGNS, 'polygon');
|
|
381
|
-
el.setAttribute('points', corners.map(p => { const q = this.toPx(p.x, p.y); return `${q.x},${q.y}`; }).join(' '));
|
|
382
|
-
el.setAttribute('fill', 'none');
|
|
383
|
-
el.setAttribute('stroke', this.store.getShapeColor());
|
|
384
|
-
el.setAttribute('stroke-dasharray', '4 3');
|
|
385
|
-
el.setAttribute('stroke-width', '2');
|
|
386
|
-
return el;
|
|
387
|
-
}
|
|
388
|
-
polyPreview(pts) {
|
|
389
|
-
const el = document.createElementNS(SVGNS, 'polyline');
|
|
390
|
-
el.setAttribute('points', pts.map(p => { const q = this.toPx(p.x, p.y); return `${q.x},${q.y}`; }).join(' '));
|
|
391
|
-
el.setAttribute('fill', 'none');
|
|
392
|
-
el.setAttribute('stroke', this.store.getShapeColor());
|
|
393
|
-
el.setAttribute('stroke-dasharray', '4 3');
|
|
394
|
-
el.setAttribute('stroke-width', '2');
|
|
395
|
-
return el;
|
|
396
|
-
}
|
|
397
|
-
/** SVG path `d` (element-pixel coords) for a straight-edged ring/polyline. */
|
|
398
|
-
straightPathD(pts, closed) {
|
|
399
|
-
if (pts.length < 2)
|
|
400
|
-
return '';
|
|
401
|
-
let d = '';
|
|
402
|
-
pts.forEach((p, i) => {
|
|
403
|
-
const q = this.toPx(p.x, p.y);
|
|
404
|
-
d += (i === 0 ? 'M ' : ' L ') + `${q.x},${q.y}`;
|
|
405
|
-
});
|
|
406
|
-
if (closed)
|
|
407
|
-
d += ' Z';
|
|
408
|
-
return d;
|
|
409
|
-
}
|
|
410
|
-
/** SVG path `d` (element-pixel coords) for the smooth cubic bezier through a
|
|
411
|
-
* polygon's anchors — the paper.js-equivalent curve. */
|
|
412
|
-
bezierPathD(poly) {
|
|
413
|
-
const closed = poly.closed !== false;
|
|
414
|
-
return this.ringBezierPathD(poly.xpoints, poly.ypoints, poly.handlesIn, poly.handlesOut, closed);
|
|
415
|
-
}
|
|
416
|
-
/** SVG cubic-bezier path `d` (element px) for any ring (exterior or hole). Uses the stored
|
|
417
|
-
* per-vertex handle offsets when present, else the Catmull-Rom default (resolveHandles). */
|
|
418
|
-
ringBezierPathD(xs, ys, inOff, outOff, closed) {
|
|
419
|
-
const n = Math.min(xs.length, ys.length);
|
|
420
|
-
if (n < 2)
|
|
421
|
-
return '';
|
|
422
|
-
const h = resolveHandles(xs, ys, closed, inOff, outOff);
|
|
423
|
-
const px = (x, y) => { const q = this.toPx(x, y); return `${q.x},${q.y}`; };
|
|
424
|
-
let d = `M ${px(xs[0], ys[0])}`;
|
|
425
|
-
const segs = closed ? n : n - 1;
|
|
426
|
-
for (let i = 0; i < segs; i++) {
|
|
427
|
-
const j = (i + 1) % n;
|
|
428
|
-
const c1 = h[i].out;
|
|
429
|
-
const c2 = h[j].in;
|
|
430
|
-
d += ` C ${px(c1[0], c1[1])} ${px(c2[0], c2[1])} ${px(xs[j], ys[j])}`;
|
|
431
|
-
}
|
|
432
|
-
if (closed)
|
|
433
|
-
d += ' Z';
|
|
434
|
-
return d;
|
|
435
|
-
}
|
|
436
|
-
/**
|
|
437
|
-
* Draw the bezier editing handles for the selected region, paper.js-style:
|
|
438
|
-
* each anchor as a small square, with tangent lines out to its two control
|
|
439
|
-
* points (drawn as small circles).
|
|
440
|
-
*/
|
|
441
|
-
drawBezierHandles(poly, color) {
|
|
442
|
-
const xs = poly.xpoints;
|
|
443
|
-
const ys = poly.ypoints;
|
|
444
|
-
const drawRing = (rxs, rys, inOff, outOff, closed) => {
|
|
445
|
-
const h = resolveHandles(rxs, rys, closed, inOff, outOff);
|
|
446
|
-
for (let i = 0; i < rxs.length; i++) {
|
|
447
|
-
const a = this.toPx(rxs[i], rys[i]);
|
|
448
|
-
if (h[i].hasIn)
|
|
449
|
-
this.drawHandle(a, this.toPx(h[i].in[0], h[i].in[1]), color);
|
|
450
|
-
if (h[i].hasOut)
|
|
451
|
-
this.drawHandle(a, this.toPx(h[i].out[0], h[i].out[1]), color);
|
|
452
|
-
this.svg.appendChild(this.anchorSquare(a.x, a.y, color));
|
|
249
|
+
// Click-to-place polygon preview: the polyline so far + a marker on the
|
|
250
|
+
// first vertex (click it to close).
|
|
251
|
+
if (this.mode === 'drawpolygon' && this.polyPoints.length) {
|
|
252
|
+
drawDraftPath(layer, this.polyPoints, shapeColor);
|
|
253
|
+
vertexMarker(layer, this.polyPoints[0].x, this.polyPoints[0].y, true, shapeColor);
|
|
453
254
|
}
|
|
454
|
-
};
|
|
455
|
-
drawRing(xs, ys, poly.handlesIn, poly.handlesOut, poly.closed !== false);
|
|
456
|
-
// Donut hole rings get their own editable bezier handles (jit-ui#102).
|
|
457
|
-
if (poly.holes && poly.holeHandlesIn && poly.holeHandlesOut) {
|
|
458
|
-
poly.holes.forEach((ring, hi) => {
|
|
459
|
-
const inOff = poly.holeHandlesIn[hi];
|
|
460
|
-
const outOff = poly.holeHandlesOut[hi];
|
|
461
|
-
if (inOff && outOff)
|
|
462
|
-
drawRing(ring.map((p) => p[0]), ring.map((p) => p[1]), inOff, outOff, true);
|
|
463
|
-
});
|
|
464
|
-
}
|
|
465
|
-
}
|
|
466
|
-
/** A tangent line from an anchor to a control point, with a circle at the end. */
|
|
467
|
-
drawHandle(anchor, ctrl, color) {
|
|
468
|
-
const line = document.createElementNS(SVGNS, 'line');
|
|
469
|
-
line.setAttribute('x1', `${anchor.x}`);
|
|
470
|
-
line.setAttribute('y1', `${anchor.y}`);
|
|
471
|
-
line.setAttribute('x2', `${ctrl.x}`);
|
|
472
|
-
line.setAttribute('y2', `${ctrl.y}`);
|
|
473
|
-
line.setAttribute('stroke', color);
|
|
474
|
-
line.setAttribute('stroke-width', '1');
|
|
475
|
-
this.svg.appendChild(line);
|
|
476
|
-
const c = document.createElementNS(SVGNS, 'circle');
|
|
477
|
-
c.setAttribute('cx', `${ctrl.x}`);
|
|
478
|
-
c.setAttribute('cy', `${ctrl.y}`);
|
|
479
|
-
c.setAttribute('r', '3');
|
|
480
|
-
c.setAttribute('fill', color);
|
|
481
|
-
this.svg.appendChild(c);
|
|
482
|
-
}
|
|
483
|
-
/** A filled-white anchor square (the editable vertex). */
|
|
484
|
-
anchorSquare(x, y, color) {
|
|
485
|
-
const r = 3.5;
|
|
486
|
-
const rect = document.createElementNS(SVGNS, 'rect');
|
|
487
|
-
rect.setAttribute('x', `${x - r}`);
|
|
488
|
-
rect.setAttribute('y', `${y - r}`);
|
|
489
|
-
rect.setAttribute('width', `${2 * r}`);
|
|
490
|
-
rect.setAttribute('height', `${2 * r}`);
|
|
491
|
-
rect.setAttribute('fill', '#ffffff');
|
|
492
|
-
rect.setAttribute('stroke', color);
|
|
493
|
-
rect.setAttribute('stroke-width', '2');
|
|
494
|
-
return rect;
|
|
495
|
-
}
|
|
496
|
-
rgba(color, alpha) {
|
|
497
|
-
// Accept #rrggbb; fall back to the color as-is for named/rgb values.
|
|
498
|
-
if (/^#([0-9a-f]{6})$/i.test(color)) {
|
|
499
|
-
const r = parseInt(color.slice(1, 3), 16);
|
|
500
|
-
const g = parseInt(color.slice(3, 5), 16);
|
|
501
|
-
const b = parseInt(color.slice(5, 7), 16);
|
|
502
|
-
return `rgba(${r},${g},${b},${alpha})`;
|
|
503
|
-
}
|
|
504
|
-
return color;
|
|
255
|
+
});
|
|
505
256
|
}
|
|
506
257
|
// ── interaction ──────────────────────────────────────────────────────
|
|
507
258
|
get isFreehand() {
|
|
@@ -525,25 +276,23 @@ export class OsdRegionOverlay {
|
|
|
525
276
|
// Whole-region drag ('move' mode): press inside the selected region
|
|
526
277
|
// to translate it, ignoring vertices/edges.
|
|
527
278
|
const sel = this.selectedRegionInfo();
|
|
528
|
-
if (sel && this.containsPoint(sel.region,
|
|
279
|
+
if (sel && this.containsPoint(sel.region, e.position)) {
|
|
529
280
|
this.startEdit('bounds', 'move', -1, sel.region, this.toImage(e.position));
|
|
530
281
|
}
|
|
531
282
|
return;
|
|
532
283
|
}
|
|
533
284
|
if (this.mode === 'select') {
|
|
534
|
-
// A bezier control handle takes top priority (it sits off the anchor)
|
|
535
|
-
|
|
536
|
-
|
|
537
|
-
|
|
538
|
-
this.startEdit('handle', 'move', hh.index, region, this.toImage(e.position), hh.side, hh.ring);
|
|
539
|
-
return;
|
|
540
|
-
}
|
|
541
|
-
// Then dragging a single polygon vertex (over body-move/resize) —
|
|
542
|
-
// 'select' grabs the nearest segment first.
|
|
543
|
-
const vh = this.hitVertex(e.position);
|
|
544
|
-
if (vh) {
|
|
285
|
+
// A bezier control handle takes top priority (it sits off the anchor), then
|
|
286
|
+
// dragging a single polygon vertex (over body-move/resize).
|
|
287
|
+
const hit = this.hitPolygonHandle(e.position);
|
|
288
|
+
if (hit) {
|
|
545
289
|
const region = this.store.getRegions()[this.selected[this.selected.length - 1]];
|
|
546
|
-
|
|
290
|
+
if (hit.kind === 'bezier') {
|
|
291
|
+
this.startEdit('handle', 'move', hit.index, region, this.toImage(e.position), hit.side, hit.ring);
|
|
292
|
+
}
|
|
293
|
+
else {
|
|
294
|
+
this.startEdit('vertex', 'move', hit.index, region, this.toImage(e.position), 'out', hit.ring);
|
|
295
|
+
}
|
|
547
296
|
return;
|
|
548
297
|
}
|
|
549
298
|
// Otherwise start a move/resize when pressing the selected region's
|
|
@@ -565,8 +314,14 @@ export class OsdRegionOverlay {
|
|
|
565
314
|
* batch so the live drag emits once on release. */
|
|
566
315
|
startEdit(kind, zone, vertexIndex, region, startImg, handleSide = 'out', ring = -1) {
|
|
567
316
|
this.edit = {
|
|
568
|
-
kind,
|
|
569
|
-
|
|
317
|
+
kind,
|
|
318
|
+
zone,
|
|
319
|
+
vertexIndex,
|
|
320
|
+
ring,
|
|
321
|
+
handleSide,
|
|
322
|
+
id: region.id,
|
|
323
|
+
startImg,
|
|
324
|
+
orig: kind === 'bounds' ? this.snapshot(region) : null,
|
|
570
325
|
};
|
|
571
326
|
this.editDragged = false;
|
|
572
327
|
this.store.beginBatch();
|
|
@@ -574,7 +329,7 @@ export class OsdRegionOverlay {
|
|
|
574
329
|
onDrag(e) {
|
|
575
330
|
if (this.mode === 'drawrect' && this.rectStart) {
|
|
576
331
|
this.rectCurrent = this.toImage(e.position);
|
|
577
|
-
this.
|
|
332
|
+
this.renderOverlay();
|
|
578
333
|
return;
|
|
579
334
|
}
|
|
580
335
|
if (this.freehandDragging && this.isFreehand) {
|
|
@@ -583,7 +338,7 @@ export class OsdRegionOverlay {
|
|
|
583
338
|
if (!last || Math.hypot(e.position.x - last.x, e.position.y - last.y) >= 4) {
|
|
584
339
|
this.polyPoints.push(this.toImage(e.position));
|
|
585
340
|
this.lastFreehandPx = { x: e.position.x, y: e.position.y };
|
|
586
|
-
this.
|
|
341
|
+
this.renderOverlay();
|
|
587
342
|
}
|
|
588
343
|
return;
|
|
589
344
|
}
|
|
@@ -595,7 +350,7 @@ export class OsdRegionOverlay {
|
|
|
595
350
|
if (this.bandStart) {
|
|
596
351
|
this.bandCurrent = this.toImage(e.position);
|
|
597
352
|
this.bandDragged = true;
|
|
598
|
-
this.
|
|
353
|
+
this.renderOverlay();
|
|
599
354
|
}
|
|
600
355
|
}
|
|
601
356
|
onRelease(e) {
|
|
@@ -633,9 +388,9 @@ export class OsdRegionOverlay {
|
|
|
633
388
|
const x1 = Math.max(start.x, end.x), y1 = Math.max(start.y, end.y);
|
|
634
389
|
// Only a real drag selects; a click-sized band falls through to onClick.
|
|
635
390
|
if (this.bandDragged && (x1 - x0 > 2 || y1 - y0 > 2)) {
|
|
636
|
-
this.store.setSelectedShapeIndices(this.
|
|
391
|
+
this.store.setSelectedShapeIndices(regionsInRect(this.store.getRegions(), x0, y0, x1, y1));
|
|
637
392
|
}
|
|
638
|
-
this.
|
|
393
|
+
this.renderOverlay();
|
|
639
394
|
}
|
|
640
395
|
}
|
|
641
396
|
onClick(e) {
|
|
@@ -654,7 +409,7 @@ export class OsdRegionOverlay {
|
|
|
654
409
|
// selection; a plain click replaces it.
|
|
655
410
|
const oe = e.originalEvent;
|
|
656
411
|
const additive = !!oe && (oe.shiftKey || oe.metaKey || oe.ctrlKey);
|
|
657
|
-
this.selectAt(this.
|
|
412
|
+
this.selectAt(this.toWorld(e.position), additive);
|
|
658
413
|
return;
|
|
659
414
|
}
|
|
660
415
|
if (this.mode === 'drawpolygon') {
|
|
@@ -675,12 +430,13 @@ export class OsdRegionOverlay {
|
|
|
675
430
|
}
|
|
676
431
|
if (this.mode === 'deletepoint') {
|
|
677
432
|
// Remove the clicked vertex — exterior or an interior ring (jit-ui#85).
|
|
678
|
-
const
|
|
679
|
-
|
|
433
|
+
const sel = this.selectedRegionInfo();
|
|
434
|
+
const vh = this.hitPolygonHandle(e.position, false);
|
|
435
|
+
if (sel && vh) {
|
|
680
436
|
if (vh.ring < 0)
|
|
681
|
-
this.store.deleteVertex(
|
|
437
|
+
this.store.deleteVertex(sel.region.id, vh.index);
|
|
682
438
|
else
|
|
683
|
-
this.store.deleteHoleVertex(
|
|
439
|
+
this.store.deleteHoleVertex(sel.region.id, vh.ring, vh.index);
|
|
684
440
|
}
|
|
685
441
|
return;
|
|
686
442
|
}
|
|
@@ -695,17 +451,17 @@ export class OsdRegionOverlay {
|
|
|
695
451
|
if (!this.drawingPolygon) {
|
|
696
452
|
this.polyPoints = [pt];
|
|
697
453
|
this.drawingPolygon = true;
|
|
698
|
-
this.
|
|
454
|
+
this.renderOverlay();
|
|
699
455
|
return;
|
|
700
456
|
}
|
|
701
457
|
const first = this.toPx(this.polyPoints[0].x, this.polyPoints[0].y);
|
|
702
|
-
const onFirst = Math.hypot(e.position.x - first.x, e.position.y - first.y) <=
|
|
458
|
+
const onFirst = Math.hypot(e.position.x - first.x, e.position.y - first.y) <= EDIT_TOL_PX;
|
|
703
459
|
if (onFirst && this.polyPoints.length >= 3) {
|
|
704
460
|
this.commitPolygon(true); // closes + resets in-progress (incl. drawingPolygon)
|
|
705
461
|
return;
|
|
706
462
|
}
|
|
707
463
|
this.polyPoints.push(pt);
|
|
708
|
-
this.
|
|
464
|
+
this.renderOverlay();
|
|
709
465
|
}
|
|
710
466
|
/**
|
|
711
467
|
* Hover feedback in select mode: move/resize cursors over the selected
|
|
@@ -716,7 +472,7 @@ export class OsdRegionOverlay {
|
|
|
716
472
|
return;
|
|
717
473
|
// A grabbable bezier control handle or vertex of the selected polygon takes
|
|
718
474
|
// priority.
|
|
719
|
-
if (this.
|
|
475
|
+
if (this.hitPolygonHandle(e.position)) {
|
|
720
476
|
this.viewer.canvas.style.cursor = 'pointer';
|
|
721
477
|
return;
|
|
722
478
|
}
|
|
@@ -725,7 +481,7 @@ export class OsdRegionOverlay {
|
|
|
725
481
|
this.viewer.canvas.style.cursor = ZONE_CURSOR[ez.zone];
|
|
726
482
|
return;
|
|
727
483
|
}
|
|
728
|
-
this.updateCursor(this.regionIndexAt(this.
|
|
484
|
+
this.updateCursor(this.regionIndexAt(this.toWorld(e.position)) >= 0);
|
|
729
485
|
}
|
|
730
486
|
/**
|
|
731
487
|
* The move/resize zone under the cursor for the currently-selected region
|
|
@@ -743,12 +499,17 @@ export class OsdRegionOverlay {
|
|
|
743
499
|
if (b instanceof Rectangle) {
|
|
744
500
|
const a = this.toPx(b.x, b.y);
|
|
745
501
|
const c = this.toPx(b.x + b.width, b.y + b.height);
|
|
746
|
-
const zone =
|
|
502
|
+
const zone = rectZone(position.x, position.y, {
|
|
503
|
+
x0: Math.min(a.x, c.x),
|
|
504
|
+
y0: Math.min(a.y, c.y),
|
|
505
|
+
x1: Math.max(a.x, c.x),
|
|
506
|
+
y1: Math.max(a.y, c.y),
|
|
507
|
+
});
|
|
747
508
|
return zone ? { zone, index } : null;
|
|
748
509
|
}
|
|
749
510
|
if (b instanceof Polygon || b instanceof MultiPolygon) {
|
|
750
511
|
// Polygons + multi-part regions support whole-region move (no resize zones).
|
|
751
|
-
return this.containsPoint(region,
|
|
512
|
+
return this.containsPoint(region, position) ? { zone: 'move', index } : null;
|
|
752
513
|
}
|
|
753
514
|
return null;
|
|
754
515
|
}
|
|
@@ -760,155 +521,34 @@ export class OsdRegionOverlay {
|
|
|
760
521
|
const region = this.store.getRegions()[index];
|
|
761
522
|
return region ? { region, index } : null;
|
|
762
523
|
}
|
|
763
|
-
/** The vertex of the selected polygon
|
|
764
|
-
* tolerance), or null. Rectangles have no
|
|
765
|
-
|
|
524
|
+
/** The bezier control handle (when `bezier`) or vertex of the selected polygon
|
|
525
|
+
* under the cursor (screen-pixel tolerance), or null. Rectangles have no
|
|
526
|
+
* editable vertices (their corners are resize zones, see {@link rectZone}). */
|
|
527
|
+
hitPolygonHandle(position, bezier = true) {
|
|
766
528
|
const sel = this.selectedRegionInfo();
|
|
767
529
|
if (!sel || !(sel.region.bounds instanceof Polygon))
|
|
768
530
|
return null;
|
|
769
|
-
const
|
|
770
|
-
|
|
771
|
-
const q = this.toPx(b.xpoints[i], b.ypoints[i]);
|
|
772
|
-
if (Math.hypot(position.x - q.x, position.y - q.y) <= EDIT_TOL) {
|
|
773
|
-
return { id: sel.region.id, ring: -1, index: i };
|
|
774
|
-
}
|
|
775
|
-
}
|
|
776
|
-
// Interior-ring (hole) vertices are draggable too (jit-ui#85).
|
|
777
|
-
if (b.holes) {
|
|
778
|
-
for (let h = 0; h < b.holes.length; h++) {
|
|
779
|
-
const ring = b.holes[h];
|
|
780
|
-
for (let i = 0; i < ring.length; i++) {
|
|
781
|
-
const q = this.toPx(ring[i][0], ring[i][1]);
|
|
782
|
-
if (Math.hypot(position.x - q.x, position.y - q.y) <= EDIT_TOL) {
|
|
783
|
-
return { id: sel.region.id, ring: h, index: i };
|
|
784
|
-
}
|
|
785
|
-
}
|
|
786
|
-
}
|
|
787
|
-
}
|
|
788
|
-
return null;
|
|
789
|
-
}
|
|
790
|
-
/** The bezier control handle of the selected region under the cursor (which
|
|
791
|
-
* anchor, and whether the in- or out-handle), or null. */
|
|
792
|
-
hitBezierHandle(position) {
|
|
793
|
-
const sel = this.selectedRegionInfo();
|
|
794
|
-
if (!sel || !(sel.region.bounds instanceof Polygon) || !sel.region.bounds.bezier)
|
|
795
|
-
return null;
|
|
796
|
-
const b = sel.region.bounds;
|
|
797
|
-
// Test one ring's control handles; returns the matched vertex/side or null.
|
|
798
|
-
const testRing = (xs, ys, inOff, outOff, closed, ring) => {
|
|
799
|
-
const h = resolveHandles(xs, ys, closed, inOff, outOff);
|
|
800
|
-
for (let i = 0; i < h.length; i++) {
|
|
801
|
-
if (h[i].hasOut) {
|
|
802
|
-
const q = this.toPx(h[i].out[0], h[i].out[1]);
|
|
803
|
-
if (Math.hypot(position.x - q.x, position.y - q.y) <= EDIT_TOL) {
|
|
804
|
-
return { id: sel.region.id, index: i, side: 'out', ring };
|
|
805
|
-
}
|
|
806
|
-
}
|
|
807
|
-
if (h[i].hasIn) {
|
|
808
|
-
const q = this.toPx(h[i].in[0], h[i].in[1]);
|
|
809
|
-
if (Math.hypot(position.x - q.x, position.y - q.y) <= EDIT_TOL) {
|
|
810
|
-
return { id: sel.region.id, index: i, side: 'in', ring };
|
|
811
|
-
}
|
|
812
|
-
}
|
|
813
|
-
}
|
|
531
|
+
const hit = hitHandle(sel.region, position.x, position.y, this.toScreen, EDIT_TOL_PX, { bezier });
|
|
532
|
+
if (!hit || hit.kind === 'corner')
|
|
814
533
|
return null;
|
|
815
|
-
};
|
|
816
|
-
const ext = testRing(b.xpoints, b.ypoints, b.handlesIn, b.handlesOut, b.closed !== false, -1);
|
|
817
|
-
if (ext)
|
|
818
|
-
return ext;
|
|
819
|
-
// Donut hole rings (jit-ui#102): their own bezier control handles.
|
|
820
|
-
if (b.holes && b.holeHandlesIn && b.holeHandlesOut) {
|
|
821
|
-
for (let hi = 0; hi < b.holes.length; hi++) {
|
|
822
|
-
const ring = b.holes[hi];
|
|
823
|
-
const hit = testRing(ring.map((p) => p[0]), ring.map((p) => p[1]), b.holeHandlesIn[hi], b.holeHandlesOut[hi], true, hi);
|
|
824
|
-
if (hit)
|
|
825
|
-
return hit;
|
|
826
|
-
}
|
|
827
|
-
}
|
|
828
|
-
return null;
|
|
534
|
+
return { kind: hit.kind, ring: hit.ring, index: hit.index, side: hit.kind === 'bezier' ? hit.side : 'out' };
|
|
829
535
|
}
|
|
830
536
|
/** The edge of `region`'s polygon nearest the cursor (within tolerance), with
|
|
831
537
|
* the clicked point in image coords as the insertion position, or null. */
|
|
832
538
|
hitEdge(position, region) {
|
|
833
|
-
|
|
834
|
-
|
|
835
|
-
const b = region.bounds;
|
|
836
|
-
let best = -1, bestRing = -1, bestDist = Infinity;
|
|
837
|
-
// Nearest edge across the exterior (ring -1) and every interior ring (hole).
|
|
838
|
-
const scan = (xs, ys, ring, closed) => {
|
|
839
|
-
const n = xs.length;
|
|
840
|
-
const segCount = closed ? n : n - 1; // closed wraps the last->first edge
|
|
841
|
-
for (let i = 0; i < segCount; i++) {
|
|
842
|
-
const j = (i + 1) % n;
|
|
843
|
-
const a = this.toPx(xs[i], ys[i]);
|
|
844
|
-
const c = this.toPx(xs[j], ys[j]);
|
|
845
|
-
const d = this.distToSegmentPx(position, a, c);
|
|
846
|
-
if (d < bestDist) {
|
|
847
|
-
bestDist = d;
|
|
848
|
-
best = i;
|
|
849
|
-
bestRing = ring;
|
|
850
|
-
}
|
|
851
|
-
}
|
|
852
|
-
};
|
|
853
|
-
scan(b.xpoints, b.ypoints, -1, b.closed !== false);
|
|
854
|
-
if (b.holes) {
|
|
855
|
-
b.holes.forEach((r, h) => scan(r.map(p => p[0]), r.map(p => p[1]), h, true));
|
|
856
|
-
}
|
|
857
|
-
if (best < 0 || bestDist > EDIT_TOL)
|
|
539
|
+
const edge = nearestEdge(region, position.x, position.y, this.toScreen);
|
|
540
|
+
if (!edge || edge.dist > EDIT_TOL_PX)
|
|
858
541
|
return null;
|
|
859
542
|
const img = this.toImage(position);
|
|
860
|
-
return { ring:
|
|
861
|
-
}
|
|
862
|
-
/** Classify a screen point against a screen-space rectangle into a zone. */
|
|
863
|
-
rectZone(px, py, x0, y0, x1, y1) {
|
|
864
|
-
const t = EDIT_TOL;
|
|
865
|
-
if (px < x0 - t || px > x1 + t || py < y0 - t || py > y1 + t)
|
|
866
|
-
return null;
|
|
867
|
-
const left = Math.abs(px - x0) <= t, right = Math.abs(px - x1) <= t;
|
|
868
|
-
const top = Math.abs(py - y0) <= t, bottom = Math.abs(py - y1) <= t;
|
|
869
|
-
if (top && left)
|
|
870
|
-
return 'nw';
|
|
871
|
-
if (top && right)
|
|
872
|
-
return 'ne';
|
|
873
|
-
if (bottom && left)
|
|
874
|
-
return 'sw';
|
|
875
|
-
if (bottom && right)
|
|
876
|
-
return 'se';
|
|
877
|
-
if (left)
|
|
878
|
-
return 'w';
|
|
879
|
-
if (right)
|
|
880
|
-
return 'e';
|
|
881
|
-
if (top)
|
|
882
|
-
return 'n';
|
|
883
|
-
if (bottom)
|
|
884
|
-
return 's';
|
|
885
|
-
if (px > x0 && px < x1 && py > y0 && py < y1)
|
|
886
|
-
return 'move';
|
|
887
|
-
return null;
|
|
543
|
+
return { ring: edge.ring, segIndex: edge.segIndex, x: img.x, y: img.y };
|
|
888
544
|
}
|
|
889
545
|
/** Snapshot the selected region's geometry at the start of an edit. */
|
|
890
546
|
snapshot(region) {
|
|
891
547
|
const b = region.bounds;
|
|
548
|
+
if (b instanceof Polygon || b instanceof MultiPolygon)
|
|
549
|
+
return { kind: 'shape', bounds: b };
|
|
892
550
|
if (b instanceof Rectangle)
|
|
893
551
|
return { kind: 'rect', x: b.x, y: b.y, w: b.width, h: b.height };
|
|
894
|
-
if (b instanceof Polygon) {
|
|
895
|
-
return {
|
|
896
|
-
kind: 'poly', xs: b.xpoints.slice(), ys: b.ypoints.slice(), closed: b.closed !== false,
|
|
897
|
-
bezier: b.bezier,
|
|
898
|
-
inOff: b.handlesIn?.map(o => o.slice()),
|
|
899
|
-
outOff: b.handlesOut?.map(o => o.slice()),
|
|
900
|
-
holes: b.holes?.map(ring => ring.map(pt => pt.slice())),
|
|
901
|
-
};
|
|
902
|
-
}
|
|
903
|
-
if (b instanceof MultiPolygon) {
|
|
904
|
-
return {
|
|
905
|
-
kind: 'multi',
|
|
906
|
-
polygons: b.polygons.map((p) => ({
|
|
907
|
-
xs: p.xpoints.slice(), ys: p.ypoints.slice(), closed: p.closed !== false,
|
|
908
|
-
holes: p.holes?.map(ring => ring.map(pt => pt.slice())),
|
|
909
|
-
})),
|
|
910
|
-
};
|
|
911
|
-
}
|
|
912
552
|
return { kind: 'rect', x: 0, y: 0, w: 0, h: 0 };
|
|
913
553
|
}
|
|
914
554
|
/**
|
|
@@ -945,91 +585,16 @@ export class OsdRegionOverlay {
|
|
|
945
585
|
const dx = curImg.x - this.edit.startImg.x;
|
|
946
586
|
const dy = curImg.y - this.edit.startImg.y;
|
|
947
587
|
const o = this.edit.orig;
|
|
588
|
+
if (!o)
|
|
589
|
+
return;
|
|
948
590
|
if (o.kind === 'rect') {
|
|
949
|
-
|
|
950
|
-
|
|
951
|
-
case 'move':
|
|
952
|
-
x0 += dx;
|
|
953
|
-
x1 += dx;
|
|
954
|
-
y0 += dy;
|
|
955
|
-
y1 += dy;
|
|
956
|
-
break;
|
|
957
|
-
case 'w':
|
|
958
|
-
x0 += dx;
|
|
959
|
-
break;
|
|
960
|
-
case 'e':
|
|
961
|
-
x1 += dx;
|
|
962
|
-
break;
|
|
963
|
-
case 'n':
|
|
964
|
-
y0 += dy;
|
|
965
|
-
break;
|
|
966
|
-
case 's':
|
|
967
|
-
y1 += dy;
|
|
968
|
-
break;
|
|
969
|
-
case 'nw':
|
|
970
|
-
x0 += dx;
|
|
971
|
-
y0 += dy;
|
|
972
|
-
break;
|
|
973
|
-
case 'ne':
|
|
974
|
-
x1 += dx;
|
|
975
|
-
y0 += dy;
|
|
976
|
-
break;
|
|
977
|
-
case 'sw':
|
|
978
|
-
x0 += dx;
|
|
979
|
-
y1 += dy;
|
|
980
|
-
break;
|
|
981
|
-
case 'se':
|
|
982
|
-
x1 += dx;
|
|
983
|
-
y1 += dy;
|
|
984
|
-
break;
|
|
985
|
-
}
|
|
986
|
-
const rect = new Rectangle();
|
|
987
|
-
rect.x = Math.round(Math.min(x0, x1));
|
|
988
|
-
rect.y = Math.round(Math.min(y0, y1));
|
|
989
|
-
rect.width = Math.round(Math.abs(x1 - x0));
|
|
990
|
-
rect.height = Math.round(Math.abs(y1 - y0));
|
|
991
|
-
this.store.updateBounds(this.edit.id, rect);
|
|
992
|
-
}
|
|
993
|
-
else if (o.kind === 'multi') {
|
|
994
|
-
// Multi-part region: translate every part (and its holes) by the delta.
|
|
995
|
-
const mp = new MultiPolygon();
|
|
996
|
-
mp.polygons = o.polygons.map((pp) => {
|
|
997
|
-
const xs = pp.xs.map((x) => Math.round(x + dx));
|
|
998
|
-
const ys = pp.ys.map((y) => Math.round(y + dy));
|
|
999
|
-
const poly = new Polygon();
|
|
1000
|
-
poly.npoints = xs.length;
|
|
1001
|
-
poly.xpoints = xs;
|
|
1002
|
-
poly.ypoints = ys;
|
|
1003
|
-
poly.coordinates = xs.map((x, i) => [x, ys[i]]);
|
|
1004
|
-
poly.closed = pp.closed;
|
|
1005
|
-
if (pp.holes) {
|
|
1006
|
-
poly.holes = pp.holes.map((ring) => ring.map(([x, y]) => [Math.round(x + dx), Math.round(y + dy)]));
|
|
1007
|
-
}
|
|
1008
|
-
return poly;
|
|
1009
|
-
});
|
|
1010
|
-
this.store.updateBounds(this.edit.id, mp);
|
|
591
|
+
const box = resizeRect({ x: o.x, y: o.y, width: o.w, height: o.h }, this.edit.zone, dx, dy);
|
|
592
|
+
this.store.updateBounds(this.edit.id, Object.assign(new Rectangle(), box));
|
|
1011
593
|
}
|
|
1012
594
|
else {
|
|
1013
|
-
// Polygon: translate every vertex
|
|
1014
|
-
//
|
|
1015
|
-
|
|
1016
|
-
const ys = o.ys.map((y) => Math.round(y + dy));
|
|
1017
|
-
const poly = new Polygon();
|
|
1018
|
-
poly.npoints = xs.length;
|
|
1019
|
-
poly.xpoints = xs;
|
|
1020
|
-
poly.ypoints = ys;
|
|
1021
|
-
poly.coordinates = xs.map((x, i) => [x, ys[i]]);
|
|
1022
|
-
poly.closed = o.closed;
|
|
1023
|
-
poly.bezier = o.bezier;
|
|
1024
|
-
if (o.inOff)
|
|
1025
|
-
poly.handlesIn = o.inOff.map((off) => off.slice());
|
|
1026
|
-
if (o.outOff)
|
|
1027
|
-
poly.handlesOut = o.outOff.map((off) => off.slice());
|
|
1028
|
-
// Translate interior rings (holes) with the exterior (jit-ui#85).
|
|
1029
|
-
if (o.holes) {
|
|
1030
|
-
poly.holes = o.holes.map((ring) => ring.map(([x, y]) => [Math.round(x + dx), Math.round(y + dy)]));
|
|
1031
|
-
}
|
|
1032
|
-
this.store.updateBounds(this.edit.id, poly);
|
|
595
|
+
// Polygon / multi-part region: translate every vertex, hole and part, rounded to
|
|
596
|
+
// whole pixels. Bezier handle offsets are relative, so they carry over unchanged.
|
|
597
|
+
this.store.updateBounds(this.edit.id, translateBounds(o.bounds, dx, dy, Math.round));
|
|
1033
598
|
}
|
|
1034
599
|
this.redraw();
|
|
1035
600
|
}
|
|
@@ -1052,114 +617,22 @@ export class OsdRegionOverlay {
|
|
|
1052
617
|
}
|
|
1053
618
|
this.store.setSelectedShapeIndices(idx >= 0 ? [idx] : []);
|
|
1054
619
|
}
|
|
1055
|
-
/**
|
|
1056
|
-
* rectangle [x0,y0]–[x1,y1] (rubber-band multi-select). */
|
|
1057
|
-
regionsInRect(x0, y0, x1, y1) {
|
|
1058
|
-
const out = [];
|
|
1059
|
-
this.store.getRegions().forEach((r, i) => {
|
|
1060
|
-
const bb = this.regionBBox(r);
|
|
1061
|
-
if (bb && bb.x0 <= x1 && bb.x1 >= x0 && bb.y0 <= y1 && bb.y1 >= y0)
|
|
1062
|
-
out.push(i);
|
|
1063
|
-
});
|
|
1064
|
-
return out;
|
|
1065
|
-
}
|
|
1066
|
-
/** Axis-aligned bounding box of a region in image coords, or null if empty. */
|
|
1067
|
-
regionBBox(r) {
|
|
1068
|
-
const b = r.bounds;
|
|
1069
|
-
if (b instanceof Rectangle) {
|
|
1070
|
-
return { x0: b.x, y0: b.y, x1: b.x + b.width, y1: b.y + b.height };
|
|
1071
|
-
}
|
|
1072
|
-
if (b instanceof Polygon && b.xpoints.length) {
|
|
1073
|
-
return {
|
|
1074
|
-
x0: Math.min(...b.xpoints), y0: Math.min(...b.ypoints),
|
|
1075
|
-
x1: Math.max(...b.xpoints), y1: Math.max(...b.ypoints),
|
|
1076
|
-
};
|
|
1077
|
-
}
|
|
1078
|
-
if (b instanceof MultiPolygon) {
|
|
1079
|
-
let x0 = Infinity, y0 = Infinity, x1 = -Infinity, y1 = -Infinity;
|
|
1080
|
-
for (const p of b.polygons) {
|
|
1081
|
-
for (let i = 0; i < p.xpoints.length; i++) {
|
|
1082
|
-
if (p.xpoints[i] < x0)
|
|
1083
|
-
x0 = p.xpoints[i];
|
|
1084
|
-
if (p.xpoints[i] > x1)
|
|
1085
|
-
x1 = p.xpoints[i];
|
|
1086
|
-
if (p.ypoints[i] < y0)
|
|
1087
|
-
y0 = p.ypoints[i];
|
|
1088
|
-
if (p.ypoints[i] > y1)
|
|
1089
|
-
y1 = p.ypoints[i];
|
|
1090
|
-
}
|
|
1091
|
-
}
|
|
1092
|
-
return x1 >= x0 ? { x0, y0, x1, y1 } : null;
|
|
1093
|
-
}
|
|
1094
|
-
return null;
|
|
1095
|
-
}
|
|
1096
|
-
/** Index of the topmost region under a point, or -1. */
|
|
620
|
+
/** Index of the topmost region under an image point, or -1. */
|
|
1097
621
|
regionIndexAt(pt) {
|
|
1098
|
-
const
|
|
1099
|
-
|
|
1100
|
-
if (this.containsPoint(regions[i], pt))
|
|
1101
|
-
return i;
|
|
1102
|
-
}
|
|
1103
|
-
return -1;
|
|
622
|
+
const opts = { toScreen: this.toScreen, tolPx: OPEN_PATH_TOL_PX };
|
|
623
|
+
return topmostRegionAt(this.store.getRegions(), pt.x, pt.y, opts);
|
|
1104
624
|
}
|
|
1105
|
-
|
|
1106
|
-
|
|
1107
|
-
|
|
1108
|
-
|
|
1109
|
-
}
|
|
1110
|
-
// Multi-part region: inside any part (exterior minus that part's holes).
|
|
1111
|
-
if (b instanceof MultiPolygon) {
|
|
1112
|
-
return b.polygons.some((p) => this.closedPolygonContains(p, pt));
|
|
1113
|
-
}
|
|
1114
|
-
if (b instanceof Polygon) {
|
|
1115
|
-
if (b.closed !== false)
|
|
1116
|
-
return this.closedPolygonContains(b, pt);
|
|
1117
|
-
// Open polyline: no interior — select when the click lands near the line.
|
|
1118
|
-
// Tolerance is in screen pixels so it stays clickable at any zoom.
|
|
1119
|
-
const xs = b.xpoints, ys = b.ypoints, n = xs.length, tolPx = 6;
|
|
1120
|
-
const here = this.toPx(pt.x, pt.y);
|
|
1121
|
-
for (let i = 0; i + 1 < n; i++) {
|
|
1122
|
-
const a = this.toPx(xs[i], ys[i]);
|
|
1123
|
-
const c = this.toPx(xs[i + 1], ys[i + 1]);
|
|
1124
|
-
if (this.distToSegmentPx(here, a, c) <= tolPx)
|
|
1125
|
-
return true;
|
|
1126
|
-
}
|
|
1127
|
-
return false;
|
|
1128
|
-
}
|
|
1129
|
-
return false;
|
|
625
|
+
/** Whether the element-pixel `position` lands on `region` (see `regionContains`). */
|
|
626
|
+
containsPoint(region, position) {
|
|
627
|
+
const pt = this.toWorld(position);
|
|
628
|
+
return regionContains(region, pt.x, pt.y, { toScreen: this.toScreen, tolPx: OPEN_PATH_TOL_PX });
|
|
1130
629
|
}
|
|
1131
|
-
/**
|
|
1132
|
-
*
|
|
1133
|
-
|
|
1134
|
-
|
|
1135
|
-
|
|
1136
|
-
|
|
1137
|
-
const intersect = ((rys[i] > pt.y) !== (rys[j] > pt.y))
|
|
1138
|
-
&& (pt.x < ((rxs[j] - rxs[i]) * (pt.y - rys[i])) / (rys[j] - rys[i]) + rxs[i]);
|
|
1139
|
-
if (intersect)
|
|
1140
|
-
hit = !hit;
|
|
1141
|
-
}
|
|
1142
|
-
return hit;
|
|
1143
|
-
};
|
|
1144
|
-
if (!inRing(b.xpoints, b.ypoints))
|
|
1145
|
-
return false;
|
|
1146
|
-
if (b.holes) {
|
|
1147
|
-
for (const ring of b.holes) {
|
|
1148
|
-
if (inRing(ring.map(p => p[0]), ring.map(p => p[1])))
|
|
1149
|
-
return false;
|
|
1150
|
-
}
|
|
1151
|
-
}
|
|
1152
|
-
return true;
|
|
1153
|
-
}
|
|
1154
|
-
/** Shortest distance from point p to segment a–b, all in screen pixels. */
|
|
1155
|
-
distToSegmentPx(p, a, b) {
|
|
1156
|
-
const dx = b.x - a.x, dy = b.y - a.y;
|
|
1157
|
-
const len2 = dx * dx + dy * dy;
|
|
1158
|
-
if (len2 === 0)
|
|
1159
|
-
return Math.hypot(p.x - a.x, p.y - a.y);
|
|
1160
|
-
let t = ((p.x - a.x) * dx + (p.y - a.y) * dy) / len2;
|
|
1161
|
-
t = Math.max(0, Math.min(1, t));
|
|
1162
|
-
return Math.hypot(p.x - (a.x + t * dx), p.y - (a.y + t * dy));
|
|
630
|
+
/** Abandon whatever pointer gesture is in progress (drawing, edit drag,
|
|
631
|
+
* rubber band) and close its store batch. */
|
|
632
|
+
endGesture() {
|
|
633
|
+
this.resetInProgress();
|
|
634
|
+
this.bandStart = this.bandCurrent = null;
|
|
635
|
+
this.bandDragged = false;
|
|
1163
636
|
}
|
|
1164
637
|
resetInProgress() {
|
|
1165
638
|
this.rectStart = this.rectCurrent = null;
|
|
@@ -1192,13 +665,7 @@ export class OsdRegionOverlay {
|
|
|
1192
665
|
return;
|
|
1193
666
|
}
|
|
1194
667
|
const region = new Region();
|
|
1195
|
-
|
|
1196
|
-
poly.npoints = this.polyPoints.length;
|
|
1197
|
-
poly.xpoints = this.polyPoints.map(p => p.x);
|
|
1198
|
-
poly.ypoints = this.polyPoints.map(p => p.y);
|
|
1199
|
-
poly.coordinates = this.polyPoints.map(p => [p.x, p.y]);
|
|
1200
|
-
poly.closed = closed;
|
|
1201
|
-
region.bounds = poly;
|
|
668
|
+
region.bounds = makePolygon(this.polyPoints.map((p) => p.x), this.polyPoints.map((p) => p.y), { closed });
|
|
1202
669
|
region.color = this.store.getShapeColor();
|
|
1203
670
|
this.resetInProgress();
|
|
1204
671
|
this.commitRegion(region);
|
|
@@ -1233,4 +700,4 @@ export class OsdRegionOverlay {
|
|
|
1233
700
|
this.redraw();
|
|
1234
701
|
}
|
|
1235
702
|
}
|
|
1236
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoib3NkLXJlZ2lvbi1vdmVybGF5LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vc3JjL2xpYi9pbXBsZW1lbnRhdGlvbnMvb3NkL29zZC1yZWdpb24tb3ZlcmxheS50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQSxPQUFPLEVBQUUsR0FBRyxFQUFFLE1BQU0sV0FBVyxDQUFDO0FBQ2hDLE9BQU8sRUFBRSxZQUFZLEVBQUUsTUFBTSxNQUFNLENBQUM7QUFFcEMsT0FBTyxFQUFFLE1BQU0sRUFBRSxTQUFTLEVBQUUsT0FBTyxFQUFFLFlBQVksRUFBRSxNQUFNLHFCQUFxQixDQUFDO0FBQy9FLE9BQU8sRUFBRSxjQUFjLEVBQUUsTUFBTSxxQkFBcUIsQ0FBQztBQUlyRCxPQUFPLEVBQUUsY0FBYyxFQUFFLGNBQWMsRUFBRSxNQUFNLGNBQWMsQ0FBQztBQUM5RCxPQUFPLEVBQUUsbUJBQW1CLEVBQUUsTUFBTSxZQUFZLENBQUM7QUFZakQsTUFBTSxLQUFLLEdBQUcsNEJBQTRCLENBQUM7QUFJM0MsTUFBTSxXQUFXLEdBQTZCO0lBQzVDLElBQUksRUFBRSxNQUFNLEVBQUUsQ0FBQyxFQUFFLFdBQVcsRUFBRSxDQUFDLEVBQUUsV0FBVyxFQUFFLENBQUMsRUFBRSxXQUFXLEVBQUUsQ0FBQyxFQUFFLFdBQVc7SUFDNUUsRUFBRSxFQUFFLGFBQWEsRUFBRSxFQUFFLEVBQUUsYUFBYSxFQUFFLEVBQUUsRUFBRSxhQUFhLEVBQUUsRUFBRSxFQUFFLGFBQWE7Q0FDM0UsQ0FBQztBQUNGLGlFQUFpRTtBQUNqRSxNQUFNLFFBQVEsR0FBRyxDQUFDLENBQUM7QUFHbkI7Ozs7Ozs7Ozs7Ozs7R0FhRztBQUNILE1BQU0sT0FBTyxnQkFBZ0I7SUE2QzNCLFlBQW9CLE1BQVcsRUFBVSxLQUFzQjtRQUEzQyxXQUFNLEdBQU4sTUFBTSxDQUFLO1FBQVUsVUFBSyxHQUFMLEtBQUssQ0FBaUI7UUExQzlDLFNBQUksR0FBRyxJQUFJLFlBQVksRUFB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QUFPLEdBQUcsQ0FBQyxDQUFDLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxJQUFJLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FBQztRQUNsSCxFQUFFLENBQUMsWUFBWSxDQUFDLE1BQU0sRUFBRSx3QkFBd0IsQ0FBQyxDQUFDO1FBQ2xELEVBQUUsQ0FBQyxZQUFZLENBQUMsUUFBUSxFQUFFLFNBQVMsQ0FBQyxDQUFDO1FBQ3JDLEVBQUUsQ0FBQyxZQUFZLENBQUMsa0JBQWtCLEVBQUUsS0FBSyxDQUFDLENBQUM7UUFDM0MsRUFBRSxDQUFDLFlBQVksQ0FBQyxjQUFjLEVBQUUsR0FBRyxDQUFDLENBQUM7UUFDckMsT0FBTyxFQUFFLENBQUM7SUFDWixDQUFDO0lBRU8sV0FBVyxDQUFDLENBQTJCLEVBQUUsQ0FBMkI7UUFDMUUsTUFBTSxPQUFPLEdBQUc7WUFDZCxFQUFFLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxFQUFFLEVBQUUsRUFBRSxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsRUFBRSxFQUFFLEVBQUUsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLEVBQUUsRUFBRSxFQUFFLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxFQUFFO1NBQy9FLENBQUM7UUFDRixNQUFNLEVBQUUsR0FBRyxRQUFRLENBQUMsZUFBZSxDQUFDLEtBQUssRUFBRSxTQUFTLENBQUMsQ0FBQztRQUN0RCxFQUFFLENBQUMsWUFBWSxDQUFDLFFBQVEsRUFBRSxPQUFPLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FBQyxFQUFFLEdBQUcsTUFBTSxDQUFDLEdBQUcsSUFBSSxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLENB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LENBQUMsQ0FBQyxDQUFDLEVBQUUsRUFBRSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxFQUFFLEtBQUssRUFBRSxNQUFNLEVBQUUsSUFBSSxDQUFDLENBQUM7WUFDbkcsQ0FBQyxDQUFDLENBQUM7UUFDTCxDQUFDO0lBQ0gsQ0FBQztJQUVELGtGQUFrRjtJQUMxRSxVQUFVLENBQUMsTUFBZ0MsRUFBRSxJQUE4QixFQUFFLEtBQWE7UUFDaEcsTUFBTSxJQUFJLEdBQUcsUUFBUSxDQUFDLGVBQWUsQ0FBQyxLQUFLLEVBQUUsTUFBTSxDQUFDLENBQUM7UUFDckQsSUFBSSxDQUFDLFlBQVksQ0FBQyxJQUFJLEVBQUUsR0FBRyxNQUFNLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQztRQUFDLElBQUksQ0FBQyxZQUFZLENBQUMsSUFBSSxFQUFFLEdBQUcsTUFBTSxDQUFDLENBQUMsRUFBRSxDQUFDLENBQUM7UUFDL0UsSUFBSSxDQUFDLFlBQVksQ0FBQyxJQUFJLEVBQUUsR0FBRyxJQUFJLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQztRQUFDLElBQUksQ0FBQyxZQUFZLENBQUMsSUFBSSxFQUFFLEdBQUcsSUFBSSxDQUFDLENBQUMsRUFBRSxDQUFDLENBQUM7UUFDM0UsSUFBSSxDQUFDLFlBQVksQ0FBQyxRQUFRLEVBQUUsS0FBSyxDQUFDLENBQUM7UUFDbkMsSUFBSSxDQUFDLFlBQVksQ0FBQyxjQUFjLEVBQUUsR0FBRyxDQUFDLENBQUM7UUFDdkMsSUFBSSxDQUFDLEdBQUcsQ0FBQyxXQUFXLENBQUMsSUFBSSxDQUFDLENBQUM7UUFDM0IsTUFBTSxDQUFDLEdBQUcsUUFBUSxDQUFDLGVBQWUsQ0FBQyxLQUFLLEVBQUUsUUFBUSxDQUFDLENBQUM7UUFDcEQsQ0FBQyxDQUFDLFlBQVksQ0FBQyxJQUFJLEVBQUUsR0FBRyxJQUFJLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQztRQUFDLENBQUMsQ0FBQyxZQUFZLENBQUMsSUFBSSxFQUFFLEdBQUcsSUFBSSxDQUFDLENBQUMsRUFBRSxDQUFDLENBQUM7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MUIsS0FBSyxHQUFHO29CQUFFLEVBQUUsSUFBSSxFQUFFLENBQUM7b0JBQUMsTUFBTTtnQkFDMUIsS0FBSyxHQUFHO29CQUFFLEVBQUUsSUFBSSxFQUFFLENBQUM7b0JBQUMsTUFBTTtnQkFDMUIsS0FBSyxHQUFHO29CQUFFLEVBQUUsSUFBSSxFQUFFLENBQUM7b0JBQUMsTUFBTTtnQkFDMUIsS0FBSyxJQUFJO29CQUFFLEVBQUUsSUFBSSxFQUFFLENBQUM7b0JBQUMsRUFBRSxJQUFJLEVBQUUsQ0FBQztvQkFBQyxNQUFNO2dCQUNyQyxLQUFLLElBQUk7b0JBQUUsRUFBRSxJQUFJLEVBQUUsQ0FBQztvQkFBQyxFQUFFLElBQUksRUFBRSxDQUFDO29CQUFDLE1BQU07Z0JBQ3JDLEtBQUssSUFBSTtvQkFBRSxFQUFFLElBQUksRUFBRSxDQUFDO29CQUFDLEVBQUUsSUFBSSxFQUFFLENBQUM7b0JBQUMsTUFBTTtnQkFDckMsS0FBSyxJQUFJO29CQUFFLEVBQUUsSUFBSSxFQUFFLENBQUM7b0JBQUMsRUFBRSxJQUFJLEVBQUUsQ0FBQztvQkFBQyxNQUFNO1lBQ3ZDLENBQUM7WUFDRCxNQUFNLElBQUksR0FBRyxJQUFJLFNBQVMsRUFBRSxDQUFDO1lBQzdCLElBQUksQ0FBQyxDQUFDLEdBQUcsSUFBSSxDQUFDLEtBQUssQ0FBQyxJQUFJLENBQUMsR0FBRyxDQUFDLEVBQUUsRUFBRSxFQUFFLENBQUMsQ0FBQyxDQUFDO1lBQ3RDLElBQUksQ0FBQyxDQUFDLEdBQUcsSUFBSSxDQUFDLEtBQUssQ0FBQyxJQUFJLENBQUMsR0FBRyxDQUFDLEVBQUUsRUFBRSxFQUFFLENBQUMsQ0FBQyxDQUFDO1lBQ3RDLElBQUksQ0FBQyxLQUFLLEdBQUcsSUFBSSxDQUFDLEtBQUssQ0FBQyxJQUFJLENBQUMsR0FBRyxDQUFDLEVBQUUsR0FBRyxFQUFFLENBQUMsQ0FBQyxDQUFDO1lBQzNDLElBQUksQ0FBQyxNQUFNLEdBQUcsSUFBSSxDQUFDLEtBQUssQ0FBQyxJQUFJLENBQUMsR0FBRyxDQUFDLEVBQUUsR0FBRyxFQUFFLENBQUMsQ0FBQyxDQUFDO1lBQzVDLElBQUksQ0FBQyxLQUFLLENBQUMsWUFBWSxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUMsRUFBRSxFQUFFLElBQUksQ0FBQyxDQUFDO1FBQzlDLENBQUM7YUFBTSxJQUFJLENBQUMsQ0FBQyxJQUFJLEtBQUssT0FBTyxFQUFFLENBQUM7WUFDOUIsd0VBQXdFO1lBQ3hFLE1BQU0sRUFBRSxHQUFHLElBQUksWUFBWSxFQUFFLENBQUM7WUFDOUIsRUFBRSxDQUFDLFFBQVEsR0FBRyxDQUFDLENBQUMsUUFBUSxDQUFDLEdBQUcsQ0FBQyxDQUFDLEVBQU8sRUFBRSxFQUFFO2dCQUN2QyxNQUFNLEVBQUUsR0FBRyxFQUFFLENBQUMsRUFBRSxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQVMsRUFBRSxFQUFFLENBQUMsSUFBSSxDQUFDLEtBQUssQ0FBQyxDQUFDLEdBQUcsRUFBRSxDQUFDLENBQUMsQ0FBQztnQkFDeEQsTUFBTSxFQUFFLEdBQUcsRUFBRSxDQUFDLEVBQUUsQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFTLEVBQUUsRUFBRSxDQUFDLElBQUksQ0FBQyxLQUFLLENBQUMsQ0FBQyxHQUFHLEVBQUUsQ0FBQyxDQUFDLENBQUM7Z0JBQ3hELE1BQU0sSUFBSSxHQUFHLElBQUksT0FBTyxFQUFFLENBQUM7Z0JBQzNCLElBQUksQ0FBQyxPQUFPLEdBQUcsRUFBRSxDQUFDLE1BQU0sQ0FBQztnQkFDekIsSUFBSSxDQUFDLE9BQU8sR0FBRyxFQUFFLENBQUM7Z0JBQ2xCLElBQUksQ0FBQyxPQUFPLEdBQUcsRUFBRSxDQUFDO2dCQUNsQixJQUFJLENBQUMsV0FBVyxHQUFHLEVBQUUsQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFTLEVBQUUsQ0FBUyxFQUFFLEVBQUUsQ0FBQyxDQUFDLENBQUMsRUFBRSxFQUFFLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDO2dCQUNoRSxJQUFJLENBQUMsTUFBTSxHQUFHLEVBQUUsQ0FBQyxNQUFNLENBQUM7Z0JBQ3hCLElBQUksRUFBRSxDQUFDLEtBQUssRUFBRSxDQUFDO29CQUNiLElBQUksQ0FBQyxLQUFLLEdBQUcsRUFBRSxDQUFDLEtBQUssQ0FBQyxHQUFHLENBQUMsQ0FBQyxJQUFnQixFQUFFLEVBQUUsQ0FDN0MsSUFBSSxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBVyxFQUFFLEVBQUUsQ0FBQyxDQUFDLElBQUksQ0FBQyxLQUFLLENBQUMsQ0FBQyxHQUFHLEVBQUUsQ0FBQyxFQUFFLElBQUksQ0FBQyxLQUFLLENBQUMsQ0FBQyxHQUFHLEVBQUUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDO2dCQUM5RSxDQUFDO2dCQUNELE9BQU8sSUFBSSxDQUFDO1lBQ2QsQ0FBQyxDQUFDLENBQUM7WUFDSCxJQUFJLENBQUMsS0FBSyxDQUFDLFlBQVksQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLEVBQUUsRUFBRSxFQUFFLENBQUMsQ0FBQztRQUM1QyxDQUFDO2FBQU0sQ0FBQztZQUNOLDBFQUEwRTtZQUMxRSwyRUFBMkU7WUFDM0UsTUFBTSxFQUFFLEdBQUcsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFTLEVBQUUsRUFBRSxDQUFDLElBQUksQ0FBQyxLQUFLLENBQUMsQ0FBQyxHQUFHLEVBQUUsQ0FBQyxDQUFDLENBQUM7WUFDdkQsTUFBTSxFQUFFLEdBQUcsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFTLEVBQUUsRUFBRSxDQUFDLElBQUksQ0FBQyxLQUFLLENBQUMsQ0FBQyxHQUFHLEVBQUUsQ0FBQyxDQUFDLENBQUM7WUFDdkQsTUFBTSxJQUFJLEdBQUcsSUFBSSxPQUFPLEVBQUUsQ0FBQztZQUMzQixJQUFJLENBQUMsT0FBTyxHQUFHLEVBQUUsQ0FBQyxNQUFNLENBQUM7WUFDekIsSUFBSSxDQUFDLE9BQU8sR0FBRyxFQUFFLENBQUM7WUFDbEIsSUFBSSxDQUFDLE9BQU8sR0FBRyxFQUFFLENBQUM7WUFDbEIsSUFBSSxDQUFDLFdBQVcsR0FBRyxFQUFFLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FBUyxFQUFFLENBQVMsRUFBRSxFQUFFLENBQUMsQ0FBQyxDQUFDLEVBQUUsRUFBRSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQztZQUNoRSxJQUFJLENBQUMsTUFBTSxHQUFHLENBQUMsQ0FBQyxNQUFNLENBQUM7WUFDdkIsSUFBSSxDQUFDLE1BQU0sR0FBRyxDQUFDLENBQUMsTUFBTSxDQUFDO1lBQ3ZCLElBQUksQ0FBQyxDQUFDLEtBQUs7Z0JBQUUsSUFBSSxDQUFDLFNBQVMsR0FBRyxDQUFDLENBQUMsS0FBSyxDQUFDLEdBQUcsQ0FBQyxDQUFDLEdBQWEsRUFBRSxFQUFFLENBQUMsR0FBRyxDQUFDLEtBQUssRUFBRSxDQUFDLENBQUM7WUFDMUUsSUFBSSxDQUFDLENBQUMsTUFBTTtnQkFBRSxJQUFJLENBQUMsVUFBVSxHQUFHLENBQUMsQ0FBQyxNQUFNLENBQUMsR0FBRyxDQUFDLENBQUMsR0FBYSxFQUFFLEVBQUUsQ0FBQyxHQUFHLENBQUMsS0FBSyxFQUFFLENBQUMsQ0FBQztZQUM3RSxrRUFBa0U7WUFDbEUsSUFBSSxDQUFDLENBQUMsS0FBSyxFQUFFLENBQUM7Z0JBQ1osSUFBSSxDQUFDLEtBQUssR0FBRyxDQUFDLENBQUMsS0FBSyxDQUFDLEdBQUcsQ0FBQyxDQUFDLElBQWdCLEVBQUUsRUFBRSxDQUM1QyxJQUFJLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFXLEVBQUUsRUFBRSxDQUFDLENBQUMsSUFBSSxDQUFDLEtBQUssQ0FBQyxDQUFDLEdBQUcsRUFBRSxDQUFDLEVBQUUsSUFBSSxDQUFDLEtBQUssQ0FBQyxDQUFDLEdBQUcsRUFBRSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUM7WUFDOUUsQ0FBQztZQUNELElBQUksQ0FBQyxLQUFLLENBQUMsWUFBWSxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUMsRUFBRSxFQUFFLElBQUksQ0FBQyxDQUFDO1FBQzlDLENBQUM7UUFDRCxJQUFJLENBQUMsTUFBTSxFQUFFLENBQUM7SUFDaEIsQ0FBQztJQUVPLFFBQVEsQ0FBQyxFQUE0QixFQUFFLFFBQVEsR0FBRyxLQUFLO1FBQzdELE1BQU0sR0FBRyxHQUFHLElBQUksQ0FBQyxhQUFhLENBQUMsRUFBRSxDQUFDLENBQUM7UUFDbkMsSUFBSSxRQUFRLEVBQUUsQ0FBQztZQUNiLDBEQUEwRDtZQUMxRCxJQUFJLEdBQUcsR0FBRyxDQUFDO2dCQUFFLE9BQU87WUFDcEIsMEVBQTBFO1lBQzFFLHdFQUF3RTtZQUN4RSxNQUFNLEdBQUcsR0FBRyxJQUFJLENBQUMsUUFBUSxDQUFDLEtBQUssRUFBRSxDQUFDO1lBQ2xDLE1BQU0sRUFBRSxHQUFHLEdBQUcsQ0FBQyxPQUFPLENBQUMsR0FBRyxDQUFDLENBQUM7WUFDNUIsSUFBSSxFQUFFLElBQUksQ0FBQztnQkFBRSxHQUFHLENBQUMsTUFBTSxDQUFDLEVBQUUsRUFBRSxDQUFDLENBQUMsQ0FBQyxDQUFDLGFBQWE7O2dCQUN4QyxHQUFHLENBQUMsSUFBSSxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQWEsWUFBWTtZQUM1QyxJQUFJLENBQUMsS0FBSyxDQUFDLHVCQUF1QixDQUFDLEdBQUcsQ0FBQyxDQUFDO1lBQ3hDLE9BQU87UUFDVCxDQUFDO1FBQ0QsSUFBSSxDQUFDLEtBQUssQ0FBQyx1QkFBdUIsQ0FBQyxHQUFHLElBQUksQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQztJQUM1RCxDQUFDO0lBRUQ7Z0VBQzREO0lBQ3BELGFBQWEsQ0FBQyxFQUFVLEVBQUUsRUFBVSxFQUFFLEVBQVUsRUFBRSxFQUFVO1FBQ2xFLE1BQU0sR0FBRyxHQUFhLEVBQUUsQ0FBQztRQUN6QixJQUFJLENBQUMsS0FBSyxDQUFDLFVBQVUsRUFBRSxDQUFDLE9BQU8sQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLEVBQUUsRUFBRTtZQUN2QyxNQUFNLEVBQUUsR0FBRyxJQUFJLENBQUMsVUFBVSxDQUFDLENBQUMsQ0FBQyxDQUFDO1lBQzlCLElBQUksRUFBRSxJQUFJLEVBQUUsQ0FBQyxFQUFFLElBQUksRUFBRSxJQUFJLEVBQUUsQ0FBQyxFQUFFLElBQUksRUFBRSxJQUFJLEVBQUUsQ0FBQyxFQUFFLElBQUksRUFBRSxJQUFJLEVBQUUsQ0FBQyxFQUFFLElBQUksRUFBRTtnQkFBRSxHQUFHLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxDQUFDO1FBQ2xGLENBQUMsQ0FBQyxDQUFDO1FBQ0gsT0FBTyxHQUFHLENBQUM7SUFDYixDQUFDO0lBRUQsK0VBQStFO0lBQ3ZFLFVBQVUsQ0FBQyxDQUFTO1FBQzFCLE1BQU0sQ0FBQyxHQUFHLENBQUMsQ0FBQyxNQUFNLENBQUM7UUFDbkIsSUFBSSxDQUFDLFlBQVksU0FBUyxFQUFFLENBQUM7WUFDM0IsT0FBTyxFQUFFLEVBQUUsRUFBRSxDQUFDLENBQUMsQ0FBQyxFQUFFLEVBQUUsRUFBRSxDQUFDLENBQUMsQ0FBQyxFQUFFLEVBQUUsRUFBRSxDQUFDLENBQUMsQ0FBQyxHQUFHLENBQUMsQ0FBQyxLQUFLLEVBQUUsRUFBRSxFQUFFLENBQUMsQ0FBQyxDQUFDLEdBQUcsQ0FBQyxDQUFDLE1BQU0sRUFBRSxDQUFDO1FBQ3JFLENBQUM7UUFDRCxJQUFJLENBQUMsWUFBWSxPQUFPLElBQUksQ0FBQyxDQUFDLE9BQU8sQ0FBQyxNQUFNLEVBQUUsQ0FBQztZQUM3QyxPQUFPO2dCQUNMLEVBQUUsRUFBRSxJQUFJLENBQUMsR0FBRyxDQUFDLEdBQUcsQ0FBQyxDQUFDLE9BQU8sQ0FBQyxFQUFFLEVBQUUsRUFBRSxJQUFJLENBQUMsR0FBRyxDQUFDLEdBQUcsQ0FBQyxDQUFDLE9BQU8sQ0FBQztnQkFDdEQsRUFBRSxFQUFFLElBQUksQ0FBQyxHQUFHLENBQUMsR0FBRyxDQUFDLENBQUMsT0FBTyxDQUFDLEVBQUUsRUFBRSxFQUFFLElBQUksQ0FBQyxHQUFHLENBQUMsR0FBRyxDQUFDLENBQUMsT0FBTyxDQUFDO2FBQ3ZELENBQUM7UUFDSixDQUFDO1FBQ0QsSUFBSSxDQUFDLFlBQVksWUFBWSxFQUFFLENBQUM7WUFDOUIsSUFBSSxFQUFFLEdBQUcsUUFBUSxFQUFFLEVBQUUsR0FBRyxRQUFRLEVBQUUsRUFBRSxHQUFHLENBQUMsUUFBUSxFQUFFLEVBQUUsR0FBRyxDQUFDLFFBQVEsQ0FBQztZQUNqRSxLQUFLLE1BQU0sQ0FBQyxJQUFJLENBQUMsQ0FBQyxRQUFRLEVBQUUsQ0FBQztnQkFDM0IsS0FBSyxJQUFJLENBQUMsR0FBRyxDQUFDLEVBQUUsQ0FBQyxHQUFHLENBQUMsQ0FBQyxPQUFPLENBQUMsTUFBTSxFQUFFLENBQUMsRUFBRSxFQUFFLENBQUM7b0JBQzFDLElBQUksQ0FBQyxDQUFDLE9BQU8sQ0FBQyxDQUFDLENBQUMsR0FBRyxFQUFFO3dCQUFFLEVBQUUsR0FBRyxDQUFDLENBQUMsT0FBTyxDQUFDLENBQUMsQ0FBQyxDQUFDO29CQUN6QyxJQUFJLENBQUMsQ0FBQyxPQUFPLENBQUMsQ0FBQyxDQUFDLEdBQUcsRUFBRTt3QkFBRSxFQUFFLEdBQUcsQ0FBQyxDQUFDLE9BQU8sQ0FBQyxDQUFDLENBQUMsQ0FBQztvQkFDekMsSUFBSSxDQUFDLENBQUMsT0FBTyxDQUFDLENBQUMsQ0FBQyxHQUFHLEVBQUU7d0JBQUUsRUFBRSxHQUFHLENBQUMsQ0FBQyxPQUFPLENBQUMsQ0FBQyxDQUFDLENBQUM7b0JBQ3pDLElBQUksQ0FBQyxDQUFDLE9BQU8sQ0FBQyxDQUFDLENBQUMsR0FBRyxFQUFFO3dCQUFFLEVBQUUsR0FBRyxDQUFDLENBQUMsT0FBTyxDQUFDLENBQUMsQ0FBQyxDQUFDO2dCQUMzQyxDQUFDO1lBQ0gsQ0FBQztZQUNELE9BQU8sRUFBRSxJQUFJLEVBQUUsQ0FBQyxDQUFDLENBQUMsRUFBRSxFQUFFLEVBQUUsRUFBRSxFQUFFLEVBQUUsRUFBRSxFQUFFLEVBQUUsQ0FBQyxDQUFDLENBQUMsSUFBSSxDQUFDO1FBQzlDLENBQUM7UUFDRCxPQUFPLElBQUksQ0FBQztJQUNkLENBQUM7SUFFRCx3REFBd0Q7SUFDaEQsYUFBYSxDQUFDLEVBQTRCO1FBQ2hELE1BQU0sT0FBTyxHQUFHLElBQUksQ0FBQyxLQUFLLENBQUMsVUFBVSxFQUFFLENBQUM7UUFDeEMsS0FBSyxJQUFJLENBQUMsR0FBRyxPQUFPLENBQUMsTUFBTSxHQUFHLENBQUMsRUFBRSxDQUFDLElBQUksQ0FBQyxFQUFFLENBQUMsRUFBRSxFQUFFLENBQUM7WUFDN0MsSUFBSSxJQUFJLENBQUMsYUFBYSxDQUFDLE9BQU8sQ0FBQyxDQUFDLENBQUMsRUFBRSxFQUFFLENBQUM7Z0JBQUUsT0FBTyxDQUFDLENBQUM7UUFDbkQsQ0FBQztRQUNELE9BQU8sQ0FBQyxDQUFDLENBQUM7SUFDWixDQUFDO0lBRU8sYUFBYSxDQUFDLE1BQWMsRUFBRSxFQUE0QjtRQUNoRSxNQUFNLENBQUMsR0FBRyxNQUFNLENBQUMsTUFBTSxDQUFDO1FBQ3hCLElBQUksQ0FBQyxZQUFZLFNBQVMsRUFBRSxDQUFDO1lBQzNCLE9BQU8sRUFBRSxDQUFDLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxJQUFJLEVBQUUsQ0FBQyxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUMsR0FBRyxDQUFDLENBQUMsS0FBSyxJQUFJLEVBQUUsQ0FBQyxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUMsSUFBSSxFQUFFLENBQUMsQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFDLEdBQUcsQ0FBQyxDQUFDLE1BQU0sQ0FBQztRQUN2RixDQUFDO1FBQ0QseUVBQXlFO1FBQ3pFLElBQUksQ0FBQyxZQUFZLFlBQVksRUFBRSxDQUFDO1lBQzlCLE9BQU8sQ0FBQyxDQUFDLFFBQVEsQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFDLEVBQUUsRUFBRSxDQUFDLElBQUksQ0FBQyxxQkFBcUIsQ0FBQyxDQUFDLEVBQUUsRUFBRSxDQUFDLENBQUMsQ0FBQztRQUNuRSxDQUFDO1FBQ0QsSUFBSSxDQUFDLFlBQVksT0FBTyxFQUFFLENBQUM7WUFDekIsSUFBSSxDQUFDLENBQUMsTUFBTSxLQUFLLEtBQUs7Z0JBQUUsT0FBTyxJQUFJLENBQUMscUJBQXFCLENBQUMsQ0FBQyxFQUFFLEVBQUUsQ0FBQyxDQUFDO1lBQ2pFLDBFQUEwRTtZQUMxRSxtRUFBbUU7WUFDbkUsTUFBTSxFQUFFLEdBQUcsQ0FBQyxDQUFDLE9BQU8sRUFBRSxFQUFFLEdBQUcsQ0FBQyxDQUFDLE9BQU8sRUFBRSxDQUFDLEdBQUcsRUFBRSxDQUFDLE1BQU0sRUFBRSxLQUFLLEdBQUcsQ0FBQyxDQUFDO1lBQy9ELE1BQU0sSUFBSSxHQUFHLElBQUksQ0FBQyxJQUFJLENBQUMsRUFBRSxDQUFDLENBQUMsRUFBRSxFQUFFLENBQUMsQ0FBQyxDQUFDLENBQUM7WUFDbkMsS0FBSyxJQUFJLENBQUMsR0FBRyxDQUFDLEVBQUUsQ0FBQyxHQUFHLENBQUMsR0FBRyxDQUFDLEVBQUUsQ0FBQyxFQUFFLEVBQUUsQ0FBQztnQkFDL0IsTUFBTSxDQUFDLEdBQUcsSUFBSSxDQUFDLElBQUksQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLEVBQUUsRUFBRSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUM7Z0JBQ2xDLE1BQU0sQ0FBQyxHQUFHLElBQUksQ0FBQyxJQUFJLENBQUMsRUFBRSxDQUFDLENBQUMsR0FBRyxDQUFDLENBQUMsRUFBRSxFQUFFLENBQUMsQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDLENBQUM7Z0JBQzFDLElBQUksSUFBSSxDQUFDLGVBQWUsQ0FBQyxJQUFJLEVBQUUsQ0FBQyxFQUFFLENBQUMsQ0FBQyxJQUFJLEtBQUs7b0JBQUUsT0FBTyxJQUFJLENBQUM7WUFDN0QsQ0FBQztZQUNELE9BQU8sS0FBSyxDQUFDO1FBQ2YsQ0FBQztRQUNELE9BQU8sS0FBSyxDQUFDO0lBQ2YsQ0FBQztJQUVEO2lFQUM2RDtJQUNyRCxxQkFBcUIsQ0FBQyxDQUFVLEVBQUUsRUFBNEI7UUFDcEUsTUFBTSxNQUFNLEdBQUcsQ0FBQyxHQUFhLEVBQUUsR0FBYSxFQUFXLEVBQUU7WUFDdkQsSUFBSSxHQUFHLEdBQUcsS0FBSyxDQUFDO1lBQ2hCLEtBQUssSUFBSSxDQUFDLEdBQUcsQ0FBQyxFQUFFLENBQUMsR0FBRyxHQUFHLENBQUMsTUFBTSxHQUFHLENBQUMsRUFBRSxDQUFDLEdBQUcsR0FBRyxDQUFDLE1BQU0sRUFBRSxDQUFDLEdBQUcsQ0FBQyxFQUFFLEVBQUUsQ0FBQztnQkFDNUQsTUFBTSxTQUFTLEdBQUcsQ0FBQyxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsR0FBRyxFQUFFLENBQUMsQ0FBQyxDQUFDLEtBQUssQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDLEdBQUcsRUFBRSxDQUFDLENBQUMsQ0FBQyxDQUFDO3VCQUNsRCxDQUFDLEVBQUUsQ0FBQyxDQUFDLEdBQUcsQ0FBQyxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsR0FBRyxHQUFHLENBQUMsQ0FBQyxDQUFDLENBQUMsR0FBRyxDQUFDLEVBQUUsQ0FBQyxDQUFDLEdBQUcsR0FBRyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsR0FBRyxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsR0FBRyxHQUFHLENBQUMsQ0FBQyxDQUFDLENBQUMsR0FBRyxHQUFHLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQztnQkFDakYsSUFBSSxTQUFTO29CQUFFLEdBQUcsR0FBRyxDQUFDLEdBQUcsQ0FBQztZQUM1QixDQUFDO1lBQ0QsT0FBTyxHQUFHLENBQUM7UUFDYixDQUFDLENBQUM7UUFDRixJQUFJLENBQUMsTUFBTSxDQUFDLENBQUMsQ0FBQyxPQUFPLEVBQUUsQ0FBQyxDQUFDLE9BQU8sQ0FBQztZQUFFLE9BQU8sS0FBSyxDQUFDO1FBQ2hELElBQUksQ0FBQyxDQUFDLEtBQUssRUFBRSxDQUFDO1lBQ1osS0FBSyxNQUFNLElBQUksSUFBSSxDQUFDLENBQUMsS0FBSyxFQUFFLENBQUM7Z0JBQzNCLElBQUksTUFBTSxDQUFDLElBQUksQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsRUFBRSxJQUFJLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUM7b0JBQUUsT0FBTyxLQUFLLENBQUM7WUFDckUsQ0FBQztRQUNILENBQUM7UUFDRCxPQUFPLElBQUksQ0FBQztJQUNkLENBQUM7SUFFRCwyRUFBMkU7SUFDbkUsZUFBZSxDQUNyQixDQUEyQixFQUFFLENBQTJCLEVBQUUsQ0FBMkI7UUFFckYsTUFBTSxFQUFFLEdBQUcsQ0FBQyxDQUFDLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FBQyxFQUFFLEVBQUUsR0FBRyxDQUFDLENBQUMsQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDLENBQUM7UUFDckMsTUFBTSxJQUFJLEdBQUcsRUFBRSxHQUFHLEVBQUUsR0FBRyxFQUFFLEdBQUcsRUFBRSxDQUFDO1FBQy9CLElBQUksSUFBSSxLQUFLLENBQUM7WUFBRSxPQUFPLElBQUksQ0FBQyxLQUFLLENBQUMsQ0FBQyxDQUFDLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDO1FBQ3hELElBQUksQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDLENBQUMsR0FBRyxFQUFFLEdBQUcsQ0FBQyxDQUFDLENBQUMsQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDLENBQUMsR0FBRyxFQUFFLENBQUMsR0FBRyxJQUFJLENBQUM7UUFDckQsQ0FBQyxHQUFHLElBQUksQ0FBQyxHQUFHLENBQUMsQ0FBQyxFQUFFLElBQUksQ0FBQyxHQUFHLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLENBQUM7UUFDaEMsT0FBTyxJQUFJLENBQUMsS0FBSyxDQUFDLENBQUMsQ0FBQyxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsQ0FBQyxHQUFHLENBQUMsR0FBRyxFQUFFLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDLENBQUMsR0FBRyxDQUFDLEdBQUcsRUFBRSxDQUFDLENBQUMsQ0FBQztJQUNoRSxDQUFDO0lBRU8sZUFBZTtRQUNyQixJQUFJLENBQUMsU0FBUyxHQUFHLElBQUksQ0FBQyxXQUFXLEdBQUcsSUFBSSxDQUFDO1FBQ3pDLElBQUksQ0FBQyxVQUFVLEdBQUcsRUFBRSxDQUFDO1FBQ3JCLElBQUksQ0FBQyxnQkFBZ0IsR0FBRyxLQUFLLENBQUM7UUFDOUIsSUFBSSxDQUFDLGNBQWMsR0FBRyxLQUFLLENBQUM7UUFDNUIsSUFBSSxDQUFDLGNBQWMsR0FBRyxJQUFJLENBQUM7UUFDM0IseUVBQXlFO1FBQ3pFLHFDQUFxQztRQUNyQyxJQUFJLElBQUksQ0FBQyxJQUFJLEVBQUUsQ0FBQztZQUNkLElBQUksQ0FBQyxLQUFLLENBQUMsUUFBUSxFQUFFLENBQUM7WUFDdEIsSUFBSSxDQUFDLElBQUksR0FBRyxJQUFJLENBQUM7UUFDbkIsQ0FBQztJQUNILENBQUM7SUFFRCx3RUFBd0U7SUFDaEUsZUFBZSxDQUFDLENBQVMsRUFBRSxDQUFTLEVBQUUsQ0FBUyxFQUFFLENBQVM7UUFDaEUsTUFBTSxNQUFNLEdBQUcsSUFBSSxNQUFNLEVBQUUsQ0FBQztRQUM1QixNQUFNLElBQUksR0FBRyxJQUFJLFNBQVMsRUFBRSxDQUFDO1FBQzdCLElBQUksQ0FBQyxDQUFDLEdBQUcsQ0FBQyxDQUFDO1FBQUMsSUFBSSxDQUFDLENBQUMsR0FBRyxDQUFDLENBQUM7UUFBQyxJQUFJLENBQUMsS0FBSyxHQUFHLENBQUMsQ0FBQztRQUFDLElBQUksQ0FBQyxNQUFNLEdBQUcsQ0FBQyxDQUFDO1FBQ3hELE1BQU0sQ0FBQyxNQUFNLEdBQUcsSUFBSSxDQUFDO1FBQ3JCLE1BQU0sQ0FBQyxLQUFLLEdBQUcsSUFBSSxDQUFDLEtBQUssQ0FBQyxhQUFhLEVBQUUsQ0FBQztRQUMxQyxJQUFJLENBQUMsWUFBWSxDQUFDLE1BQU0sQ0FBQyxDQUFDO0lBQzVCLENBQUM7SUFFTyxhQUFhLENBQUMsTUFBZTtRQUNuQyxJQUFJLElBQUksQ0FBQyxVQUFVLENBQUMsTUFBTSxHQUFHLENBQUMsTUFBTSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUM7WUFBQyxJQUFJLENBQUMsZUFBZSxFQUFFLENBQUM7WUFBQyxPQUFPO1FBQUMsQ0FBQztRQUNsRixNQUFNLE1BQU0sR0FBRyxJQUFJLE1BQU0sRUFBRSxDQUFDO1FBQzVCLE1BQU0sSUFBSSxHQUFHLElBQUksT0FBTyxFQUFFLENBQUM7UUFDM0IsSUFBSSxDQUFDLE9BQU8sR0FBRyxJQUFJLENBQUMsVUFBVSxDQUFDLE1BQU0sQ0FBQztRQUN0QyxJQUFJLENBQUMsT0FBTyxHQUFHLElBQUksQ0FBQyxVQUFVLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDO1FBQzdDLElBQUksQ0FBQyxPQUFPLEdBQUcsSUFBSSxDQUFDLFVBQVUsQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUM7UUFDN0MsSUFBSSxDQUFDLFdBQVcsR0FBRyxJQUFJLENBQUMsVUFBVSxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQztRQUN4RCxJQUFJLENBQUMsTUFBTSxHQUFHLE1BQU0sQ0FBQztRQUNyQixNQUFNLENBQUMsTUFBTSxHQUFHLElBQUksQ0FBQztRQUNyQixNQUFNLENBQUMsS0FBSyxHQUFHLElBQUksQ0FBQyxLQUFLLENBQUMsYUFBYSxFQUFFLENBQUM7UUFDMUMsSUFBSSxDQUFDLGVBQWUsRUFBRSxDQUFDO1FBQ3ZCLElBQUksQ0FBQyxZQUFZLENBQUMsTUFBTSxDQUFDLENBQUM7SUFDNUIsQ0FBQztJQUVEOzs7Ozs7T0FNRztJQUNLLFlBQVksQ0FBQyxNQUFjO1FBQ2pDLDRFQUE0RTtRQUM1RSxvRUFBb0U7UUFDcEUsSUFBSSxNQUFNLENBQUMsS0FBSyxJQUFJLElBQUk7WUFBRSxNQUFNLENBQUMsS0FBSyxHQUFHLFFBQVEsQ0FBQztRQUNsRCxJQUFJLENBQUMsS0FBSyxDQUFDLFNBQVMsQ0FBQyxNQUFNLENBQUMsQ0FBQztRQUM3QixJQUFJLENBQUMsTUFBTSxFQUFFLENBQUM7SUFDaEIsQ0FBQztJQUVEOzs7O09BSUc7SUFDSCxpQkFBaUIsQ0FBQyxNQUFlO1FBQy9CLE1BQU0sT0FBTyxHQUFHLElBQUksQ0FBQyxLQUFLLENBQUMsVUFBVSxFQUFFLENBQUM7UUFDeEMsS0FBSyxNQUFNLEdBQUcsSUFBSSxJQUFJLENBQUMsUUFBUSxFQUFFLENBQUM7WUFDaEMsTUFBTSxNQUFNLEdBQUcsT0FBTyxDQUFDLEdBQUcsQ0FBQyxDQUFDO1lBQzVCLElBQUksTUFBTTtnQkFBRSxJQUFJLENBQUMsS0FBSyxDQUFDLFNBQVMsQ0FBQyxNQUFNLENBQUMsRUFBRSxFQUFFLE1BQU0sQ0FBQyxDQUFDO1FBQ3RELENBQUM7UUFDRCxJQUFJLENBQUMsTUFBTSxFQUFFLENBQUM7SUFDaEIsQ0FBQztDQUNGIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgT1NEIH0gZnJvbSAnLi9vc2QtbGliJztcbmltcG9ydCB7IFN1YnNjcmlwdGlvbiB9IGZyb20gJ3J4anMnO1xuXG5pbXBvcnQgeyBSZWdpb24sIFJlY3RhbmdsZSwgUG9seWdvbiwgTXVsdGlQb2x5Z29uIH0gZnJvbSAnLi4vLi4vbW9kZWxzL3JlZ2lvbic7XG5pbXBvcnQgeyByZXNvbHZlSGFuZGxlcyB9IGZyb20gJy4uLy4uL21vZGVscy9iZXppZXInO1xuaW1wb3J0IHsgSVJlZ2lvblN0b3JlIH0gZnJvbSAnLi4vLi4vY29udHJhY3RzL3Zpc3VhbGl6ZXIuY29udHJhY3QnO1xuaW1wb3J0IHsgSVJlZ2lvbkVkaXRBcGkgfSBmcm9tICcuLi8uLi9jb250cmFjdHMvcmVnaW9uLXN0b3JlLmNvbnRyYWN0JztcbmltcG9ydCB7IElSZWdpb25PdmVybGF5LCBSZWdpb25Ub29sTW9kZSB9IGZyb20gJy4uLy4uL2NvbnRyYWN0cy9yZWdpb24tb3ZlcmxheS5jb250cmFjdCc7XG5pbXBvcnQgeyBlbGVtZW50VG9JbWFnZSwgaW1hZ2VUb0VsZW1lbnQgfSBmcm9tICcuL29zZC1jb29yZHMnO1xuaW1wb3J0IHsgT1NEX1pPT01fUEVSX1NDUk9MTCB9IGZyb20gJy4vb3NkLXpvb20nO1xuXG4vKipcbiAqIFRoZSBzaGFyZWQgcmVnaW9uIHN0b3JlIGFzIHRoZSBvdmVybGF5IG5lZWRzIGl0OiB0aGUgY3Jvc3MtYmFja2VuZFxuICoge0BsaW5rIElSZWdpb25TdG9yZX0gKHJlYWQgcmVnaW9ucywgc2VsZWN0aW9uLCBjb2xvdXJzKSBwbHVzIHRoZSBSZWdpb24tbmF0aXZlXG4gKiB7QGxpbmsgSVJlZ2lvbkVkaXRBcGl9IChhZGQvbW92ZS9yZXNpemUvdmVydGV4IGVkaXRzKS4gVGhlIHNoYXJlZCBSZWdpb25TdG9yZVxuICogc2F0aXNmaWVzIGJvdGguIFRoZSBvdmVybGF5IGVkaXRzIHRocm91Z2ggdGhlc2UgdHlwZWQgb3BlcmF0aW9ucyBvbiB0aGVcbiAqIG5ldXRyYWwgUmVnaW9uIG1vZGVsIOKAlCBpdCBuZXZlciB0b3VjaGVzIGEgYmFja2VuZCdzIG93biBzaGFwZSByZXByZXNlbnRhdGlvblxuICogKGUuZy4gUGxvdGx5J3MgYHgwL3kwL3gxL3kxYCAvIGBN4oCmTOKAplpgIGRpY3RzKS5cbiAqL1xuZXhwb3J0IHR5cGUgUmVnaW9uRWRpdFN0b3JlID0gSVJlZ2lvblN0b3JlICYgSVJlZ2lvbkVkaXRBcGk7XG5cbmNvbnN0IFNWR05TID0gJ2h0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnJztcblxuLyoqIE1vdmUvcmVzaXplIHpvbmVzIG9uIHRoZSBzZWxlY3RlZCByZWN0YW5nbGUuICovXG50eXBlIEVkaXRab25lID0gJ21vdmUnIHwgJ24nIHwgJ3MnIHwgJ2UnIHwgJ3cnIHwgJ25lJyB8ICdudycgfCAnc2UnIHwgJ3N3JztcbmNvbnN0IFpPTkVfQ1VSU09SOiBSZWNvcmQ8RWRpdFpvbmUsIHN0cmluZz4gPSB7XG4gIG1vdmU6ICdtb3ZlJywgbjogJ25zLXJlc2l6ZScsIHM6ICducy1yZXNpemUnLCBlOiAnZXctcmVzaXplJywgdzogJ2V3LXJlc2l6ZScsXG4gIG5lOiAnbmVzdy1yZXNpemUnLCBzdzogJ25lc3ctcmVzaXplJywgbnc6ICdud3NlLXJlc2l6ZScsIHNlOiAnbndzZS1yZXNpemUnLFxufTtcbi8qKiBTY3JlZW4tcGl4ZWwgdG9sZXJhbmNlIGZvciBncmFiYmluZyBhbiBlZGdlL2Nvcm5lciBoYW5kbGUuICovXG5jb25zdCBFRElUX1RPTCA9IDg7XG5cblxuLyoqXG4gKiBPcGVuU2VhZHJhZ29uIGltcGxlbWVudGF0aW9uIG9mIHtAbGluayBJUmVnaW9uT3ZlcmxheX0uXG4gKlxuICogLSBSZW5kZXJzIHRoZSBzdG9yZSdzIHJlZ2lvbnMgKHJlY3QvcG9seWdvbikgaW4gaW1hZ2UtcGl4ZWwgc3BhY2UsIGtlcHRcbiAqICAgYWxpZ25lZCBvbiBldmVyeSBwYW4vem9vbSB2aWEgdGhlIE9TRCB2aWV3cG9ydCBBUEkuXG4gKiAtIERyYXdzIG5ldyByZWN0YW5nbGUgYW5kIHBvbHlnb24gcmVnaW9ucyAoY29tbWl0dGVkIHRvIHRoZSBzaGFyZWQgc3RvcmUpLlxuICogLSBDbGljay10by1zZWxlY3QgaW4gJ3NlbGVjdCcgbW9kZS5cbiAqXG4gKiBSZWFkcy93cml0ZXMgdGhlIHNoYXJlZCB7QGxpbmsgSVJlZ2lvblN0b3JlfSwgc28gcmVnaW9ucyBzdGF5IGluIHN5bmMgd2l0aCB0aGVcbiAqIFJlZ2lvbiBFZGl0b3IgYW5kIHRoZSBQbG90bHkgYmFja2VuZC4gVGhlIHdhbmQsIHZlcnRleC1lcmFzZXIgYW5kIHpvb20tdG8tYm94XG4gKiB0b29scyBhcmUgTk9UIGhhbmRsZWQgaGVyZSDigJQgdGhleSdyZSBvd25lZCBieSBPcGVuU2VhZHJhZ29uVmlzdWFsaXplclNlcnZpY2VcbiAqICh3aGljaCBiaW5kcyB0aGVtIHRvIE9TRCB2aWEgdGhlIHNoYXJlZCBjb29yZGluYXRlIHRyYW5zZm9ybSArIHZpZXdwb3J0IHBpeGVsXG4gKiByZWFkYmFjayksIHRoZSBzYW1lIHNpbmdsZXRvbiB0b29sIHNlcnZpY2VzIHRoZSBQbG90bHkgYmFja2VuZCB1c2VzLlxuICovXG5leHBvcnQgY2xhc3MgT3NkUmVnaW9uT3ZlcmxheSBpbXBsZW1lbnRzIElSZWdpb25PdmVybGF5IHtcblxuICBwcml2YXRlIHJlYWRvbmx5IHN2ZzogU1ZHU1ZHRWxlbWVudDtcbiAgcHJpdmF0ZSByZWFkb25seSBzdWJzID0gbmV3IFN1YnNjcmlwdGlvbigpO1xuICBwcml2YXRlIHJlYWRvbmx5IG9zZDogYW55ID0gT1NEO1xuXG4gIHByaXZhdGUgc2VsZWN0ZWQ6IG51bWJlcltdID0gW107XG4gIHByaXZhdGUgbW9kZTogUmVnaW9uVG9vbE1vZGUgPSAnbm9uZSc7XG5cbiAgcHJpdmF0ZSB0cmFja2VyOiBhbnk7XG4gIHByaXZhdGUgcmVjdFN0YXJ0OiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH0gfCBudWxsID0gbnVsbDsgLy8gaW1hZ2UgY29vcmRzXG4gIHByaXZhdGUgcmVjdEN1cnJlbnQ6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSB8IG51bGwgPSBudWxsO1xuICBwcml2YXRlIHBvbHlQb2ludHM6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfVtdID0gW107ICAgICAgICAvLyBpbWFnZSBjb29yZHNcbiAgLyoqIFRydWUgd2hpbGUgZHJhZ2dpbmcgYSBmcmVlaGFuZCBwYXRoIChmcmVlZm9ybSAvIHBvbHlsaW5lKS4gKi9cbiAgcHJpdmF0ZSBmcmVlaGFuZERyYWdnaW5nID0gZmFsc2U7XG4gIC8qKiBUcnVlIHdoaWxlIHBsYWNpbmcgYSBjbGljay10by1hZGQgcG9seWdvbiAoJ2RyYXdwb2x5Z29uJyBtb2RlKS4gKi9cbiAgcHJpdmF0ZSBkcmF3aW5nUG9seWdvbiA9IGZhbHNlO1xuICAvKiogTGFzdCBlbGVtZW50LXBpeGVsIHBvaW50IGFwcGVuZGVkLCB0byB0aGluIHRoZSBmcmVlaGFuZCBwYXRoLiAqL1xuICBwcml2YXRlIGxhc3RGcmVlaGFuZFB4OiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH0gfCBudWxsID0gbnVsbDtcbiAgLyoqXG4gICAqIEluLXByb2dyZXNzIGVkaXQgb2YgdGhlIHNlbGVjdGVkIHJlZ2lvbjpcbiAgICogIC0ga2luZCAnYm91bmRzJyDigJQgcmVjdGFuZ2xlIHJlc2l6ZS9tb3ZlIG9yIHdob2xlLXJlZ2lvbiBtb3ZlICh1c2VzIGB6b25lYCk7XG4gICAqICAtIGtpbmQgJ3ZlcnRleCcg4oCUIGRyYWdnaW5nIGEgc2luZ2xlIHBvbHlnb24gdmVydGV4ICh1c2VzIGB2ZXJ0ZXhJbmRleGApLlxuICAgKi9cbiAgcHJpdmF0ZSBlZGl0OiB7XG4gICAga2luZDogJ2JvdW5kcycgfCAndmVydGV4JyB8ICdoYW5kbGUnO1xuICAgIHpvbmU6IEVkaXRab25lO1xuICAgIHZlcnRleEluZGV4OiBudW1iZXI7XG4gICAgLyoqIFdoaWNoIHJpbmcgdGhlIGRyYWdnZWQgdmVydGV4IGJlbG9uZ3MgdG86IC0xID0gZXh0ZXJpb3IsIGVsc2UgYSBob2xlXG4gICAgICogIGluZGV4IGludG8gYFBvbHlnb24uaG9sZXNgIChqaXQtdWkjODUpLiAqL1xuICAgIHJpbmc6IG51bWJlcjtcbiAgICBoYW5kbGVTaWRlOiAnaW4nIHwgJ291dCc7XG4gICAgaWQ6IG51bWJlcjtcbiAgICBzdGFydEltZzogeyB4OiBudW1iZXI7IHk6IG51bWJlciB9O1xuICAgIG9yaWc6IGFueTtcbiAgfSB8IG51bGwgPSBudWxsO1xuICBwcml2YXRlIGVkaXREcmFnZ2VkID0gZmFsc2U7XG4gIC8qKiBSdWJiZXItYmFuZCAobWFycXVlZSkgbXVsdGktc2VsZWN0IGluICdzZWxlY3QnIG1vZGU6IHByZXNzIG9uIGVtcHR5IHNwYWNlXG4gICAqICBhbmQgZHJhZyB0byBzZWxlY3QgZXZlcnkgcmVnaW9uIHRoZSBiYW5kIGludGVyc2VjdHMuIEltYWdlIGNvb3Jkcy4gKi9cbiAgcHJpdmF0ZSBiYW5kU3RhcnQ6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSB8IG51bGwgPSBudWxsO1xuICBwcml2YXRlIGJhbmRDdXJyZW50OiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH0gfCBudWxsID0gbnVsbDtcbiAgcHJpdmF0ZSBiYW5kRHJhZ2dlZCA9IGZhbHNlO1xuXG4gIHByaXZhdGUgcmVhZG9ubHkgcmVkcmF3SGFuZGxlciA9ICgpID0+IHRoaXMucmVkcmF3KCk7XG5cbiAgY29uc3RydWN0b3IocHJpdmF0ZSB2aWV3ZXI6IGFueSwgcHJpdmF0ZSBzdG9yZTogUmVnaW9uRWRpdFN0b3JlKSB7XG4gICAgdGhpcy5zdmcgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50TlMoU1ZHTlMsICdzdmcnKSBhcyBTVkdTVkdFbGVtZW50O1xuICAgIE9iamVjdC5hc3NpZ24odGhpcy5zdmcuc3R5bGUsIHtcbiAgICAgIHBvc2l0aW9uOiAnYWJzb2x1dGUnLCBsZWZ0OiAnMCcsIHRvcDogJzAnLCB3aWR0aDogJzEwMCUnLCBoZWlnaHQ6ICcxMDAlJyxcbiAgICAgIHBvaW50ZXJFdmVudHM6ICdub25lJywgLy8gT1NEIGhhbmRsZXMgbmF2aWdhdGlvbiB1bmxlc3Mgd2UncmUgZHJhd2luZ1xuICAgIH0pO1xuICAgIHRoaXMudmlld2VyLmNhbnZhcy5hcHBlbmRDaGlsZCh0aGlzLnN2Zyk7XG5cbiAgICB0aGlzLnZpZXdlci5hZGRIYW5kbGVyKCd1cGRhdGUtdmlld3BvcnQnLCB0aGlzLnJlZHJhd0hhbmRsZXIpO1xuICAgIHRoaXMudmlld2VyLmFkZEhhbmRsZXIoJ2FuaW1hdGlvbicsIHRoaXMucmVkcmF3SGFuZGxlcik7XG4gICAgdGhpcy52aWV3ZXIuYWRkSGFuZGxlcigncmVzaXplJywgdGhpcy5yZWRyYXdIYW5kbGVyKTtcbiAgICB0aGlzLnZpZXdlci5hZGRIYW5kbGVyKCdyb3RhdGUnLCB0aGlzLnJlZHJhd0hhbmRsZXIpO1xuICAgIC8vIEtlZXAgd2hlZWwtem9vbSBhbGl2ZSB3aGlsZSBhIHRvb2wgaGFzIG1vdXNlLW5hdiBkaXNhYmxlZCAoc2VlIGhhbmRsZXIpLlxuICAgICh0aGlzLnZpZXdlci5lbGVtZW50IGFzIEhUTUxFbGVtZW50IHwgdW5kZWZpbmVkKVxuICAgICAgPy5hZGRFdmVudExpc3RlbmVyKCd3aGVlbCcsIHRoaXMud2hlZWxab29tSGFuZGxlciwgeyBwYXNzaXZlOiBmYWxzZSB9KTtcblxuICAgIHRoaXMudHJhY2tlciA9IG5ldyB0aGlzLm9zZC5Nb3VzZVRyYWNrZXIoe1xuICAgICAgZWxlbWVudDogdGhpcy52aWV3ZXIuY2FudmFzLFxuICAgICAgcHJlc3NIYW5kbGVyOiAoZTogYW55KSA9PiB0aGlzLm9uUHJlc3MoZSksXG4gICAgICBkcmFnSGFuZGxlcjogKGU6IGFueSkgPT4gdGhpcy5vbkRyYWcoZSksXG4gICAgICByZWxlYXNlSGFuZGxlcjogKGU6IGFueSkgPT4gdGhpcy5vblJlbGVhc2UoZSksXG4gICAgICBjbGlja0hhbmRsZXI6IChlOiBhbnkpID0+IHRoaXMub25DbGljayhlKSxcbiAgICAgIG1vdmVIYW5kbGVyOiAoZTogYW55KSA9PiB0aGlzLm9uTW92ZShlKSxcbiAgICB9KTtcbiAgICB0aGlzLnRyYWNrZXIuc2V0VHJhY2tpbmcoZmFsc2UpO1xuXG4gICAgdGhpcy5zdWJzLmFkZCh0aGlzLnN0b3JlLmdldFJlZ2lvblVwZGF0ZUV2ZW50KCkuc3Vic2NyaWJlKHRoaXMucmVkcmF3SGFuZGxlcikpO1xuICAgIHRoaXMuc3Vicy5hZGQodGhpcy5zdG9yZS5nZXRTZWxlY3RlZFNoYXBlSW5kaWNlcyQoKS5zdWJzY3JpYmUoaWR4ID0+IHtcbiAgICAgIHRoaXMuc2VsZWN0ZWQgPSBpZHggfHwgW107XG4gICAgICB0aGlzLnJlZHJhdygpO1xuICAgIH0pKTtcblxuICAgIHRoaXMucmVkcmF3KCk7XG4gIH1cblxuICAvKiogU3dpdGNoIGRyYXdpbmcvc2VsZWN0aW9uIG1vZGU7IHRvZ2dsZXMgT1NEIG5hdmlnYXRpb24gYWNjb3JkaW5nbHkuICovXG4gIHNldE1vZGUobW9kZTogUmVnaW9uVG9vbE1vZGUpOiB2b2lkIHtcbiAgICB0aGlzLm1vZGUgPSBtb2RlO1xuICAgIHRoaXMucmVzZXRJblByb2dyZXNzKCk7XG4gICAgLy8gQW55IGFjdGl2ZSByZWdpb24gdG9vbCB0YWtlcyBvdmVyIHRoZSBwb2ludGVyIOKAlCBPU0QgcGFuL3pvb20gaXMgZGlzYWJsZWRcbiAgICAvLyBzbyBkcmFnZ2luZyBkcmF3cyAoYW5kIGNsaWNrcyBzZWxlY3QpIGluc3RlYWQgb2YgcGFubmluZy4gV2l0aCBubyB0b29sLFxuICAgIC8vIE9TRCBuYXZpZ2F0ZXMgbm9ybWFsbHkuXG4gICAgdGhpcy52aWV3ZXIuc2V0TW91c2VOYXZFbmFibGVkKG1vZGUgPT09ICdub25lJyk7XG4gICAgdGhpcy50cmFja2VyLnNldFRyYWNraW5nKG1vZGUgIT09ICdub25lJyk7XG4gICAgdGhpcy51cGRhdGVDdXJzb3IoZmFsc2UpO1xuICAgIHRoaXMucmVkcmF3KCk7XG4gIH1cblxuICAvKiogRHJpdmUgT1NEIHpvb20gZnJvbSB0aGUgd2hlZWwgd2hpbGUgYW55IHRvb2wgb3ducyB0aGUgcG9pbnRlci5cbiAgICpcbiAgICogT1NEJ3MgbmF0aXZlIHNjcm9sbC16b29tIGlzIHBhcnQgb2YgbW91c2UtbmF2LCBzbyBgc2V0TW91c2VOYXZFbmFibGVkKGZhbHNlKWBcbiAgICogKHVzZWQgYnkgZXZlcnkgcmVnaW9uIHRvb2wgYW5kIGJ5IHRoZSB3YW5kL2JydXNoL2VyYXNlci9TQU0gdG9vbHMpIGRpc2FibGVzXG4gICAqIGl0LiBUaGUgY292ZXJpbmctY2FudmFzIHRvb2xzIGFsc28gc2l0IGFib3ZlIHRoZSBPU0QgY2FudmFzIGFuZCBzd2FsbG93IHRoZVxuICAgKiB3aGVlbCBvdXRyaWdodC4gVGhpcyBsaXN0ZW5lciBpcyBib3VuZCBvbmNlIHRvIHRoZSB2aWV3ZXIgZWxlbWVudCDigJQgYW5cbiAgICogYW5jZXN0b3Igb2YgYm90aCB0aGUgT1NEIGNhbnZhcyBhbmQgdGhlIHRvb2wgb3ZlcmxheXMg4oCUIGFuZCBmb3J3YXJkcyB0aGVcbiAgICogd2hlZWwgdG8gYSBjdXJzb3ItY2VudHJlZCB6b29tIHdoZW5ldmVyIG1vdXNlLW5hdiBpcyBvZmYuIFdoZW4gbmF2IGlzIG9uIChub1xuICAgKiB0b29sIGFjdGl2ZSkgaXQgZG9lcyBub3RoaW5nIGFuZCBPU0Qgem9vbXMgbmF0aXZlbHkuIChqaXQtdWkjOTQpICovXG4gIHByaXZhdGUgcmVhZG9ubHkgd2hlZWxab29tSGFuZGxlciA9IChlOiBXaGVlbEV2ZW50KSA9PiB7XG4gICAgY29uc3QgdnAgPSB0aGlzLnZpZXdlcj8udmlld3BvcnQ7XG4gICAgY29uc3QgZWwgPSB0aGlzLnZpZXdlcj8uZWxlbWVudCBhcyBIVE1MRWxlbWVudCB8IHVuZGVmaW5lZDtcbiAgICAvLyBOYXYgb24g4oaSIG5vIHRvb2wgYWN0aXZlIOKGkiBsZXQgT1NEIGhhbmRsZSBzY3JvbGwtem9vbSBuYXRpdmVseS5cbiAgICBpZiAoIXZwIHx8ICFlbCB8fCBlLmRlbHRhWSA9PT0gMCB8fCB0aGlzLnZpZXdlci5pc01vdXNlTmF2RW5hYmxlZCgpKSByZXR1cm47XG4gICAgZS5wcmV2ZW50RGVmYXVsdCgpO1xuICAgIGNvbnN0IHJlY3QgPSBlbC5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKTtcbiAgICBjb25zdCByZWZQb2ludCA9IHZwLnBvaW50RnJvbVBpeGVsKG5ldyB0aGlzLm9zZC5Qb2ludChlLmNsaWVudFggLSByZWN0LmxlZnQsIGUuY2xpZW50WSAtIHJlY3QudG9wKSk7XG4gICAgdnAuem9vbUJ5KGUuZGVsdGFZIDwgMCA/IE9TRF9aT09NX1BFUl9TQ1JPTEwgOiAxIC8gT1NEX1pPT01fUEVSX1NDUk9MTCwgcmVmUG9pbnQpO1xuICAgIHZwLmFwcGx5Q29uc3RyYWludHMoKTtcbiAgfTtcblxuICAvKiogQ3Vyc29yIGZlZWRiYWNrIHBlciBtb2RlIChjcm9zc2hhaXIgd2hpbGUgZHJhd2luZzsgcG9pbnRlciBvdmVyIGEgcmVnaW9uXG4gICAqICBpbiBzZWxlY3QgbW9kZSkuICovXG4gIHByaXZhdGUgdXBkYXRlQ3Vyc29yKG92ZXJSZWdpb246IGJvb2xlYW4pOiB2b2lkIHtcbiAgICBjb25zdCBjYW52YXMgPSB0aGlzLnZpZXdlci5jYW52YXMgYXMgSFRNTEVsZW1lbnQ7XG4gICAgaWYgKHRoaXMubW9kZSA9PT0gJ2RyYXdyZWN0JyB8fCB0aGlzLm1vZGUgPT09ICdkcmF3Y2xvc2VkcGF0aCcgfHwgdGhpcy5tb2RlID09PSAnZHJhd29wZW5wYXRoJ1xuICAgICAgICB8fCB0aGlzLm1vZGUgPT09ICdkcmF3cG9seWdvbicgfHwgdGhpcy5tb2RlID09PSAnYWRkcG9pbnQnIHx8IHRoaXMubW9kZSA9PT0gJ2RlbGV0ZXBvaW50Jykge1xuICAgICAgY2FudmFzLnN0eWxlLmN1cnNvciA9ICdjcm9zc2hhaXInO1xuICAgIH0gZWxzZSBpZiAodGhpcy5tb2RlID09PSAnbW92ZScpIHtcbiAgICAgIGNhbnZhcy5zdHlsZS5jdXJzb3IgPSAnbW92ZSc7XG4gICAgfSBlbHNlIGlmICh0aGlzLm1vZGUgPT09ICdzZWxlY3QnKSB7XG4gICAgICBjYW52YXMuc3R5bGUuY3Vyc29yID0gb3ZlclJlZ2lvbiA/ICdwb2ludGVyJyA6ICdkZWZhdWx0JztcbiAgICB9IGVsc2Uge1xuICAgICAgY2FudmFzLnN0eWxlLmN1cnNvciA9ICcnOyAvLyBPU0QgZGVmYXVsdCAoZ3JhYilcbiAgICB9XG4gIH1cblxuICAvKiogV2hldGhlciB0aGUgc2VsZWN0ZWQgcmVnaW9uJ3MgdmVydGljZXMvaGFuZGxlcyBzaG91bGQgYmUgZHJhd24uIFNob3duXG4gICAqICB3aGVuZXZlciBhIHJlZ2lvbiBpcyBzZWxlY3RlZCDigJQgaW5jbHVkaW5nIGBub25lYCAoZGlzcGxheSkgbW9kZSBhbmQgd2hpbGVcbiAgICogIGFub3RoZXIgdG9vbCAod2FuZCwgYnJ1c2gsIFNBTeKApikgaXMgYWN0aXZlIOKAlCBzbyBhIHNlbGVjdGlvbiBhbHdheXMgcmV2ZWFsc1xuICAgKiAgaXRzIHZlcnRpY2VzLiBTdXBwcmVzc2VkIG9ubHkgd2hpbGUgYWN0aXZlbHkgZHJhd2luZyBhIGJyYW5kLW5ldyBzaGFwZSxcbiAgICogIHdoZXJlIHN0cmF5IGhhbmRsZXMgd291bGQgYmUgbm9pc2UuICovXG4gIHByaXZhdGUgZ2V0IHNob3dzU2VsZWN0ZWRWZXJ0aWNlcygpOiBib29sZWFuIHtcbiAgICByZXR1cm4gdGhpcy5tb2RlICE9PSAnZHJhd3JlY3QnICYmIHRoaXMubW9kZSAhPT0gJ2RyYXdwb2x5Z29uJ1xuICAgICAgJiYgdGhpcy5tb2RlICE9PSAnZHJhd2Nsb3NlZHBhdGgnICYmIHRoaXMubW9kZSAhPT0gJ2RyYXdvcGVucGF0aCc7XG4gIH1cblxuICBkZXN0cm95KCk6IHZvaWQge1xuICAgIHRoaXMuc3Vicy51bnN1YnNjcmliZSgpO1xuICAgICh0aGlzLnZpZXdlci5lbGVtZW50IGFzIEhUTUxFbGVtZW50IHwgdW5kZWZpbmVkKVxuICAgICAgPy5yZW1vdmVFdmVudExpc3RlbmVyKCd3aGVlbCcsIHRoaXMud2hlZWxab29tSGFuZGxlcik7XG4gICAgdGhpcy52aWV3ZXIucmVtb3ZlSGFuZGxlcigndXBkYXRlLXZpZXdwb3J0JywgdGhpcy5yZWRyYXdIYW5kbGVyKTtcbiAgICB0aGlzLnZpZXdlci5yZW1vdmVIYW5kbGVyKCdhbmltYXRpb24nLCB0aGlzLnJlZHJhd0hhbmRsZXIpO1xuICAgIHRoaXMudmlld2VyLnJlbW92ZUhhbmRsZXIoJ3Jlc2l6ZScsIHRoaXMucmVkcmF3SGFuZGxlcik7XG4gICAgdGhpcy52aWV3ZXIucmVtb3ZlSGFuZGxlcigncm90YXRlJywgdGhpcy5yZWRyYXdIYW5kbGVyKTtcbiAgICBpZiAodGhpcy50cmFja2VyKSB0aGlzLnRyYWNrZXIuZGVzdHJveSgpO1xuICAgIGlmICh0aGlzLnN2Zy5wYXJlbnROb2RlKSB0aGlzLnN2Zy5wYXJlbnROb2RlLnJlbW92ZUNoaWxkKHRoaXMuc3ZnKTtcbiAgfVxuXG4gIC8vIOKUgOKUgCBjb29yZGluYXRlIGhlbHBlcnMg4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSAXG4gIC8qKiBJbWFnZS1waXhlbCBwb2ludCAtPiBlbGVtZW50IHBpeGVsIHBvaW50LiAqL1xuICBwcml2YXRlIHRvUHgoaW1nWDogbnVtYmVyLCBpbWdZOiBudW1iZXIpOiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH0ge1xuICAgIHJldHVybiBpbWFnZVRvRWxlbWVudCh0aGlzLnZpZXdlciwgaW1nWCwgaW1nWSk7XG4gIH1cbiAgLyoqIEVsZW1lbnQgcGl4ZWwgcG9pbnQgKGZyb20gYSBNb3VzZVRyYWNrZXIgZXZlbnQpIC0+IGltYWdlLXBpeGVsIHBvaW50LiAqL1xuICBwcml2YXRlIHRvSW1hZ2UocG9zOiBhbnkpOiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH0ge1xuICAgIGNvbnN0IHAgPSBlbGVtZW50VG9JbWFnZSh0aGlzLnZpZXdlciwgcG9zLngsIHBvcy55KTtcbiAgICByZXR1cm4geyB4OiBNYXRoLnJvdW5kKHAueCksIHk6IE1hdGgucm91bmQocC55KSB9O1xuICB9XG5cbiAgLy8g4pSA4pSAIHJlbmRlcmluZyDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIBcbiAgcmVkcmF3KCk6IHZvaWQge1xuICAgIHdoaWxlICh0aGlzLnN2Zy5maXJzdENoaWxkKSB0aGlzLnN2Zy5yZW1vdmVDaGlsZCh0aGlzLnN2Zy5maXJzdENoaWxkKTtcblxuICAgIGNvbnN0IHJlZ2lvbnMgPSB0aGlzLnN0b3JlLmdldFJlZ2lvbnMoKTtcbiAgICByZWdpb25zLmZvckVhY2goKHIsIGkpID0+IHtcbiAgICAgIGNvbnN0IGVsID0gdGhpcy5idWlsZFJlZ2lvbkVsKHIsIHRoaXMuc2VsZWN0ZWQuaW5jbHVkZXMoaSkpO1xuICAgICAgaWYgKGVsKSB0aGlzLnN2Zy5hcHBlbmRDaGlsZChlbCk7XG4gICAgfSk7XG5cbiAgICAvLyBIYW5kbGVzIG9uIHRoZSBzZWxlY3RlZCBwb2x5Z29uLCBzbyB0aGUgdXNlciBjYW4gZ3JhYi9pbnNlcnQvZGVsZXRlXG4gICAgLy8gdmVydGljZXMuIEJlemllciByZWdpb25zIGFsc28gZ2V0IHRoZWlyIGN1YmljXG4gICAgLy8gY29udHJvbCBoYW5kbGVzICh0YW5nZW50IGxpbmVzICsgY29udHJvbCBwb2ludHMpLCBtaXJyb3JpbmcgcGFwZXIuanMnc1xuICAgIC8vIGZ1bGx5U2VsZWN0ZWQgcmVuZGVyaW5nLlxuICAgIGlmICh0aGlzLnNob3dzU2VsZWN0ZWRWZXJ0aWNlcykge1xuICAgICAgY29uc3Qgc2VsID0gdGhpcy5zZWxlY3RlZFJlZ2lvbkluZm8oKTtcbiAgICAgIGNvbnN0IGIgPSBzZWw/LnJlZ2lvbi5ib3VuZHM7XG4gICAgICAvLyBIYW5kbGVzL3ZlcnRpY2VzIHRha2UgdGhlIHJlZ2lvbidzIG93biBjb2xvdXIgKG5vdCB0aGUgZ2xvYmFsIHNoYXBlXG4gICAgICAvLyBjb2xvdXIpIHNvIHRoZXkgbWF0Y2ggdGhlIHNoYXBlIHRoZXkgYmVsb25nIHRvLlxuICAgICAgY29uc3QgY29sb3IgPSBzZWwgPyBzZWwucmVnaW9uLmNvbG9yIHx8IHRoaXMuc3RvcmUuZ2V0U2hhcGVDb2xvcigpIDogJyc7XG4gICAgICBpZiAoYiBpbnN0YW5jZW9mIFBvbHlnb24pIHtcbiAgICAgICAgaWYgKGIuYmV6aWVyKSB7XG4gICAgICAgICAgdGhpcy5kcmF3QmV6aWVySGFuZGxlcyhiLCBjb2xvcik7XG4gICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBiLnhwb2ludHMubGVuZ3RoOyBpKyspIHtcbiAgICAgICAgICAgIGNvbnN0IHEgPSB0aGlzLnRvUHgoYi54cG9pbnRzW2ldLCBiLnlwb2ludHNbaV0pO1xuICAgICAgICAgICAgdGhpcy5zdmcuYXBwZW5kQ2hpbGQodGhpcy52ZXJ0ZXhNYXJrZXIocS54LCBxLnksIGZhbHNlLCBjb2xvcikpO1xuICAgICAgICAgIH1cbiAgICAgICAgICAvLyBJbnRlcmlvci1yaW5nIChob2xlKSB2ZXJ0aWNlcyB0b28sIHNvIGEgZG9udXQncyBpbm5lciBvdXRsaW5lIHNob3dzXG4gICAgICAgICAgLy8gaXRzIHZlcnRpY2VzIHdoZW4gc2VsZWN0ZWQgKGppdC11aSM4NSkuXG4gICAgICAgICAgaWYgKGIuaG9sZXMpIHtcbiAgICAgICAgICAgIGZvciAoY29uc3QgcmluZyBvZiBiLmhvbGVzKSB7XG4gICAgICAgICAgICAgIGZvciAoY29uc3QgW2h4LCBoeV0gb2YgcmluZykge1xuICAgICAgICAgICAgICAgIGNvbnN0IHEgPSB0aGlzLnRvUHgoaHgsIGh5KTtcbiAgICAgICAgICAgICAgICB0aGlzLnN2Zy5hcHBlbmRDaGlsZCh0aGlzLnZlcnRleE1hcmtlcihxLngsIHEueSwgZmFsc2UsIGNvbG9yKSk7XG4gICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgIH0gZWxzZSBpZiAoYiBpbnN0YW5jZW9mIFJlY3RhbmdsZSkge1xuICAgICAgICAvLyBUaGUgZm91ciBjb3JuZXJzIGFzIGdyYWIvcmVzaXplIGhhbmRsZXMuXG4gICAgICAgIGNvbnN0IGNvcm5lcnM6IFtudW1iZXIsIG51bWJlcl1bXSA9IFtcbiAgICAgICAgICBbYi54LCBiLnldLCBbYi54ICsgYi53aWR0aCwgYi55XSxcbiAgICAgICAgICBbYi54ICsgYi53aWR0aCwgYi55ICsgYi5oZWlnaHRdLCBbYi54LCBiLnkgKyBiLmhlaWdodF0sXG4gICAgICAgIF07XG4gICAgICAgIGZvciAoY29uc3QgW2N4LCBjeV0gb2YgY29ybmVycykge1xuICAgICAgICAgIGNvbnN0IHEgPSB0aGlzLnRvUHgoY3gsIGN5KTtcbiAgICAgICAgICB0aGlzLnN2Zy5hcHBlbmRDaGlsZCh0aGlzLnZlcnRleE1hcmtlcihxLngsIHEueSwgZmFsc2UsIGNvbG9yKSk7XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICB9XG5cbiAgICAvLyBSdWJiZXItYmFuZCAobWFycXVlZSkgc2VsZWN0aW9uIHByZXZpZXcuXG4gICAgaWYgKHRoaXMubW9kZSA9PT0gJ3NlbGVjdCcgJiYgdGhpcy5iYW5kU3RhcnQgJiYgdGhpcy5iYW5kQ3VycmVudCkge1xuICAgICAgdGhpcy5zdmcuYXBwZW5kQ2hpbGQodGhpcy5zZWxlY3Rpb25CYW5kKHRoaXMuYmFuZFN0YXJ0LCB0aGlzLmJhbmRDdXJyZW50KSk7XG4gICAgfVxuXG4gICAgLy8gSW4tcHJvZ3Jlc3MgZHJhd2luZyBwcmV2aWV3LlxuICAgIGlmICh0aGlzLm1vZGUgPT09ICdkcmF3cmVjdCcgJiYgdGhpcy5yZWN0U3RhcnQgJiYgdGhpcy5yZWN0Q3VycmVudCkge1xuICAgICAgdGhpcy5zdmcuYXBwZW5kQ2hpbGQodGhpcy5yZWN0UHJldmlldyh0aGlzLnJlY3RTdGFydCwgdGhpcy5yZWN0Q3VycmVudCkpO1xuICAgIH1cbiAgICBpZiAoKHRoaXMubW9kZSA9PT0gJ2RyYXdjbG9zZWRwYXRoJyB8fCB0aGlzLm1vZGUgPT09ICdkcmF3b3BlbnBhdGgnKSAmJiB0aGlzLnBvbHlQb2ludHMubGVuZ3RoKSB7XG4gICAgICB0aGlzLnN2Zy5hcHBlbmRDaGlsZCh0aGlzLnBvbHlQcmV2aWV3KHRoaXMucG9seVBvaW50cykpO1xuICAgIH1cbiAgICAvLyBDbGljay10by1wbGFjZSBwb2x5Z29uIHByZXZpZXc6IHRoZSBwb2x5bGluZSBzbyBmYXIgKyBhIG1hcmtlciBvbiB0aGVcbiAgICAvLyBmaXJzdCB2ZXJ0ZXggKGNsaWNrIGl0IHRvIGNsb3NlKS5cbiAgICBpZiAodGhpcy5tb2RlID09PSAnZHJhd3BvbHlnb24nICYmIHRoaXMucG9seVBvaW50cy5sZW5ndGgpIHtcbiAgICAgIHRoaXMuc3ZnLmFwcGVuZENoaWxkKHRoaXMucG9seVByZXZpZXcodGhpcy5wb2x5UG9pbnRzKSk7XG4gICAgICBjb25zdCBmID0gdGhpcy50b1B4KHRoaXMucG9seVBvaW50c1swXS54LCB0aGlzLnBvbHlQb2ludHNbMF0ueSk7XG4gICAgICB0aGlzLnN2Zy5hcHBlbmRDaGlsZCh0aGlzLnZlcnRleE1hcmtlcihmLngsIGYueSwgdHJ1ZSkpO1xuICAgIH1cbiAgfVxuXG4gIC8qKiBBIHNtYWxsIHZlcnRleCBoYW5kbGUgKGZpbGxlZCBmb3IgYW4gZW1waGFzaXNlZCBtYXJrZXIsIGhvbGxvdyBvdGhlcndpc2UpLlxuICAgKiAgQ29sb3VyIGRlZmF1bHRzIHRvIHRoZSBnbG9iYWwgc2hhcGUgY29sb3VyICh1c2VkIGJ5IHRoZSBpbi1wcm9ncmVzcyBkcmF3XG4gICAqICBwcmV2aWV3KTsgc2VsZWN0ZWQtcmVnaW9uIGhhbmRsZXMgcGFzcyB0aGUgcmVnaW9uJ3Mgb3duIGNvbG91ci4gKi9cbiAgcHJpdmF0ZSB2ZXJ0ZXhNYXJrZXIoeDogbnVtYmVyLCB5OiBudW1iZXIsIGVtcGhhc2lzZWQ6IGJvb2xlYW4sXG4gICAgICAgICAgICAgICAgICAgICAgIGNvbG9yOiBzdHJpbmcgPSB0aGlzLnN0b3JlLmdldFNoYXBlQ29sb3IoKSk6IFNWR0VsZW1lbnQge1xuICAgIGNvbnN0IGMgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50TlMoU1ZHTlMsICdjaXJjbGUnKTtcbiAgICBjLnNldEF0dHJpYnV0ZSgnY3gnLCBgJHt4fWApO1xuICAgIGMuc2V0QXR0cmlidXRlKCdjeScsIGAke3l9YCk7XG4gICAgYy5zZXRBdHRyaWJ1dGUoJ3InLCBlbXBoYXNpc2VkID8gJzUnIDogJzQnKTtcbiAgICBjLnNldEF0dHJpYnV0ZSgnZmlsbCcsIGVtcGhhc2lzZWQgPyBjb2xvciA6ICcjZmZmZmZmJyk7XG4gICAgYy5zZXRBdHRyaWJ1dGUoJ3N0cm9rZScsIGNvbG9yKTtcbiAgICBjLnNldEF0dHJpYnV0ZSgnc3Ryb2tlLXdpZHRoJywgJzInKTtcbiAgICByZXR1cm4gYztcbiAgfVxuXG4gIHByaXZhdGUgYnVpbGRSZWdpb25FbChyZWdpb246IFJlZ2lvbiwgc2VsZWN0ZWQ6IGJvb2xlYW4pOiBTVkdFbGVtZW50IHwgbnVsbCB7XG4gICAgY29uc3QgY29sb3IgPSByZWdpb24uY29sb3IgfHwgdGhpcy5zdG9yZS5nZXRTaGFwZUNvbG9yKCk7XG4gICAgY29uc3QgYm91bmRzID0gcmVnaW9uLmJvdW5kcztcbiAgICBsZXQgcHRzOiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH1bXSB8IG51bGwgPSBudWxsO1xuICAgIGxldCBjbG9zZWQgPSB0cnVlO1xuICAgIGxldCBlbDogU1ZHRWxlbWVudCB8IG51bGwgPSBudWxsO1xuXG4gICAgaWYgKGJvdW5kcyBpbnN0YW5jZW9mIE11bHRpUG9seWdvbikge1xuICAgICAgLy8gTXVsdGktcGFydCByZWdpb24gKGppdC11aSM4NSk6IG9uZSBldmVuLW9kZCA8cGF0aD4gd2l0aCBldmVyeSBwYXJ0J3NcbiAgICAgIC8vIGV4dGVyaW9yIHBsdXMgaXRzIGhvbGVzLiBBbGwgcGFydHMnIHZlcnRpY2VzIGRyaXZlIHRoZSBsYWJlbCBiYm94LlxuICAgICAgY29uc3QgcGFydHMgPSBib3VuZHMucG9seWdvbnMuZmlsdGVyKChwKSA9PiAocC54cG9pbnRzPy5sZW5ndGggPz8gMCkgPj0gMyk7XG4gICAgICBpZiAocGFydHMubGVuZ3RoID09PSAwKSByZXR1cm4gbnVsbDtcbiAgICAgIHB0cyA9IFtdO1xuICAgICAgbGV0IGQgPSAnJztcbiAgICAgIGZvciAoY29uc3QgcGFydCBvZiBwYXJ0cykge1xuICAgICAgICBjb25zdCBleHQgPSBwYXJ0Lnhwb2ludHMubWFwKCh4LCBpKSA9PiAoeyB4LCB5OiBwYXJ0Lnlwb2ludHNbaV0gfSkpO1xuICAgICAgICBwdHMucHVzaCguLi5leHQpO1xuICAgICAgICBkICs9IChkID8gJyAnIDogJycpICsgdGhpcy5zdHJhaWdodFBhdGhEKGV4dCwgdHJ1ZSk7XG4gICAgICAgIGlmIChwYXJ0LmhvbGVzKSB7XG4gICAgICAgICAgZm9yIChjb25zdCByaW5nIG9mIHBhcnQuaG9sZXMpIHtcbiAgICAgICAgICAgIGQgKz0gJyAnICsgdGhpcy5zdHJhaWdodFBhdGhEKHJpbmcubWFwKChbeCwgeV0pID0+ICh7IHgsIHkgfSkpLCB0cnVlKTtcbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICAgIGVsID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudE5TKFNWR05TLCAncGF0aCcpO1xuICAgICAgZWwuc2V0QXR0cmlidXRlKCdkJywgZCk7XG4gICAgICBlbC5zZXRBdHRyaWJ1dGUoJ2ZpbGwtcnVsZScsICdldmVub2RkJyk7XG4gICAgfSBlbHNlIGlmIChib3VuZHMgaW5zdGFuY2VvZiBSZWN0YW5nbGUpIHtcbiAgICAgIHB0cyA9IFtcbiAgICAgICAgeyB4OiBib3VuZHMueCwgeTogYm91bmRzLnkgfSxcbiAgICAgICAgeyB4OiBib3VuZHMueCArIGJvdW5kcy53aWR0aCwgeTogYm91bmRzLnkgfSxcbiAgICAgICAgeyB4OiBib3VuZHMueCArIGJvdW5kcy53aWR0aCwgeTogYm91bmRzLnkgKyBib3VuZHMuaGVpZ2h0IH0sXG4gICAgICAgIHsgeDogYm91bmRzLngsIHk6IGJvdW5kcy55ICsgYm91bmRzLmhlaWdodCB9LFxuICAgICAgXTtcbiAgICB9IGVsc2UgaWYgKGJvdW5kcyBpbnN0YW5jZW9mIFBvbHlnb24pIHtcbiAgICAgIGNsb3NlZCA9IGJvdW5kcy5jbG9zZWQgIT09IGZhbHNlO1xuICAgICAgLy8gVGhlIGFuY2hvcnMgZHJpdmUgdGhlIGxhYmVsIGJib3ggYW5kIChmb3Igbm9uLWJlemllcikgdGhlIHJlbmRlcmVkIHNoYXBlLlxuICAgICAgcHRzID0gYm91bmRzLnhwb2ludHMubWFwKCh4LCBpKSA9PiAoeyB4LCB5OiBib3VuZHMueXBvaW50c1tpXSB9KSk7XG4gICAgfVxuICAgIGlmICghcHRzIHx8IHB0cy5sZW5ndGggPT09IDApIHJldHVybiBudWxsO1xuXG4gICAgaWYgKCFlbCkge1xuICAgICAgLy8gQmV6aWVyIHJlZ2lvbnMgcmVuZGVyIGFzIGEgdHJ1ZSBjdWJpYy1iZXppZXIgcGF0aCB0aHJvdWdoIHRoZSBhbmNob3JzXG4gICAgICAvLyAocGFwZXIuanMtZXF1aXZhbGVudCBzbW9vdGggY3VydmUpOyBldmVyeXRoaW5nIGVsc2UgYXMgYSBzdHJhaWdodFxuICAgICAgLy8gcG9seWdvbi9wb2x5bGluZS5cbiAgICAgIGNvbnN0IGlzQmV6aWVyID0gYm91bmRzIGluc3RhbmNlb2YgUG9seWdvbiAmJiBib3VuZHMuYmV6aWVyICYmIHB0cy5sZW5ndGggPj0gMjtcbiAgICAgIC8vIEludGVyaW9yIHJpbmdzIChob2xlcykg4oCUIHB1bmNoIHRocm91Z2ggd2l0aCBldmVuLW9kZCBmaWxsIChqaXQtdWkjODUpLlxuICAgICAgY29uc3QgaG9sZXMgPSAoY2xvc2VkICYmIGJvdW5kcyBpbnN0YW5jZW9mIFBvbHlnb24gJiYgYm91bmRzLmhvbGVzPy5sZW5ndGgpXG4gICAgICAgID8gYm91bmRzLmhvbGVzIDogbnVsbDtcbiAgICAgIGlmIChpc0JlemllciB8fCBob2xlcykge1xuICAgICAgICBlbCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhTVkdOUywgJ3BhdGgnKTtcbiAgICAgICAgLy8gRXh0ZXJpb3Igc3VicGF0aCAoc21vb3RoIGZvciBiZXppZXIsIHN0cmFpZ2h0IG90aGVyd2lzZSkgZm9sbG93ZWQgYnkgYVxuICAgICAgICAvLyBzdHJhaWdodCBzdWJwYXRoIHBlciBob2xlLlxuICAgICAgICBsZXQgZCA9IGlzQmV6aWVyID8gdGhpcy5iZXppZXJQYXRoRChib3VuZHMgYXMgUG9seWdvbikgOiB0aGlzLnN0cmFpZ2h0UGF0aEQocHRzLCBjbG9zZWQpO1xuICAgICAgICBpZiAoaG9sZXMpIHtcbiAgICAgICAgICBjb25zdCBwb2x5ID0gYm91bmRzIGFzIFBvbHlnb247XG4gICAgICAgICAgaG9sZXMuZm9yRWFjaCgocmluZywgaGkpID0+IHtcbiAgICAgICAgICAgIGNvbnN0IHhzID0gcmluZy5tYXAoKHApID0+IHBbMF0pO1xuICAgICAgICAgICAgY29uc3QgeXMgPSByaW5nLm1hcCgocCkgPT4gcFsxXSk7XG4gICAgICAgICAgICAvLyBXaGVuIHRoZSBkb251dCBpcyBhIGJlemllciwgc21vb3RoIGl0cyBob2xlcyB0b28gKGppdC11aSMxMDIpIOKAlCB1c2luZyBzdG9yZWQgaG9sZVxuICAgICAgICAgICAgLy8gaGFuZGxlcyB3aGVuIHByZXNlbnQsIGVsc2UgdGhlIENhdG11bGwtUm9tIGRlZmF1bHQgKHZpYSByZXNvbHZlSGFuZGxlcykuXG4gICAgICAgICAgICBkICs9XG4gICAgICAgICAgICAgICcgJyArXG4gICAgICAgICAgICAgIChpc0JlemllclxuICAgICAgICAgICAgICAgID8gdGhpcy5yaW5nQmV6aWVyUGF0aEQoeHMsIHlzLCBwb2x5LmhvbGVIYW5kbGVzSW4/LltoaV0sIHBvbHkuaG9sZUhhbmRsZXNPdXQ/LltoaV0sIHRydWUpXG4gICAgICAgICAgICAgICAgOiB0aGlzLnN0cmFpZ2h0UGF0aEQocmluZy5tYXAoKFt4LCB5XSkgPT4gKHsgeCwgeSB9KSksIHRydWUpKTtcbiAgICAgICAgICB9KTtcbiAgICAgICAgICBlbC5zZXRBdHRyaWJ1dGUoJ2ZpbGwtcnVsZScsICdldmVub2RkJyk7XG4gICAgICAgIH1cbiAgICAgICAgZWwuc2V0QXR0cmlidXRlKCdkJywgZCk7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICBlbCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhTVkdOUywgY2xvc2VkID8gJ3BvbHlnb24nIDogJ3BvbHlsaW5lJyk7XG4gICAgICAgIGVsLnNldEF0dHJpYnV0ZSgncG9pbnRzJywgcHRzLm1hcChwID0+IHsgY29uc3QgcSA9IHRoaXMudG9QeChwLngsIHAueSk7IHJldHVybiBgJHtxLnh9LCR7cS55fWA7IH0pLmpvaW4oJyAnKSk7XG4gICAgICB9XG4gICAgfVxuICAgIGVsLnNldEF0dHJpYnV0ZSgnZmlsbCcsIHNlbGVjdGVkID8gdGhpcy5yZ2JhKGNvbG9yLCAwLjM1KSA6ICdub25lJyk7XG4gICAgZWwuc2V0QXR0cmlidXRlKCdzdHJva2UnLCBjb2xvcik7XG4gICAgZWwuc2V0QXR0cmlidXRlKCdzdHJva2Utd2lkdGgnLCBzZWxlY3RlZCA/ICc0JyA6ICcyJyk7XG5cbiAgICAvLyBUaGUgY2xhc3MgbGFiZWwgKGxlZ2VuZCksIHNob3duIHdoZW4gdGhlIFJlZ2lvbiBFZGl0b3IncyBcInNob3cgbGFiZWxzXCIgaXNcbiAgICAvLyBvbiDigJQgbWlycm9ycyBQbG90bHkncyBwZXItc2hhcGUgbGFiZWwgKHRvcC1sZWZ0LCBkcmF3biBpbiB0aGUgcmVnaW9uJ3NcbiAgICAvLyBjb2xvdXIpLiBXaXRob3V0IHRoaXMgT1NEIHNob3dlZCByZWdpb25zIHdpdGggbm8gbGFiZWwgZXZlbiB0aG91Z2ggUGxvdGx5XG4gICAgLy8gZGlkLiByZWdpb24ubGFiZWwgaXMgcmVzdG9yZWQgZnJvbSB0aGUgc2hhcGUncyBsZWdlbmQgaW4gZ2V0UmVnaW9uKCkuXG4gICAgY29uc3QgbGFiZWwgPSByZWdpb24ubGFiZWw7XG4gICAgaWYgKHRoaXMuc3RvcmUuZ2V0U2hvd1NoYXBlTGFiZWwoKSAmJiBsYWJlbCAhPSBudWxsICYmIGAke2xhYmVsfWAubGVuZ3RoID4gMCkge1xuICAgICAgY29uc3QgZyA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhTVkdOUywgJ2cnKTtcbiAgICAgIGcuYXBwZW5kQ2hpbGQoZWwpO1xuICAgICAgY29uc3QgbWluWCA9IE1hdGgubWluKC4uLnB0cy5tYXAocCA9PiBwLngpKTtcbiAgICAgIGNvbnN0IG1pblkgPSBNYXRoLm1pbiguLi5wdHMubWFwKHAgPT4gcC55KSk7XG4gICAgICBjb25zdCBxID0gdGhpcy50b1B4KG1pblgsIG1pblkpO1xuICAgICAgY29uc3QgdGV4dCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhTVkdOUywgJ3RleHQnKTtcbiAgICAgIHRleHQuc2V0QXR0cmlidXRlKCd4JywgYCR7cS54fWApO1xuICAgICAgdGV4dC5zZXRBdHRyaWJ1dGUoJ3knLCBgJHtxLnkgLSA0fWApOyAvLyBqdXN0IGFib3ZlIHRoZSB0b3AtbGVmdCBjb3JuZXJcbiAgICAgIHRleHQuc2V0QXR0cmlidXRlKCdmaWxsJywgY29sb3IpO1xuICAgICAgdGV4dC5zZXRBdHRyaWJ1dGUoJ2ZvbnQtc2l6ZScsICcxMycpO1xuICAgICAgdGV4dC5zZXRBdHRyaWJ1dGUoJ2ZvbnQtZmFtaWx5JywgJ3NhbnMtc2VyaWYnKTtcbiAgICAgIC8vIERhcmsgaGFsbyBzbyB0aGUgbGFiZWwgc3RheXMgbGVnaWJsZSBvdmVyIGJvdGggYnJpZ2h0IGFuZCBkYXJrIHRpbGVzLlxuICAgICAgdGV4dC5zZXRBdHRyaWJ1dGUoJ3BhaW50LW9yZGVyJywgJ3N0cm9rZScpO1xuICAgICAgdGV4dC5zZXRBdHRyaWJ1dGUoJ3N0cm9rZScsICdyZ2JhKDAsMCwwLDAuNjUpJyk7XG4gICAgICB0ZXh0LnNldEF0dHJpYnV0ZSgnc3Ryb2tlLXdpZHRoJywgJzInKTtcbiAgICAgIHRleHQudGV4dENvbnRlbnQgPSBgJHtsYWJlbH1gO1xuICAgICAgZy5hcHBlbmRDaGlsZCh0ZXh0KTtcbiAgICAgIHJldHVybiBnO1xuICAgIH1cbiAgICByZXR1cm4gZWw7XG4gIH1cblxuICAvKiogTWFycXVlZSByZWN0YW5nbGUgZm9yIHJ1YmJlci1iYW5kIG11bHRpLXNlbGVjdCAoZGFzaGVkIG91dGxpbmUgKyBmYWludCBmaWxsKS4gKi9cbiAgcHJpdmF0ZSBzZWxlY3Rpb25CYW5kKGE6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSwgYjogeyB4OiBudW1iZXI7IHk6IG51bWJlciB9KTogU1ZHRWxlbWVudCB7XG4gICAgY29uc3QgY29ybmVycyA9IFtcbiAgICAgIHsgeDogYS54LCB5OiBhLnkgfSwgeyB4OiBiLngsIHk6IGEueSB9LCB7IHg6IGIueCwgeTogYi55IH0sIHsgeDogYS54LCB5OiBiLnkgfSxcbiAgICBdO1xuICAgIGNvbnN0IGVsID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudE5TKFNWR05TLCAncG9seWdvbicpO1xuICAgIGVsLnNldEF0dHJpYnV0ZSgncG9pbnRzJywgY29ybmVycy5tYXAocCA9PiB7IGNvbnN0IHEgPSB0aGlzLnRvUHgocC54LCBwLnkpOyByZXR1cm4gYCR7cS54fSwke3EueX1gOyB9KS5qb2luKCcgJykpO1xuICAgIGVsLnNldEF0dHJpYnV0ZSgnZmlsbCcsICdyZ2JhKDEyMCwxNzAsMjU1LDAuMTUpJyk7XG4gICAgZWwuc2V0QXR0cmlidXRlKCdzdHJva2UnLCAnIzRhOTBlMicpO1xuICAgIGVsLnNldEF0dHJpYnV0ZSgnc3Ryb2tlLWRhc2hhcnJheScsICc0IDMnKTtcbiAgICBlbC5zZXRBdHRyaWJ1dGUoJ3N0cm9rZS13aWR0aCcsICcxJyk7XG4gICAgcmV0dXJuIGVsO1xuICB9XG5cbiAgcHJpdmF0ZSByZWN0UHJldmlldyhhOiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH0sIGI6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSk6IFNWR0VsZW1lbnQge1xuICAgIGNvbnN0IGNvcm5lcnMgPSBbXG4gICAgICB7IHg6IGEueCwgeTogYS55IH0sIHsgeDogYi54LCB5OiBhLnkgfSwgeyB4OiBiLngsIHk6IGIueSB9LCB7IHg6IGEueCwgeTogYi55IH0sXG4gICAgXTtcbiAgICBjb25zdCBlbCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhTVkdOUywgJ3BvbHlnb24nKTtcbiAgICBlbC5zZXRBdHRyaWJ1dGUoJ3BvaW50cycsIGNvcm5lcnMubWFwKHAgPT4geyBjb25zdCBxID0gdGhpcy50b1B4KHAueCwgcC55KTsgcmV0dXJuIGAke3EueH0sJHtxLnl9YDsgfSkuam9pbignICcpKTtcbiAgICBlbC5zZXRBdHRyaWJ1dGUoJ2ZpbGwnLCAnbm9uZScpO1xuICAgIGVsLnNldEF0dHJpYnV0ZSgnc3Ryb2tlJywgdGhpcy5zdG9yZS5nZXRTaGFwZUNvbG9yKCkpO1xuICAgIGVsLnNldEF0dHJpYnV0ZSgnc3Ryb2tlLWRhc2hhcnJheScsICc0IDMnKTtcbiAgICBlbC5zZXRBdHRyaWJ1dGUoJ3N0cm9rZS13aWR0aCcsICcyJyk7XG4gICAgcmV0dXJuIGVsO1xuICB9XG5cbiAgcHJpdmF0ZSBwb2x5UHJldmlldyhwdHM6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfVtdKTogU1ZHRWxlbWVudCB7XG4gICAgY29uc3QgZWwgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50TlMoU1ZHTlMsICdwb2x5bGluZScpO1xuICAgIGVsLnNldEF0dHJpYnV0ZSgncG9pbnRzJywgcHRzLm1hcChwID0+IHsgY29uc3QgcSA9IHRoaXMudG9QeChwLngsIHAueSk7IHJldHVybiBgJHtxLnh9LCR7cS55fWA7IH0pLmpvaW4oJyAnKSk7XG4gICAgZWwuc2V0QXR0cmlidXRlKCdmaWxsJywgJ25vbmUnKTtcbiAgICBlbC5zZXRBdHRyaWJ1dGUoJ3N0cm9rZScsIHRoaXMuc3RvcmUuZ2V0U2hhcGVDb2xvcigpKTtcbiAgICBlbC5zZXRBdHRyaWJ1dGUoJ3N0cm9rZS1kYXNoYXJyYXknLCAnNCAzJyk7XG4gICAgZWwuc2V0QXR0cmlidXRlKCdzdHJva2Utd2lkdGgnLCAnMicpO1xuICAgIHJldHVybiBlbDtcbiAgfVxuXG4gIC8qKiBTVkcgcGF0aCBgZGAgKGVsZW1lbnQtcGl4ZWwgY29vcmRzKSBmb3IgYSBzdHJhaWdodC1lZGdlZCByaW5nL3BvbHlsaW5lLiAqL1xuICBwcml2YXRlIHN0cmFpZ2h0UGF0aEQocHRzOiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH1bXSwgY2xvc2VkOiBib29sZWFuKTogc3RyaW5nIHtcbiAgICBpZiAocHRzLmxlbmd0aCA8IDIpIHJldHVybiAnJztcbiAgICBsZXQgZCA9ICcnO1xuICAgIHB0cy5mb3JFYWNoKChwLCBpKSA9PiB7XG4gICAgICBjb25zdCBxID0gdGhpcy50b1B4KHAueCwgcC55KTtcbiAgICAgIGQgKz0gKGkgPT09IDAgPyAnTSAnIDogJyBMICcpICsgYCR7cS54fSwke3EueX1gO1xuICAgIH0pO1xuICAgIGlmIChjbG9zZWQpIGQgKz0gJyBaJztcbiAgICByZXR1cm4gZDtcbiAgfVxuXG4gIC8qKiBTVkcgcGF0aCBgZGAgKGVsZW1lbnQtcGl4ZWwgY29vcmRzKSBmb3IgdGhlIHNtb290aCBjdWJpYyBiZXppZXIgdGhyb3VnaCBhXG4gICAqICBwb2x5Z29uJ3MgYW5jaG9ycyDigJQgdGhlIHBhcGVyLmpzLWVxdWl2YWxlbnQgY3VydmUuICovXG4gIHByaXZhdGUgYmV6aWVyUGF0aEQocG9seTogUG9seWdvbik6IHN0cmluZyB7XG4gICAgY29uc3QgY2xvc2VkID0gcG9seS5jbG9zZWQgIT09IGZhbHNlO1xuICAgIHJldHVybiB0aGlzLnJpbmdCZXppZXJQYXRoRChwb2x5Lnhwb2ludHMsIHBvbHkueXBvaW50cywgcG9seS5oYW5kbGVzSW4sIHBvbHkuaGFuZGxlc091dCwgY2xvc2VkKTtcbiAgfVxuXG4gIC8qKiBTVkcgY3ViaWMtYmV6aWVyIHBhdGggYGRgIChlbGVtZW50IHB4KSBmb3IgYW55IHJpbmcgKGV4dGVyaW9yIG9yIGhvbGUpLiBVc2VzIHRoZSBzdG9yZWRcbiAgICogIHBlci12ZXJ0ZXggaGFuZGxlIG9mZnNldHMgd2hlbiBwcmVzZW50LCBlbHNlIHRoZSBDYXRtdWxsLVJvbSBkZWZhdWx0IChyZXNvbHZlSGFuZGxlcykuICovXG4gIHByaXZhdGUgcmluZ0JlemllclBhdGhEKFxuICAgIHhzOiBudW1iZXJbXSwgeXM6IG51bWJlcltdLCBpbk9mZjogbnVtYmVyW11bXSB8IHVuZGVmaW5lZCwgb3V0T2ZmOiBudW1iZXJbXVtdIHwgdW5kZWZpbmVkLCBjbG9zZWQ6IGJvb2xlYW4sXG4gICk6IHN0cmluZyB7XG4gICAgY29uc3QgbiA9IE1hdGgubWluKHhzLmxlbmd0aCwgeXMubGVuZ3RoKTtcbiAgICBpZiAobiA8IDIpIHJldHVybiAnJztcbiAgICBjb25zdCBoID0gcmVzb2x2ZUhhbmRsZXMoeHMsIHlzLCBjbG9zZWQsIGluT2ZmLCBvdXRPZmYpO1xuICAgIGNvbnN0IHB4ID0gKHg6IG51bWJlciwgeTogbnVtYmVyKSA9PiB7IGNvbnN0IHEgPSB0aGlzLnRvUHgoeCwgeSk7IHJldHVybiBgJHtxLnh9LCR7cS55fWA7IH07XG4gICAgbGV0IGQgPSBgTSAke3B4KHhzWzBdLCB5c1swXSl9YDtcbiAgICBjb25zdCBzZWdzID0gY2xvc2VkID8gbiA6IG4gLSAxO1xuICAgIGZvciAobGV0IGkgPSAwOyBpIDwgc2VnczsgaSsrKSB7XG4gICAgICBjb25zdCBqID0gKGkgKyAxKSAlIG47XG4gICAgICBjb25zdCBjMSA9IGhbaV0ub3V0O1xuICAgICAgY29uc3QgYzIgPSBoW2pdLmluO1xuICAgICAgZCArPSBgIEMgJHtweChjMVswXSwgYzFbMV0pfSAke3B4KGMyWzBdLCBjMlsxXSl9ICR7cHgoeHNbal0sIHlzW2pdKX1gO1xuICAgIH1cbiAgICBpZiAoY2xvc2VkKSBkICs9ICcgWic7XG4gICAgcmV0dXJuIGQ7XG4gIH1cblxuICAvKipcbiAgICogRHJhdyB0aGUgYmV6aWVyIGVkaXRpbmcgaGFuZGxlcyBmb3IgdGhlIHNlbGVjdGVkIHJlZ2lvbiwgcGFwZXIuanMtc3R5bGU6XG4gICAqIGVhY2ggYW5jaG9yIGFzIGEgc21hbGwgc3F1YXJlLCB3aXRoIHRhbmdlbnQgbGluZXMgb3V0IHRvIGl0cyB0d28gY29udHJvbFxuICAgKiBwb2ludHMgKGRyYXduIGFzIHNtYWxsIGNpcmNsZXMpLlxuICAgKi9cbiAgcHJpdmF0ZSBkcmF3QmV6aWVySGFuZGxlcyhwb2x5OiBQb2x5Z29uLCBjb2xvcjogc3RyaW5nKTogdm9pZCB7XG4gICAgY29uc3QgeHMgPSBwb2x5Lnhwb2ludHM7XG4gICAgY29uc3QgeXMgPSBwb2x5Lnlwb2ludHM7XG4gICAgY29uc3QgZHJhd1JpbmcgPSAocnhzOiBudW1iZXJbXSwgcnlzOiBudW1iZXJbXSwgaW5PZmY6IG51bWJlcltdW10gfCB1bmRlZmluZWQsXG4gICAgICAgICAgICAgICAgICAgICAgb3V0T2ZmOiBudW1iZXJbXVtdIHwgdW5kZWZpbmVkLCBjbG9zZWQ6IGJvb2xlYW4pOiB2b2lkID0+IHtcbiAgICAgIGNvbnN0IGggPSByZXNvbHZlSGFuZGxlcyhyeHMsIHJ5cywgY2xvc2VkLCBpbk9mZiwgb3V0T2ZmKTtcbiAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgcnhzLmxlbmd0aDsgaSsrKSB7XG4gICAgICAgIGNvbnN0IGEgPSB0aGlzLnRvUHgocnhzW2ldLCByeXNbaV0pO1xuICAgICAgICBpZiAoaFtpXS5oYXNJbikgdGhpcy5kcmF3SGFuZGxlKGEsIHRoaXMudG9QeChoW2ldLmluWzBdLCBoW2ldLmluWzFdKSwgY29sb3IpO1xuICAgICAgICBpZiAoaFtpXS5oYXNPdXQpIHRoaXMuZHJhd0hhbmRsZShhLCB0aGlzLnRvUHgoaFtpXS5vdXRbMF0sIGhbaV0ub3V0WzFdKSwgY29sb3IpO1xuICAgICAgICB0aGlzLnN2Zy5hcHBlbmRDaGlsZCh0aGlzLmFuY2hvclNxdWFyZShhLngsIGEueSwgY29sb3IpKTtcbiAgICAgIH1cbiAgICB9O1xuICAgIGRyYXdSaW5nKHhzLCB5cywgcG9seS5oYW5kbGVzSW4sIHBvbHkuaGFuZGxlc091dCwgcG9seS5jbG9zZWQgIT09IGZhbHNlKTtcbiAgICAvLyBEb251dCBob2xlIHJpbmdzIGdldCB0aGVpciBvd24gZWRpdGFibGUgYmV6aWVyIGhhbmRsZXMgKGppdC11aSMxMDIpLlxuICAgIGlmIChwb2x5LmhvbGVzICYmIHBvbHkuaG9sZUhhbmRsZXNJbiAmJiBwb2x5LmhvbGVIYW5kbGVzT3V0KSB7XG4gICAgICBwb2x5LmhvbGVzLmZvckVhY2goKHJpbmcsIGhpKSA9PiB7XG4gICAgICAgIGNvbnN0IGluT2ZmID0gcG9seS5ob2xlSGFuZGxlc0luIVtoaV07XG4gICAgICAgIGNvbnN0IG91dE9mZiA9IHBvbHkuaG9sZUhhbmRsZXNPdXQhW2hpXTtcbiAgICAgICAgaWYgKGluT2ZmICYmIG91dE9mZikgZHJhd1JpbmcocmluZy5tYXAoKHApID0+IHBbMF0pLCByaW5nLm1hcCgocCkgPT4gcFsxXSksIGluT2ZmLCBvdXRPZmYsIHRydWUpO1xuICAgICAgfSk7XG4gICAgfVxuICB9XG5cbiAgLyoqIEEgdGFuZ2VudCBsaW5lIGZyb20gYW4gYW5jaG9yIHRvIGEgY29udHJvbCBwb2ludCwgd2l0aCBhIGNpcmNsZSBhdCB0aGUgZW5kLiAqL1xuICBwcml2YXRlIGRyYXdIYW5kbGUoYW5jaG9yOiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH0sIGN0cmw6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSwgY29sb3I6IHN0cmluZyk6IHZvaWQge1xuICAgIGNvbnN0IGxpbmUgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50TlMoU1ZHTlMsICdsaW5lJyk7XG4gICAgbGluZS5zZXRBdHRyaWJ1dGUoJ3gxJywgYCR7YW5jaG9yLnh9YCk7IGxpbmUuc2V0QXR0cmlidXRlKCd5MScsIGAke2FuY2hvci55fWApO1xuICAgIGxpbmUuc2V0QXR0cmlidXRlKCd4MicsIGAke2N0cmwueH1gKTsgbGluZS5zZXRBdHRyaWJ1dGUoJ3kyJywgYCR7Y3RybC55fWApO1xuICAgIGxpbmUuc2V0QXR0cmlidXRlKCdzdHJva2UnLCBjb2xvcik7XG4gICAgbGluZS5zZXRBdHRyaWJ1dGUoJ3N0cm9rZS13aWR0aCcsICcxJyk7XG4gICAgdGhpcy5zdmcuYXBwZW5kQ2hpbGQobGluZSk7XG4gICAgY29uc3QgYyA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhTVkdOUywgJ2NpcmNsZScpO1xuICAgIGMuc2V0QXR0cmlidXRlKCdjeCcsIGAke2N0cmwueH1gKTsgYy5zZXRBdHRyaWJ1dGUoJ2N5JywgYCR7Y3RybC55fWApO1xuICAgIGMuc2V0QXR0cmlidXRlKCdyJywgJzMnKTtcbiAgICBjLnNldEF0dHJpYnV0ZSgnZmlsbCcsIGNvbG9yKTtcbiAgICB0aGlzLnN2Zy5hcHBlbmRDaGlsZChjKTtcbiAgfVxuXG4gIC8qKiBBIGZpbGxlZC13aGl0ZSBhbmNob3Igc3F1YXJlICh0aGUgZWRpdGFibGUgdmVydGV4KS4gKi9cbiAgcHJpdmF0ZSBhbmNob3JTcXVhcmUoeDogbnVtYmVyLCB5OiBudW1iZXIsIGNvbG9yOiBzdHJpbmcpOiBTVkdFbGVtZW50IHtcbiAgICBjb25zdCByID0gMy41O1xuICAgIGNvbnN0IHJlY3QgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50TlMoU1ZHTlMsICdyZWN0Jyk7XG4gICAgcmVjdC5zZXRBdHRyaWJ1dGUoJ3gnLCBgJHt4IC0gcn1gKTsgcmVjdC5zZXRBdHRyaWJ1dGUoJ3knLCBgJHt5IC0gcn1gKTtcbiAgICByZWN0LnNldEF0dHJpYnV0ZSgnd2lkdGgnLCBgJHsyICogcn1gKTsgcmVjdC5zZXRBdHRyaWJ1dGUoJ2hlaWdodCcsIGAkezIgKiByfWApO1xuICAgIHJlY3Quc2V0QXR0cmlidXRlKCdmaWxsJywgJyNmZmZmZmYnKTtcbiAgICByZWN0LnNldEF0dHJpYnV0ZSgnc3Ryb2tlJywgY29sb3IpO1xuICAgIHJlY3Quc2V0QXR0cmlidXRlKCdzdHJva2Utd2lkdGgnLCAnMicpO1xuICAgIHJldHVybiByZWN0O1xuICB9XG5cbiAgcHJpdmF0ZSByZ2JhKGNvbG9yOiBzdHJpbmcsIGFscGhhOiBudW1iZXIpOiBzdHJpbmcge1xuICAgIC8vIEFjY2VwdCAjcnJnZ2JiOyBmYWxsIGJhY2sgdG8gdGhlIGNvbG9yIGFzLWlzIGZvciBuYW1lZC9yZ2IgdmFsdWVzLlxuICAgIGlmICgvXiMoWzAtOWEtZl17Nn0pJC9pLnRlc3QoY29sb3IpKSB7XG4gICAgICBjb25zdCByID0gcGFyc2VJbnQoY29sb3Iuc2xpY2UoMSwgMyksIDE2KTtcbiAgICAgIGNvbnN0IGcgPSBwYXJzZUludChjb2xvci5zbGljZSgzLCA1KSwgMTYpO1xuICAgICAgY29uc3QgYiA9IHBhcnNlSW50KGNvbG9yLnNsaWNlKDUsIDcpLCAxNik7XG4gICAgICByZXR1cm4gYHJnYmEoJHtyfSwke2d9LCR7Yn0sJHthbHBoYX0pYDtcbiAgICB9XG4gICAgcmV0dXJuIGNvbG9yO1xuICB9XG5cbiAgLy8g4pSA4pSAIGludGVyYWN0aW9uIOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgFxuICBwcml2YXRlIGdldCBpc0ZyZWVoYW5kKCk6IGJvb2xlYW4ge1xuICAgIHJldHVybiB0aGlzLm1vZGUgPT09ICdkcmF3Y2xvc2VkcGF0aCcgfHwgdGhpcy5tb2RlID09PSAnZHJhd29wZW5wYXRoJztcbiAgfVxuXG4gIHByaXZhdGUgb25QcmVzcyhlOiBhbnkpOiB2b2lkIHtcbiAgICBpZiAodGhpcy5tb2RlID09PSAnZHJhd3JlY3QnKSB7XG4gICAgICB0aGlzLnJlY3RTdGFydCA9IHRoaXMudG9JbWFnZShlLnBvc2l0aW9uKTtcbiAgICAgIHRoaXMucmVjdEN1cnJlbnQgPSB0aGlzLnJlY3RTdGFydDtcbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgaWYgKHRoaXMuaXNGcmVlaGFuZCkge1xuICAgICAgLy8gRnJlZWhhbmQgZHJhdyAobWF0Y2hlcyBQbG90bHkgZHJhd2Nsb3NlZHBhdGgvZHJhd29wZW5wYXRoKTogcHJlc3MgdG9cbiAgICAgIC8vIHN0YXJ0LCBkcmFnIHRvIHRyYWNlLCByZWxlYXNlIHRvIGNvbW1pdC5cbiAgICAgIHRoaXMuZnJlZWhhbmREcmFnZ2luZyA9IHRydWU7XG4gICAgICB0aGlzLnBvbHlQb2ludHMgPSBbdGhpcy50b0ltYWdlKGUucG9zaXRpb24pXTtcbiAgICAgIHRoaXMubGFzdEZyZWVoYW5kUHggPSB7IHg6IGUucG9zaXRpb24ueCwgeTogZS5wb3NpdGlvbi55IH07XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGlmICh0aGlzLm1vZGUgPT09ICdtb3ZlJykge1xuICAgICAgLy8gV2hvbGUtcmVnaW9uIGRyYWcgKCdtb3ZlJyBtb2RlKTogcHJlc3MgaW5zaWRlIHRoZSBzZWxlY3RlZCByZWdpb25cbiAgICAgIC8vIHRvIHRyYW5zbGF0ZSBpdCwgaWdub3JpbmcgdmVydGljZXMvZWRnZXMuXG4gICAgICBjb25zdCBzZWwgPSB0aGlzLnNlbGVjdGVkUmVnaW9uSW5mbygpO1xuICAgICAgaWYgKHNlbCAmJiB0aGlzLmNvbnRhaW5zUG9pbnQoc2VsLnJlZ2lvbiwgdGhpcy50b0ltYWdlKGUucG9zaXRpb24pKSkge1xuICAgICAgICB0aGlzLnN0YXJ0RWRpdCgnYm91bmRzJywgJ21vdmUnLCAtMSwgc2VsLnJlZ2lvbiwgdGhpcy50b0ltYWdlKGUucG9zaXRpb24pKTtcbiAgICAgIH1cbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgaWYgKHRoaXMubW9kZSA9PT0gJ3NlbGVjdCcpIHtcbiAgICAgIC8vIEEgYmV6aWVyIGNvbnRyb2wgaGFuZGxlIHRha2VzIHRvcCBwcmlvcml0eSAoaXQgc2l0cyBvZmYgdGhlIGFuY2hvcikuXG4gICAgICBjb25zdCBoaCA9IHRoaXMuaGl0QmV6aWVySGFuZGxlKGUucG9zaXRpb24pO1xuICAgICAgaWYgKGhoKSB7XG4gICAgICAgIGNvbnN0IHJlZ2lvbiA9IHRoaXMuc3RvcmUuZ2V0UmVnaW9ucygpW3RoaXMuc2VsZWN0ZWRbdGhpcy5zZWxlY3RlZC5sZW5ndGggLSAxXV07XG4gICAgICAgIHRoaXMuc3RhcnRFZGl0KCdoYW5kbGUnLCAnbW92ZScsIGhoLmluZGV4LCByZWdpb24sIHRoaXMudG9JbWFnZShlLnBvc2l0aW9uKSwgaGguc2lkZSwgaGgucmluZyk7XG4gICAgICAgIHJldHVybjtcbiAgICAgIH1cbiAgICAgIC8vIFRoZW4gZHJhZ2dpbmcgYSBzaW5nbGUgcG9seWdvbiB2ZXJ0ZXggKG92ZXIgYm9keS1tb3ZlL3Jlc2l6ZSkg4oCUXG4gICAgICAvLyAnc2VsZWN0JyBncmFicyB0aGUgbmVhcmVzdCBzZWdtZW50IGZpcnN0LlxuICAgICAgY29uc3QgdmggPSB0aGlzLmhpdFZlcnRleChlLnBvc2l0aW9uKTtcbiAgICAgIGlmICh2aCkge1xuICAgICAgICBjb25zdCByZWdpb24gPSB0aGlzLnN0b3JlLmdldFJlZ2lvbnMoKVt0aGlzLnNlbGVjdGVkW3RoaXMuc2VsZWN0ZWQubGVuZ3RoIC0gMV1dO1xuICAgICAgICB0aGlzLnN0YXJ0RWRpdCgndmVydGV4JywgJ21vdmUnLCB2aC5pbmRleCwgcmVnaW9uLCB0aGlzLnRvSW1hZ2UoZS5wb3NpdGlvbiksICdvdXQnLCB2aC5yaW5nKTtcbiAgICAgICAgcmV0dXJuO1xuICAgICAgfVxuICAgICAgLy8gT3RoZXJ3aXNlIHN0YXJ0IGEgbW92ZS9yZXNpemUgd2hlbiBwcmVzc2luZyB0aGUgc2VsZWN0ZWQgcmVnaW9uJ3NcbiAgICAgIC8vIGJvZHkvaGFuZGxlcy5cbiAgICAgIGNvbnN0IGV6ID0gdGhpcy5lZGl0Wm9uZUF0KGUucG9zaXRpb24pO1xuICAgICAgaWYgKGV6KSB7XG4gICAgICAgIHRoaXMuc3RhcnRFZGl0KCdib3VuZHMnLCBlei56b25lLCAtMSwgdGhpcy5zdG9yZS5nZXRSZWdpb25zKClbZXouaW5kZXhdLCB0aGlzLnRvSW1hZ2UoZS5wb3NpdGlvbikpO1xuICAgICAgICByZXR1cm47XG4gICAgICB9XG4gICAgICAvLyBQcmVzcyBvbiBlbXB0eSBzcGFjZSAvIGEgbm9uLXNlbGVjdGVkIHJlZ2lvbjogYmVnaW4gYSBydWJiZXItYmFuZFxuICAgICAgLy8gbXVsdGktc2VsZWN0LiBBIHBsYWluIGNsaWNrIChubyBkcmFnKSBmYWxscyB0aHJvdWdoIHRvIG9uQ2xpY2ssIHdoaWNoXG4gICAgICAvLyBzaW5nbGUtc2VsZWN0cyBvciBjbGVhcnMuXG4gICAgICB0aGlzLmJhbmRTdGFydCA9IHRoaXMudG9JbWFnZShlLnBvc2l0aW9uKTtcbiAgICAgIHRoaXMuYmFuZEN1cnJlbnQgPSB0aGlzLmJhbmRTdGFydDtcbiAgICAgIHRoaXMuYmFuZERyYWdnZWQgPSBmYWxzZTtcbiAgICB9XG4gIH1cblxuICAvKiogQmVnaW4gYW4gZWRpdCBnZXN0dXJlIChtb3ZlL3Jlc2l6ZSBvciBzaW5nbGUtdmVydGV4IGRyYWcpIGFuZCBvcGVuIGEgc3RvcmVcbiAgICogIGJhdGNoIHNvIHRoZSBsaXZlIGRyYWcgZW1pdHMgb25jZSBvbiByZWxlYXNlLiAqL1xuICBwcml2YXRlIHN0YXJ0RWRpdChraW5kOiAnYm91bmRzJyB8ICd2ZXJ0ZXgnIHwgJ2hhbmRsZScsIHpvbmU6IEVkaXRab25lLCB2ZXJ0ZXhJbmRleDogbnVtYmVyLFxuICAgICAgICAgICAgICAgICAgICByZWdpb246IFJlZ2lvbiwgc3RhcnRJbWc6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSxcbiAgICAgICAgICAgICAgICAgICAgaGFuZGxlU2lkZTogJ2luJyB8ICdvdXQnID0gJ291dCcsIHJpbmcgPSAtMSk6IHZvaWQge1xuICAgIHRoaXMuZWRpdCA9IHtcbiAgICAgIGtpbmQsIHpvbmUsIHZlcnRleEluZGV4LCByaW5nLCBoYW5kbGVTaWRlLCBpZDogcmVnaW9uLmlkLFxuICAgICAgc3RhcnRJbWcsIG9yaWc6IGtpbmQgPT09ICdib3VuZHMnID8gdGhpcy5zbmFwc2hvdChyZWdpb24pIDogbnVsbCxcbiAgICB9O1xuICAgIHRoaXMuZWRpdERyYWdnZWQgPSBmYWxzZTtcbiAgICB0aGlzLnN0b3JlLmJlZ2luQmF0Y2goKTtcbiAgfVxuXG4gIHByaXZhdGUgb25EcmFnKGU6IGFueSk6IHZvaWQge1xuICAgIGlmICh0aGlzLm1vZGUgPT09ICdkcmF3cmVjdCcgJiYgdGhpcy5yZWN0U3RhcnQpIHtcbiAgICAgIHRoaXMucmVjdEN1cnJlbnQgPSB0aGlzLnRvSW1hZ2UoZS5wb3NpdGlvbik7XG4gICAgICB0aGlzLnJlZHJhdygpO1xuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICBpZiAodGhpcy5mcmVlaGFuZERyYWdnaW5nICYmIHRoaXMuaXNGcmVlaGFuZCkge1xuICAgICAgLy8gVGhpbiB0aGUgcGF0aDogb25seSBzYW1wbGUgb25jZSB0aGUgY3Vyc29yIGhhcyBtb3ZlZCBhIGZldyBzY3JlZW4gcHguXG4gICAgICBjb25zdCBsYXN0ID0gdGhpcy5sYXN0RnJlZWhhbmRQeDtcbiAgICAgIGlmICghbGFzdCB8fCBNYXRoLmh5cG90KGUucG9zaXRpb24ueCAtIGxhc3QueCwgZS5wb3NpdGlvbi55IC0gbGFzdC55KSA+PSA0KSB7XG4gICAgICAgIHRoaXMucG9seVBvaW50cy5wdXNoKHRoaXMudG9JbWFnZShlLnBvc2l0aW9uKSk7XG4gICAgICAgIHRoaXMubGFzdEZyZWVoYW5kUHggPSB7IHg6IGUucG9zaXRpb24ueCwgeTogZS5wb3NpdGlvbi55IH07XG4gICAgICAgIHRoaXMucmVkcmF3KCk7XG4gICAgICB9XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGlmICh0aGlzLmVkaXQpIHtcbiAgICAgIHRoaXMuZWRpdERyYWdnZWQgPSB0cnVlO1xuICAgICAgdGhpcy5hcHBseUVkaXQodGhpcy50b0ltYWdlKGUucG9zaXRpb24pKTtcbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgaWYgKHRoaXMuYmFuZFN0YXJ0KSB7XG4gICAgICB0aGlzLmJhbmRDdXJyZW50ID0gdGhpcy50b0ltYWdlKGUucG9zaXRpb24pO1xuICAgICAgdGhpcy5iYW5kRHJhZ2dlZCA9IHRydWU7XG4gICAgICB0aGlzLnJlZHJhdygpO1xuICAgIH1cbiAgfVxuXG4gIHByaXZhdGUgb25SZWxlYXNlKGU6IGFueSk6IHZvaWQge1xuICAgIGlmICh0aGlzLm1vZGUgPT09ICdkcmF3cmVjdCcgJiYgdGhpcy5yZWN0U3RhcnQpIHtcbiAgICAgIGNvbnN0IGVuZCA9IHRoaXMudG9JbWFnZShlLnBvc2l0aW9uKTtcbiAgICAgIGNvbnN0IHggPSBNYXRoLm1pbih0aGlzLnJlY3RTdGFydC54LCBlbmQueCk7XG4gICAgICBjb25zdCB5ID0gTWF0aC5taW4odGhpcy5yZWN0U3RhcnQueSwgZW5kLnkpO1xuICAgICAgY29uc3QgdyA9IE1hdGguYWJzKGVuZC54IC0gdGhpcy5yZWN0U3RhcnQueCk7XG4gICAgICBjb25zdCBoID0gTWF0aC5hYnMoZW5kLnkgLSB0aGlzLnJlY3RTdGFydC55KTtcbiAgICAgIHRoaXMucmVjdFN0YXJ0ID0gdGhpcy5yZWN0Q3VycmVudCA9IG51bGw7XG4gICAgICBpZiAodyA+IDIgJiYgaCA+IDIpIHRoaXMuY29tbWl0UmVjdGFuZ2xlKHgsIHksIHcsIGgpO1xuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICBpZiAodGhpcy5mcmVlaGFuZERyYWdnaW5nKSB7XG4gICAgICB0aGlzLmZyZWVoYW5kRHJhZ2dpbmcgPSBmYWxzZTtcbiAgICAgIHRoaXMubGFzdEZyZWVoYW5kUHggPSBudWxsO1xuICAgICAgLy8gQ2xvc2VkID0gZnJlZWZvcm0gKGRyYXdjbG9zZWRwYXRoKTsgb3BlbiA9IHBvbHlsaW5lIChkcmF3b3BlbnBhdGgpLlxuICAgICAgdGhpcy5jb21taXRQb2x5Z29uKHRoaXMubW9kZSA9PT0gJ2RyYXdjbG9zZWRwYXRoJyk7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIC8vIE1vdmUvcmVzaXplIGFscmVhZHkgYXBwbGllZCBsaXZlOyBmbHVzaCB0aGUgY29hbGVzY2VkIGVkaXRzICsgZW5kIHRoZVxuICAgIC8vIGdlc3R1cmUgKGtlZXAgc2VsZWN0aW9uKS5cbiAgICBpZiAodGhpcy5lZGl0KSB7XG4gICAgICB0aGlzLnN0b3JlLmVuZEJhdGNoKCk7XG4gICAgICB0aGlzLmVkaXQgPSBudWxsO1xuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICAvLyBGaW5pc2ggYSBydWJiZXItYmFuZCBzZWxlY3Rpb246IHNlbGVjdCBldmVyeSByZWdpb24gdGhlIGJhbmQgaW50ZXJzZWN0cy5cbiAgICBpZiAodGhpcy5iYW5kU3RhcnQpIHtcbiAgICAgIGNvbnN0IHN0YXJ0ID0gdGhpcy5iYW5kU3RhcnQ7XG4gICAgICBjb25zdCBlbmQgPSB0aGlzLmJhbmRDdXJyZW50ID8/IHN0YXJ0O1xuICAgICAgdGhpcy5iYW5kU3RhcnQgPSB0aGlzLmJhbmRDdXJyZW50ID0gbnVsbDtcbiAgICAgIGNvbnN0IHgwID0gTWF0aC5taW4oc3RhcnQueCwgZW5kLngpLCB5MCA9IE1hdGgubWluKHN0YXJ0LnksIGVuZC55KTtcbiAgICAgIGNvbnN0IHgxID0gTWF0aC5tYXgoc3RhcnQueCwgZW5kLngpLCB5MSA9IE1hdGgubWF4KHN0YXJ0LnksIGVuZC55KTtcbiAgICAgIC8vIE9ubHkgYSByZWFsIGRyYWcgc2VsZWN0czsgYSBjbGljay1zaXplZCBiYW5kIGZhbGxzIHRocm91Z2ggdG8gb25DbGljay5cbiAgICAgIGlmICh0aGlzLmJhbmREcmFnZ2VkICYmICh4MSAtIHgwID4gMiB8fCB5MSAtIHkwID4gMikpIHtcbiAgICAgICAgdGhpcy5zdG9yZS5zZXRTZWxlY3RlZFNoYXBlSW5kaWNlcyh0aGlzLnJlZ2lvbnNJblJlY3QoeDAsIHkwLCB4MSwgeTEpKTtcbiAgICAgIH1cbiAgICAgIHRoaXMucmVkcmF3KCk7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSBvbkNsaWNrKGU6IGFueSk6IHZvaWQge1xuICAgIGlmICh0aGlzLm1vZGUgPT09ICdzZWxlY3QnKSB7XG4gICAgICAvLyBBIG1vdmUvcmVzaXplL3ZlcnRleCBkcmFnIG9yIGEgcnViYmVyLWJhbmQgZHJhZyBhbHNvIGVuZHMgd2l0aCBhIGNsaWNrXG4gICAgICAvLyBldmVudCDigJQgZG9uJ3QgdHJlYXQgaXQgYXMgYSByZS1zZWxlY3Rpb24uXG4gICAgICBpZiAodGhpcy5lZGl0RHJhZ2dlZCkgeyB0aGlzLmVkaXREcmFnZ2VkID0gZmFsc2U7IHJldHVybjsgfVxuICAgICAgaWYgKHRoaXMuYmFuZERyYWdnZWQpIHsgdGhpcy5iYW5kRHJhZ2dlZCA9IGZhbHNlOyByZXR1cm47IH1cbiAgICAgIC8vIFNoaWZ0IChvciBDbWQvQ3RybCkgdG9nZ2xlcyB0aGUgY2xpY2tlZCByZWdpb24gaW4vb3V0IG9mIHRoZSBjdXJyZW50XG4gICAgICAvLyBzZWxlY3Rpb247IGEgcGxhaW4gY2xpY2sgcmVwbGFjZXMgaXQuXG4gICAgICBjb25zdCBvZSA9IGUub3JpZ2luYWxFdmVudDtcbiAgICAgIGNvbnN0IGFkZGl0aXZlID0gISFvZSAmJiAob2Uuc2hpZnRLZXkgfHwgb2UubWV0YUtleSB8fCBvZS5jdHJsS2V5KTtcbiAgICAgIHRoaXMuc2VsZWN0QXQodGhpcy50b0ltYWdlKGUucG9zaXRpb24pLCBhZGRpdGl2ZSk7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGlmICh0aGlzLm1vZGUgPT09ICdkcmF3cG9seWdvbicpIHtcbiAgICAgIHRoaXMub25EcmF3UG9seWdvbkNsaWNrKGUpO1xuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICBpZiAodGhpcy5tb2RlID09PSAnYWRkcG9pbnQnKSB7XG4gICAgICAvLyBJbnNlcnQgYSB2ZXJ0ZXggb24gdGhlIGNsaWNrZWQgZWRnZSDigJQgZXh0ZXJpb3Igb3IgYW4gaW50ZXJpb3IgcmluZy5cbiAgICAgIGNvbnN0IHNlbCA9IHRoaXMuc2VsZWN0ZWRSZWdpb25JbmZvKCk7XG4gICAgICBjb25zdCBlZGdlID0gc2VsID8gdGhpcy5oaXRFZGdlKGUucG9zaXRpb24sIHNlbC5yZWdpb24pIDogbnVsbDtcbiAgICAgIGlmIChzZWwgJiYgZWRnZSkge1xuICAgICAgICBpZiAoZWRnZS5yaW5nIDwgMCkgdGhpcy5zdG9yZS5hZGRWZXJ0ZXgoc2VsLnJlZ2lvbi5pZCwgZWRnZS5zZWdJbmRleCwgZWRnZS54LCBlZGdlLnkpO1xuICAgICAgICBlbHNlIHRoaXMuc3RvcmUuYWRkSG9sZVZlcnRleChzZWwucmVnaW9uLmlkLCBlZGdlLnJpbmcsIGVkZ2Uuc2VnSW5kZXgsIGVkZ2UueCwgZWRnZS55KTtcbiAgICAgIH1cbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgaWYgKHRoaXMubW9kZSA9PT0gJ2RlbGV0ZXBvaW50Jykge1xuICAgICAgLy8gUmVtb3ZlIHRoZSBjbGlja2VkIHZlcnRleCDigJQgZXh0ZXJpb3Igb3IgYW4gaW50ZXJpb3IgcmluZyAoaml0LXVpIzg1KS5cbiAgICAgIGNvbnN0IHZoID0gdGhpcy5oaXRWZXJ0ZXgoZS5wb3NpdGlvbik7XG4gICAgICBpZiAodmgpIHtcbiAgICAgICAgaWYgKHZoLnJpbmcgPCAwKSB0aGlzLnN0b3JlLmRlbGV0ZVZlcnRleCh2aC5pZCwgdmguaW5kZXgpO1xuICAgICAgICBlbHNlIHRoaXMuc3RvcmUuZGVsZXRlSG9sZVZlcnRleCh2aC5pZCwgdmgucmluZywgdmguaW5kZXgpO1xuICAgICAgfVxuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgfVxuXG4gIC8qKlxuICAgKiBDbGljay10by1wbGFjZSBwb2x5Z29uICgnZHJhd3BvbHlnb24nKTogdGhlIGZpcnN0IGNsaWNrIHN0YXJ0cyB0aGVcbiAgICogcG9seWdvbiwgZWFjaCBzdWJzZXF1ZW50IGNsaWNrIGFkZHMgYSB2ZXJ0ZXgsIGFuZCBjbGlja2luZyBuZWFyIHRoZSBmaXJzdFxuICAgKiB2ZXJ0ZXggKHdpdGggYXQgbGVhc3QgMyBwbGFjZWQpIGNsb3NlcyBhbmQgY29tbWl0cyBpdC5cbiAgICovXG4gIHByaXZhdGUgb25EcmF3UG9seWdvbkNsaWNrKGU6IGFueSk6IHZvaWQge1xuICAgIGNvbnN0IHB0ID0gdGhpcy50b0ltYWdlKGUucG9zaXRpb24pO1xuICAgIGlmICghdGhpcy5kcmF3aW5nUG9seWdvbikge1xuICAgICAgdGhpcy5wb2x5UG9pbnRzID0gW3B0XTtcbiAgICAgIHRoaXMuZHJhd2luZ1BvbHlnb24gPSB0cnVlO1xuICAgICAgdGhpcy5yZWRyYXcoKTtcbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgY29uc3QgZmlyc3QgPSB0aGlzLnRvUHgodGhpcy5wb2x5UG9pbnRzWzBdLngsIHRoaXMucG9seVBvaW50c1swXS55KTtcbiAgICBjb25zdCBvbkZpcnN0ID0gTWF0aC5oeXBvdChlLnBvc2l0aW9uLnggLSBmaXJzdC54LCBlLnBvc2l0aW9uLnkgLSBmaXJzdC55KSA8PSBFRElUX1RPTDtcbiAgICBpZiAob25GaXJzdCAmJiB0aGlzLnBvbHlQb2ludHMubGVuZ3RoID49IDMpIHtcbiAgICAgIHRoaXMuY29tbWl0UG9seWdvbih0cnVlKTsgLy8gY2xvc2VzICsgcmVzZXRzIGluLXByb2dyZXNzIChpbmNsLiBkcmF3aW5nUG9seWdvbilcbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgdGhpcy5wb2x5UG9pbnRzLnB1c2gocHQpO1xuICAgIHRoaXMucmVkcmF3KCk7XG4gIH1cblxuICAvKipcbiAgICogSG92ZXIgZmVlZGJhY2sgaW4gc2VsZWN0IG1vZGU6IG1vdmUvcmVzaXplIGN1cnNvcnMgb3ZlciB0aGUgc2VsZWN0ZWRcbiAgICogcmVnaW9uJ3MgYm9keS9lZGdlcy9jb3JuZXJzLCBhIHBvaW50ZXIgb3ZlciBhbnkgb3RoZXIgcmVnaW9uLlxuICAgKi9cbiAgcHJpdmF0ZSBvbk1vdmUoZTogYW55KTogdm9pZCB7XG4gICAgaWYgKHRoaXMubW9kZSAhPT0gJ3NlbGVjdCcpIHJldHVybjtcbiAgICAvLyBBIGdyYWJiYWJsZSBiZXppZXIgY29udHJvbCBoYW5kbGUgb3IgdmVydGV4IG9mIHRoZSBzZWxlY3RlZCBwb2x5Z29uIHRha2VzXG4gICAgLy8gcHJpb3JpdHkuXG4gICAgaWYgKHRoaXMuaGl0QmV6aWVySGFuZGxlKGUucG9zaXRpb24pIHx8IHRoaXMuaGl0VmVydGV4KGUucG9zaXRpb24pKSB7XG4gICAgICAodGhpcy52aWV3ZXIuY2FudmFzIGFzIEhUTUxFbGVtZW50KS5zdHlsZS5jdXJzb3IgPSAncG9pbnRlcic7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGNvbnN0IGV6ID0gdGhpcy5lZGl0Wm9uZUF0KGUucG9zaXRpb24pO1xuICAgIGlmIChleikge1xuICAgICAgKHRoaXMudmlld2VyLmNhbnZhcyBhcyBIVE1MRWxlbWVudCkuc3R5bGUuY3Vyc29yID0gWk9ORV9DVVJTT1JbZXouem9uZV07XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIHRoaXMudXBkYXRlQ3Vyc29yKHRoaXMucmVnaW9uSW5kZXhBdCh0aGlzLnRvSW1hZ2UoZS5wb3NpdGlvbikpID49IDApO1xuICB9XG5cbiAgLyoqXG4gICAqIFRoZSBtb3ZlL3Jlc2l6ZSB6b25lIHVuZGVyIHRoZSBjdXJzb3IgZm9yIHRoZSBjdXJyZW50bHktc2VsZWN0ZWQgcmVnaW9uXG4gICAqIChyZWN0YW5nbGVzIGdldCBlZGdlL2Nvcm5lciBoYW5kbGVzICsgYm9keTsgcG9seWdvbnMgZ2V0IGJvZHktbW92ZSBvbmx5KSxcbiAgICogb3IgbnVsbCBpZiB0aGUgY3Vyc29yIGlzbid0IG92ZXIgdGhlIHNlbGVjdGVkIHJlZ2lvbi5cbiAgICovXG4gIHByaXZhdGUgZWRpdFpvbmVBdChwb3NpdGlvbjogeyB4OiBudW1iZXI7IHk6IG51bWJlciB9KTogeyB6b25lOiBFZGl0Wm9uZTsgaW5kZXg6IG51bWJlciB9IHwgbnVsbCB7XG4gICAgaWYgKHRoaXMuc2VsZWN0ZWQubGVuZ3RoID09PSAwKSByZXR1cm4gbnVsbDtcbiAgICBjb25zdCBpbmRleCA9IHRoaXMuc2VsZWN0ZWRbdGhpcy5zZWxlY3RlZC5sZW5ndGggLSAxXTtcbiAgICBjb25zdCByZWdpb24gPSB0aGlzLnN0b3JlLmdldFJlZ2lvbnMoKVtpbmRleF07XG4gICAgaWYgKCFyZWdpb24pIHJldHVybiBudWxsO1xuICAgIGNvbnN0IGIgPSByZWdpb24uYm91bmRzO1xuICAgIGlmIChiIGluc3RhbmNlb2YgUmVjdGFuZ2xlKSB7XG4gICAgICBjb25zdCBhID0gdGhpcy50b1B4KGIueCwgYi55KTtcbiAgICAgIGNvbnN0IGMgPSB0aGlzLnRvUHgoYi54ICsgYi53aWR0aCwgYi55ICsgYi5oZWlnaHQpO1xuICAgICAgY29uc3Qgem9uZSA9IHRoaXMucmVjdFpvbmUocG9zaXRpb24ueCwgcG9zaXRpb24ueSxcbiAgICAgICAgTWF0aC5taW4oYS54LCBjLngpLCBNYXRoLm1pbihhLnksIGMueSksIE1hdGgubWF4KGEueCwgYy54KSwgTWF0aC5tYXgoYS55LCBjLnkpKTtcbiAgICAgIHJldHVybiB6b25lID8geyB6b25lLCBpbmRleCB9IDogbnVsbDtcbiAgICB9XG4gICAgaWYgKGIgaW5zdGFuY2VvZiBQb2x5Z29uIHx8IGIgaW5zdGFuY2VvZiBNdWx0aVBvbHlnb24pIHtcbiAgICAgIC8vIFBvbHlnb25zICsgbXVsdGktcGFydCByZWdpb25zIHN1cHBvcnQgd2hvbGUtcmVnaW9uIG1vdmUgKG5vIHJlc2l6ZSB6b25lcykuXG4gICAgICByZXR1cm4gdGhpcy5jb250YWluc1BvaW50KHJlZ2lvbiwgdGhpcy50b0ltYWdlKHBvc2l0aW9uKSkgPyB7IHpvbmU6ICdtb3ZlJywgaW5kZXggfSA6IG51bGw7XG4gICAgfVxuICAgIHJldHVybiBudWxsO1xuICB9XG5cbiAgLyoqIFRoZSBjdXJyZW50bHktc2VsZWN0ZWQgcmVnaW9uICh0aGUgbGFzdCBvbmUgc2VsZWN0ZWQpLCBvciBudWxsLiAqL1xuICBwcml2YXRlIHNlbGVjdGVkUmVnaW9uSW5mbygpOiB7IHJlZ2lvbjogUmVnaW9uOyBpbmRleDogbnVtYmVyIH0gfCBudWxsIHtcbiAgICBpZiAodGhpcy5zZWxlY3RlZC5sZW5ndGggPT09IDApIHJldHVybiBudWxsO1xuICAgIGNvbnN0IGluZGV4ID0gdGhpcy5zZWxlY3RlZFt0aGlzLnNlbGVjdGVkLmxlbmd0aCAtIDFdO1xuICAgIGNvbnN0IHJlZ2lvbiA9IHRoaXMuc3RvcmUuZ2V0UmVnaW9ucygpW2luZGV4XTtcbiAgICByZXR1cm4gcmVnaW9uID8geyByZWdpb24sIGluZGV4IH0gOiBudWxsO1xuICB9XG5cbiAgLyoqIFRoZSB2ZXJ0ZXggb2YgdGhlIHNlbGVjdGVkIHBvbHlnb24gdW5kZXIgdGhlIGN1cnNvciAoc2NyZWVuLXBpeGVsXG4gICAqICB0b2xlcmFuY2UpLCBvciBudWxsLiBSZWN0YW5nbGVzIGhhdmUgbm8gZWRpdGFibGUgdmVydGljZXMuICovXG4gIHByaXZhdGUgaGl0VmVydGV4KHBvc2l0aW9uOiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH0pOiB7IGlkOiBudW1iZXI7IHJpbmc6IG51bWJlcjsgaW5kZXg6IG51bWJlciB9IHwgbnVsbCB7XG4gICAgY29uc3Qgc2VsID0gdGhpcy5zZWxlY3RlZFJlZ2lvbkluZm8oKTtcbiAgICBpZiAoIXNlbCB8fCAhKHNlbC5yZWdpb24uYm91bmRzIGluc3RhbmNlb2YgUG9seWdvbikpIHJldHVybiBudWxsO1xuICAgIGNvbnN0IGIgPSBzZWwucmVnaW9uLmJvdW5kcztcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IGIueHBvaW50cy5sZW5ndGg7IGkrKykge1xuICAgICAgY29uc3QgcSA9IHRoaXMudG9QeChiLnhwb2ludHNbaV0sIGIueXBvaW50c1tpXSk7XG4gICAgICBpZiAoTWF0aC5oeXBvdChwb3NpdGlvbi54IC0gcS54LCBwb3NpdGlvbi55IC0gcS55KSA8PSBFRElUX1RPTCkge1xuICAgICAgICByZXR1cm4geyBpZDogc2VsLnJlZ2lvbi5pZCwgcmluZzogLTEsIGluZGV4OiBpIH07XG4gICAgICB9XG4gICAgfVxuICAgIC8vIEludGVyaW9yLXJpbmcgKGhvbGUpIHZlcnRpY2VzIGFyZSBkcmFnZ2FibGUgdG9vIChqaXQtdWkjODUpLlxuICAgIGlmIChiLmhvbGVzKSB7XG4gICAgICBmb3IgKGxldCBoID0gMDsgaCA8IGIuaG9sZXMubGVuZ3RoOyBoKyspIHtcbiAgICAgICAgY29uc3QgcmluZyA9IGIuaG9sZXNbaF07XG4gICAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgcmluZy5sZW5ndGg7IGkrKykge1xuICAgICAgICAgIGNvbnN0IHEgPSB0aGlzLnRvUHgocmluZ1tpXVswXSwgcmluZ1tpXVsxXSk7XG4gICAgICAgICAgaWYgKE1hdGguaHlwb3QocG9zaXRpb24ueCAtIHEueCwgcG9zaXRpb24ueSAtIHEueSkgPD0gRURJVF9UT0wpIHtcbiAgICAgICAgICAgIHJldHVybiB7IGlkOiBzZWwucmVnaW9uLmlkLCByaW5nOiBoLCBpbmRleDogaSB9O1xuICAgICAgICAgIH1cbiAgICAgICAgfVxuICAgICAgfVxuICAgIH1cbiAgICByZXR1cm4gbnVsbDtcbiAgfVxuXG4gIC8qKiBUaGUgYmV6aWVyIGNvbnRyb2wgaGFuZGxlIG9mIHRoZSBzZWxlY3RlZCByZWdpb24gdW5kZXIgdGhlIGN1cnNvciAod2hpY2hcbiAgICogIGFuY2hvciwgYW5kIHdoZXRoZXIgdGhlIGluLSBvciBvdXQtaGFuZGxlKSwgb3IgbnVsbC4gKi9cbiAgcHJpdmF0ZSBoaXRCZXppZXJIYW5kbGUoXG4gICAgcG9zaXRpb246IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSxcbiAgKTogeyBpZDogbnVtYmVyOyBpbmRleDogbnVtYmVyOyBzaWRlOiAnaW4nIHwgJ291dCc7IHJpbmc6IG51bWJlciB9IHwgbnVsbCB7XG4gICAgY29uc3Qgc2VsID0gdGhpcy5zZWxlY3RlZFJlZ2lvbkluZm8oKTtcbiAgICBpZiAoIXNlbCB8fCAhKHNlbC5yZWdpb24uYm91bmRzIGluc3RhbmNlb2YgUG9seWdvbikgfHwgIXNlbC5yZWdpb24uYm91bmRzLmJlemllcikgcmV0dXJuIG51bGw7XG4gICAgY29uc3QgYiA9IHNlbC5yZWdpb24uYm91bmRzO1xuICAgIC8vIFRlc3Qgb25lIHJpbmcncyBjb250cm9sIGhhbmRsZXM7IHJldHVybnMgdGhlIG1hdGNoZWQgdmVydGV4L3NpZGUgb3IgbnVsbC5cbiAgICBjb25zdCB0ZXN0UmluZyA9IChcbiAgICAgIHhzOiBudW1iZXJbXSwgeXM6IG51bWJlcltdLCBpbk9mZjogbnVtYmVyW11bXSB8IHVuZGVmaW5lZCwgb3V0T2ZmOiBudW1iZXJbXVtdIHwgdW5kZWZpbmVkLFxuICAgICAgY2xvc2VkOiBib29sZWFuLCByaW5nOiBudW1iZXIsXG4gICAgKTogeyBpZDogbnVtYmVyOyBpbmRleDogbnVtYmVyOyBzaWRlOiAnaW4nIHwgJ291dCc7IHJpbmc6IG51bWJlciB9IHwgbnVsbCA9PiB7XG4gICAgICBjb25zdCBoID0gcmVzb2x2ZUhhbmRsZXMoeHMsIHlzLCBjbG9zZWQsIGluT2ZmLCBvdXRPZmYpO1xuICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBoLmxlbmd0aDsgaSsrKSB7XG4gICAgICAgIGlmIChoW2ldLmhhc091dCkge1xuICAgICAgICAgIGNvbnN0IHEgPSB0aGlzLnRvUHgoaFtpXS5vdXRbMF0sIGhbaV0ub3V0WzFdKTtcbiAgICAgICAgICBpZiAoTWF0aC5oeXBvdChwb3NpdGlvbi54IC0gcS54LCBwb3NpdGlvbi55IC0gcS55KSA8PSBFRElUX1RPTCkge1xuICAgICAgICAgICAgcmV0dXJuIHsgaWQ6IHNlbC5yZWdpb24uaWQsIGluZGV4OiBpLCBzaWRlOiAnb3V0JywgcmluZyB9O1xuICAgICAgICAgIH1cbiAgICAgICAgfVxuICAgICAgICBpZiAoaFtpXS5oYXNJbikge1xuICAgICAgICAgIGNvbnN0IHEgPSB0aGlzLnRvUHgoaFtpXS5pblswXSwgaFtpXS5pblsxXSk7XG4gICAgICAgICAgaWYgKE1hdGguaHlwb3QocG9zaXRpb24ueCAtIHEueCwgcG9zaXRpb24ueSAtIHEueSkgPD0gRURJVF9UT0wpIHtcbiAgICAgICAgICAgIHJldHVybiB7IGlkOiBzZWwucmVnaW9uLmlkLCBpbmRleDogaSwgc2lkZTogJ2luJywgcmluZyB9O1xuICAgICAgICAgIH1cbiAgICAgICAgfVxuICAgICAgfVxuICAgICAgcmV0dXJuIG51bGw7XG4gICAgfTtcbiAgICBjb25zdCBleHQgPSB0ZXN0UmluZyhiLnhwb2ludHMsIGIueXBvaW50cywgYi5oYW5kbGVzSW4sIGIuaGFuZGxlc091dCwgYi5jbG9zZWQgIT09IGZhbHNlLCAtMSk7XG4gICAgaWYgKGV4dCkgcmV0dXJuIGV4dDtcbiAgICAvLyBEb251dCBob2xlIHJpbmdzIChqaXQtdWkjMTAyKTogdGhlaXIgb3duIGJlemllciBjb250cm9sIGhhbmRsZXMuXG4gICAgaWYgKGIuaG9sZXMgJiYgYi5ob2xlSGFuZGxlc0luICYmIGIuaG9sZUhhbmRsZXNPdXQpIHtcbiAgICAgIGZvciAobGV0IGhpID0gMDsgaGkgPCBiLmhvbGVzLmxlbmd0aDsgaGkrKykge1xuICAgICAgICBjb25zdCByaW5nID0gYi5ob2xlc1toaV07XG4gICAgICAgIGNvbnN0IGhpdCA9IHRlc3RSaW5nKFxuICAgICAgICAgIHJpbmcubWFwKChwKSA9PiBwWzBdKSwgcmluZy5tYXAoKHApID0+IHBbMV0pLFxuICAgICAgICAgIGIuaG9sZUhhbmRsZXNJbltoaV0sIGIuaG9sZUhhbmRsZXNPdXRbaGldLCB0cnVlLCBoaSxcbiAgICAgICAgKTtcbiAgICAgICAgaWYgKGhpdCkgcmV0dXJuIGhpdDtcbiAgICAgIH1cbiAgICB9XG4gICAgcmV0dXJuIG51bGw7XG4gIH1cblxuICAvKiogVGhlIGVkZ2Ugb2YgYHJlZ2lvbmAncyBwb2x5Z29uIG5lYXJlc3QgdGhlIGN1cnNvciAod2l0aGluIHRvbGVyYW5jZSksIHdpdGhcbiAgICogIHRoZSBjbGlja2VkIHBvaW50IGluIGltYWdlIGNvb3JkcyBhcyB0aGUgaW5zZXJ0aW9uIHBvc2l0aW9uLCBvciBudWxsLiAqL1xuICBwcml2YXRlIGhpdEVkZ2UocG9zaXRpb246IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSwgcmVnaW9uOiBSZWdpb24pOlxuICAgIHsgcmluZzogbnVtYmVyOyBzZWdJbmRleDogbnVtYmVyOyB4OiBudW1iZXI7IHk6IG51bWJlciB9IHwgbnVsbCB7XG4gICAgaWYgKCEocmVnaW9uLmJvdW5kcyBpbnN0YW5jZW9mIFBvbHlnb24pKSByZXR1cm4gbnVsbDtcbiAgICBjb25zdCBiID0gcmVnaW9uLmJvdW5kcztcbiAgICBsZXQgYmVzdCA9IC0xLCBiZXN0UmluZyA9IC0xLCBiZXN0RGlzdCA9IEluZmluaXR5O1xuICAgIC8vIE5lYXJlc3QgZWRnZSBhY3Jvc3MgdGhlIGV4dGVyaW9yIChyaW5nIC0xKSBhbmQgZXZlcnkgaW50ZXJpb3IgcmluZyAoaG9sZSkuXG4gICAgY29uc3Qgc2NhbiA9ICh4czogbnVtYmVyW10sIHlzOiBudW1iZXJbXSwgcmluZzogbnVtYmVyLCBjbG9zZWQ6IGJvb2xlYW4pID0+IHtcbiAgICAgIGNvbnN0IG4gPSB4cy5sZW5ndGg7XG4gICAgICBjb25zdCBzZWdDb3VudCA9IGNsb3NlZCA/IG4gOiBuIC0gMTsgLy8gY2xvc2VkIHdyYXBzIHRoZSBsYXN0LT5maXJzdCBlZGdlXG4gICAgICBmb3IgKGxldCBpID0gMDsgaSA8IHNlZ0NvdW50OyBpKyspIHtcbiAgICAgICAgY29uc3QgaiA9IChpICsgMSkgJSBuO1xuICAgICAgICBjb25zdCBhID0gdGhpcy50b1B4KHhzW2ldLCB5c1tpXSk7XG4gICAgICAgIGNvbnN0IGMgPSB0aGlzLnRvUHgoeHNbal0sIHlzW2pdKTtcbiAgICAgICAgY29uc3QgZCA9IHRoaXMuZGlzdFRvU2VnbWVudFB4KHBvc2l0aW9uLCBhLCBjKTtcbiAgICAgICAgaWYgKGQgPCBiZXN0RGlzdCkgeyBiZXN0RGlzdCA9IGQ7IGJlc3QgPSBpOyBiZXN0UmluZyA9IHJpbmc7IH1cbiAgICAgIH1cbiAgICB9O1xuICAgIHNjYW4oYi54cG9pbnRzLCBiLnlwb2ludHMsIC0xLCBiLmNsb3NlZCAhPT0gZmFsc2UpO1xuICAgIGlmIChiLmhvbGVzKSB7XG4gICAgICBiLmhvbGVzLmZvckVhY2goKHIsIGgpID0+IHNjYW4oci5tYXAocCA9PiBwWzBdKSwgci5tYXAocCA9PiBwWzFdKSwgaCwgdHJ1ZSkpO1xuICAgIH1cbiAgICBpZiAoYmVzdCA8IDAgfHwgYmVzdERpc3QgPiBFRElUX1RPTCkgcmV0dXJuIG51bGw7XG4gICAgY29uc3QgaW1nID0gdGhpcy50b0ltYWdlKHBvc2l0aW9uKTtcbiAgICByZXR1cm4geyByaW5nOiBiZXN0UmluZywgc2VnSW5kZXg6IGJlc3QsIHg6IGltZy54LCB5OiBpbWcueSB9O1xuICB9XG5cbiAgLyoqIENsYXNzaWZ5IGEgc2NyZWVuIHBvaW50IGFnYWluc3QgYSBzY3JlZW4tc3BhY2UgcmVjdGFuZ2xlIGludG8gYSB6b25lLiAqL1xuICBwcml2YXRlIHJlY3Rab25lKHB4OiBudW1iZXIsIHB5OiBudW1iZXIsIHgwOiBudW1iZXIsIHkwOiBudW1iZXIsIHgxOiBudW1iZXIsIHkxOiBudW1iZXIpOiBFZGl0Wm9uZSB8IG51bGwge1xuICAgIGNvbnN0IHQgPSBFRElUX1RPTDtcbiAgICBpZiAocHggPCB4MCAtIHQgfHwgcHggPiB4MSArIHQgfHwgcHkgPCB5MCAtIHQgfHwgcHkgPiB5MSArIHQpIHJldHVybiBudWxsO1xuICAgIGNvbnN0IGxlZnQgPSBNYXRoLmFicyhweCAtIHgwKSA8PSB0LCByaWdodCA9IE1hdGguYWJzKHB4IC0geDEpIDw9IHQ7XG4gICAgY29uc3QgdG9wID0gTWF0aC5hYnMocHkgLSB5MCkgPD0gdCwgYm90dG9tID0gTWF0aC5hYnMocHkgLSB5MSkgPD0gdDtcbiAgICBpZiAodG9wICYmIGxlZnQpIHJldHVybiAnbncnO1xuICAgIGlmICh0b3AgJiYgcmlnaHQpIHJldHVybiAnbmUnO1xuICAgIGlmIChib3R0b20gJiYgbGVmdCkgcmV0dXJuICdzdyc7XG4gICAgaWYgKGJvdHRvbSAmJiByaWdodCkgcmV0dXJuICdzZSc7XG4gICAgaWYgKGxlZnQpIHJldHVybiAndyc7XG4gICAgaWYgKHJpZ2h0KSByZXR1cm4gJ2UnO1xuICAgIGlmICh0b3ApIHJldHVybiAnbic7XG4gICAgaWYgKGJvdHRvbSkgcmV0dXJuICdzJztcbiAgICBpZiAocHggPiB4MCAmJiBweCA8IHgxICYmIHB5ID4geTAgJiYgcHkgPCB5MSkgcmV0dXJuICdtb3ZlJztcbiAgICByZXR1cm4gbnVsbDtcbiAgfVxuXG4gIC8qKiBTbmFwc2hvdCB0aGUgc2VsZWN0ZWQgcmVnaW9uJ3MgZ2VvbWV0cnkgYXQgdGhlIHN0YXJ0IG9mIGFuIGVkaXQuICovXG4gIHByaXZhdGUgc25hcHNob3QocmVnaW9uOiBSZWdpb24pOiBhbnkge1xuICAgIGNvbnN0IGIgPSByZWdpb24uYm91bmRzO1xuICAgIGlmIChiIGluc3RhbmNlb2YgUmVjdGFuZ2xlKSByZXR1cm4geyBraW5kOiAncmVjdCcsIHg6IGIueCwgeTogYi55LCB3OiBiLndpZHRoLCBoOiBiLmhlaWdodCB9O1xuICAgIGlmIChiIGluc3RhbmNlb2YgUG9seWdvbikge1xuICAgICAgcmV0dXJuIHtcbiAgICAgICAga2luZDogJ3BvbHknLCB4czogYi54cG9pbnRzLnNsaWNlKCksIHlzOiBiLnlwb2ludHMuc2xpY2UoKSwgY2xvc2VkOiBiLmNsb3NlZCAhPT0gZmFsc2UsXG4gICAgICAgIGJlemllcjogYi5iZXppZXIsXG4gICAgICAgIGluT2ZmOiBiLmhhbmRsZXNJbj8ubWFwKG8gPT4gby5zbGljZSgpKSxcbiAgICAgICAgb3V0T2ZmOiBiLmhhbmRsZXNPdXQ/Lm1hcChvID0+IG8uc2xpY2UoKSksXG4gICAgICAgIGhvbGVzOiBiLmhvbGVzPy5tYXAocmluZyA9PiByaW5nLm1hcChwdCA9PiBwdC5zbGljZSgpKSksXG4gICAgICB9O1xuICAgIH1cbiAgICBpZiAoYiBpbnN0YW5jZW9mIE11bHRpUG9seWdvbikge1xuICAgICAgcmV0dXJuIHtcbiAgICAgICAga2luZDogJ211bHRpJyxcbiAgICAgICAgcG9seWdvbnM6IGIucG9seWdvbnMubWFwKChwKSA9PiAoe1xuICAgICAgICAgIHhzOiBwLnhwb2ludHMuc2xpY2UoKSwgeXM6IHAueXBvaW50cy5zbGljZSgpLCBjbG9zZWQ6IHAuY2xvc2VkICE9PSBmYWxzZSxcbiAgICAgICAgICBob2xlczogcC5ob2xlcz8ubWFwKHJpbmcgPT4gcmluZy5tYXAocHQgPT4gcHQuc2xpY2UoKSkpLFxuICAgICAgICB9KSksXG4gICAgICB9O1xuICAgIH1cbiAgICByZXR1cm4geyBraW5kOiAncmVjdCcsIHg6IDAsIHk6IDAsIHc6IDAsIGg6IDAgfTtcbiAgfVxuXG4gIC8qKlxuICAgKiBBcHBseSB0aGUgaW4tcHJvZ3Jlc3MgbW92ZS9yZXNpemUgdG8gdGhlIHJlZ2lvbiwgbGl2ZSwgdGhyb3VnaCB0aGVcbiAgICogUmVnaW9uLW5hdGl2ZSBlZGl0IEFQSS4gUmVjb21wdXRlZCBhYnNvbHV0ZWx5IGZyb20gdGhlIGdlc3R1cmUtc3RhcnRcbiAgICogc25hcHNob3QgKGBvcmlnYCkgKyB0aGUgdG90YWwgZGVsdGEsIHNvIGVhY2ggZnJhbWUgaXMgaWRlbXBvdGVudC5cbiAgICovXG4gIHByaXZhdGUgYXBwbHlFZGl0KGN1ckltZzogeyB4OiBudW1iZXI7IHk6IG51bWJlciB9KTogdm9pZCB7XG4gICAgaWYgKCF0aGlzLmVkaXQpIHJldHVybjtcblxuICAgIGlmICh0aGlzLmVkaXQua2luZCA9PT0gJ3ZlcnRleCcpIHtcbiAgICAgIC8vIERyYWcgYSBzaW5nbGUgdmVydGV4IHRvIHRoZSBjdXJzb3IgKGFic29sdXRlIOKAlCBpZGVtcG90ZW50KS4gUm91dGUgdG8gdGhlXG4gICAgICAvLyBleHRlcmlvciBvciB0aGUgbWF0Y2hpbmcgaW50ZXJpb3IgcmluZyAoaG9sZSkg4oCUIGppdC11aSM4NS5cbiAgICAgIGlmICh0aGlzLmVkaXQucmluZyA8IDApIHtcbiAgICAgICAgdGhpcy5zdG9yZS5tb3ZlVmVydGV4KHRoaXMuZWRpdC5pZCwgdGhpcy5lZGl0LnZlcnRleEluZGV4LCBjdXJJbWcueCwgY3VySW1nLnkpO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgdGhpcy5zdG9yZS5tb3ZlSG9sZVZlcnRleCh0aGlzLmVkaXQuaWQsIHRoaXMuZWRpdC5yaW5nLCB0aGlzLmVkaXQudmVydGV4SW5kZXgsIGN1ckltZy54LCBjdXJJbWcueSk7XG4gICAgICB9XG4gICAgICB0aGlzLnJlZHJhdygpO1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGlmICh0aGlzLmVkaXQua2luZCA9PT0gJ2hhbmRsZScpIHtcbiAgICAgIC8vIERyYWcgYSBiZXppZXIgY29udHJvbCBoYW5kbGUgdG8gdGhlIGN1cnNvciDigJQgZXh0ZXJpb3IgKHJpbmcgLTEpIG9yIGEgZG9udXQgaG9sZSByaW5nLlxuICAgICAgaWYgKHRoaXMuZWRpdC5yaW5nIDwgMCkge1xuICAgICAgICB0aGlzLnN0b3JlLm1vdmVCZXppZXJIYW5kbGUodGhpcy5lZGl0LmlkLCB0aGlzLmVkaXQudmVydGV4SW5kZXgsIHRoaXMuZWRpdC5oYW5kbGVTaWRlLCBjdXJJbWcueCwgY3VySW1nLnkpO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgdGhpcy5zdG9yZS5tb3ZlSG9sZUJlemllckhhbmRsZShcbiAgICAgICAgICB0aGlzLmVkaXQuaWQsIHRoaXMuZWRpdC5yaW5nLCB0aGlzLmVkaXQudmVydGV4SW5kZXgsIHRoaXMuZWRpdC5oYW5kbGVTaWRlLCBjdXJJbWcueCwgY3VySW1nLnksXG4gICAgICAgICk7XG4gICAgICB9XG4gICAgICB0aGlzLnJlZHJhdygpO1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGNvbnN0IGR4ID0gY3VySW1nLnggLSB0aGlzLmVkaXQuc3RhcnRJbWcueDtcbiAgICBjb25zdCBkeSA9IGN1ckltZy55IC0gdGhpcy5lZGl0LnN0YXJ0SW1nLnk7XG5cbiAgICBjb25zdCBvID0gdGhpcy5lZGl0Lm9yaWc7XG4gICAgaWYgKG8ua2luZCA9PT0gJ3JlY3QnKSB7XG4gICAgICBsZXQgeDAgPSBvLngsIHkwID0gby55LCB4MSA9IG8ueCArIG8udywgeTEgPSBvLnkgKyBvLmg7XG4gICAgICBzd2l0Y2ggKHRoaXMuZWRpdC56b25lKSB7XG4gICAgICAgIGNhc2UgJ21vdmUnOiB4MCArPSBkeDsgeDEgKz0gZHg7IHkwICs9IGR5OyB5MSArPSBkeTsgYnJlYWs7XG4gICAgICAgIGNhc2UgJ3cnOiB4MCArPSBkeDsgYnJlYWs7XG4gICAgICAgIGNhc2UgJ2UnOiB4MSArPSBkeDsgYnJlYWs7XG4gICAgICAgIGNhc2UgJ24nOiB5MCArPSBkeTsgYnJlYWs7XG4gICAgICAgIGNhc2UgJ3MnOiB5MSArPSBkeTsgYnJlYWs7XG4gICAgICAgIGNhc2UgJ253JzogeDAgKz0gZHg7IHkwICs9IGR5OyBicmVhaztcbiAgICAgICAgY2FzZSAnbmUnOiB4MSArPSBkeDsgeTAgKz0gZHk7IGJyZWFrO1xuICAgICAgICBjYXNlICdzdyc6IHgwICs9IGR4OyB5MSArPSBkeTsgYnJlYWs7XG4gICAgICAgIGNhc2UgJ3NlJzogeDEgKz0gZHg7IHkxICs9IGR5OyBicmVhaztcbiAgICAgIH1cbiAgICAgIGNvbnN0IHJlY3QgPSBuZXcgUmVjdGFuZ2xlKCk7XG4gICAgICByZWN0LnggPSBNYXRoLnJvdW5kKE1hdGgubWluKHgwLCB4MSkpO1xuICAgICAgcmVjdC55ID0gTWF0aC5yb3VuZChNYXRoLm1pbih5MCwgeTEpKTtcbiAgICAgIHJlY3Qud2lkdGggPSBNYXRoLnJvdW5kKE1hdGguYWJzKHgxIC0geDApKTtcbiAgICAgIHJlY3QuaGVpZ2h0ID0gTWF0aC5yb3VuZChNYXRoLmFicyh5MSAtIHkwKSk7XG4gICAgICB0aGlzLnN0b3JlLnVwZGF0ZUJvdW5kcyh0aGlzLmVkaXQuaWQsIHJlY3QpO1xuICAgIH0gZWxzZSBpZiAoby5raW5kID09PSAnbXVsdGknKSB7XG4gICAgICAvLyBNdWx0aS1wYXJ0IHJlZ2lvbjogdHJhbnNsYXRlIGV2ZXJ5IHBhcnQgKGFuZCBpdHMgaG9sZXMpIGJ5IHRoZSBkZWx0YS5cbiAgICAgIGNvbnN0IG1wID0gbmV3IE11bHRpUG9seWdvbigpO1xuICAgICAgbXAucG9seWdvbnMgPSBvLnBvbHlnb25zLm1hcCgocHA6IGFueSkgPT4ge1xuICAgICAgICBjb25zdCB4cyA9IHBwLnhzLm1hcCgoeDogbnVtYmVyKSA9PiBNYXRoLnJvdW5kKHggKyBkeCkpO1xuICAgICAgICBjb25zdCB5cyA9IHBwLnlzLm1hcCgoeTogbnVtYmVyKSA9PiBNYXRoLnJvdW5kKHkgKyBkeSkpO1xuICAgICAgICBjb25zdCBwb2x5ID0gbmV3IFBvbHlnb24oKTtcbiAgICAgICAgcG9seS5ucG9pbnRzID0geHMubGVuZ3RoO1xuICAgICAgICBwb2x5Lnhwb2ludHMgPSB4cztcbiAgICAgICAgcG9seS55cG9pbnRzID0geXM7XG4gICAgICAgIHBvbHkuY29vcmRpbmF0ZXMgPSB4cy5tYXAoKHg6IG51bWJlciwgaTogbnVtYmVyKSA9PiBbeCwgeXNbaV1dKTtcbiAgICAgICAgcG9seS5jbG9zZWQgPSBwcC5jbG9zZWQ7XG4gICAgICAgIGlmIChwcC5ob2xlcykge1xuICAgICAgICAgIHBvbHkuaG9sZXMgPSBwcC5ob2xlcy5tYXAoKHJpbmc6IG51bWJlcltdW10pID0+XG4gICAgICAgICAgICByaW5nLm1hcCgoW3gsIHldOiBudW1iZXJbXSkgPT4gW01hdGgucm91bmQoeCArIGR4KSwgTWF0aC5yb3VuZCh5ICsgZHkpXSkpO1xuICAgICAgICB9XG4gICAgICAgIHJldHVybiBwb2x5O1xuICAgICAgfSk7XG4gICAgICB0aGlzLnN0b3JlLnVwZGF0ZUJvdW5kcyh0aGlzLmVkaXQuaWQsIG1wKTtcbiAgICB9IGVsc2Uge1xuICAgICAgLy8gUG9seWdvbjogdHJhbnNsYXRlIGV2ZXJ5IHZlcnRleCAodGhlIG9ubHkgcG9seWdvbiBlZGl0IHpvbmUgaXMgJ21vdmUnKS5cbiAgICAgIC8vIEJlemllciBmbGFnICsgaGFuZGxlIG9mZnNldHMgYXJlIHJlbGF0aXZlLCBzbyB0aGV5IGNhcnJ5IG92ZXIgdW5jaGFuZ2VkLlxuICAgICAgY29uc3QgeHMgPSBvLnhzLm1hcCgoeDogbnVtYmVyKSA9PiBNYXRoLnJvdW5kKHggKyBkeCkpO1xuICAgICAgY29uc3QgeXMgPSBvLnlzLm1hcCgoeTogbnVtYmVyKSA9PiBNYXRoLnJvdW5kKHkgKyBkeSkpO1xuICAgICAgY29uc3QgcG9seSA9IG5ldyBQb2x5Z29uKCk7XG4gICAgICBwb2x5Lm5wb2ludHMgPSB4cy5sZW5ndGg7XG4gICAgICBwb2x5Lnhwb2ludHMgPSB4cztcbiAgICAgIHBvbHkueXBvaW50cyA9IHlzO1xuICAgICAgcG9seS5jb29yZGluYXRlcyA9IHhzLm1hcCgoeDogbnVtYmVyLCBpOiBudW1iZXIpID0+IFt4LCB5c1tpXV0pO1xuICAgICAgcG9seS5jbG9zZWQgPSBvLmNsb3NlZDtcbiAgICAgIHBvbHkuYmV6aWVyID0gby5iZXppZXI7XG4gICAgICBpZiAoby5pbk9mZikgcG9seS5oYW5kbGVzSW4gPSBvLmluT2ZmLm1hcCgob2ZmOiBudW1iZXJbXSkgPT4gb2ZmLnNsaWNlKCkpO1xuICAgICAgaWYgKG8ub3V0T2ZmKSBwb2x5LmhhbmRsZXNPdXQgPSBvLm91dE9mZi5tYXAoKG9mZjogbnVtYmVyW10pID0+IG9mZi5zbGljZSgpKTtcbiAgICAgIC8vIFRyYW5zbGF0ZSBpbnRlcmlvciByaW5ncyAoaG9sZXMpIHdpdGggdGhlIGV4dGVyaW9yIChqaXQtdWkjODUpLlxuICAgICAgaWYgKG8uaG9sZXMpIHtcbiAgICAgICAgcG9seS5ob2xlcyA9IG8uaG9sZXMubWFwKChyaW5nOiBudW1iZXJbXVtdKSA9PlxuICAgICAgICAgIHJpbmcubWFwKChbeCwgeV06IG51bWJlcltdKSA9PiBbTWF0aC5yb3VuZCh4ICsgZHgpLCBNYXRoLnJvdW5kKHkgKyBkeSldKSk7XG4gICAgICB9XG4gICAgICB0aGlzLnN0b3JlLnVwZGF0ZUJvdW5kcyh0aGlzLmVkaXQuaWQsIHBvbHkpO1xuICAgIH1cbiAgICB0aGlzLnJlZHJhdygpO1xuICB9XG5cbiAgcHJpdmF0ZSBzZWxlY3RBdChwdDogeyB4OiBudW1iZXI7IHk6IG51bWJlciB9LCBhZGRpdGl2ZSA9IGZhbHNlKTogdm9pZCB7XG4gICAgY29uc3QgaWR4ID0gdGhpcy5yZWdpb25JbmRleEF0KHB0KTtcbiAgICBpZiAoYWRkaXRpdmUpIHtcbiAgICAgIC8vIFNoaWZ0LWNsaWNrIG9uIGVtcHR5IHNwYWNlIGtlZXBzIHRoZSBjdXJyZW50IHNlbGVjdGlvbi5cbiAgICAgIGlmIChpZHggPCAwKSByZXR1cm47XG4gICAgICAvLyBgdGhpcy5zZWxlY3RlZGAgbWlycm9ycyB0aGUgc3RvcmUncyBjdXJyZW50IHNlbGVjdGlvbiAoa2VwdCBpbiBzeW5jIHZpYVxuICAgICAgLy8gdGhlIHN1YnNjcmlwdGlvbiksIHNvIGl0J3MgdGhlIHNvdXJjZSBvZiB0cnV0aCB3aXRob3V0IGEgc3luYyBnZXR0ZXIuXG4gICAgICBjb25zdCBjdXIgPSB0aGlzLnNlbGVjdGVkLnNsaWNlKCk7XG4gICAgICBjb25zdCBhdCA9IGN1ci5pbmRleE9mKGlkeCk7XG4gICAgICBpZiAoYXQgPj0gMCkgY3VyLnNwbGljZShhdCwgMSk7IC8vIHRvZ2dsZSBvZmZcbiAgICAgIGVsc2UgY3VyLnB1c2goaWR4KTsgICAgICAgICAgICAgLy8gdG9nZ2xlIG9uXG4gICAgICB0aGlzLnN0b3JlLnNldFNlbGVjdGVkU2hhcGVJbmRpY2VzKGN1cik7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIHRoaXMuc3RvcmUuc2V0U2VsZWN0ZWRTaGFwZUluZGljZXMoaWR4ID49IDAgPyBbaWR4XSA6IFtdKTtcbiAgfVxuXG4gIC8qKiBJbmRpY2VzIG9mIGV2ZXJ5IHJlZ2lvbiB3aG9zZSBib3VuZGluZyBib3ggaW50ZXJzZWN0cyB0aGUgaW1hZ2Utc3BhY2VcbiAgICogIHJlY3RhbmdsZSBbeDAseTBd4oCTW3gxLHkxXSAocnViYmVyLWJhbmQgbXVsdGktc2VsZWN0KS4gKi9cbiAgcHJpdmF0ZSByZWdpb25zSW5SZWN0KHgwOiBudW1iZXIsIHkwOiBudW1iZXIsIHgxOiBudW1iZXIsIHkxOiBudW1iZXIpOiBudW1iZXJbXSB7XG4gICAgY29uc3Qgb3V0OiBudW1iZXJbXSA9IFtdO1xuICAgIHRoaXMuc3RvcmUuZ2V0UmVnaW9ucygpLmZvckVhY2goKHIsIGkpID0+IHtcbiAgICAgIGNvbnN0IGJiID0gdGhpcy5yZWdpb25CQm94KHIpO1xuICAgICAgaWYgKGJiICYmIGJiLngwIDw9IHgxICYmIGJiLngxID49IHgwICYmIGJiLnkwIDw9IHkxICYmIGJiLnkxID49IHkwKSBvdXQucHVzaChpKTtcbiAgICB9KTtcbiAgICByZXR1cm4gb3V0O1xuICB9XG5cbiAgLyoqIEF4aXMtYWxpZ25lZCBib3VuZGluZyBib3ggb2YgYSByZWdpb24gaW4gaW1hZ2UgY29vcmRzLCBvciBudWxsIGlmIGVtcHR5LiAqL1xuICBwcml2YXRlIHJlZ2lvbkJCb3gocjogUmVnaW9uKTogeyB4MDogbnVtYmVyOyB5MDogbnVtYmVyOyB4MTogbnVtYmVyOyB5MTogbnVtYmVyIH0gfCBudWxsIHtcbiAgICBjb25zdCBiID0gci5ib3VuZHM7XG4gICAgaWYgKGIgaW5zdGFuY2VvZiBSZWN0YW5nbGUpIHtcbiAgICAgIHJldHVybiB7IHgwOiBiLngsIHkwOiBiLnksIHgxOiBiLnggKyBiLndpZHRoLCB5MTogYi55ICsgYi5oZWlnaHQgfTtcbiAgICB9XG4gICAgaWYgKGIgaW5zdGFuY2VvZiBQb2x5Z29uICYmIGIueHBvaW50cy5sZW5ndGgpIHtcbiAgICAgIHJldHVybiB7XG4gICAgICAgIHgwOiBNYXRoLm1pbiguLi5iLnhwb2ludHMpLCB5MDogTWF0aC5taW4oLi4uYi55cG9pbnRzKSxcbiAgICAgICAgeDE6IE1hdGgubWF4KC4uLmIueHBvaW50cyksIHkxOiBNYXRoLm1heCguLi5iLnlwb2ludHMpLFxuICAgICAgfTtcbiAgICB9XG4gICAgaWYgKGIgaW5zdGFuY2VvZiBNdWx0aVBvbHlnb24pIHtcbiAgICAgIGxldCB4MCA9IEluZmluaXR5LCB5MCA9IEluZmluaXR5LCB4MSA9IC1JbmZpbml0eSwgeTEgPSAtSW5maW5pdHk7XG4gICAgICBmb3IgKGNvbnN0IHAgb2YgYi5wb2x5Z29ucykge1xuICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IHAueHBvaW50cy5sZW5ndGg7IGkrKykge1xuICAgICAgICAgIGlmIChwLnhwb2ludHNbaV0gPCB4MCkgeDAgPSBwLnhwb2ludHNbaV07XG4gICAgICAgICAgaWYgKHAueHBvaW50c1tpXSA+IHgxKSB4MSA9IHAueHBvaW50c1tpXTtcbiAgICAgICAgICBpZiAocC55cG9pbnRzW2ldIDwgeTApIHkwID0gcC55cG9pbnRzW2ldO1xuICAgICAgICAgIGlmIChwLnlwb2ludHNbaV0gPiB5MSkgeTEgPSBwLnlwb2ludHNbaV07XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICAgIHJldHVybiB4MSA+PSB4MCA/IHsgeDAsIHkwLCB4MSwgeTEgfSA6IG51bGw7XG4gICAgfVxuICAgIHJldHVybiBudWxsO1xuICB9XG5cbiAgLyoqIEluZGV4IG9mIHRoZSB0b3Btb3N0IHJlZ2lvbiB1bmRlciBhIHBvaW50LCBvciAtMS4gKi9cbiAgcHJpdmF0ZSByZWdpb25JbmRleEF0KHB0OiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH0pOiBudW1iZXIge1xuICAgIGNvbnN0IHJlZ2lvbnMgPSB0aGlzLnN0b3JlLmdldFJlZ2lvbnMoKTtcbiAgICBmb3IgKGxldCBpID0gcmVnaW9ucy5sZW5ndGggLSAxOyBpID49IDA7IGktLSkge1xuICAgICAgaWYgKHRoaXMuY29udGFpbnNQb2ludChyZWdpb25zW2ldLCBwdCkpIHJldHVybiBpO1xuICAgIH1cbiAgICByZXR1cm4gLTE7XG4gIH1cblxuICBwcml2YXRlIGNvbnRhaW5zUG9pbnQocmVnaW9uOiBSZWdpb24sIHB0OiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH0pOiBib29sZWFuIHtcbiAgICBjb25zdCBiID0gcmVnaW9uLmJvdW5kcztcbiAgICBpZiAoYiBpbnN0YW5jZW9mIFJlY3RhbmdsZSkge1xuICAgICAgcmV0dXJuIHB0LnggPj0gYi54ICYmIHB0LnggPD0gYi54ICsgYi53aWR0aCAmJiBwdC55ID49IGIueSAmJiBwdC55IDw9IGIueSArIGIuaGVpZ2h0O1xuICAgIH1cbiAgICAvLyBNdWx0aS1wYXJ0IHJlZ2lvbjogaW5zaWRlIGFueSBwYXJ0IChleHRlcmlvciBtaW51cyB0aGF0IHBhcnQncyBob2xlcykuXG4gICAgaWYgKGIgaW5zdGFuY2VvZiBNdWx0aVBvbHlnb24pIHtcbiAgICAgIHJldHVybiBiLnBvbHlnb25zLnNvbWUoKHApID0+IHRoaXMuY2xvc2VkUG9seWdvbkNvbnRhaW5zKHAsIHB0KSk7XG4gICAgfVxuICAgIGlmIChiIGluc3RhbmNlb2YgUG9seWdvbikge1xuICAgICAgaWYgKGIuY2xvc2VkICE9PSBmYWxzZSkgcmV0dXJuIHRoaXMuY2xvc2VkUG9seWdvbkNvbnRhaW5zKGIsIHB0KTtcbiAgICAgIC8vIE9wZW4gcG9seWxpbmU6IG5vIGludGVyaW9yIOKAlCBzZWxlY3Qgd2hlbiB0aGUgY2xpY2sgbGFuZHMgbmVhciB0aGUgbGluZS5cbiAgICAgIC8vIFRvbGVyYW5jZSBpcyBpbiBzY3JlZW4gcGl4ZWxzIHNvIGl0IHN0YXlzIGNsaWNrYWJsZSBhdCBhbnkgem9vbS5cbiAgICAgIGNvbnN0IHhzID0gYi54cG9pbnRzLCB5cyA9IGIueXBvaW50cywgbiA9IHhzLmxlbmd0aCwgdG9sUHggPSA2O1xuICAgICAgY29uc3QgaGVyZSA9IHRoaXMudG9QeChwdC54LCBwdC55KTtcbiAgICAgIGZvciAobGV0IGkgPSAwOyBpICsgMSA8IG47IGkrKykge1xuICAgICAgICBjb25zdCBhID0gdGhpcy50b1B4KHhzW2ldLCB5c1tpXSk7XG4gICAgICAgIGNvbnN0IGMgPSB0aGlzLnRvUHgoeHNbaSArIDFdLCB5c1tpICsgMV0pO1xuICAgICAgICBpZiAodGhpcy5kaXN0VG9TZWdtZW50UHgoaGVyZSwgYSwgYykgPD0gdG9sUHgpIHJldHVybiB0cnVlO1xuICAgICAgfVxuICAgICAgcmV0dXJuIGZhbHNlO1xuICAgIH1cbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICAvKiogUG9pbnQtaW4tY2xvc2VkLXBvbHlnb24gKGltYWdlIGNvb3JkcykgaG9ub3VyaW5nIGludGVyaW9yIHJpbmdzIChob2xlcyk6XG4gICAqICBpbnNpZGUgdGhlIGV4dGVyaW9yIEFORCBvdXRzaWRlIGV2ZXJ5IGhvbGUgKGV2ZW4tb2RkKS4gKi9cbiAgcHJpdmF0ZSBjbG9zZWRQb2x5Z29uQ29udGFpbnMoYjogUG9seWdvbiwgcHQ6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSk6IGJvb2xlYW4ge1xuICAgIGNvbnN0IGluUmluZyA9IChyeHM6IG51bWJlcltdLCByeXM6IG51bWJlcltdKTogYm9vbGVhbiA9PiB7XG4gICAgICBsZXQgaGl0ID0gZmFsc2U7XG4gICAgICBmb3IgKGxldCBpID0gMCwgaiA9IHJ4cy5sZW5ndGggLSAxOyBpIDwgcnhzLmxlbmd0aDsgaiA9IGkrKykge1xuICAgICAgICBjb25zdCBpbnRlcnNlY3QgPSAoKHJ5c1tpXSA+IHB0LnkpICE9PSAocnlzW2pdID4gcHQueSkpXG4gICAgICAgICAgJiYgKHB0LnggPCAoKHJ4c1tqXSAtIHJ4c1tpXSkgKiAocHQueSAtIHJ5c1tpXSkpIC8gKHJ5c1tqXSAtIHJ5c1tpXSkgKyByeHNbaV0pO1xuICAgICAgICBpZiAoaW50ZXJzZWN0KSBoaXQgPSAhaGl0O1xuICAgICAgfVxuICAgICAgcmV0dXJuIGhpdDtcbiAgICB9O1xuICAgIGlmICghaW5SaW5nKGIueHBvaW50cywgYi55cG9pbnRzKSkgcmV0dXJuIGZhbHNlO1xuICAgIGlmIChiLmhvbGVzKSB7XG4gICAgICBmb3IgKGNvbnN0IHJpbmcgb2YgYi5ob2xlcykge1xuICAgICAgICBpZiAoaW5SaW5nKHJpbmcubWFwKHAgPT4gcFswXSksIHJpbmcubWFwKHAgPT4gcFsxXSkpKSByZXR1cm4gZmFsc2U7XG4gICAgICB9XG4gICAgfVxuICAgIHJldHVybiB0cnVlO1xuICB9XG5cbiAgLyoqIFNob3J0ZXN0IGRpc3RhbmNlIGZyb20gcG9pbnQgcCB0byBzZWdtZW50IGHigJNiLCBhbGwgaW4gc2NyZWVuIHBpeGVscy4gKi9cbiAgcHJpdmF0ZSBkaXN0VG9TZWdtZW50UHgoXG4gICAgcDogeyB4OiBudW1iZXI7IHk6IG51bWJlciB9LCBhOiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH0sIGI6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSxcbiAgKTogbnVtYmVyIHtcbiAgICBjb25zdCBkeCA9IGIueCAtIGEueCwgZHkgPSBiLnkgLSBhLnk7XG4gICAgY29uc3QgbGVuMiA9IGR4ICogZHggKyBkeSAqIGR5O1xuICAgIGlmIChsZW4yID09PSAwKSByZXR1cm4gTWF0aC5oeXBvdChwLnggLSBhLngsIHAueSAtIGEueSk7XG4gICAgbGV0IHQgPSAoKHAueCAtIGEueCkgKiBkeCArIChwLnkgLSBhLnkpICogZHkpIC8gbGVuMjtcbiAgICB0ID0gTWF0aC5tYXgoMCwgTWF0aC5taW4oMSwgdCkpO1xuICAgIHJldHVybiBNYXRoLmh5cG90KHAueCAtIChhLnggKyB0ICogZHgpLCBwLnkgLSAoYS55ICsgdCAqIGR5KSk7XG4gIH1cblxuICBwcml2YXRlIHJlc2V0SW5Qcm9ncmVzcygpOiB2b2lkIHtcbiAgICB0aGlzLnJlY3RTdGFydCA9IHRoaXMucmVjdEN1cnJlbnQgPSBudWxsO1xuICAgIHRoaXMucG9seVBvaW50cyA9IFtdO1xuICAgIHRoaXMuZnJlZWhhbmREcmFnZ2luZyA9IGZhbHNlO1xuICAgIHRoaXMuZHJhd2luZ1BvbHlnb24gPSBmYWxzZTtcbiAgICB0aGlzLmxhc3RGcmVlaGFuZFB4ID0gbnVsbDtcbiAgICAvLyBDbG9zZSBhbnkgb3BlbiBlZGl0IGJhdGNoIChlLmcuIGEgbW9kZSBzd2l0Y2ggbWlkLWRyYWcpIHNvIHRoZSBzdG9yZSdzXG4gICAgLy8gZW1pdCBjb2FsZXNjaW5nIGRvZXNuJ3QgZ2V0IHN0dWNrLlxuICAgIGlmICh0aGlzLmVkaXQpIHtcbiAgICAgIHRoaXMuc3RvcmUuZW5kQmF0Y2goKTtcbiAgICAgIHRoaXMuZWRpdCA9IG51bGw7XG4gICAgfVxuICB9XG5cbiAgLy8g4pSA4pSAIGNvbW1pdCB0byB0aGUgc3RvcmUg4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSAXG4gIHByaXZhdGUgY29tbWl0UmVjdGFuZ2xlKHg6IG51bWJlciwgeTogbnVtYmVyLCB3OiBudW1iZXIsIGg6IG51bWJlcik6IHZvaWQge1xuICAgIGNvbnN0IHJlZ2lvbiA9IG5ldyBSZWdpb24oKTtcbiAgICBjb25zdCByZWN0ID0gbmV3IFJlY3RhbmdsZSgpO1xuICAgIHJlY3QueCA9IHg7IHJlY3QueSA9IHk7IHJlY3Qud2lkdGggPSB3OyByZWN0LmhlaWdodCA9IGg7XG4gICAgcmVnaW9uLmJvdW5kcyA9IHJlY3Q7XG4gICAgcmVnaW9uLmNvbG9yID0gdGhpcy5zdG9yZS5nZXRTaGFwZUNvbG9yKCk7XG4gICAgdGhpcy5jb21taXRSZWdpb24ocmVnaW9uKTtcbiAgfVxuXG4gIHByaXZhdGUgY29tbWl0UG9seWdvbihjbG9zZWQ6IGJvb2xlYW4pOiB2b2lkIHtcbiAgICBpZiAodGhpcy5wb2x5UG9pbnRzLmxlbmd0aCA8IChjbG9zZWQgPyAzIDogMikpIHsgdGhpcy5yZXNldEluUHJvZ3Jlc3MoKTsgcmV0dXJuOyB9XG4gICAgY29uc3QgcmVnaW9uID0gbmV3IFJlZ2lvbigpO1xuICAgIGNvbnN0IHBvbHkgPSBuZXcgUG9seWdvbigpO1xuICAgIHBvbHkubnBvaW50cyA9IHRoaXMucG9seVBvaW50cy5sZW5ndGg7XG4gICAgcG9seS54cG9pbnRzID0gdGhpcy5wb2x5UG9pbnRzLm1hcChwID0+IHAueCk7XG4gICAgcG9seS55cG9pbnRzID0gdGhpcy5wb2x5UG9pbnRzLm1hcChwID0+IHAueSk7XG4gICAgcG9seS5jb29yZGluYXRlcyA9IHRoaXMucG9seVBvaW50cy5tYXAocCA9PiBbcC54LCBwLnldKTtcbiAgICBwb2x5LmNsb3NlZCA9IGNsb3NlZDtcbiAgICByZWdpb24uYm91bmRzID0gcG9seTtcbiAgICByZWdpb24uY29sb3IgPSB0aGlzLnN0b3JlLmdldFNoYXBlQ29sb3IoKTtcbiAgICB0aGlzLnJlc2V0SW5Qcm9ncmVzcygpO1xuICAgIHRoaXMuY29tbWl0UmVnaW9uKHJlZ2lvbik7XG4gIH1cblxuICAvKipcbiAgICogQWRkIGEgZnJlc2hseS1kcmF3biByZWdpb24gdG8gdGhlIHNoYXJlZCBzdG9yZSBhbmQgcmVkcmF3IGltbWVkaWF0ZWx5LiBUaGVcbiAgICogc3RvcmUgbWludHMgdGhlIGlkLCBzZWxlY3RzIHRoZSBuZXcgcmVnaW9uIChzbyBpdCByZW5kZXJzIHNvbGlkL2hpZ2hsaWdodGVkXG4gICAqIHJhdGhlciB0aGFuIGFzIGEgZGFzaGVkIGluLXByb2dyZXNzIHNoYXBlKSBhbmQgZW1pdHMgdGhlIGZ1bGwgcmVnaW9uIGxpc3QgdG9cbiAgICogdGhlIFJlZ2lvbiBFZGl0b3Ig4oCUIHdlIHN0aWxsIHJlZHJhdyBsb2NhbGx5IHJhdGhlciB0aGFuIHJlbHlpbmcgc29sZWx5IG9uXG4gICAqIHRoZSBzdG9yZSdzIHVwZGF0ZSBldmVudCwgd2hpY2ggY2FuIGJlIHN3YWxsb3dlZCB3aGVuIFBsb3RseSBpc24ndCBhY3RpdmUuXG4gICAqL1xuICBwcml2YXRlIGNvbW1pdFJlZ2lvbihyZWdpb246IFJlZ2lvbik6IHZvaWQge1xuICAgIC8vIERlZmF1bHQgY2xhc3MvYW5ub3RhdGlvbiBuYW1lLCBtYXRjaGluZyB0aGUgUGxvdGx5IGJhY2tlbmQgYW5kIHRoZSBSZWdpb25cbiAgICAvLyBFZGl0b3IncyBcIkFkZFwiIGFjdGlvbnMgc28gYSBmcmVzaGx5IGRyYXduIHJlZ2lvbiBpc24ndCB1bmxhYmVsZWQuXG4gICAgaWYgKHJlZ2lvbi5sYWJlbCA9PSBudWxsKSByZWdpb24ubGFiZWwgPSAnUmVnaW9uJztcbiAgICB0aGlzLnN0b3JlLmFkZFJlZ2lvbihyZWdpb24pO1xuICAgIHRoaXMucmVkcmF3KCk7XG4gIH1cblxuICAvKipcbiAgICogQ29udmVydCB0aGUgc2VsZWN0ZWQgcmVnaW9uKHMpIHRvL2Zyb20gYSBiZXppZXIgY3VydmUgKHRvQmV6aWVyID0gdHJ1ZSAvXG4gICAqIHRvUG9seWdvbiA9IGZhbHNlKS4gT25lLXNob3Q7IHRoZSBhbmNob3JzIGFyZSB1bmNoYW5nZWQsXG4gICAqIG9ubHkgdGhlIHNtb290aC1jdXJ2ZSByZW5kZXJpbmcgaXMgdG9nZ2xlZC5cbiAgICovXG4gIHNldFNlbGVjdGVkQmV6aWVyKGJlemllcjogYm9vbGVhbik6IHZvaWQge1xuICAgIGNvbnN0IHJlZ2lvbnMgPSB0aGlzLnN0b3JlLmdldFJlZ2lvbnMoKTtcbiAgICBmb3IgKGNvbnN0IGlkeCBvZiB0aGlzLnNlbGVjdGVkKSB7XG4gICAgICBjb25zdCByZWdpb24gPSByZWdpb25zW2lkeF07XG4gICAgICBpZiAocmVnaW9uKSB0aGlzLnN0b3JlLnNldEJlemllcihyZWdpb24uaWQsIGJlemllcik7XG4gICAgfVxuICAgIHRoaXMucmVkcmF3KCk7XG4gIH1cbn1cbiJdfQ==
|
|
703
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoib3NkLXJlZ2lvbi1vdmVybGF5LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vc3JjL2xpYi9pbXBsZW1lbnRhdGlvbnMvb3NkL29zZC1yZWdpb24tb3ZlcmxheS50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFDQSxPQUFPLEVBQUUsR0FBRyxFQUFFLE1BQU0sV0FBVyxDQUFDO0FBQ2hDLE9BQU8sRUFBRSxZQUFZLEVBQUUsTUFBTSxNQUFNLENBQUM7QUFFcEMsT0FBTyxFQUFFLE1BQU0sRUFBRSxTQUFTLEVBQUUsT0FBTyxFQUFFLFlBQVksRUFBRSxNQUFNLHFCQUFxQixDQUFDO0FBSS9FLE9BQU8sRUFBRSxjQUFjLEVBQUUsY0FBYyxFQUFFLE1BQU0sY0FBYyxDQUFDO0FBRTlELE9BQU8sRUFBRSxtQkFBbUIsRUFBRSxNQUFNLFlBQVksQ0FBQztBQUNqRCxPQUFPLEVBQUUsZUFBZSxFQUFFLE1BQU0sMkJBQTJCLENBQUM7QUFDNUQsT0FBTyxFQUFFLFdBQVcsRUFBRSxNQUFNLDhCQUE4QixDQUFDO0FBQzNELE9BQU8sRUFDTCxnQkFBZ0IsRUFFaEIsU0FBUyxFQUNULFdBQVcsRUFDWCxjQUFjLEVBQ2QsYUFBYSxFQUNiLGVBQWUsR0FDaEIsTUFBTSxzQ0FBc0MsQ0FBQztBQUM5QyxPQUFPLEVBQUUsaUJBQWlCLEVBQUUsb0JBQW9CLEVBQUUsTUFBTSwwQ0FBMEMsQ0FBQztBQUNuRyxPQUFPLEVBQ0wsYUFBYSxFQUNiLGFBQWEsRUFDYixlQUFlLEVBQ2YsaUJBQWlCLEVBQ2pCLG9CQUFvQixFQUNwQixnQkFBZ0IsRUFDaEIsWUFBWSxHQUNiLE1BQU0sMkJBQTJCLENBQUM7QUFDbkMsT0FBTyxFQUFFLFdBQVcsRUFBWSxXQUFXLEVBQUUsUUFBUSxFQUFFLFVBQVUsRUFBRSxNQUFNLHNDQUFzQyxDQUFDO0FBWWhILE1BQU0sS0FBSyxHQUFHLDRCQUE0QixDQUFDO0FBUTNDOzs7Ozs7Ozs7Ozs7O0dBYUc7QUFDSCxNQUFN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TUFBTSxDQUFDLENBQUM7UUFDdEQsQ0FBQztRQUNELElBQUksQ0FBQyxNQUFNLEVBQUUsQ0FBQztJQUNoQixDQUFDO0NBQ0YiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgdHlwZSAqIGFzIE9wZW5TZWFkcmFnb24gZnJvbSAnb3BlbnNlYWRyYWdvbic7XG5pbXBvcnQgeyBPU0QgfSBmcm9tICcuL29zZC1saWInO1xuaW1wb3J0IHsgU3Vic2NyaXB0aW9uIH0gZnJvbSAncnhqcyc7XG5cbmltcG9ydCB7IFJlZ2lvbiwgUmVjdGFuZ2xlLCBQb2x5Z29uLCBNdWx0aVBvbHlnb24gfSBmcm9tICcuLi8uLi9tb2RlbHMvcmVnaW9uJztcbmltcG9ydCB7IElSZWdpb25TdG9yZSB9IGZyb20gJy4uLy4uL2NvbnRyYWN0cy92aXN1YWxpemVyLmNvbnRyYWN0JztcbmltcG9ydCB7IElSZWdpb25FZGl0QXBpIH0gZnJvbSAnLi4vLi4vY29udHJhY3RzL3JlZ2lvbi1zdG9yZS5jb250cmFjdCc7XG5pbXBvcnQgeyBJUmVnaW9uT3ZlcmxheSwgUmVnaW9uVG9vbE1vZGUgfSBmcm9tICcuLi8uLi9jb250cmFjdHMvcmVnaW9uLW92ZXJsYXkuY29udHJhY3QnO1xuaW1wb3J0IHsgZWxlbWVudFRvSW1hZ2UsIGltYWdlVG9FbGVtZW50IH0gZnJvbSAnLi9vc2QtY29vcmRzJztcbmltcG9ydCB7IE9zZFZpZXdlckxpa2UgfSBmcm9tICcuL29zZC12aWV3ZXItbGlrZSc7XG5pbXBvcnQgeyBPU0RfWk9PTV9QRVJfU0NST0xMIH0gZnJvbSAnLi9vc2Qtem9vbSc7XG5pbXBvcnQgeyB0cmFuc2xhdGVCb3VuZHMgfSBmcm9tICcuLi8uLi9tb2RlbHMvcG9seWdvbi1lZGl0JztcbmltcG9ydCB7IG1ha2VQb2x5Z29uIH0gZnJvbSAnLi4vLi4vbW9kZWxzL3BvbHlnb24tZmFjdG9yeSc7XG5pbXBvcnQge1xuICBPUEVOX1BBVEhfVE9MX1BYLFxuICBUb1NjcmVlbixcbiAgaGl0SGFuZGxlLFxuICBuZWFyZXN0RWRnZSxcbiAgcmVnaW9uQ29udGFpbnMsXG4gIHJlZ2lvbnNJblJlY3QsXG4gIHRvcG1vc3RSZWdpb25BdCxcbn0gZnJvbSAnLi4vLi4vcmVnaW9uLW92ZXJsYXkvcmVnaW9uLWdlb21ldHJ5JztcbmltcG9ydCB7IFN2Z1JlZ2lvblJlbmRlcmVyLCBhZmZpbmVGcm9tUHJvamVjdGlvbiB9IGZyb20gJy4uLy4uL3JlZ2lvbi1vdmVybGF5L3N2Zy1yZWdpb24tcmVuZGVyZXInO1xuaW1wb3J0IHtcbiAgZHJhd0RyYWZ0UGF0aCxcbiAgZHJhd0RyYWZ0UmVjdCxcbiAgZHJhd1JlZ2lvbkxhYmVsLFxuICBkcmF3U2VsZWN0aW9uQmFuZCxcbiAgZHJhd1NlbGVjdGlvbkhhbmRsZXMsXG4gIHN0eWxlUmVnaW9uU2hhcGUsXG4gIHZlcnRleE1hcmtlcixcbn0gZnJvbSAnLi9vc2QtcmVnaW9uLW92ZXJsYXktZHJhdyc7XG5pbXBvcnQgeyBFRElUX1RPTF9QWCwgRWRpdFpvbmUsIFpPTkVfQ1VSU09SLCByZWN0Wm9uZSwgcmVzaXplUmVjdCB9IGZyb20gJy4uLy4uL3JlZ2lvbi1vdmVybGF5L3JlZ2lvbi1oaXQtdGVzdCc7XG5cbi8qKlxuICogVGhlIHNoYXJlZCByZWdpb24gc3RvcmUgYXMgdGhlIG92ZXJsYXkgbmVlZHMgaXQ6IHRoZSBjcm9zcy1iYWNrZW5kXG4gKiB7QGxpbmsgSVJlZ2lvblN0b3JlfSAocmVhZCByZWdpb25zLCBzZWxlY3Rpb24sIGNvbG91cnMpIHBsdXMgdGhlIFJlZ2lvbi1uYXRpdmVcbiAqIHtAbGluayBJUmVnaW9uRWRpdEFwaX0gKGFkZC9tb3ZlL3Jlc2l6ZS92ZXJ0ZXggZWRpdHMpLiBUaGUgc2hhcmVkIFJlZ2lvblN0b3JlXG4gKiBzYXRpc2ZpZXMgYm90aC4gVGhlIG92ZXJsYXkgZWRpdHMgdGhyb3VnaCB0aGVzZSB0eXBlZCBvcGVyYXRpb25zIG9uIHRoZVxuICogbmV1dHJhbCBSZWdpb24gbW9kZWwg4oCUIGl0IG5ldmVyIHRvdWNoZXMgYSBiYWNrZW5kJ3Mgb3duIHNoYXBlIHJlcHJlc2VudGF0aW9uXG4gKiAoZS5nLiBQbG90bHkncyBgeDAveTAveDEveTFgIC8gYE3igKZM4oCmWmAgZGljdHMpLlxuICovXG5leHBvcnQgdHlwZSBSZWdpb25FZGl0U3RvcmUgPSBJUmVnaW9uU3RvcmUgJiBJUmVnaW9uRWRpdEFwaTtcblxuY29uc3QgU1ZHTlMgPSAnaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmcnO1xuXG4vKiogQSByZWdpb24ncyBnZW9tZXRyeSBhdCB0aGUgc3RhcnQgb2YgYSBtb3ZlL3Jlc2l6ZSAoc2VlIGBzbmFwc2hvdGApOiBhIHJlY3RhbmdsZSdzXG4gKiAgYm94IGZvciBhIHJlc2l6ZSwgb3IgdGhlIHBvbHlnb24vbXVsdGktcG9seWdvbiBib3VuZHMgdGhlbXNlbHZlcyBmb3IgYSBtb3ZlIOKAlCB0aGVcbiAqICBzdG9yZSBpcyBjb3B5LW9uLXdyaXRlLCBzbyB0aGUgZ2VzdHVyZS1zdGFydCBpbnN0YW5jZSBuZXZlciBjaGFuZ2VzIHVuZGVyIHRoZSBkcmFnLiAqL1xudHlwZSBFZGl0U25hcHNob3QgPVxuICB7IGtpbmQ6ICdyZWN0JzsgeDogbnVtYmVyOyB5OiBudW1iZXI7IHc6IG51bWJlcjsgaDogbnVtYmVyIH0gfCB7IGtpbmQ6ICdzaGFwZSc7IGJvdW5kczogUG9seWdvbiB8IE11bHRpUG9seWdvbiB9O1xuXG4vKipcbiAqIE9wZW5TZWFkcmFnb24gaW1wbGVtZW50YXRpb24gb2Yge0BsaW5rIElSZWdpb25PdmVybGF5fS5cbiAqXG4gKiAtIFJlbmRlcnMgdGhlIHN0b3JlJ3MgcmVnaW9ucyAocmVjdC9wb2x5Z29uKSBpbiBpbWFnZS1waXhlbCBzcGFjZSwga2VwdFxuICogICBhbGlnbmVkIG9uIGV2ZXJ5IHBhbi96b29tIHZpYSB0aGUgT1NEIHZpZXdwb3J0IEFQSS5cbiAqIC0gRHJhd3MgbmV3IHJlY3RhbmdsZSBhbmQgcG9seWdvbiByZWdpb25zIChjb21taXR0ZWQgdG8gdGhlIHNoYXJlZCBzdG9yZSkuXG4gKiAtIENsaWNrLXRvLXNlbGVjdCBpbiAnc2VsZWN0JyBtb2RlLlxuICpcbiAqIFJlYWRzL3dyaXRlcyB0aGUgc2hhcmVkIHtAbGluayBJUmVnaW9uU3RvcmV9LCBzbyByZWdpb25zIHN0YXkgaW4gc3luYyB3aXRoIHRoZVxuICogUmVnaW9uIEVkaXRvciBhbmQgdGhlIFBsb3RseSBiYWNrZW5kLiBUaGUgd2FuZCwgdmVydGV4LWVyYXNlciBhbmQgem9vbS10by1ib3hcbiAqIHRvb2xzIGFyZSBOT1QgaGFuZGxlZCBoZXJlIOKAlCB0aGV5J3JlIG93bmVkIGJ5IE9wZW5TZWFkcmFnb25WaXN1YWxpemVyU2VydmljZVxuICogKHdoaWNoIGJpbmRzIHRoZW0gdG8gT1NEIHZpYSB0aGUgc2hhcmVkIGNvb3JkaW5hdGUgdHJhbnNmb3JtICsgdmlld3BvcnQgcGl4ZWxcbiAqIHJlYWRiYWNrKSwgdGhlIHNhbWUgc2luZ2xldG9uIHRvb2wgc2VydmljZXMgdGhlIFBsb3RseSBiYWNrZW5kIHVzZXMuXG4gKi9cbmV4cG9ydCBjbGFzcyBPc2RSZWdpb25PdmVybGF5IGltcGxlbWVudHMgSVJlZ2lvbk92ZXJsYXkge1xuICBwcml2YXRlIHJlYWRvbmx5IHN2ZzogU1ZHU1ZHRWxlbWVudDtcbiAgcHJpdmF0ZSByZWFkb25seSBzdWJzID0gbmV3IFN1YnNjcmlwdGlvbigpO1xuICBwcml2YXRlIHNlbGVjdGVkOiBudW1iZXJbXSA9IFtdO1xuICBwcml2YXRlIG1vZGU6IFJlZ2lvblRvb2xNb2RlID0gJ25vbmUnO1xuXG4gIHByaXZhdGUgdHJhY2tlcjogT3BlblNlYWRyYWdvbi5Nb3VzZVRyYWNrZXI7XG4gIHByaXZhdGUgcmVjdFN0YXJ0OiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH0gfCBudWxsID0gbnVsbDsgLy8gaW1hZ2UgY29vcmRzXG4gIHByaXZhdGUgcmVjdEN1cnJlbnQ6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSB8IG51bGwgPSBudWxsO1xuICBwcml2YXRlIHBvbHlQb2ludHM6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfVtdID0gW107IC8vIGltYWdlIGNvb3Jkc1xuICAvKiogVHJ1ZSB3aGlsZSBkcmFnZ2luZyBhIGZyZWVoYW5kIHBhdGggKGZyZWVmb3JtIC8gcG9seWxpbmUpLiAqL1xuICBwcml2YXRlIGZyZWVoYW5kRHJhZ2dpbmcgPSBmYWxzZTtcbiAgLyoqIFRydWUgd2hpbGUgcGxhY2luZyBhIGNsaWNrLXRvLWFkZCBwb2x5Z29uICgnZHJhd3BvbHlnb24nIG1vZGUpLiAqL1xuICBwcml2YXRlIGRyYXdpbmdQb2x5Z29uID0gZmFsc2U7XG4gIC8qKiBMYXN0IGVsZW1lbnQtcGl4ZWwgcG9pbnQgYXBwZW5kZWQsIHRvIHRoaW4gdGhlIGZyZWVoYW5kIHBhdGguICovXG4gIHByaXZhdGUgbGFzdEZyZWVoYW5kUHg6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSB8IG51bGwgPSBudWxsO1xuICAvKipcbiAgICogSW4tcHJvZ3Jlc3MgZWRpdCBvZiB0aGUgc2VsZWN0ZWQgcmVnaW9uOlxuICAgKiAgLSBraW5kICdib3VuZHMnIOKAlCByZWN0YW5nbGUgcmVzaXplL21vdmUgb3Igd2hvbGUtcmVnaW9uIG1vdmUgKHVzZXMgYHpvbmVgKTtcbiAgICogIC0ga2luZCAndmVydGV4JyDigJQgZHJhZ2dpbmcgYSBzaW5nbGUgcG9seWdvbiB2ZXJ0ZXggKHVzZXMgYHZlcnRleEluZGV4YCkuXG4gICAqL1xuICBwcml2YXRlIGVkaXQ6IHtcbiAgICBraW5kOiAnYm91bmRzJyB8ICd2ZXJ0ZXgnIHwgJ2hhbmRsZSc7XG4gICAgem9uZTogRWRpdFpvbmU7XG4gICAgdmVydGV4SW5kZXg6IG51bWJlcjtcbiAgICAvKiogV2hpY2ggcmluZyB0aGUgZHJhZ2dlZCB2ZXJ0ZXggYmVsb25ncyB0bzogLTEgPSBleHRlcmlvciwgZWxzZSBhIGhvbGVcbiAgICAgKiAgaW5kZXggaW50byBgUG9seWdvbi5ob2xlc2AgKGppdC11aSM4NSkuICovXG4gICAgcmluZzogbnVtYmVyO1xuICAgIGhhbmRsZVNpZGU6ICdpbicgfCAnb3V0JztcbiAgICBpZDogbnVtYmVyO1xuICAgIHN0YXJ0SW1nOiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH07XG4gICAgLyoqIEdlc3R1cmUtc3RhcnQgZ2VvbWV0cnk7IHNldCBmb3IgJ2JvdW5kcycgZWRpdHMgb25seS4gKi9cbiAgICBvcmlnOiBFZGl0U25hcHNob3QgfCBudWxsO1xuICB9IHwgbnVsbCA9IG51bGw7XG4gIHByaXZhdGUgZWRpdERyYWdnZWQgPSBmYWxzZTtcbiAgLyoqIFJ1YmJlci1iYW5kIChtYXJxdWVlKSBtdWx0aS1zZWxlY3QgaW4gJ3NlbGVjdCcgbW9kZTogcHJlc3Mgb24gZW1wdHkgc3BhY2VcbiAgICogIGFuZCBkcmFnIHRvIHNlbGVjdCBldmVyeSByZWdpb24gdGhlIGJhbmQgaW50ZXJzZWN0cy4gSW1hZ2UgY29vcmRzLiAqL1xuICBwcml2YXRlIGJhbmRTdGFydDogeyB4OiBudW1iZXI7IHk6IG51bWJlciB9IHwgbnVsbCA9IG51bGw7XG4gIHByaXZhdGUgYmFuZEN1cnJlbnQ6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSB8IG51bGwgPSBudWxsO1xuICBwcml2YXRlIGJhbmREcmFnZ2VkID0gZmFsc2U7XG5cbiAgcHJpdmF0ZSByZWFkb25seSByZWRyYXdIYW5kbGVyID0gKCkgPT4gdGhpcy5yZWRyYXcoKTtcbiAgLyoqIEEgY2FtZXJhIG1vdmUgKCd1cGRhdGUtdmlld3BvcnQnLCByYWlzZWQgb24gZXZlcnkgcmVkcmF3biBmcmFtZSwgYW5pbWF0ZWQgb25lc1xuICAgKiAgaW5jbHVkZWQ7ICdyZXNpemUnOyAncm90YXRlJykuIFRoZSByZWdpb25zIGFyZSBkcmF3biBpbiBpbWFnZSBjb29yZGluYXRlcywgc29cbiAgICogIG9ubHkgdGhlIHJlbmRlcmVyJ3MgdHJhbnNmb3JtIGFuZCBpdHMgZmV3IHNjcmVlbi1zcGFjZSBlbGVtZW50cyBmb2xsb3c7IG5vdGhpbmdcbiAgICogIGlzIHJlYnVpbHQgKE9TRC1QTE9UTFktMTEpLiBBIHRpbGUtb25seSBmcmFtZSAobG9hZGluZywgcmVjb2xvcikgbGVhdmVzIHRoZVxuICAgKiAgcHJvamVjdGlvbiwgYW5kIHNvIHRoZSBET00sIHVudG91Y2hlZC4gKi9cbiAgcHJpdmF0ZSByZWFkb25seSBjYW1lcmFIYW5kbGVyID0gKCkgPT4gdGhpcy51cGRhdGVDYW1lcmEoKTtcbiAgcHJpdmF0ZSByZWFkb25seSByZW5kZXJlcjogU3ZnUmVnaW9uUmVuZGVyZXI7XG4gIC8qKiBPU0QncyBNb3VzZVRyYWNrZXIgZHJvcHMgYSBjYW5jZWxsZWQgcG9pbnRlciAodG91Y2ggaW50ZXJydXB0ZWQsIHBvaW50ZXJcbiAgICogIGNhcHR1cmUgbG9zdCB0byB0aGUgYnJvd3Nlcikgd2l0aG91dCBjYWxsaW5nIHJlbGVhc2VIYW5kbGVyLCBzbyB0aGVcbiAgICogIGdlc3R1cmUgaXMgZW5kZWQgaGVyZSBpbnN0ZWFkLiAqL1xuICBwcml2YXRlIHJlYWRvbmx5IHBvaW50ZXJDYW5jZWxIYW5kbGVyID0gKCkgPT4ge1xuICAgIHRoaXMuZW5kR2VzdHVyZSgpO1xuICAgIHRoaXMucmVkcmF3KCk7XG4gIH07XG5cbiAgY29uc3RydWN0b3IoXG4gICAgcHJpdmF0ZSB2aWV3ZXI6IE9zZFZpZXdlckxpa2UsXG4gICAgcHJpdmF0ZSBzdG9yZTogUmVnaW9uRWRpdFN0b3JlLFxuICApIHtcbiAgICB0aGlzLnN2ZyA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhTVkdOUywgJ3N2ZycpIGFzIFNWR1NWR0VsZW1lbnQ7XG4gICAgT2JqZWN0LmFzc2lnbih0aGlzLnN2Zy5zdHlsZSwge1xuICAgICAgcG9zaXRpb246ICdhYnNvbHV0ZScsXG4gICAgICBsZWZ0OiAnMCcsXG4gICAgICB0b3A6ICcwJyxcbiAgICAgIHdpZHRoOiAnMTAwJScsXG4gICAgICBoZWlnaHQ6ICcxMDAlJyxcbiAgICAgIHBvaW50ZXJFdmVudHM6ICdub25lJywgLy8gT1NEIGhhbmRsZXMgbmF2aWdhdGlvbiB1bmxlc3Mgd2UncmUgZHJhd2luZ1xuICAgIH0pO1xuICAgIHRoaXMudmlld2VyLmNhbnZhcy5hcHBlbmRDaGlsZCh0aGlzLnN2Zyk7XG4gICAgdGhpcy5yZW5kZXJlciA9IG5ldyBTdmdSZWdpb25SZW5kZXJlcih0aGlzLnN2Zywge1xuICAgICAgcmVjdEVsZW1lbnQ6ICdwb2x5Z29uJyxcbiAgICAgIHN0eWxlU2hhcGU6IChlbCwgcmVnaW9uLCBzZWxlY3RlZCkgPT4gc3R5bGVSZWdpb25TaGFwZShlbCwgcmVnaW9uLCBzZWxlY3RlZCwgdGhpcy5zdG9yZS5nZXRTaGFwZUNvbG9yKCkpLFxuICAgICAgLy8gVGhlIGNsYXNzIGxhYmVsLCB3aGVuIHRoZSBSZWdpb24gRWRpdG9yJ3MgXCJzaG93IGxhYmVsc1wiIGlzIG9uLlxuICAgICAgZGVjb3JhdGU6IChyZWdpb24sIF9pLCBfc2VsZWN0ZWQsIGxheWVyKSA9PiB7XG4gICAgICAgIGlmICh0aGlzLnN0b3JlLmdldFNob3dTaGFwZUxhYmVsKCkpIGRyYXdSZWdpb25MYWJlbChsYXllciwgcmVnaW9uLCB0aGlzLnN0b3JlLmdldFNoYXBlQ29sb3IoKSk7XG4gICAgICB9LFxuICAgIH0pO1xuICAgIHRoaXMudmlld2VyLmNhbnZhcy5hZGRFdmVudExpc3RlbmVyKCdwb2ludGVyY2FuY2VsJywgdGhpcy5wb2ludGVyQ2FuY2VsSGFuZGxlcik7XG5cbiAgICAvLyAndXBkYXRlLXZpZXdwb3J0JyBmaXJlcyBvbiBldmVyeSByZWRyYXduIGZyYW1lLCBhbmltYXRlZCBvbmVzIGluY2x1ZGVkIOKAlFxuICAgIC8vIGFsc28gbGlzdGVuaW5nIHRvICdhbmltYXRpb24nIHJlYnVpbHQgdGhlIHdob2xlIFNWRyB0d2ljZSBwZXIgZnJhbWUuXG4gICAgdGhpcy52aWV3ZXIuYWRkSGFuZGxlcigndXBkYXRlLXZpZXdwb3J0JywgdGhpcy5jYW1lcmFIYW5kbGVyKTtcbiAgICB0aGlzLnZpZXdlci5hZGRIYW5kbGVyKCdyZXNpemUnLCB0aGlzLmNhbWVyYUhhbmRsZXIpO1xuICAgIHRoaXMudmlld2VyLmFkZEhhbmRsZXIoJ3JvdGF0ZScsIHRoaXMuY2FtZXJhSGFuZGxlcik7XG4gICAgLy8gS2VlcCB3aGVlbC16b29tIGFsaXZlIHdoaWxlIGEgdG9vbCBoYXMgbW91c2UtbmF2IGRpc2FibGVkIChzZWUgaGFuZGxlcikuXG4gICAgdGhpcy52aWV3ZXIuZWxlbWVudD8uYWRkRXZlbnRMaXN0ZW5lcignd2hlZWwnLCB0aGlzLndoZWVsWm9vbUhhbmRsZXIsIHsgcGFzc2l2ZTogZmFsc2UgfSk7XG5cbiAgICB0aGlzLnRyYWNrZXIgPSBuZXcgT1NELk1vdXNlVHJhY2tlcih7XG4gICAgICBlbGVtZW50OiB0aGlzLnZpZXdlci5jYW52YXMsXG4gICAgICBwcmVzc0hhbmRsZXI6IChlOiBhbnkpID0+IHRoaXMub25QcmVzcyhlKSxcbiAgICAgIGRyYWdIYW5kbGVyOiAoZTogYW55KSA9PiB0aGlzLm9uRHJhZyhlKSxcbiAgICAgIHJlbGVhc2VIYW5kbGVyOiAoZTogYW55KSA9PiB0aGlzLm9uUmVsZWFzZShlKSxcbiAgICAgIGNsaWNrSGFuZGxlcjogKGU6IGFueSkgPT4gdGhpcy5vbkNsaWNrKGUpLFxuICAgICAgbW92ZUhhbmRsZXI6IChlOiBhbnkpID0+IHRoaXMub25Nb3ZlKGUpLFxuICAgIH0pO1xuICAgIHRoaXMudHJhY2tlci5zZXRUcmFja2luZyhmYWxzZSk7XG5cbiAgICB0aGlzLnN1YnMuYWRkKHRoaXMuc3RvcmUuZ2V0UmVnaW9uVXBkYXRlRXZlbnQoKS5zdWJzY3JpYmUodGhpcy5yZWRyYXdIYW5kbGVyKSk7XG4gICAgdGhpcy5zdWJzLmFkZChcbiAgICAgIHRoaXMuc3RvcmUuZ2V0U2VsZWN0ZWRTaGFwZUluZGljZXMkKCkuc3Vic2NyaWJlKChpZHgpID0+IHtcbiAgICAgICAgdGhpcy5zZWxlY3RlZCA9IGlkeCB8fCBbXTtcbiAgICAgICAgdGhpcy5yZWRyYXcoKTtcbiAgICAgIH0pLFxuICAgICk7XG5cbiAgICB0aGlzLnJlZHJhdygpO1xuICB9XG5cbiAgLyoqIFN3aXRjaCBkcmF3aW5nL3NlbGVjdGlvbiBtb2RlOyB0b2dnbGVzIE9TRCBuYXZpZ2F0aW9uIGFjY29yZGluZ2x5LiAqL1xuICBzZXRNb2RlKG1vZGU6IFJlZ2lvblRvb2xNb2RlKTogdm9pZCB7XG4gICAgdGhpcy5tb2RlID0gbW9kZTtcbiAgICB0aGlzLnJlc2V0SW5Qcm9ncmVzcygpO1xuICAgIC8vIEFueSBhY3RpdmUgcmVnaW9uIHRvb2wgdGFrZXMgb3ZlciB0aGUgcG9pbnRlciDigJQgT1NEIHBhbi96b29tIGlzIGRpc2FibGVkXG4gICAgLy8gc28gZHJhZ2dpbmcgZHJhd3MgKGFuZCBjbGlja3Mgc2VsZWN0KSBpbnN0ZWFkIG9mIHBhbm5pbmcuIFdpdGggbm8gdG9vbCxcbiAgICAvLyBPU0QgbmF2aWdhdGVzIG5vcm1hbGx5LlxuICAgIHRoaXMudmlld2VyLnNldE1vdXNlTmF2RW5hYmxlZChtb2RlID09PSAnbm9uZScpO1xuICAgIHRoaXMudHJhY2tlci5zZXRUcmFja2luZyhtb2RlICE9PSAnbm9uZScpO1xuICAgIHRoaXMudXBkYXRlQ3Vyc29yKGZhbHNlKTtcbiAgICB0aGlzLnJlbmRlck92ZXJsYXkoKTtcbiAgfVxuXG4gIC8qKiBEcml2ZSBPU0Qgem9vbSBmcm9tIHRoZSB3aGVlbCB3aGlsZSBhbnkgdG9vbCBvd25zIHRoZSBwb2ludGVyLlxuICAgKlxuICAgKiBPU0QncyBuYXRpdmUgc2Nyb2xsLXpvb20gaXMgcGFydCBvZiBtb3VzZS1uYXYsIHNvIGBzZXRNb3VzZU5hdkVuYWJsZWQoZmFsc2UpYFxuICAgKiAodXNlZCBieSBldmVyeSByZWdpb24gdG9vbCBhbmQgYnkgdGhlIHdhbmQvYnJ1c2gvZXJhc2VyL1NBTSB0b29scykgZGlzYWJsZXNcbiAgICogaXQuIFRoZSBjb3ZlcmluZy1jYW52YXMgdG9vbHMgYWxzbyBzaXQgYWJvdmUgdGhlIE9TRCBjYW52YXMgYW5kIHN3YWxsb3cgdGhlXG4gICAqIHdoZWVsIG91dHJpZ2h0LiBUaGlzIGxpc3RlbmVyIGlzIGJvdW5kIG9uY2UgdG8gdGhlIHZpZXdlciBlbGVtZW50IOKAlCBhblxuICAgKiBhbmNlc3RvciBvZiBib3RoIHRoZSBPU0QgY2FudmFzIGFuZCB0aGUgdG9vbCBvdmVybGF5cyDigJQgYW5kIGZvcndhcmRzIHRoZVxuICAgKiB3aGVlbCB0byBhIGN1cnNvci1jZW50cmVkIHpvb20gd2hlbmV2ZXIgbW91c2UtbmF2IGlzIG9mZi4gV2hlbiBuYXYgaXMgb24gKG5vXG4gICAqIHRvb2wgYWN0aXZlKSBpdCBkb2VzIG5vdGhpbmcgYW5kIE9TRCB6b29tcyBuYXRpdmVseS4gKGppdC11aSM5NCkgKi9cbiAgcHJpdmF0ZSByZWFkb25seSB3aGVlbFpvb21IYW5kbGVyID0gKGU6IFdoZWVsRXZlbnQpID0+IHtcbiAgICBjb25zdCB2cCA9IHRoaXMudmlld2VyPy52aWV3cG9ydDtcbiAgICBjb25zdCBlbCA9IHRoaXMudmlld2VyPy5lbGVtZW50O1xuICAgIC8vIE5hdiBvbiDihpIgbm8gdG9vbCBhY3RpdmUg4oaSIGxldCBPU0QgaGFuZGxlIHNjcm9sbC16b29tIG5hdGl2ZWx5LlxuICAgIGlmICghdnAgfHwgIWVsIHx8IGUuZGVsdGFZID09PSAwIHx8IHRoaXMudmlld2VyLmlzTW91c2VOYXZFbmFibGVkKCkpIHJldHVybjtcbiAgICBlLnByZXZlbnREZWZhdWx0KCk7XG4gICAgY29uc3QgcmVjdCA9IGVsLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpO1xuICAgIGNvbnN0IHJlZlBvaW50ID0gdnAucG9pbnRGcm9tUGl4ZWwobmV3IE9TRC5Qb2ludChlLmNsaWVudFggLSByZWN0LmxlZnQsIGUuY2xpZW50WSAtIHJlY3QudG9wKSk7XG4gICAgdnAuem9vbUJ5KGUuZGVsdGFZIDwgMCA/IE9TRF9aT09NX1BFUl9TQ1JPTEwgOiAxIC8gT1NEX1pPT01fUEVSX1NDUk9MTCwgcmVmUG9pbnQpO1xuICAgIHZwLmFwcGx5Q29uc3RyYWludHMoKTtcbiAgfTtcblxuICAvKiogQ3Vyc29yIGZlZWRiYWNrIHBlciBtb2RlIChjcm9zc2hhaXIgd2hpbGUgZHJhd2luZzsgcG9pbnRlciBvdmVyIGEgcmVnaW9uXG4gICAqICBpbiBzZWxlY3QgbW9kZSkuICovXG4gIHByaXZhdGUgdXBkYXRlQ3Vyc29yKG92ZXJSZWdpb246IGJvb2xlYW4pOiB2b2lkIHtcbiAgICBjb25zdCBjYW52YXMgPSB0aGlzLnZpZXdlci5jYW52YXM7XG4gICAgaWYgKFxuICAgICAgdGhpcy5tb2RlID09PSAnZHJhd3JlY3QnIHx8XG4gICAgICB0aGlzLm1vZGUgPT09ICdkcmF3Y2xvc2VkcGF0aCcgfHxcbiAgICAgIHRoaXMubW9kZSA9PT0gJ2RyYXdvcGVucGF0aCcgfHxcbiAgICAgIHRoaXMubW9kZSA9PT0gJ2RyYXdwb2x5Z29uJyB8fFxuICAgICAgdGhpcy5tb2RlID09PSAnYWRkcG9pbnQnIHx8XG4gICAgICB0aGlzLm1vZGUgPT09ICdkZWxldGVwb2ludCdcbiAgICApIHtcbiAgICAgIGNhbnZhcy5zdHlsZS5jdXJzb3IgPSAnY3Jvc3NoYWlyJztcbiAgICB9IGVsc2UgaWYgKHRoaXMubW9kZSA9PT0gJ21vdmUnKSB7XG4gICAgICBjYW52YXMuc3R5bGUuY3Vyc29yID0gJ21vdmUnO1xuICAgIH0gZWxzZSBpZiAodGhpcy5tb2RlID09PSAnc2VsZWN0Jykge1xuICAgICAgY2FudmFzLnN0eWxlLmN1cnNvciA9IG92ZXJSZWdpb24gPyAncG9pbnRlcicgOiAnZGVmYXVsdCc7XG4gICAgfSBlbHNlIHtcbiAgICAgIGNhbnZhcy5zdHlsZS5jdXJzb3IgPSAnJzsgLy8gT1NEIGRlZmF1bHQgKGdyYWIpXG4gICAgfVxuICB9XG5cbiAgLyoqIFdoZXRoZXIgdGhlIHNlbGVjdGVkIHJlZ2lvbidzIHZlcnRpY2VzL2hhbmRsZXMgc2hvdWxkIGJlIGRyYXduLiBTaG93blxuICAgKiAgd2hlbmV2ZXIgYSByZWdpb24gaXMgc2VsZWN0ZWQg4oCUIGluY2x1ZGluZyBgbm9uZWAgKGRpc3BsYXkpIG1vZGUgYW5kIHdoaWxlXG4gICAqICBhbm90aGVyIHRvb2wgKHdhbmQsIGJydXNoLCBTQU3igKYpIGlzIGFjdGl2ZSDigJQgc28gYSBzZWxlY3Rpb24gYWx3YXlzIHJldmVhbHNcbiAgICogIGl0cyB2ZXJ0aWNlcy4gU3VwcHJlc3NlZCBvbmx5IHdoaWxlIGFjdGl2ZWx5IGRyYXdpbmcgYSBicmFuZC1uZXcgc2hhcGUsXG4gICAqICB3aGVyZSBzdHJheSBoYW5kbGVzIHdvdWxkIGJlIG5vaXNlLiAqL1xuICBwcml2YXRlIGdldCBzaG93c1NlbGVjdGVkVmVydGljZXMoKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuIChcbiAgICAgIHRoaXMubW9kZSAhPT0gJ2RyYXdyZWN0JyAmJlxuICAgICAgdGhpcy5tb2RlICE9PSAnZHJhd3BvbHlnb24nICYmXG4gICAgICB0aGlzLm1vZGUgIT09ICdkcmF3Y2xvc2VkcGF0aCcgJiZcbiAgICAgIHRoaXMubW9kZSAhPT0gJ2RyYXdvcGVucGF0aCdcbiAgICApO1xuICB9XG5cbiAgZGVzdHJveSgpOiB2b2lkIHtcbiAgICAvLyBDbG9zZSBhIGdlc3R1cmUgaW4gZmxpZ2h0IGZpcnN0OiBhIGRyYWcncyBvcGVuIHN0b3JlIGJhdGNoIHdvdWxkXG4gICAgLy8gb3RoZXJ3aXNlIHN1cHByZXNzIGV2ZXJ5IGxhdGVyIHJlZ2lvbi11cGRhdGUgZW1pc3Npb24gYXBwLXdpZGUuXG4gICAgdGhpcy5lbmRHZXN0dXJlKCk7XG4gICAgdGhpcy52aWV3ZXIuY2FudmFzLnJlbW92ZUV2ZW50TGlzdGVuZXIoJ3BvaW50ZXJjYW5jZWwnLCB0aGlzLnBvaW50ZXJDYW5jZWxIYW5kbGVyKTtcbiAgICB0aGlzLnN1YnMudW5zdWJzY3JpYmUoKTtcbiAgICB0aGlzLnZpZXdlci5lbGVtZW50Py5yZW1vdmVFdmVudExpc3RlbmVyKCd3aGVlbCcsIHRoaXMud2hlZWxab29tSGFuZGxlcik7XG4gICAgdGhpcy52aWV3ZXIucmVtb3ZlSGFuZGxlcigndXBkYXRlLXZpZXdwb3J0JywgdGhpcy5jYW1lcmFIYW5kbGVyKTtcbiAgICB0aGlzLnZpZXdlci5yZW1vdmVIYW5kbGVyKCdyZXNpemUnLCB0aGlzLmNhbWVyYUhhbmRsZXIpO1xuICAgIHRoaXMudmlld2VyLnJlbW92ZUhhbmRsZXIoJ3JvdGF0ZScsIHRoaXMuY2FtZXJhSGFuZGxlcik7XG4gICAgaWYgKHRoaXMudHJhY2tlcikgdGhpcy50cmFja2VyLmRlc3Ryb3koKTtcbiAgICBpZiAodGhpcy5zdmcucGFyZW50Tm9kZSkgdGhpcy5zdmcucGFyZW50Tm9kZS5yZW1vdmVDaGlsZCh0aGlzLnN2Zyk7XG4gIH1cblxuICAvLyDilIDilIAgY29vcmRpbmF0ZSBoZWxwZXJzIOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgFxuICAvKiogSW1hZ2UtcGl4ZWwgcG9pbnQgLT4gZWxlbWVudCBwaXhlbCBwb2ludC4gKi9cbiAgcHJpdmF0ZSB0b1B4KGltZ1g6IG51bWJlciwgaW1nWTogbnVtYmVyKTogeyB4OiBudW1iZXI7IHk6IG51bWJlciB9IHtcbiAgICByZXR1cm4gaW1hZ2VUb0VsZW1lbnQodGhpcy52aWV3ZXIsIGltZ1gsIGltZ1kpO1xuICB9XG4gIC8qKiBFbGVtZW50IHBpeGVsIHBvaW50IChmcm9tIGEgTW91c2VUcmFja2VyIGV2ZW50KSAtPiBpbWFnZS1waXhlbCBwb2ludCwgcm91bmRlZFxuICAgKiAgdG8gd2hvbGUgcGl4ZWxzICh3aGVyZSBhIGRyYXduIHZlcnRleCBsYW5kcykuICovXG4gIHByaXZhdGUgdG9JbWFnZShwb3M6IGFueSk6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSB7XG4gICAgY29uc3QgcCA9IGVsZW1lbnRUb0ltYWdlKHRoaXMudmlld2VyLCBwb3MueCwgcG9zLnkpO1xuICAgIHJldHVybiB7IHg6IE1hdGgucm91bmQocC54KSwgeTogTWF0aC5yb3VuZChwLnkpIH07XG4gIH1cbiAgLyoqIEVsZW1lbnQgcGl4ZWwgcG9pbnQgLT4gZXhhY3QgaW1hZ2UgcG9pbnQsIGZvciBoaXQgdGVzdHMuICovXG4gIHByaXZhdGUgdG9Xb3JsZChwb3M6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSk6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSB7XG4gICAgcmV0dXJuIGVsZW1lbnRUb0ltYWdlKHRoaXMudmlld2VyLCBwb3MueCwgcG9zLnkpO1xuICB9XG4gIC8qKiBJbWFnZSBwb2ludCAtPiBlbGVtZW50IHB4LCBhcyB0aGUgc2hhcmVkIHJlZ2lvbiBnZW9tZXRyeSB3YW50cyBpdC4gKi9cbiAgcHJpdmF0ZSByZWFkb25seSB0b1NjcmVlbjogVG9TY3JlZW4gPSAoeCwgeSkgPT4ge1xuICAgIGNvbnN0IHEgPSB0aGlzLnRvUHgoeCwgeSk7XG4gICAgcmV0dXJuIFtxLngsIHEueV07XG4gIH07XG5cbiAgLy8g4pSA4pSAIHJlbmRlcmluZyDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIBcbiAgLyoqIEZvbGxvdyB0aGUgY3VycmVudCBpbWFnZeKGkmVsZW1lbnQgcHJvamVjdGlvbjogdGhlIHJlbmRlcmVyIHJld3JpdGVzIG9uZSB0cmFuc2Zvcm1cbiAgICogIGFuZCByZS1wb3NpdGlvbnMgaXRzIHNjcmVlbi1zcGFjZSBlbGVtZW50cywgb3IgZG9lcyBub3RoaW5nIHdoZW4gaXQgZGlkIG5vdCBtb3ZlLiAqL1xuICBwcml2YXRlIHVwZGF0ZUNhbWVyYSgpOiB2b2lkIHtcbiAgICB0aGlzLnJlbmRlcmVyLnNldENhbWVyYShhZmZpbmVGcm9tUHJvamVjdGlvbih0aGlzLnRvU2NyZWVuKSk7XG4gIH1cblxuICAvKiogUmVidWlsZCBldmVyeXRoaW5nOiB0aGUgcmVnaW9ucyAoaW4gaW1hZ2UgY29vcmRpbmF0ZXMpLCB0aGVpciBsYWJlbHMgYW5kIHRoZSBvdmVybGF5LiAqL1xuICByZWRyYXcoKTogdm9pZCB7XG4gICAgdGhpcy51cGRhdGVDYW1lcmEoKTtcbiAgICB0aGlzLnJlbmRlcmVyLnJlbmRlcih0aGlzLnN0b3JlLmdldFJlZ2lvbnMoKSwgdGhpcy5zZWxlY3RlZCk7XG4gICAgdGhpcy5yZW5kZXJPdmVybGF5KCk7XG4gIH1cblxuICAvKipcbiAgICogUmVidWlsZCB0aGUgc2NyZWVuLXNwYWNlIG92ZXJsYXkgb25seTogdGhlIHNlbGVjdGVkIHJlZ2lvbidzIGhhbmRsZXMsIHRoZSBydWJiZXIgYmFuZFxuICAgKiBhbmQgYW55IGluLXByb2dyZXNzIGRyYXdpbmcuIERyYXdpbmcgYW5kIG1hcnF1ZWUgZHJhZ3MgY2FsbCB0aGlzIHJhdGhlciB0aGFuXG4gICAqIHtAbGluayByZWRyYXd9LCBzbyB0aGUgcmVnaW9ucyBhcmUgbm90IHJlYnVpbHQgcGVyIHBvaW50ZXIgbW92ZS5cbiAgICovXG4gIHByaXZhdGUgcmVuZGVyT3ZlcmxheSgpOiB2b2lkIHtcbiAgICBjb25zdCBzaGFwZUNvbG9yID0gdGhpcy5zdG9yZS5nZXRTaGFwZUNvbG9yKCk7XG4gICAgdGhpcy5yZW5kZXJlci5yZW5kZXJPdmVybGF5KChsYXllcikgPT4ge1xuICAgICAgLy8gSGFuZGxlcyBvbiB0aGUgc2VsZWN0ZWQgcmVnaW9uLCBzbyB0aGUgdXNlciBjYW4gZ3JhYi9pbnNlcnQvZGVsZXRlXG4gICAgICAvLyB2ZXJ0aWNlcyDigJQgaW4gdGhlIHJlZ2lvbidzIG93biBjb2xvdXIsIHNvIHRoZXkgbWF0Y2ggdGhlIHNoYXBlLlxuICAgICAgY29uc3Qgc2VsID0gdGhpcy5zaG93c1NlbGVjdGVkVmVydGljZXMgPyB0aGlzLnNlbGVjdGVkUmVnaW9uSW5mbygpIDogbnVsbDtcbiAgICAgIGlmIChzZWwpIGRyYXdTZWxlY3Rpb25IYW5kbGVzKGxheWVyLCBzZWwucmVnaW9uLCBzZWwucmVnaW9uLmNvbG9yIHx8IHNoYXBlQ29sb3IpO1xuICAgICAgLy8gUnViYmVyLWJhbmQgKG1hcnF1ZWUpIHNlbGVjdGlvbiBwcmV2aWV3LlxuICAgICAgaWYgKHRoaXMubW9kZSA9PT0gJ3NlbGVjdCcgJiYgdGhpcy5iYW5kU3RhcnQgJiYgdGhpcy5iYW5kQ3VycmVudCkge1xuICAgICAgICBkcmF3U2VsZWN0aW9uQmFuZChsYXllciwgdGhpcy5iYW5kU3RhcnQsIHRoaXMuYmFuZEN1cnJlbnQpO1xuICAgICAgfVxuICAgICAgLy8gSW4tcHJvZ3Jlc3MgZHJhd2luZyBwcmV2aWV3LlxuICAgICAgaWYgKHRoaXMubW9kZSA9PT0gJ2RyYXdyZWN0JyAmJiB0aGlzLnJlY3RTdGFydCAmJiB0aGlzLnJlY3RDdXJyZW50KSB7XG4gICAgICAgIGRyYXdEcmFmdFJlY3QobGF5ZXIsIHRoaXMucmVjdFN0YXJ0LCB0aGlzLnJlY3RDdXJyZW50LCBzaGFwZUNvbG9yKTtcbiAgICAgIH1cbiAgICAgIGlmICgodGhpcy5tb2RlID09PSAnZHJhd2Nsb3NlZHBhdGgnIHx8IHRoaXMubW9kZSA9PT0gJ2RyYXdvcGVucGF0aCcpICYmIHRoaXMucG9seVBvaW50cy5sZW5ndGgpIHtcbiAgICAgICAgZHJhd0RyYWZ0UGF0aChsYXllciwgdGhpcy5wb2x5UG9pbnRzLCBzaGFwZUNvbG9yKTtcbiAgICAgIH1cbiAgICAgIC8vIENsaWNrLXRvLXBsYWNlIHBvbHlnb24gcHJldmlldzogdGhlIHBvbHlsaW5lIHNvIGZhciArIGEgbWFya2VyIG9uIHRoZVxuICAgICAgLy8gZmlyc3QgdmVydGV4IChjbGljayBpdCB0byBjbG9zZSkuXG4gICAgICBpZiAodGhpcy5tb2RlID09PSAnZHJhd3BvbHlnb24nICYmIHRoaXMucG9seVBvaW50cy5sZW5ndGgpIHtcbiAgICAgICAgZHJhd0RyYWZ0UGF0aChsYXllciwgdGhpcy5wb2x5UG9pbnRzLCBzaGFwZUNvbG9yKTtcbiAgICAgICAgdmVydGV4TWFya2VyKGxheWVyLCB0aGlzLnBvbHlQb2ludHNbMF0ueCwgdGhpcy5wb2x5UG9pbnRzWzBdLnksIHRydWUsIHNoYXBlQ29sb3IpO1xuICAgICAgfVxuICAgIH0pO1xuICB9XG5cbiAgLy8g4pSA4pSAIGludGVyYWN0aW9uIOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgFxuICBwcml2YXRlIGdldCBpc0ZyZWVoYW5kKCk6IGJvb2xlYW4ge1xuICAgIHJldHVybiB0aGlzLm1vZGUgPT09ICdkcmF3Y2xvc2VkcGF0aCcgfHwgdGhpcy5tb2RlID09PSAnZHJhd29wZW5wYXRoJztcbiAgfVxuXG4gIHByaXZhdGUgb25QcmVzcyhlOiBhbnkpOiB2b2lkIHtcbiAgICBpZiAodGhpcy5tb2RlID09PSAnZHJhd3JlY3QnKSB7XG4gICAgICB0aGlzLnJlY3RTdGFydCA9IHRoaXMudG9JbWFnZShlLnBvc2l0aW9uKTtcbiAgICAgIHRoaXMucmVjdEN1cnJlbnQgPSB0aGlzLnJlY3RTdGFydDtcbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgaWYgKHRoaXMuaXNGcmVlaGFuZCkge1xuICAgICAgLy8gRnJlZWhhbmQgZHJhdyAobWF0Y2hlcyBQbG90bHkgZHJhd2Nsb3NlZHBhdGgvZHJhd29wZW5wYXRoKTogcHJlc3MgdG9cbiAgICAgIC8vIHN0YXJ0LCBkcmFnIHRvIHRyYWNlLCByZWxlYXNlIHRvIGNvbW1pdC5cbiAgICAgIHRoaXMuZnJlZWhhbmREcmFnZ2luZyA9IHRydWU7XG4gICAgICB0aGlzLnBvbHlQb2ludHMgPSBbdGhpcy50b0ltYWdlKGUucG9zaXRpb24pXTtcbiAgICAgIHRoaXMubGFzdEZyZWVoYW5kUHggPSB7IHg6IGUucG9zaXRpb24ueCwgeTogZS5wb3NpdGlvbi55IH07XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGlmICh0aGlzLm1vZGUgPT09ICdtb3ZlJykge1xuICAgICAgLy8gV2hvbGUtcmVnaW9uIGRyYWcgKCdtb3ZlJyBtb2RlKTogcHJlc3MgaW5zaWRlIHRoZSBzZWxlY3RlZCByZWdpb25cbiAgICAgIC8vIHRvIHRyYW5zbGF0ZSBpdCwgaWdub3JpbmcgdmVydGljZXMvZWRnZXMuXG4gICAgICBjb25zdCBzZWwgPSB0aGlzLnNlbGVjdGVkUmVnaW9uSW5mbygpO1xuICAgICAgaWYgKHNlbCAmJiB0aGlzLmNvbnRhaW5zUG9pbnQoc2VsLnJlZ2lvbiwgZS5wb3NpdGlvbikpIHtcbiAgICAgICAgdGhpcy5zdGFydEVkaXQoJ2JvdW5kcycsICdtb3ZlJywgLTEsIHNlbC5yZWdpb24sIHRoaXMudG9JbWFnZShlLnBvc2l0aW9uKSk7XG4gICAgICB9XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGlmICh0aGlzLm1vZGUgPT09ICdzZWxlY3QnKSB7XG4gICAgICAvLyBBIGJlemllciBjb250cm9sIGhhbmRsZSB0YWtlcyB0b3AgcHJpb3JpdHkgKGl0IHNpdHMgb2ZmIHRoZSBhbmNob3IpLCB0aGVuXG4gICAgICAvLyBkcmFnZ2luZyBhIHNpbmdsZSBwb2x5Z29uIHZlcnRleCAob3ZlciBib2R5LW1vdmUvcmVzaXplKS5cbiAgICAgIGNvbnN0IGhpdCA9IHRoaXMuaGl0UG9seWdvbkhhbmRsZShlLnBvc2l0aW9uKTtcbiAgICAgIGlmIChoaXQpIHtcbiAgICAgICAgY29uc3QgcmVnaW9uID0gdGhpcy5zdG9yZS5nZXRSZWdpb25zKClbdGhpcy5zZWxlY3RlZFt0aGlzLnNlbGVjdGVkLmxlbmd0aCAtIDFdXTtcbiAgICAgICAgaWYgKGhpdC5raW5kID09PSAnYmV6aWVyJykge1xuICAgICAgICAgIHRoaXMuc3RhcnRFZGl0KCdoYW5kbGUnLCAnbW92ZScsIGhpdC5pbmRleCwgcmVnaW9uLCB0aGlzLnRvSW1hZ2UoZS5wb3NpdGlvbiksIGhpdC5zaWRlLCBoaXQucmluZyk7XG4gICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgdGhpcy5zdGFydEVkaXQoJ3ZlcnRleCcsICdtb3ZlJywgaGl0LmluZGV4LCByZWdpb24sIHRoaXMudG9JbWFnZShlLnBvc2l0aW9uKSwgJ291dCcsIGhpdC5yaW5nKTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm47XG4gICAgICB9XG4gICAgICAvLyBPdGhlcndpc2Ugc3RhcnQgYSBtb3ZlL3Jlc2l6ZSB3aGVuIHByZXNzaW5nIHRoZSBzZWxlY3RlZCByZWdpb24nc1xuICAgICAgLy8gYm9keS9oYW5kbGVzLlxuICAgICAgY29uc3QgZXogPSB0aGlzLmVkaXRab25lQXQoZS5wb3NpdGlvbik7XG4gICAgICBpZiAoZXopIHtcbiAgICAgICAgdGhpcy5zdGFydEVkaXQoJ2JvdW5kcycsIGV6LnpvbmUsIC0xLCB0aGlzLnN0b3JlLmdldFJlZ2lvbnMoKVtlei5pbmRleF0sIHRoaXMudG9JbWFnZShlLnBvc2l0aW9uKSk7XG4gICAgICAgIHJldHVybjtcbiAgICAgIH1cbiAgICAgIC8vIFByZXNzIG9uIGVtcHR5IHNwYWNlIC8gYSBub24tc2VsZWN0ZWQgcmVnaW9uOiBiZWdpbiBhIHJ1YmJlci1iYW5kXG4gICAgICAvLyBtdWx0aS1zZWxlY3QuIEEgcGxhaW4gY2xpY2sgKG5vIGRyYWcpIGZhbGxzIHRocm91Z2ggdG8gb25DbGljaywgd2hpY2hcbiAgICAgIC8vIHNpbmdsZS1zZWxlY3RzIG9yIGNsZWFycy5cbiAgICAgIHRoaXMuYmFuZFN0YXJ0ID0gdGhpcy50b0ltYWdlKGUucG9zaXRpb24pO1xuICAgICAgdGhpcy5iYW5kQ3VycmVudCA9IHRoaXMuYmFuZFN0YXJ0O1xuICAgICAgdGhpcy5iYW5kRHJhZ2dlZCA9IGZhbHNlO1xuICAgIH1cbiAgfVxuXG4gIC8qKiBCZWdpbiBhbiBlZGl0IGdlc3R1cmUgKG1vdmUvcmVzaXplIG9yIHNpbmdsZS12ZXJ0ZXggZHJhZykgYW5kIG9wZW4gYSBzdG9yZVxuICAgKiAgYmF0Y2ggc28gdGhlIGxpdmUgZHJhZyBlbWl0cyBvbmNlIG9uIHJlbGVhc2UuICovXG4gIHByaXZhdGUgc3RhcnRFZGl0KFxuICAgIGtpbmQ6ICdib3VuZHMnIHwgJ3ZlcnRleCcgfCAnaGFuZGxlJyxcbiAgICB6b25lOiBFZGl0Wm9uZSxcbiAgICB2ZXJ0ZXhJbmRleDogbnVtYmVyLFxuICAgIHJlZ2lvbjogUmVnaW9uLFxuICAgIHN0YXJ0SW1nOiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH0sXG4gICAgaGFuZGxlU2lkZTogJ2luJyB8ICdvdXQnID0gJ291dCcsXG4gICAgcmluZyA9IC0xLFxuICApOiB2b2lkIHtcbiAgICB0aGlzLmVkaXQgPSB7XG4gICAgICBraW5kLFxuICAgICAgem9uZSxcbiAgICAgIHZlcnRleEluZGV4LFxuICAgICAgcmluZyxcbiAgICAgIGhhbmRsZVNpZGUsXG4gICAgICBpZDogcmVnaW9uLmlkLFxuICAgICAgc3RhcnRJbWcsXG4gICAgICBvcmlnOiBraW5kID09PSAnYm91bmRzJyA/IHRoaXMuc25hcHNob3QocmVnaW9uKSA6IG51bGwsXG4gICAgfTtcbiAgICB0aGlzLmVkaXREcmFnZ2VkID0gZmFsc2U7XG4gICAgdGhpcy5zdG9yZS5iZWdpbkJhdGNoKCk7XG4gIH1cblxuICBwcml2YXRlIG9uRHJhZyhlOiBhbnkpOiB2b2lkIHtcbiAgICBpZiAodGhpcy5tb2RlID09PSAnZHJhd3JlY3QnICYmIHRoaXMucmVjdFN0YXJ0KSB7XG4gICAgICB0aGlzLnJlY3RDdXJyZW50ID0gdGhpcy50b0ltYWdlKGUucG9zaXRpb24pO1xuICAgICAgdGhpcy5yZW5kZXJPdmVybGF5KCk7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGlmICh0aGlzLmZyZWVoYW5kRHJhZ2dpbmcgJiYgdGhpcy5pc0ZyZWVoYW5kKSB7XG4gICAgICAvLyBUaGluIHRoZSBwYXRoOiBvbmx5IHNhbXBsZSBvbmNlIHRoZSBjdXJzb3IgaGFzIG1vdmVkIGEgZmV3IHNjcmVlbiBweC5cbiAgICAgIGNvbnN0IGxhc3QgPSB0aGlzLmxhc3RGcmVlaGFuZFB4O1xuICAgICAgaWYgKCFsYXN0IHx8IE1hdGguaHlwb3QoZS5wb3NpdGlvbi54IC0gbGFzdC54LCBlLnBvc2l0aW9uLnkgLSBsYXN0LnkpID49IDQpIHtcbiAgICAgICAgdGhpcy5wb2x5UG9pbnRzLnB1c2godGhpcy50b0ltYWdlKGUucG9zaXRpb24pKTtcbiAgICAgICAgdGhpcy5sYXN0RnJlZWhhbmRQeCA9IHsgeDogZS5wb3NpdGlvbi54LCB5OiBlLnBvc2l0aW9uLnkgfTtcbiAgICAgICAgdGhpcy5yZW5kZXJPdmVybGF5KCk7XG4gICAgICB9XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGlmICh0aGlzLmVkaXQpIHtcbiAgICAgIHRoaXMuZWRpdERyYWdnZWQgPSB0cnVlO1xuICAgICAgdGhpcy5hcHBseUVkaXQodGhpcy50b0ltYWdlKGUucG9zaXRpb24pKTtcbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgaWYgKHRoaXMuYmFuZFN0YXJ0KSB7XG4gICAgICB0aGlzLmJhbmRDdXJyZW50ID0gdGhpcy50b0ltYWdlKGUucG9zaXRpb24pO1xuICAgICAgdGhpcy5iYW5kRHJhZ2dlZCA9IHRydWU7XG4gICAgICB0aGlzLnJlbmRlck92ZXJsYXkoKTtcbiAgICB9XG4gIH1cblxuICBwcml2YXRlIG9uUmVsZWFzZShlOiBhbnkpOiB2b2lkIHtcbiAgICBpZiAodGhpcy5tb2RlID09PSAnZHJhd3JlY3QnICYmIHRoaXMucmVjdFN0YXJ0KSB7XG4gICAgICBjb25zdCBlbmQgPSB0aGlzLnRvSW1hZ2UoZS5wb3NpdGlvbik7XG4gICAgICBjb25zdCB4ID0gTWF0aC5taW4odGhpcy5yZWN0U3RhcnQueCwgZW5kLngpO1xuICAgICAgY29uc3QgeSA9IE1hdGgubWluKHRoaXMucmVjdFN0YXJ0LnksIGVuZC55KTtcbiAgICAgIGNvbnN0IHcgPSBNYXRoLmFicyhlbmQueCAtIHRoaXMucmVjdFN0YXJ0LngpO1xuICAgICAgY29uc3QgaCA9IE1hdGguYWJzKGVuZC55IC0gdGhpcy5yZWN0U3RhcnQueSk7XG4gICAgICB0aGlzLnJlY3RTdGFydCA9IHRoaXMucmVjdEN1cnJlbnQgPSBudWxsO1xuICAgICAgaWYgKHcgPiAyICYmIGggPiAyKSB0aGlzLmNvbW1pdFJlY3RhbmdsZSh4LCB5LCB3LCBoKTtcbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgaWYgKHRoaXMuZnJlZWhhbmREcmFnZ2luZykge1xuICAgICAgdGhpcy5mcmVlaGFuZERyYWdnaW5nID0gZmFsc2U7XG4gICAgICB0aGlzLmxhc3RGcmVlaGFuZFB4ID0gbnVsbDtcbiAgICAgIC8vIENsb3NlZCA9IGZyZWVmb3JtIChkcmF3Y2xvc2VkcGF0aCk7IG9wZW4gPSBwb2x5bGluZSAoZHJhd29wZW5wYXRoKS5cbiAgICAgIHRoaXMuY29tbWl0UG9seWdvbih0aGlzLm1vZGUgPT09ICdkcmF3Y2xvc2VkcGF0aCcpO1xuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICAvLyBNb3ZlL3Jlc2l6ZSBhbHJlYWR5IGFwcGxpZWQgbGl2ZTsgZmx1c2ggdGhlIGNvYWxlc2NlZCBlZGl0cyArIGVuZCB0aGVcbiAgICAvLyBnZXN0dXJlIChrZWVwIHNlbGVjdGlvbikuXG4gICAgaWYgKHRoaXMuZWRpdCkge1xuICAgICAgdGhpcy5zdG9yZS5lbmRCYXRjaCgpO1xuICAgICAgdGhpcy5lZGl0ID0gbnVsbDtcbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgLy8gRmluaXNoIGEgcnViYmVyLWJhbmQgc2VsZWN0aW9uOiBzZWxlY3QgZXZlcnkgcmVnaW9uIHRoZSBiYW5kIGludGVyc2VjdHMuXG4gICAgaWYgKHRoaXMuYmFuZFN0YXJ0KSB7XG4gICAgICBjb25zdCBzdGFydCA9IHRoaXMuYmFuZFN0YXJ0O1xuICAgICAgY29uc3QgZW5kID0gdGhpcy5iYW5kQ3VycmVudCA/PyBzdGFydDtcbiAgICAgIHRoaXMuYmFuZFN0YXJ0ID0gdGhpcy5iYW5kQ3VycmVudCA9IG51bGw7XG4gICAgICBjb25zdCB4MCA9IE1hdGgubWluKHN0YXJ0LngsIGVuZC54KSxcbiAgICAgICAgeTAgPSBNYXRoLm1pbihzdGFydC55LCBlbmQueSk7XG4gICAgICBjb25zdCB4MSA9IE1hdGgubWF4KHN0YXJ0LngsIGVuZC54KSxcbiAgICAgICAgeTEgPSBNYXRoLm1heChzdGFydC55LCBlbmQueSk7XG4gICAgICAvLyBPbmx5IGEgcmVhbCBkcmFnIHNlbGVjdHM7IGEgY2xpY2stc2l6ZWQgYmFuZCBmYWxscyB0aHJvdWdoIHRvIG9uQ2xpY2suXG4gICAgICBpZiAodGhpcy5iYW5kRHJhZ2dlZCAmJiAoeDEgLSB4MCA+IDIgfHwgeTEgLSB5MCA+IDIpKSB7XG4gICAgICAgIHRoaXMuc3RvcmUuc2V0U2VsZWN0ZWRTaGFwZUluZGljZXMocmVnaW9uc0luUmVjdCh0aGlzLnN0b3JlLmdldFJlZ2lvbnMoKSwgeDAsIHkwLCB4MSwgeTEpKTtcbiAgICAgIH1cbiAgICAgIHRoaXMucmVuZGVyT3ZlcmxheSgpO1xuICAgIH1cbiAgfVxuXG4gIHByaXZhdGUgb25DbGljayhlOiBhbnkpOiB2b2lkIHtcbiAgICBpZiAodGhpcy5tb2RlID09PSAnc2VsZWN0Jykge1xuICAgICAgLy8gQSBtb3ZlL3Jlc2l6ZS92ZXJ0ZXggZHJhZyBvciBhIHJ1YmJlci1iYW5kIGRyYWcgYWxzbyBlbmRzIHdpdGggYSBjbGlja1xuICAgICAgLy8gZXZlbnQg4oCUIGRvbid0IHRyZWF0IGl0IGFzIGEgcmUtc2VsZWN0aW9uLlxuICAgICAgaWYgKHRoaXMuZWRpdERyYWdnZWQpIHtcbiAgICAgICAgdGhpcy5lZGl0RHJhZ2dlZCA9IGZhbHNlO1xuICAgICAgICByZXR1cm47XG4gICAgICB9XG4gICAgICBpZiAodGhpcy5iYW5kRHJhZ2dlZCkge1xuICAgICAgICB0aGlzLmJhbmREcmFnZ2VkID0gZmFsc2U7XG4gICAgICAgIHJldHVybjtcbiAgICAgIH1cbiAgICAgIC8vIFNoaWZ0IChvciBDbWQvQ3RybCkgdG9nZ2xlcyB0aGUgY2xpY2tlZCByZWdpb24gaW4vb3V0IG9mIHRoZSBjdXJyZW50XG4gICAgICAvLyBzZWxlY3Rpb247IGEgcGxhaW4gY2xpY2sgcmVwbGFjZXMgaXQuXG4gICAgICBjb25zdCBvZSA9IGUub3JpZ2luYWxFdmVudDtcbiAgICAgIGNvbnN0IGFkZGl0aXZlID0gISFvZSAmJiAob2Uuc2hpZnRLZXkgfHwgb2UubWV0YUtleSB8fCBvZS5jdHJsS2V5KTtcbiAgICAgIHRoaXMuc2VsZWN0QXQodGhpcy50b1dvcmxkKGUucG9zaXRpb24pLCBhZGRpdGl2ZSk7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGlmICh0aGlzLm1vZGUgPT09ICdkcmF3cG9seWdvbicpIHtcbiAgICAgIHRoaXMub25EcmF3UG9seWdvbkNsaWNrKGUpO1xuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICBpZiAodGhpcy5tb2RlID09PSAnYWRkcG9pbnQnKSB7XG4gICAgICAvLyBJbnNlcnQgYSB2ZXJ0ZXggb24gdGhlIGNsaWNrZWQgZWRnZSDigJQgZXh0ZXJpb3Igb3IgYW4gaW50ZXJpb3IgcmluZy5cbiAgICAgIGNvbnN0IHNlbCA9IHRoaXMuc2VsZWN0ZWRSZWdpb25JbmZvKCk7XG4gICAgICBjb25zdCBlZGdlID0gc2VsID8gdGhpcy5oaXRFZGdlKGUucG9zaXRpb24sIHNlbC5yZWdpb24pIDogbnVsbDtcbiAgICAgIGlmIChzZWwgJiYgZWRnZSkge1xuICAgICAgICBpZiAoZWRnZS5yaW5nIDwgMCkgdGhpcy5zdG9yZS5hZGRWZXJ0ZXgoc2VsLnJlZ2lvbi5pZCwgZWRnZS5zZWdJbmRleCwgZWRnZS54LCBlZGdlLnkpO1xuICAgICAgICBlbHNlIHRoaXMuc3RvcmUuYWRkSG9sZVZlcnRleChzZWwucmVnaW9uLmlkLCBlZGdlLnJpbmcsIGVkZ2Uuc2VnSW5kZXgsIGVkZ2UueCwgZWRnZS55KTtcbiAgICAgIH1cbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgaWYgKHRoaXMubW9kZSA9PT0gJ2RlbGV0ZXBvaW50Jykge1xuICAgICAgLy8gUmVtb3ZlIHRoZSBjbGlja2VkIHZlcnRleCDigJQgZXh0ZXJpb3Igb3IgYW4gaW50ZXJpb3IgcmluZyAoaml0LXVpIzg1KS5cbiAgICAgIGNvbnN0IHNlbCA9IHRoaXMuc2VsZWN0ZWRSZWdpb25JbmZvKCk7XG4gICAgICBjb25zdCB2aCA9IHRoaXMuaGl0UG9seWdvbkhhbmRsZShlLnBvc2l0aW9uLCBmYWxzZSk7XG4gICAgICBpZiAoc2VsICYmIHZoKSB7XG4gICAgICAgIGlmICh2aC5yaW5nIDwgMCkgdGhpcy5zdG9yZS5kZWxldGVWZXJ0ZXgoc2VsLnJlZ2lvbi5pZCwgdmguaW5kZXgpO1xuICAgICAgICBlbHNlIHRoaXMuc3RvcmUuZGVsZXRlSG9sZVZlcnRleChzZWwucmVnaW9uLmlkLCB2aC5yaW5nLCB2aC5pbmRleCk7XG4gICAgICB9XG4gICAgICByZXR1cm47XG4gICAgfVxuICB9XG5cbiAgLyoqXG4gICAqIENsaWNrLXRvLXBsYWNlIHBvbHlnb24gKCdkcmF3cG9seWdvbicpOiB0aGUgZmlyc3QgY2xpY2sgc3RhcnRzIHRoZVxuICAgKiBwb2x5Z29uLCBlYWNoIHN1YnNlcXVlbnQgY2xpY2sgYWRkcyBhIHZlcnRleCwgYW5kIGNsaWNraW5nIG5lYXIgdGhlIGZpcnN0XG4gICAqIHZlcnRleCAod2l0aCBhdCBsZWFzdCAzIHBsYWNlZCkgY2xvc2VzIGFuZCBjb21taXRzIGl0LlxuICAgKi9cbiAgcHJpdmF0ZSBvbkRyYXdQb2x5Z29uQ2xpY2soZTogYW55KTogdm9pZCB7XG4gICAgY29uc3QgcHQgPSB0aGlzLnRvSW1hZ2UoZS5wb3NpdGlvbik7XG4gICAgaWYgKCF0aGlzLmRyYXdpbmdQb2x5Z29uKSB7XG4gICAgICB0aGlzLnBvbHlQb2ludHMgPSBbcHRdO1xuICAgICAgdGhpcy5kcmF3aW5nUG9seWdvbiA9IHRydWU7XG4gICAgICB0aGlzLnJlbmRlck92ZXJsYXkoKTtcbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgY29uc3QgZmlyc3QgPSB0aGlzLnRvUHgodGhpcy5wb2x5UG9pbnRzWzBdLngsIHRoaXMucG9seVBvaW50c1swXS55KTtcbiAgICBjb25zdCBvbkZpcnN0ID0gTWF0aC5oeXBvdChlLnBvc2l0aW9uLnggLSBmaXJzdC54LCBlLnBvc2l0aW9uLnkgLSBmaXJzdC55KSA8PSBFRElUX1RPTF9QWDtcbiAgICBpZiAob25GaXJzdCAmJiB0aGlzLnBvbHlQb2ludHMubGVuZ3RoID49IDMpIHtcbiAgICAgIHRoaXMuY29tbWl0UG9seWdvbih0cnVlKTsgLy8gY2xvc2VzICsgcmVzZXRzIGluLXByb2dyZXNzIChpbmNsLiBkcmF3aW5nUG9seWdvbilcbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgdGhpcy5wb2x5UG9pbnRzLnB1c2gocHQpO1xuICAgIHRoaXMucmVuZGVyT3ZlcmxheSgpO1xuICB9XG5cbiAgLyoqXG4gICAqIEhvdmVyIGZlZWRiYWNrIGluIHNlbGVjdCBtb2RlOiBtb3ZlL3Jlc2l6ZSBjdXJzb3JzIG92ZXIgdGhlIHNlbGVjdGVkXG4gICAqIHJlZ2lvbidzIGJvZHkvZWRnZXMvY29ybmVycywgYSBwb2ludGVyIG92ZXIgYW55IG90aGVyIHJlZ2lvbi5cbiAgICovXG4gIHByaXZhdGUgb25Nb3ZlKGU6IGFueSk6IHZvaWQge1xuICAgIGlmICh0aGlzLm1vZGUgIT09ICdzZWxlY3QnKSByZXR1cm47XG4gICAgLy8gQSBncmFiYmFibGUgYmV6aWVyIGNvbnRyb2wgaGFuZGxlIG9yIHZlcnRleCBvZiB0aGUgc2VsZWN0ZWQgcG9seWdvbiB0YWtlc1xuICAgIC8vIHByaW9yaXR5LlxuICAgIGlmICh0aGlzLmhpdFBvbHlnb25IYW5kbGUoZS5wb3NpdGlvbikpIHtcbiAgICAgIHRoaXMudmlld2VyLmNhbnZhcy5zdHlsZS5jdXJzb3IgPSAncG9pbnRlcic7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGNvbnN0IGV6ID0gdGhpcy5lZGl0Wm9uZUF0KGUucG9zaXRpb24pO1xuICAgIGlmIChleikge1xuICAgICAgdGhpcy52aWV3ZXIuY2FudmFzLnN0eWxlLmN1cnNvciA9IFpPTkVfQ1VSU09SW2V6LnpvbmVdO1xuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICB0aGlzLnVwZGF0ZUN1cnNvcih0aGlzLnJlZ2lvbkluZGV4QXQodGhpcy50b1dvcmxkKGUucG9zaXRpb24pKSA+PSAwKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBUaGUgbW92ZS9yZXNpemUgem9uZSB1bmRlciB0aGUgY3Vyc29yIGZvciB0aGUgY3VycmVudGx5LXNlbGVjdGVkIHJlZ2lvblxuICAgKiAocmVjdGFuZ2xlcyBnZXQgZWRnZS9jb3JuZXIgaGFuZGxlcyArIGJvZHk7IHBvbHlnb25zIGdldCBib2R5LW1vdmUgb25seSksXG4gICAqIG9yIG51bGwgaWYgdGhlIGN1cnNvciBpc24ndCBvdmVyIHRoZSBzZWxlY3RlZCByZWdpb24uXG4gICAqL1xuICBwcml2YXRlIGVkaXRab25lQXQocG9zaXRpb246IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSk6IHsgem9uZTogRWRpdFpvbmU7IGluZGV4OiBudW1iZXIgfSB8IG51bGwge1xuICAgIGlmICh0aGlzLnNlbGVjdGVkLmxlbmd0aCA9PT0gMCkgcmV0dXJuIG51bGw7XG4gICAgY29uc3QgaW5kZXggPSB0aGlzLnNlbGVjdGVkW3RoaXMuc2VsZWN0ZWQubGVuZ3RoIC0gMV07XG4gICAgY29uc3QgcmVnaW9uID0gdGhpcy5zdG9yZS5nZXRSZWdpb25zKClbaW5kZXhdO1xuICAgIGlmICghcmVnaW9uKSByZXR1cm4gbnVsbDtcbiAgICBjb25zdCBiID0gcmVnaW9uLmJvdW5kcztcbiAgICBpZiAoYiBpbnN0YW5jZW9mIFJlY3RhbmdsZSkge1xuICAgICAgY29uc3QgYSA9IHRoaXMudG9QeChiLngsIGIueSk7XG4gICAgICBjb25zdCBjID0gdGhpcy50b1B4KGIueCArIGIud2lkdGgsIGIueSArIGIuaGVpZ2h0KTtcbiAgICAgIGNvbnN0IHpvbmUgPSByZWN0Wm9uZShwb3NpdGlvbi54LCBwb3NpdGlvbi55LCB7XG4gICAgICAgIHgwOiBNYXRoLm1pbihhLngsIGMueCksXG4gICAgICAgIHkwOiBNYXRoLm1pbihhLnksIGMueSksXG4gICAgICAgIHgxOiBNYXRoLm1heChhLngsIGMueCksXG4gICAgICAgIHkxOiBNYXRoLm1heChhLnksIGMueSksXG4gICAgICB9KTtcbiAgICAgIHJldHVybiB6b25lID8geyB6b25lLCBpbmRleCB9IDogbnVsbDtcbiAgICB9XG4gICAgaWYgKGIgaW5zdGFuY2VvZiBQb2x5Z29uIHx8IGIgaW5zdGFuY2VvZiBNdWx0aVBvbHlnb24pIHtcbiAgICAgIC8vIFBvbHlnb25zICsgbXVsdGktcGFydCByZWdpb25zIHN1cHBvcnQgd2hvbGUtcmVnaW9uIG1vdmUgKG5vIHJlc2l6ZSB6b25lcykuXG4gICAgICByZXR1cm4gdGhpcy5jb250YWluc1BvaW50KHJlZ2lvbiwgcG9zaXRpb24pID8geyB6b25lOiAnbW92ZScsIGluZGV4IH0gOiBudWxsO1xuICAgIH1cbiAgICByZXR1cm4gbnVsbDtcbiAgfVxuXG4gIC8qKiBUaGUgY3VycmVudGx5LXNlbGVjdGVkIHJlZ2lvbiAodGhlIGxhc3Qgb25lIHNlbGVjdGVkKSwgb3IgbnVsbC4gKi9cbiAgcHJpdmF0ZSBzZWxlY3RlZFJlZ2lvbkluZm8oKTogeyByZWdpb246IFJlZ2lvbjsgaW5kZXg6IG51bWJlciB9IHwgbnVsbCB7XG4gICAgaWYgKHRoaXMuc2VsZWN0ZWQubGVuZ3RoID09PSAwKSByZXR1cm4gbnVsbDtcbiAgICBjb25zdCBpbmRleCA9IHRoaXMuc2VsZWN0ZWRbdGhpcy5zZWxlY3RlZC5sZW5ndGggLSAxXTtcbiAgICBjb25zdCByZWdpb24gPSB0aGlzLnN0b3JlLmdldFJlZ2lvbnMoKVtpbmRleF07XG4gICAgcmV0dXJuIHJlZ2lvbiA/IHsgcmVnaW9uLCBpbmRleCB9IDogbnVsbDtcbiAgfVxuXG4gIC8qKiBUaGUgYmV6aWVyIGNvbnRyb2wgaGFuZGxlICh3aGVuIGBiZXppZXJgKSBvciB2ZXJ0ZXggb2YgdGhlIHNlbGVjdGVkIHBvbHlnb25cbiAgICogIHVuZGVyIHRoZSBjdXJzb3IgKHNjcmVlbi1waXhlbCB0b2xlcmFuY2UpLCBvciBudWxsLiBSZWN0YW5nbGVzIGhhdmUgbm9cbiAgICogIGVkaXRhYmxlIHZlcnRpY2VzICh0aGVpciBjb3JuZXJzIGFyZSByZXNpemUgem9uZXMsIHNlZSB7QGxpbmsgcmVjdFpvbmV9KS4gKi9cbiAgcHJpdmF0ZSBoaXRQb2x5Z29uSGFuZGxlKFxuICAgIHBvc2l0aW9uOiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH0sXG4gICAgYmV6aWVyID0gdHJ1ZSxcbiAgKTogeyBraW5kOiAndmVydGV4JyB8ICdiZXppZXInOyByaW5nOiBudW1iZXI7IGluZGV4OiBudW1iZXI7IHNpZGU6ICdpbicgfCAnb3V0JyB9IHwgbnVsbCB7XG4gICAgY29uc3Qgc2VsID0gdGhpcy5zZWxlY3RlZFJlZ2lvbkluZm8oKTtcbiAgICBpZiAoIXNlbCB8fCAhKHNlbC5yZWdpb24uYm91bmRzIGluc3RhbmNlb2YgUG9seWdvbikpIHJldHVybiBudWxsO1xuICAgIGNvbnN0IGhpdCA9IGhpdEhhbmRsZShzZWwucmVnaW9uLCBwb3NpdGlvbi54LCBwb3NpdGlvbi55LCB0aGlzLnRvU2NyZWVuLCBFRElUX1RPTF9QWCwgeyBiZXppZXIgfSk7XG4gICAgaWYgKCFoaXQgfHwgaGl0LmtpbmQgPT09ICdjb3JuZXInKSByZXR1cm4gbnVsbDtcbiAgICByZXR1cm4geyBraW5kOiBoaXQua2luZCwgcmluZzogaGl0LnJpbmcsIGluZGV4OiBoaXQuaW5kZXgsIHNpZGU6IGhpdC5raW5kID09PSAnYmV6aWVyJyA/IGhpdC5zaWRlIDogJ291dCcgfTtcbiAgfVxuXG4gIC8qKiBUaGUgZWRnZSBvZiBgcmVnaW9uYCdzIHBvbHlnb24gbmVhcmVzdCB0aGUgY3Vyc29yICh3aXRoaW4gdG9sZXJhbmNlKSwgd2l0aFxuICAgKiAgdGhlIGNsaWNrZWQgcG9pbnQgaW4gaW1hZ2UgY29vcmRzIGFzIHRoZSBpbnNlcnRpb24gcG9zaXRpb24sIG9yIG51bGwuICovXG4gIHByaXZhdGUgaGl0RWRnZShcbiAgICBwb3NpdGlvbjogeyB4OiBudW1iZXI7IHk6IG51bWJlciB9LFxuICAgIHJlZ2lvbjogUmVnaW9uLFxuICApOiB7IHJpbmc6IG51bWJlcjsgc2VnSW5kZXg6IG51bWJlcjsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSB8IG51bGwge1xuICAgIGNvbnN0IGVkZ2UgPSBuZWFyZXN0RWRnZShyZWdpb24sIHBvc2l0aW9uLngsIHBvc2l0aW9uLnksIHRoaXMudG9TY3JlZW4pO1xuICAgIGlmICghZWRnZSB8fCBlZGdlLmRpc3QgPiBFRElUX1RPTF9QWCkgcmV0dXJuIG51bGw7XG4gICAgY29uc3QgaW1nID0gdGhpcy50b0ltYWdlKHBvc2l0aW9uKTtcbiAgICByZXR1cm4geyByaW5nOiBlZGdlLnJpbmcsIHNlZ0luZGV4OiBlZGdlLnNlZ0luZGV4LCB4OiBpbWcueCwgeTogaW1nLnkgfTtcbiAgfVxuXG4gIC8qKiBTbmFwc2hvdCB0aGUgc2VsZWN0ZWQgcmVnaW9uJ3MgZ2VvbWV0cnkgYXQgdGhlIHN0YXJ0IG9mIGFuIGVkaXQuICovXG4gIHByaXZhdGUgc25hcHNob3QocmVnaW9uOiBSZWdpb24pOiBFZGl0U25hcHNob3Qge1xuICAgIGNvbnN0IGIgPSByZWdpb24uYm91bmRzO1xuICAgIGlmIChiIGluc3RhbmNlb2YgUG9seWdvbiB8fCBiIGluc3RhbmNlb2YgTXVsdGlQb2x5Z29uKSByZXR1cm4geyBraW5kOiAnc2hhcGUnLCBib3VuZHM6IGIgfTtcbiAgICBpZiAoYiBpbnN0YW5jZW9mIFJlY3RhbmdsZSkgcmV0dXJuIHsga2luZDogJ3JlY3QnLCB4OiBiLngsIHk6IGIueSwgdzogYi53aWR0aCwgaDogYi5oZWlnaHQgfTtcbiAgICByZXR1cm4geyBraW5kOiAncmVjdCcsIHg6IDAsIHk6IDAsIHc6IDAsIGg6IDAgfTtcbiAgfVxuXG4gIC8qKlxuICAgKiBBcHBseSB0aGUgaW4tcHJvZ3Jlc3MgbW92ZS9yZXNpemUgdG8gdGhlIHJlZ2lvbiwgbGl2ZSwgdGhyb3VnaCB0aGVcbiAgICogUmVnaW9uLW5hdGl2ZSBlZGl0IEFQSS4gUmVjb21wdXRlZCBhYnNvbHV0ZWx5IGZyb20gdGhlIGdlc3R1cmUtc3RhcnRcbiAgICogc25hcHNob3QgKGBvcmlnYCkgKyB0aGUgdG90YWwgZGVsdGEsIHNvIGVhY2ggZnJhbWUgaXMgaWRlbXBvdGVudC5cbiAgICovXG4gIHByaXZhdGUgYXBwbHlFZGl0KGN1ckltZzogeyB4OiBudW1iZXI7IHk6IG51bWJlciB9KTogdm9pZCB7XG4gICAgaWYgKCF0aGlzLmVkaXQpIHJldHVybjtcblxuICAgIGlmICh0aGlzLmVkaXQua2luZCA9PT0gJ3ZlcnRleCcpIHtcbiAgICAgIC8vIERyYWcgYSBzaW5nbGUgdmVydGV4IHRvIHRoZSBjdXJzb3IgKGFic29sdXRlIOKAlCBpZGVtcG90ZW50KS4gUm91dGUgdG8gdGhlXG4gICAgICAvLyBleHRlcmlvciBvciB0aGUgbWF0Y2hpbmcgaW50ZXJpb3IgcmluZyAoaG9sZSkg4oCUIGppdC11aSM4NS5cbiAgICAgIGlmICh0aGlzLmVkaXQucmluZyA8IDApIHtcbiAgICAgICAgdGhpcy5zdG9yZS5tb3ZlVmVydGV4KHRoaXMuZWRpdC5pZCwgdGhpcy5lZGl0LnZlcnRleEluZGV4LCBjdXJJbWcueCwgY3VySW1nLnkpO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgdGhpcy5zdG9yZS5tb3ZlSG9sZVZlcnRleCh0aGlzLmVkaXQuaWQsIHRoaXMuZWRpdC5yaW5nLCB0aGlzLmVkaXQudmVydGV4SW5kZXgsIGN1ckltZy54LCBjdXJJbWcueSk7XG4gICAgICB9XG4gICAgICB0aGlzLnJlZHJhdygpO1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGlmICh0aGlzLmVkaXQua2luZCA9PT0gJ2hhbmRsZScpIHtcbiAgICAgIC8vIERyYWcgYSBiZXppZXIgY29udHJvbCBoYW5kbGUgdG8gdGhlIGN1cnNvciDigJQgZXh0ZXJpb3IgKHJpbmcgLTEpIG9yIGEgZG9udXQgaG9sZSByaW5nLlxuICAgICAgaWYgKHRoaXMuZWRpdC5yaW5nIDwgMCkge1xuICAgICAgICB0aGlzLnN0b3JlLm1vdmVCZXppZXJIYW5kbGUodGhpcy5lZGl0LmlkLCB0aGlzLmVkaXQudmVydGV4SW5kZXgsIHRoaXMuZWRpdC5oYW5kbGVTaWRlLCBjdXJJbWcueCwgY3VySW1nLnkpO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgdGhpcy5zdG9yZS5tb3ZlSG9sZUJlemllckhhbmRsZShcbiAgICAgICAgICB0aGlzLmVkaXQuaWQsXG4gICAgICAgICAgdGhpcy5lZGl0LnJpbmcsXG4gICAgICAgICAgdGhpcy5lZGl0LnZlcnRleEluZGV4LFxuICAgICAgICAgIHRoaXMuZWRpdC5oYW5kbGVTaWRlLFxuICAgICAgICAgIGN1ckltZy54LFxuICAgICAgICAgIGN1ckltZy55LFxuICAgICAgICApO1xuICAgICAgfVxuICAgICAgdGhpcy5yZWRyYXcoKTtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBjb25zdCBkeCA9IGN1ckltZy54IC0gdGhpcy5lZGl0LnN0YXJ0SW1nLng7XG4gICAgY29uc3QgZHkgPSBjdXJJbWcueSAtIHRoaXMuZWRpdC5zdGFydEltZy55O1xuXG4gICAgY29uc3QgbyA9IHRoaXMuZWRpdC5vcmlnO1xuICAgIGlmICghbykgcmV0dXJuO1xuICAgIGlmIChvLmtpbmQgPT09ICdyZWN0Jykge1xuICAgICAgY29uc3QgYm94ID0gcmVzaXplUmVjdCh7IHg6IG8ueCwgeTogby55LCB3aWR0aDogby53LCBoZWlnaHQ6IG8uaCB9LCB0aGlzLmVkaXQuem9uZSwgZHgsIGR5KTtcbiAgICAgIHRoaXMuc3RvcmUudXBkYXRlQm91bmRzKHRoaXMuZWRpdC5pZCwgT2JqZWN0LmFzc2lnbihuZXcgUmVjdGFuZ2xlKCksIGJveCkpO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBQb2x5Z29uIC8gbXVsdGktcGFydCByZWdpb246IHRyYW5zbGF0ZSBldmVyeSB2ZXJ0ZXgsIGhvbGUgYW5kIHBhcnQsIHJvdW5kZWQgdG9cbiAgICAgIC8vIHdob2xlIHBpeGVscy4gQmV6aWVyIGhhbmRsZSBvZmZzZXRzIGFyZSByZWxhdGl2ZSwgc28gdGhleSBjYXJyeSBvdmVyIHVuY2hhbmdlZC5cbiAgICAgIHRoaXMuc3RvcmUudXBkYXRlQm91bmRzKHRoaXMuZWRpdC5pZCwgdHJhbnNsYXRlQm91bmRzKG8uYm91bmRzLCBkeCwgZHksIE1hdGgucm91bmQpKTtcbiAgICB9XG4gICAgdGhpcy5yZWRyYXcoKTtcbiAgfVxuXG4gIHByaXZhdGUgc2VsZWN0QXQocHQ6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSwgYWRkaXRpdmUgPSBmYWxzZSk6IHZvaWQge1xuICAgIGNvbnN0IGlkeCA9IHRoaXMucmVnaW9uSW5kZXhBdChwdCk7XG4gICAgaWYgKGFkZGl0aXZlKSB7XG4gICAgICAvLyBTaGlmdC1jbGljayBvbiBlbXB0eSBzcGFjZSBrZWVwcyB0aGUgY3VycmVudCBzZWxlY3Rpb24uXG4gICAgICBpZiAoaWR4IDwgMCkgcmV0dXJuO1xuICAgICAgLy8gYHRoaXMuc2VsZWN0ZWRgIG1pcnJvcnMgdGhlIHN0b3JlJ3MgY3VycmVudCBzZWxlY3Rpb24gKGtlcHQgaW4gc3luYyB2aWFcbiAgICAgIC8vIHRoZSBzdWJzY3JpcHRpb24pLCBzbyBpdCdzIHRoZSBzb3VyY2Ugb2YgdHJ1dGggd2l0aG91dCBhIHN5bmMgZ2V0dGVyLlxuICAgICAgY29uc3QgY3VyID0gdGhpcy5zZWxlY3RlZC5zbGljZSgpO1xuICAgICAgY29uc3QgYXQgPSBjdXIuaW5kZXhPZihpZHgpO1xuICAgICAgaWYgKGF0ID49IDApXG4gICAgICAgIGN1ci5zcGxpY2UoYXQsIDEpOyAvLyB0b2dnbGUgb2ZmXG4gICAgICBlbHNlIGN1ci5wdXNoKGlkeCk7IC8vIHRvZ2dsZSBvblxuICAgICAgdGhpcy5zdG9yZS5zZXRTZWxlY3RlZFNoYXBlSW5kaWNlcyhjdXIpO1xuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICB0aGlzLnN0b3JlLnNldFNlbGVjdGVkU2hhcGVJbmRpY2VzKGlkeCA+PSAwID8gW2lkeF0gOiBbXSk7XG4gIH1cblxuICAvKiogSW5kZXggb2YgdGhlIHRvcG1vc3QgcmVnaW9uIHVuZGVyIGFuIGltYWdlIHBvaW50LCBvciAtMS4gKi9cbiAgcHJpdmF0ZSByZWdpb25JbmRleEF0KHB0OiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH0pOiBudW1iZXIge1xuICAgIGNvbnN0IG9wdHMgPSB7IHRvU2NyZWVuOiB0aGlzLnRvU2NyZWVuLCB0b2xQeDogT1BFTl9QQVRIX1RPTF9QWCB9O1xuICAgIHJldHVybiB0b3Btb3N0UmVnaW9uQXQodGhpcy5zdG9yZS5nZXRSZWdpb25zKCksIHB0LngsIHB0LnksIG9wdHMpO1xuICB9XG5cbiAgLyoqIFdoZXRoZXIgdGhlIGVsZW1lbnQtcGl4ZWwgYHBvc2l0aW9uYCBsYW5kcyBvbiBgcmVnaW9uYCAoc2VlIGByZWdpb25Db250YWluc2ApLiAqL1xuICBwcml2YXRlIGNvbnRhaW5zUG9pbnQocmVnaW9uOiBSZWdpb24sIHBvc2l0aW9uOiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH0pOiBib29sZWFuIHtcbiAgICBjb25zdCBwdCA9IHRoaXMudG9Xb3JsZChwb3NpdGlvbik7XG4gICAgcmV0dXJuIHJlZ2lvbkNvbnRhaW5zKHJlZ2lvbiwgcHQueCwgcHQueSwgeyB0b1NjcmVlbjogdGhpcy50b1NjcmVlbiwgdG9sUHg6IE9QRU5fUEFUSF9UT0xfUFggfSk7XG4gIH1cblxuICAvKiogQWJhbmRvbiB3aGF0ZXZlciBwb2ludGVyIGdlc3R1cmUgaXMgaW4gcHJvZ3Jlc3MgKGRyYXdpbmcsIGVkaXQgZHJhZyxcbiAgICogIHJ1YmJlciBiYW5kKSBhbmQgY2xvc2UgaXRzIHN0b3JlIGJhdGNoLiAqL1xuICBwcml2YXRlIGVuZEdlc3R1cmUoKTogdm9pZCB7XG4gICAgdGhpcy5yZXNldEluUHJvZ3Jlc3MoKTtcbiAgICB0aGlzLmJhbmRTdGFydCA9IHRoaXMuYmFuZEN1cnJlbnQgPSBudWxsO1xuICAgIHRoaXMuYmFuZERyYWdnZWQgPSBmYWxzZTtcbiAgfVxuXG4gIHByaXZhdGUgcmVzZXRJblByb2dyZXNzKCk6IHZvaWQge1xuICAgIHRoaXMucmVjdFN0YXJ0ID0gdGhpcy5yZWN0Q3VycmVudCA9IG51bGw7XG4gICAgdGhpcy5wb2x5UG9pbnRzID0gW107XG4gICAgdGhpcy5mcmVlaGFuZERyYWdnaW5nID0gZmFsc2U7XG4gICAgdGhpcy5kcmF3aW5nUG9seWdvbiA9IGZhbHNlO1xuICAgIHRoaXMubGFzdEZyZWVoYW5kUHggPSBudWxsO1xuICAgIC8vIENsb3NlIGFueSBvcGVuIGVkaXQgYmF0Y2ggKGUuZy4gYSBtb2RlIHN3aXRjaCBtaWQtZHJhZykgc28gdGhlIHN0b3JlJ3NcbiAgICAvLyBlbWl0IGNvYWxlc2NpbmcgZG9lc24ndCBnZXQgc3R1Y2suXG4gICAgaWYgKHRoaXMuZWRpdCkge1xuICAgICAgdGhpcy5zdG9yZS5lbmRCYXRjaCgpO1xuICAgICAgdGhpcy5lZGl0ID0gbnVsbDtcbiAgICB9XG4gIH1cblxuICAvLyDilIDilIAgY29tbWl0IHRvIHRoZSBzdG9yZSDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIDilIBcbiAgcHJpdmF0ZSBjb21taXRSZWN0YW5nbGUoeDogbnVtYmVyLCB5OiBudW1iZXIsIHc6IG51bWJlciwgaDogbnVtYmVyKTogdm9pZCB7XG4gICAgY29uc3QgcmVnaW9uID0gbmV3IFJlZ2lvbigpO1xuICAgIGNvbnN0IHJlY3QgPSBuZXcgUmVjdGFuZ2xlKCk7XG4gICAgcmVjdC54ID0geDtcbiAgICByZWN0LnkgPSB5O1xuICAgIHJlY3Qud2lkdGggPSB3O1xuICAgIHJlY3QuaGVpZ2h0ID0gaDtcbiAgICByZWdpb24uYm91bmRzID0gcmVjdDtcbiAgICByZWdpb24uY29sb3IgPSB0aGlzLnN0b3JlLmdldFNoYXBlQ29sb3IoKTtcbiAgICB0aGlzLmNvbW1pdFJlZ2lvbihyZWdpb24pO1xuICB9XG5cbiAgcHJpdmF0ZSBjb21taXRQb2x5Z29uKGNsb3NlZDogYm9vbGVhbik6IHZvaWQge1xuICAgIGlmICh0aGlzLnBvbHlQb2ludHMubGVuZ3RoIDwgKGNsb3NlZCA/IDMgOiAyKSkge1xuICAgICAgdGhpcy5yZXNldEluUHJvZ3Jlc3MoKTtcbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgY29uc3QgcmVnaW9uID0gbmV3IFJlZ2lvbigpO1xuICAgIHJlZ2lvbi5ib3VuZHMgPSBtYWtlUG9seWdvbihcbiAgICAgIHRoaXMucG9seVBvaW50cy5tYXAoKHApID0+IHAueCksXG4gICAgICB0aGlzLnBvbHlQb2ludHMubWFwKChwKSA9PiBwLnkpLFxuICAgICAgeyBjbG9zZWQgfSxcbiAgICApO1xuICAgIHJlZ2lvbi5jb2xvciA9IHRoaXMuc3RvcmUuZ2V0U2hhcGVDb2xvcigpO1xuICAgIHRoaXMucmVzZXRJblByb2dyZXNzKCk7XG4gICAgdGhpcy5jb21taXRSZWdpb24ocmVnaW9uKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBBZGQgYSBmcmVzaGx5LWRyYXduIHJlZ2lvbiB0byB0aGUgc2hhcmVkIHN0b3JlIGFuZCByZWRyYXcgaW1tZWRpYXRlbHkuIFRoZVxuICAgKiBzdG9yZSBtaW50cyB0aGUgaWQsIHNlbGVjdHMgdGhlIG5ldyByZWdpb24gKHNvIGl0IHJlbmRlcnMgc29saWQvaGlnaGxpZ2h0ZWRcbiAgICogcmF0aGVyIHRoYW4gYXMgYSBkYXNoZWQgaW4tcHJvZ3Jlc3Mgc2hhcGUpIGFuZCBlbWl0cyB0aGUgZnVsbCByZWdpb24gbGlzdCB0b1xuICAgKiB0aGUgUmVnaW9uIEVkaXRvciDigJQgd2Ugc3RpbGwgcmVkcmF3IGxvY2FsbHkgcmF0aGVyIHRoYW4gcmVseWluZyBzb2xlbHkgb25cbiAgICogdGhlIHN0b3JlJ3MgdXBkYXRlIGV2ZW50LCB3aGljaCBjYW4gYmUgc3dhbGxvd2VkIHdoZW4gUGxvdGx5IGlzbid0IGFjdGl2ZS5cbiAgICovXG4gIHByaXZhdGUgY29tbWl0UmVnaW9uKHJlZ2lvbjogUmVnaW9uKTogdm9pZCB7XG4gICAgLy8gRGVmYXVsdCBjbGFzcy9hbm5vdGF0aW9uIG5hbWUsIG1hdGNoaW5nIHRoZSBQbG90bHkgYmFja2VuZCBhbmQgdGhlIFJlZ2lvblxuICAgIC8vIEVkaXRvcidzIFwiQWRkXCIgYWN0aW9ucyBzbyBhIGZyZXNobHkgZHJhd24gcmVnaW9uIGlzbid0IHVubGFiZWxlZC5cbiAgICBpZiAocmVnaW9uLmxhYmVsID09IG51bGwpIHJlZ2lvbi5sYWJlbCA9ICdSZWdpb24nO1xuICAgIHRoaXMuc3RvcmUuYWRkUmVnaW9uKHJlZ2lvbik7XG4gICAgdGhpcy5yZWRyYXcoKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBDb252ZXJ0IHRoZSBzZWxlY3RlZCByZWdpb24ocykgdG8vZnJvbSBhIGJlemllciBjdXJ2ZSAodG9CZXppZXIgPSB0cnVlIC9cbiAgICogdG9Qb2x5Z29uID0gZmFsc2UpLiBPbmUtc2hvdDsgdGhlIGFuY2hvcnMgYXJlIHVuY2hhbmdlZCxcbiAgICogb25seSB0aGUgc21vb3RoLWN1cnZlIHJlbmRlcmluZyBpcyB0b2dnbGVkLlxuICAgKi9cbiAgc2V0U2VsZWN0ZWRCZXppZXIoYmV6aWVyOiBib29sZWFuKTogdm9pZCB7XG4gICAgY29uc3QgcmVnaW9ucyA9IHRoaXMuc3RvcmUuZ2V0UmVnaW9ucygpO1xuICAgIGZvciAoY29uc3QgaWR4IG9mIHRoaXMuc2VsZWN0ZWQpIHtcbiAgICAgIGNvbnN0IHJlZ2lvbiA9IHJlZ2lvbnNbaWR4XTtcbiAgICAgIGlmIChyZWdpb24pIHRoaXMuc3RvcmUuc2V0QmV6aWVyKHJlZ2lvbi5pZCwgYmV6aWVyKTtcbiAgICB9XG4gICAgdGhpcy5yZWRyYXcoKTtcbiAgfVxufVxuIl19
|