@xiuchang-midscene/shared 2.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +9 -0
- package/dist/es/baseDB.mjs +109 -0
- package/dist/es/baseDB.mjs.bak +109 -0
- package/dist/es/build/copy-static.mjs +31 -0
- package/dist/es/build/copy-static.mjs.bak +31 -0
- package/dist/es/build/rspack-config.mjs +4 -0
- package/dist/es/build/rspack-config.mjs.bak +4 -0
- package/dist/es/cli/cli-runner.mjs +140 -0
- package/dist/es/cli/cli-runner.mjs.bak +140 -0
- package/dist/es/cli/index.mjs +2 -0
- package/dist/es/cli/index.mjs.bak +2 -0
- package/dist/es/common.mjs +37 -0
- package/dist/es/common.mjs.bak +37 -0
- package/dist/es/constants/example-code.mjs +223 -0
- package/dist/es/constants/example-code.mjs.bak +223 -0
- package/dist/es/constants/index.mjs +23 -0
- package/dist/es/constants/index.mjs.bak +23 -0
- package/dist/es/env/basic.mjs +6 -0
- package/dist/es/env/basic.mjs.bak +6 -0
- package/dist/es/env/constants.mjs +70 -0
- package/dist/es/env/constants.mjs.bak +70 -0
- package/dist/es/env/global-config-manager.mjs +94 -0
- package/dist/es/env/global-config-manager.mjs.bak +94 -0
- package/dist/es/env/helper.mjs +43 -0
- package/dist/es/env/helper.mjs.bak +43 -0
- package/dist/es/env/index.mjs +5 -0
- package/dist/es/env/index.mjs.bak +5 -0
- package/dist/es/env/init-debug.mjs +18 -0
- package/dist/es/env/init-debug.mjs.bak +18 -0
- package/dist/es/env/model-config-manager.mjs +79 -0
- package/dist/es/env/model-config-manager.mjs.bak +79 -0
- package/dist/es/env/parse-model-config.mjs +132 -0
- package/dist/es/env/parse-model-config.mjs.bak +132 -0
- package/dist/es/env/types.mjs +220 -0
- package/dist/es/env/types.mjs.bak +220 -0
- package/dist/es/env/utils.mjs +26 -0
- package/dist/es/env/utils.mjs.bak +26 -0
- package/dist/es/extractor/constants.mjs +2 -0
- package/dist/es/extractor/constants.mjs.bak +2 -0
- package/dist/es/extractor/debug.mjs +6 -0
- package/dist/es/extractor/debug.mjs.bak +6 -0
- package/dist/es/extractor/dom-util.mjs +92 -0
- package/dist/es/extractor/dom-util.mjs.bak +92 -0
- package/dist/es/extractor/index.mjs +5 -0
- package/dist/es/extractor/index.mjs.bak +5 -0
- package/dist/es/extractor/locator.mjs +250 -0
- package/dist/es/extractor/locator.mjs.bak +250 -0
- package/dist/es/extractor/tree.mjs +78 -0
- package/dist/es/extractor/tree.mjs.bak +78 -0
- package/dist/es/extractor/util.mjs +245 -0
- package/dist/es/extractor/util.mjs.bak +245 -0
- package/dist/es/extractor/web-extractor.mjs +303 -0
- package/dist/es/extractor/web-extractor.mjs.bak +303 -0
- package/dist/es/img/box-select.mjs +824 -0
- package/dist/es/img/box-select.mjs.bak +824 -0
- package/dist/es/img/canvas-fallback.mjs +238 -0
- package/dist/es/img/canvas-fallback.mjs.bak +238 -0
- package/dist/es/img/get-photon.mjs +45 -0
- package/dist/es/img/get-photon.mjs.bak +45 -0
- package/dist/es/img/get-sharp.mjs +11 -0
- package/dist/es/img/get-sharp.mjs.bak +11 -0
- package/dist/es/img/index.mjs +4 -0
- package/dist/es/img/index.mjs.bak +4 -0
- package/dist/es/img/info.mjs +29 -0
- package/dist/es/img/info.mjs.bak +29 -0
- package/dist/es/img/transform.mjs +295 -0
- package/dist/es/img/transform.mjs.bak +295 -0
- package/dist/es/index.mjs +4 -0
- package/dist/es/index.mjs.bak +4 -0
- package/dist/es/logger.mjs +64 -0
- package/dist/es/logger.mjs.bak +64 -0
- package/dist/es/mcp/base-server.mjs +281 -0
- package/dist/es/mcp/base-server.mjs.bak +281 -0
- package/dist/es/mcp/base-tools.mjs +91 -0
- package/dist/es/mcp/base-tools.mjs.bak +91 -0
- package/dist/es/mcp/chrome-path.mjs +35 -0
- package/dist/es/mcp/chrome-path.mjs.bak +35 -0
- package/dist/es/mcp/index.mjs +7 -0
- package/dist/es/mcp/index.mjs.bak +7 -0
- package/dist/es/mcp/inject-report-html-plugin.mjs +53 -0
- package/dist/es/mcp/inject-report-html-plugin.mjs.bak +53 -0
- package/dist/es/mcp/launcher-helper.mjs +52 -0
- package/dist/es/mcp/launcher-helper.mjs.bak +52 -0
- package/dist/es/mcp/tool-generator.mjs +297 -0
- package/dist/es/mcp/tool-generator.mjs.bak +297 -0
- package/dist/es/mcp/types.mjs +3 -0
- package/dist/es/mcp/types.mjs.bak +3 -0
- package/dist/es/node/fs.mjs +44 -0
- package/dist/es/node/fs.mjs.bak +44 -0
- package/dist/es/node/index.mjs +2 -0
- package/dist/es/node/index.mjs.bak +2 -0
- package/dist/es/node/port.mjs +24 -0
- package/dist/es/node/port.mjs.bak +24 -0
- package/dist/es/oss/demo.mjs +30 -0
- package/dist/es/oss/demo.mjs.bak +30 -0
- package/dist/es/oss/index.mjs +90 -0
- package/dist/es/oss/index.mjs.bak +90 -0
- package/dist/es/polyfills/async-hooks.mjs +2 -0
- package/dist/es/polyfills/async-hooks.mjs.bak +2 -0
- package/dist/es/polyfills/index.mjs +1 -0
- package/dist/es/polyfills/index.mjs.bak +1 -0
- package/dist/es/types/index.mjs +3 -0
- package/dist/es/types/index.mjs.bak +3 -0
- package/dist/es/us-keyboard-layout.mjs +1414 -0
- package/dist/es/us-keyboard-layout.mjs.LICENSE.txt +5 -0
- package/dist/es/us-keyboard-layout.mjs.bak +1414 -0
- package/dist/es/utils.mjs +72 -0
- package/dist/es/utils.mjs.bak +72 -0
- package/dist/es/zod-schema-utils.mjs +54 -0
- package/dist/es/zod-schema-utils.mjs.bak +54 -0
- package/dist/lib/baseDB.js +149 -0
- package/dist/lib/baseDB.js.bak +149 -0
- package/dist/lib/build/copy-static.js +79 -0
- package/dist/lib/build/copy-static.js.bak +79 -0
- package/dist/lib/build/rspack-config.js +38 -0
- package/dist/lib/build/rspack-config.js.bak +38 -0
- package/dist/lib/cli/cli-runner.js +196 -0
- package/dist/lib/cli/cli-runner.js.bak +196 -0
- package/dist/lib/cli/index.js +48 -0
- package/dist/lib/cli/index.js.bak +48 -0
- package/dist/lib/common.js +93 -0
- package/dist/lib/common.js.bak +93 -0
- package/dist/lib/constants/example-code.js +260 -0
- package/dist/lib/constants/example-code.js.bak +260 -0
- package/dist/lib/constants/index.js +96 -0
- package/dist/lib/constants/index.js.bak +96 -0
- package/dist/lib/env/basic.js +40 -0
- package/dist/lib/env/basic.js.bak +40 -0
- package/dist/lib/env/constants.js +113 -0
- package/dist/lib/env/constants.js.bak +113 -0
- package/dist/lib/env/global-config-manager.js +128 -0
- package/dist/lib/env/global-config-manager.js.bak +128 -0
- package/dist/lib/env/helper.js +80 -0
- package/dist/lib/env/helper.js.bak +80 -0
- package/dist/lib/env/index.js +90 -0
- package/dist/lib/env/index.js.bak +90 -0
- package/dist/lib/env/init-debug.js +52 -0
- package/dist/lib/env/init-debug.js.bak +52 -0
- package/dist/lib/env/model-config-manager.js +113 -0
- package/dist/lib/env/model-config-manager.js.bak +113 -0
- package/dist/lib/env/parse-model-config.js +178 -0
- package/dist/lib/env/parse-model-config.js.bak +178 -0
- package/dist/lib/env/types.js +554 -0
- package/dist/lib/env/types.js.bak +554 -0
- package/dist/lib/env/utils.js +72 -0
- package/dist/lib/env/utils.js.bak +72 -0
- package/dist/lib/extractor/constants.js +42 -0
- package/dist/lib/extractor/constants.js.bak +42 -0
- package/dist/lib/extractor/debug.js +12 -0
- package/dist/lib/extractor/debug.js.bak +12 -0
- package/dist/lib/extractor/dom-util.js +153 -0
- package/dist/lib/extractor/dom-util.js.bak +153 -0
- package/dist/lib/extractor/index.js +81 -0
- package/dist/lib/extractor/index.js.bak +81 -0
- package/dist/lib/extractor/locator.js +296 -0
- package/dist/lib/extractor/locator.js.bak +296 -0
- package/dist/lib/extractor/tree.js +124 -0
- package/dist/lib/extractor/tree.js.bak +124 -0
- package/dist/lib/extractor/util.js +336 -0
- package/dist/lib/extractor/util.js.bak +336 -0
- package/dist/lib/extractor/web-extractor.js +349 -0
- package/dist/lib/extractor/web-extractor.js.bak +349 -0
- package/dist/lib/img/box-select.js +875 -0
- package/dist/lib/img/box-select.js.bak +875 -0
- package/dist/lib/img/canvas-fallback.js +305 -0
- package/dist/lib/img/canvas-fallback.js.bak +305 -0
- package/dist/lib/img/get-photon.js +82 -0
- package/dist/lib/img/get-photon.js.bak +82 -0
- package/dist/lib/img/get-sharp.js +45 -0
- package/dist/lib/img/get-sharp.js.bak +45 -0
- package/dist/lib/img/index.js +95 -0
- package/dist/lib/img/index.js.bak +95 -0
- package/dist/lib/img/info.js +83 -0
- package/dist/lib/img/info.js.bak +83 -0
- package/dist/lib/img/transform.js +387 -0
- package/dist/lib/img/transform.js.bak +387 -0
- package/dist/lib/index.js +47 -0
- package/dist/lib/index.js.bak +47 -0
- package/dist/lib/logger.js +114 -0
- package/dist/lib/logger.js.bak +114 -0
- package/dist/lib/mcp/base-server.js +331 -0
- package/dist/lib/mcp/base-server.js.bak +331 -0
- package/dist/lib/mcp/base-tools.js +125 -0
- package/dist/lib/mcp/base-tools.js.bak +125 -0
- package/dist/lib/mcp/chrome-path.js +72 -0
- package/dist/lib/mcp/chrome-path.js.bak +72 -0
- package/dist/lib/mcp/index.js +100 -0
- package/dist/lib/mcp/index.js.bak +100 -0
- package/dist/lib/mcp/inject-report-html-plugin.js +98 -0
- package/dist/lib/mcp/inject-report-html-plugin.js.bak +98 -0
- package/dist/lib/mcp/launcher-helper.js +86 -0
- package/dist/lib/mcp/launcher-helper.js.bak +86 -0
- package/dist/lib/mcp/tool-generator.js +334 -0
- package/dist/lib/mcp/tool-generator.js.bak +334 -0
- package/dist/lib/mcp/types.js +40 -0
- package/dist/lib/mcp/types.js.bak +40 -0
- package/dist/lib/node/fs.js +97 -0
- package/dist/lib/node/fs.js.bak +97 -0
- package/dist/lib/node/index.js +65 -0
- package/dist/lib/node/index.js.bak +65 -0
- package/dist/lib/node/port.js +61 -0
- package/dist/lib/node/port.js.bak +61 -0
- package/dist/lib/oss/demo.js +36 -0
- package/dist/lib/oss/demo.js.bak +36 -0
- package/dist/lib/oss/index.js +138 -0
- package/dist/lib/oss/index.js.bak +138 -0
- package/dist/lib/polyfills/async-hooks.js +36 -0
- package/dist/lib/polyfills/async-hooks.js.bak +36 -0
- package/dist/lib/polyfills/index.js +58 -0
- package/dist/lib/polyfills/index.js.bak +58 -0
- package/dist/lib/types/index.js +37 -0
- package/dist/lib/types/index.js.bak +37 -0
- package/dist/lib/us-keyboard-layout.js +1457 -0
- package/dist/lib/us-keyboard-layout.js.LICENSE.txt +5 -0
- package/dist/lib/us-keyboard-layout.js.bak +1457 -0
- package/dist/lib/utils.js +148 -0
- package/dist/lib/utils.js.bak +148 -0
- package/dist/lib/zod-schema-utils.js +97 -0
- package/dist/lib/zod-schema-utils.js.bak +97 -0
- package/dist/types/baseDB.d.ts +25 -0
- package/dist/types/baseDB.d.ts.bak +25 -0
- package/dist/types/build/copy-static.d.ts +31 -0
- package/dist/types/build/copy-static.d.ts.bak +31 -0
- package/dist/types/build/rspack-config.d.ts +8 -0
- package/dist/types/build/rspack-config.d.ts.bak +8 -0
- package/dist/types/cli/cli-runner.d.ts +14 -0
- package/dist/types/cli/cli-runner.d.ts.bak +14 -0
- package/dist/types/cli/index.d.ts +2 -0
- package/dist/types/cli/index.d.ts.bak +2 -0
- package/dist/types/common.d.ts +12 -0
- package/dist/types/common.d.ts.bak +12 -0
- package/dist/types/constants/example-code.d.ts +2 -0
- package/dist/types/constants/example-code.d.ts.bak +2 -0
- package/dist/types/constants/index.d.ts +21 -0
- package/dist/types/constants/index.d.ts.bak +21 -0
- package/dist/types/env/basic.d.ts +6 -0
- package/dist/types/env/basic.d.ts.bak +6 -0
- package/dist/types/env/constants.d.ts +40 -0
- package/dist/types/env/constants.d.ts.bak +40 -0
- package/dist/types/env/global-config-manager.d.ts +32 -0
- package/dist/types/env/global-config-manager.d.ts.bak +32 -0
- package/dist/types/env/helper.d.ts +4 -0
- package/dist/types/env/helper.d.ts.bak +4 -0
- package/dist/types/env/index.d.ts +4 -0
- package/dist/types/env/index.d.ts.bak +4 -0
- package/dist/types/env/init-debug.d.ts +1 -0
- package/dist/types/env/init-debug.d.ts.bak +1 -0
- package/dist/types/env/model-config-manager.d.ts +25 -0
- package/dist/types/env/model-config-manager.d.ts.bak +25 -0
- package/dist/types/env/parse-model-config.d.ts +31 -0
- package/dist/types/env/parse-model-config.d.ts.bak +31 -0
- package/dist/types/env/types.d.ts +318 -0
- package/dist/types/env/types.d.ts.bak +318 -0
- package/dist/types/env/utils.d.ts +38 -0
- package/dist/types/env/utils.d.ts.bak +38 -0
- package/dist/types/extractor/constants.d.ts +1 -0
- package/dist/types/extractor/constants.d.ts.bak +1 -0
- package/dist/types/extractor/debug.d.ts +1 -0
- package/dist/types/extractor/debug.d.ts.bak +1 -0
- package/dist/types/extractor/dom-util.d.ts +56 -0
- package/dist/types/extractor/dom-util.d.ts.bak +56 -0
- package/dist/types/extractor/index.d.ts +32 -0
- package/dist/types/extractor/index.d.ts.bak +32 -0
- package/dist/types/extractor/locator.d.ts +9 -0
- package/dist/types/extractor/locator.d.ts.bak +9 -0
- package/dist/types/extractor/tree.d.ts +6 -0
- package/dist/types/extractor/tree.d.ts.bak +6 -0
- package/dist/types/extractor/util.d.ts +47 -0
- package/dist/types/extractor/util.d.ts.bak +47 -0
- package/dist/types/extractor/web-extractor.d.ts +19 -0
- package/dist/types/extractor/web-extractor.d.ts.bak +19 -0
- package/dist/types/img/box-select.d.ts +26 -0
- package/dist/types/img/box-select.d.ts.bak +26 -0
- package/dist/types/img/canvas-fallback.d.ts +105 -0
- package/dist/types/img/canvas-fallback.d.ts.bak +105 -0
- package/dist/types/img/get-photon.d.ts +19 -0
- package/dist/types/img/get-photon.d.ts.bak +19 -0
- package/dist/types/img/get-sharp.d.ts +3 -0
- package/dist/types/img/get-sharp.d.ts.bak +3 -0
- package/dist/types/img/index.d.ts +3 -0
- package/dist/types/img/index.d.ts.bak +3 -0
- package/dist/types/img/info.d.ts +29 -0
- package/dist/types/img/info.d.ts.bak +29 -0
- package/dist/types/img/transform.d.ts +107 -0
- package/dist/types/img/transform.d.ts.bak +107 -0
- package/dist/types/index.d.ts +4 -0
- package/dist/types/index.d.ts.bak +4 -0
- package/dist/types/logger.d.ts +5 -0
- package/dist/types/logger.d.ts.bak +5 -0
- package/dist/types/mcp/base-server.d.ts +93 -0
- package/dist/types/mcp/base-server.d.ts.bak +93 -0
- package/dist/types/mcp/base-tools.d.ts +79 -0
- package/dist/types/mcp/base-tools.d.ts.bak +79 -0
- package/dist/types/mcp/chrome-path.d.ts +2 -0
- package/dist/types/mcp/chrome-path.d.ts.bak +2 -0
- package/dist/types/mcp/index.d.ts +7 -0
- package/dist/types/mcp/index.d.ts.bak +7 -0
- package/dist/types/mcp/inject-report-html-plugin.d.ts +18 -0
- package/dist/types/mcp/inject-report-html-plugin.d.ts.bak +18 -0
- package/dist/types/mcp/launcher-helper.d.ts +94 -0
- package/dist/types/mcp/launcher-helper.d.ts.bak +94 -0
- package/dist/types/mcp/tool-generator.d.ts +10 -0
- package/dist/types/mcp/tool-generator.d.ts.bak +10 -0
- package/dist/types/mcp/types.d.ts +103 -0
- package/dist/types/mcp/types.d.ts.bak +103 -0
- package/dist/types/node/fs.d.ts +15 -0
- package/dist/types/node/fs.d.ts.bak +15 -0
- package/dist/types/node/index.d.ts +2 -0
- package/dist/types/node/index.d.ts.bak +2 -0
- package/dist/types/node/port.d.ts +8 -0
- package/dist/types/node/port.d.ts.bak +8 -0
- package/dist/types/oss/demo.d.ts +1 -0
- package/dist/types/oss/demo.d.ts.bak +1 -0
- package/dist/types/oss/index.d.ts +34 -0
- package/dist/types/oss/index.d.ts.bak +34 -0
- package/dist/types/polyfills/async-hooks.d.ts +6 -0
- package/dist/types/polyfills/async-hooks.d.ts.bak +6 -0
- package/dist/types/polyfills/index.d.ts +4 -0
- package/dist/types/polyfills/index.d.ts.bak +4 -0
- package/dist/types/types/index.d.ts +34 -0
- package/dist/types/types/index.d.ts.bak +34 -0
- package/dist/types/us-keyboard-layout.d.ts +32 -0
- package/dist/types/us-keyboard-layout.d.ts.bak +32 -0
- package/dist/types/utils.d.ts +34 -0
- package/dist/types/utils.d.ts.bak +34 -0
- package/dist/types/zod-schema-utils.d.ts +23 -0
- package/dist/types/zod-schema-utils.d.ts.bak +23 -0
- package/package.json +132 -0
- package/src/baseDB.ts +158 -0
- package/src/build/copy-static.ts +68 -0
- package/src/build/rspack-config.ts +12 -0
- package/src/cli/cli-runner.ts +224 -0
- package/src/cli/index.ts +8 -0
- package/src/common.ts +67 -0
- package/src/constants/example-code.ts +223 -0
- package/src/constants/index.ts +29 -0
- package/src/env/basic.ts +12 -0
- package/src/env/constants.ts +234 -0
- package/src/env/global-config-manager.ts +191 -0
- package/src/env/helper.ts +58 -0
- package/src/env/index.ts +4 -0
- package/src/env/init-debug.ts +34 -0
- package/src/env/model-config-manager.ts +149 -0
- package/src/env/parse-model-config.ts +294 -0
- package/src/env/types.ts +547 -0
- package/src/env/utils.ts +89 -0
- package/src/extractor/constants.ts +5 -0
- package/src/extractor/debug.ts +10 -0
- package/src/extractor/dom-util.ts +226 -0
- package/src/extractor/index.ts +48 -0
- package/src/extractor/locator.ts +469 -0
- package/src/extractor/tree.ts +179 -0
- package/src/extractor/util.ts +482 -0
- package/src/extractor/web-extractor.ts +481 -0
- package/src/img/box-select.ts +588 -0
- package/src/img/canvas-fallback.ts +393 -0
- package/src/img/get-photon.ts +108 -0
- package/src/img/get-sharp.ts +18 -0
- package/src/img/index.ts +26 -0
- package/src/img/info.ts +75 -0
- package/src/img/transform.ts +594 -0
- package/src/index.ts +8 -0
- package/src/logger.ts +96 -0
- package/src/mcp/base-server.ts +502 -0
- package/src/mcp/base-tools.ts +185 -0
- package/src/mcp/chrome-path.ts +48 -0
- package/src/mcp/index.ts +7 -0
- package/src/mcp/inject-report-html-plugin.ts +119 -0
- package/src/mcp/launcher-helper.ts +200 -0
- package/src/mcp/tool-generator.ts +429 -0
- package/src/mcp/types.ts +112 -0
- package/src/node/fs.ts +84 -0
- package/src/node/index.ts +2 -0
- package/src/node/port.ts +37 -0
- package/src/oss/demo.ts +61 -0
- package/src/oss/index.ts +187 -0
- package/src/polyfills/async-hooks.ts +6 -0
- package/src/polyfills/index.ts +4 -0
- package/src/types/index.ts +52 -0
- package/src/us-keyboard-layout.ts +723 -0
- package/src/utils.ts +149 -0
- package/src/zod-schema-utils.ts +133 -0
|
@@ -0,0 +1,482 @@
|
|
|
1
|
+
import type { Rect } from '../types';
|
|
2
|
+
import { generateHashId } from '../utils';
|
|
3
|
+
import { extractTextWithPosition } from './web-extractor';
|
|
4
|
+
|
|
5
|
+
const MAX_VALUE_LENGTH = 300;
|
|
6
|
+
|
|
7
|
+
let debugMode = false;
|
|
8
|
+
|
|
9
|
+
export function setDebugMode(mode: boolean) {
|
|
10
|
+
debugMode = mode;
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
export function getDebugMode(): boolean {
|
|
14
|
+
return debugMode;
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
export function logger(..._msg: any[]): void {
|
|
18
|
+
if (!debugMode) {
|
|
19
|
+
return;
|
|
20
|
+
}
|
|
21
|
+
console.log(..._msg);
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
export function isElementPartiallyInViewport(
|
|
25
|
+
rect: ReturnType<typeof getRect>,
|
|
26
|
+
currentWindow: typeof window,
|
|
27
|
+
currentDocument: typeof document,
|
|
28
|
+
visibleAreaRatio: number = 2 / 3,
|
|
29
|
+
) {
|
|
30
|
+
const elementHeight = rect.height;
|
|
31
|
+
const elementWidth = rect.width;
|
|
32
|
+
|
|
33
|
+
const viewportRect = {
|
|
34
|
+
left: 0,
|
|
35
|
+
top: 0,
|
|
36
|
+
width:
|
|
37
|
+
currentWindow.innerWidth || currentDocument.documentElement.clientWidth,
|
|
38
|
+
height:
|
|
39
|
+
currentWindow.innerHeight || currentDocument.documentElement.clientHeight,
|
|
40
|
+
right:
|
|
41
|
+
currentWindow.innerWidth || currentDocument.documentElement.clientWidth,
|
|
42
|
+
bottom:
|
|
43
|
+
currentWindow.innerHeight || currentDocument.documentElement.clientHeight,
|
|
44
|
+
x: 0,
|
|
45
|
+
y: 0,
|
|
46
|
+
zoom: 1,
|
|
47
|
+
};
|
|
48
|
+
|
|
49
|
+
const overlapRect = overlappedRect(rect, viewportRect);
|
|
50
|
+
if (!overlapRect) {
|
|
51
|
+
return false;
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
const visibleArea = overlapRect.width * overlapRect.height;
|
|
55
|
+
const totalArea = elementHeight * elementWidth;
|
|
56
|
+
// return visibleArea > 30 * 30 || visibleArea / totalArea >= 2 / 3;
|
|
57
|
+
return visibleArea / totalArea >= visibleAreaRatio;
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
export function getPseudoElementContent(
|
|
61
|
+
element: globalThis.Node,
|
|
62
|
+
currentWindow: typeof globalThis.window,
|
|
63
|
+
): {
|
|
64
|
+
before: string;
|
|
65
|
+
after: string;
|
|
66
|
+
} {
|
|
67
|
+
if (!(element instanceof currentWindow.HTMLElement)) {
|
|
68
|
+
return { before: '', after: '' };
|
|
69
|
+
}
|
|
70
|
+
const beforeContent = currentWindow
|
|
71
|
+
.getComputedStyle(element, '::before')
|
|
72
|
+
.getPropertyValue('content');
|
|
73
|
+
const afterContent = currentWindow
|
|
74
|
+
.getComputedStyle(element, '::after')
|
|
75
|
+
.getPropertyValue('content');
|
|
76
|
+
return {
|
|
77
|
+
before: beforeContent === 'none' ? '' : beforeContent.replace(/"/g, ''),
|
|
78
|
+
after: afterContent === 'none' ? '' : afterContent.replace(/"/g, ''),
|
|
79
|
+
};
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
export function hasOverflowY(
|
|
83
|
+
element: globalThis.HTMLElement,
|
|
84
|
+
currentWindow: typeof globalThis.window,
|
|
85
|
+
): boolean {
|
|
86
|
+
const style = currentWindow.getComputedStyle(element);
|
|
87
|
+
return (
|
|
88
|
+
style.overflowY === 'scroll' ||
|
|
89
|
+
style.overflowY === 'auto' ||
|
|
90
|
+
style.overflowY === 'hidden'
|
|
91
|
+
);
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
export interface ExtractedRect {
|
|
95
|
+
width: number;
|
|
96
|
+
height: number;
|
|
97
|
+
left: number;
|
|
98
|
+
top: number;
|
|
99
|
+
right: number;
|
|
100
|
+
bottom: number;
|
|
101
|
+
x: number;
|
|
102
|
+
y: number;
|
|
103
|
+
zoom: number;
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
// tell if two rects are overlapped, return the overlapped rect. If not, return null
|
|
107
|
+
export function overlappedRect(
|
|
108
|
+
rect1: ExtractedRect,
|
|
109
|
+
rect2: ExtractedRect,
|
|
110
|
+
): ExtractedRect | null {
|
|
111
|
+
const left = Math.max(rect1.left, rect2.left);
|
|
112
|
+
const top = Math.max(rect1.top, rect2.top);
|
|
113
|
+
const right = Math.min(rect1.right, rect2.right);
|
|
114
|
+
const bottom = Math.min(rect1.bottom, rect2.bottom);
|
|
115
|
+
if (left < right && top < bottom) {
|
|
116
|
+
return {
|
|
117
|
+
left,
|
|
118
|
+
top,
|
|
119
|
+
right,
|
|
120
|
+
bottom,
|
|
121
|
+
width: right - left,
|
|
122
|
+
height: bottom - top,
|
|
123
|
+
x: left,
|
|
124
|
+
y: top,
|
|
125
|
+
zoom: 1,
|
|
126
|
+
};
|
|
127
|
+
}
|
|
128
|
+
return null;
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
export function getRect(
|
|
132
|
+
el: globalThis.HTMLElement | globalThis.Node,
|
|
133
|
+
baseZoom: number, // base zoom
|
|
134
|
+
currentWindow: typeof globalThis.window,
|
|
135
|
+
): ExtractedRect {
|
|
136
|
+
let originalRect: DOMRect;
|
|
137
|
+
let newZoom = 1;
|
|
138
|
+
|
|
139
|
+
// Check if node is an Element (HTMLElement and SVGElement both have getBoundingClientRect)
|
|
140
|
+
const hasGetBoundingClientRect = el instanceof Element;
|
|
141
|
+
|
|
142
|
+
if (!hasGetBoundingClientRect) {
|
|
143
|
+
// For text nodes and other nodes without getBoundingClientRect, use Range API
|
|
144
|
+
const range = currentWindow.document.createRange();
|
|
145
|
+
range.selectNodeContents(el);
|
|
146
|
+
originalRect = range.getBoundingClientRect();
|
|
147
|
+
} else {
|
|
148
|
+
// For HTMLElement and SVGElement, use getBoundingClientRect directly
|
|
149
|
+
originalRect = (el as Element).getBoundingClientRect();
|
|
150
|
+
// from Chrome v128, the API would return differently https://docs.google.com/document/d/1AcnDShjT-kEuRaMchZPm5uaIgNZ4OiYtM4JI9qiV8Po/edit
|
|
151
|
+
if (el instanceof currentWindow.HTMLElement && !('currentCSSZoom' in el)) {
|
|
152
|
+
newZoom =
|
|
153
|
+
Number.parseFloat((currentWindow.getComputedStyle(el) as any).zoom) ||
|
|
154
|
+
1;
|
|
155
|
+
}
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
const zoom = newZoom * baseZoom;
|
|
159
|
+
|
|
160
|
+
return {
|
|
161
|
+
width: originalRect.width * zoom,
|
|
162
|
+
height: originalRect.height * zoom,
|
|
163
|
+
left: originalRect.left * zoom,
|
|
164
|
+
top: originalRect.top * zoom,
|
|
165
|
+
right: originalRect.right * zoom,
|
|
166
|
+
bottom: originalRect.bottom * zoom,
|
|
167
|
+
x: originalRect.x * zoom,
|
|
168
|
+
y: originalRect.y * zoom,
|
|
169
|
+
zoom,
|
|
170
|
+
};
|
|
171
|
+
}
|
|
172
|
+
|
|
173
|
+
const isElementCovered = (
|
|
174
|
+
el: globalThis.HTMLElement | globalThis.Node,
|
|
175
|
+
rect: ExtractedRect,
|
|
176
|
+
currentWindow: typeof globalThis.window,
|
|
177
|
+
) => {
|
|
178
|
+
// Gets the center coordinates of the element
|
|
179
|
+
const x = rect.left + rect.width / 2;
|
|
180
|
+
const y = rect.top + rect.height / 2;
|
|
181
|
+
|
|
182
|
+
// Gets the element above that point
|
|
183
|
+
const topElement = currentWindow.document.elementFromPoint(x, y);
|
|
184
|
+
if (!topElement) {
|
|
185
|
+
return false; // usually because it's outside the screen
|
|
186
|
+
}
|
|
187
|
+
|
|
188
|
+
if (topElement === el) {
|
|
189
|
+
return false;
|
|
190
|
+
}
|
|
191
|
+
if (el?.contains(topElement)) {
|
|
192
|
+
return false;
|
|
193
|
+
}
|
|
194
|
+
|
|
195
|
+
if ((topElement as HTMLElement)?.contains(el)) {
|
|
196
|
+
return false;
|
|
197
|
+
}
|
|
198
|
+
|
|
199
|
+
const rectOfTopElement = getRect(topElement as HTMLElement, 1, currentWindow);
|
|
200
|
+
|
|
201
|
+
// get the remaining area of the base element
|
|
202
|
+
const overlapRect = overlappedRect(rect, rectOfTopElement);
|
|
203
|
+
if (!overlapRect) {
|
|
204
|
+
return false;
|
|
205
|
+
}
|
|
206
|
+
|
|
207
|
+
// Todo: we should modify the 'box-select' as well to make the indicator more accurate
|
|
208
|
+
// const remainingArea =
|
|
209
|
+
// rect.width * rect.height - overlapRect.width * overlapRect.height;
|
|
210
|
+
|
|
211
|
+
// if (remainingArea > 100) {
|
|
212
|
+
// return false;
|
|
213
|
+
// }
|
|
214
|
+
|
|
215
|
+
logger(el, 'Element is covered by another element', {
|
|
216
|
+
topElement,
|
|
217
|
+
el,
|
|
218
|
+
rect,
|
|
219
|
+
x,
|
|
220
|
+
y,
|
|
221
|
+
});
|
|
222
|
+
return true;
|
|
223
|
+
// Determines if the returned element is the target element itself
|
|
224
|
+
// return el.contains(topElement) || (topElement as HTMLElement).contains(el);
|
|
225
|
+
// return topElement !== el && !el.contains(topElement);
|
|
226
|
+
};
|
|
227
|
+
|
|
228
|
+
export function elementRect(
|
|
229
|
+
el: globalThis.HTMLElement | globalThis.Node | null,
|
|
230
|
+
currentWindow: typeof globalThis.window,
|
|
231
|
+
currentDocument: typeof globalThis.document,
|
|
232
|
+
baseZoom = 1,
|
|
233
|
+
):
|
|
234
|
+
| {
|
|
235
|
+
left: number;
|
|
236
|
+
top: number;
|
|
237
|
+
width: number;
|
|
238
|
+
height: number;
|
|
239
|
+
zoom: number;
|
|
240
|
+
isVisible: boolean;
|
|
241
|
+
}
|
|
242
|
+
| false {
|
|
243
|
+
if (!el) {
|
|
244
|
+
logger(el, 'Element is not in the DOM hierarchy');
|
|
245
|
+
return false;
|
|
246
|
+
}
|
|
247
|
+
|
|
248
|
+
if (
|
|
249
|
+
!(el instanceof currentWindow.HTMLElement) &&
|
|
250
|
+
el.nodeType !== Node.TEXT_NODE &&
|
|
251
|
+
el.nodeName.toLowerCase() !== 'svg'
|
|
252
|
+
) {
|
|
253
|
+
logger(el, 'Element is not in the DOM hierarchy');
|
|
254
|
+
return false;
|
|
255
|
+
}
|
|
256
|
+
|
|
257
|
+
if (el instanceof currentWindow.HTMLElement) {
|
|
258
|
+
const style = currentWindow.getComputedStyle(el);
|
|
259
|
+
if (
|
|
260
|
+
style.display === 'none' ||
|
|
261
|
+
style.visibility === 'hidden' ||
|
|
262
|
+
(style.opacity === '0' && el.tagName !== 'INPUT')
|
|
263
|
+
) {
|
|
264
|
+
logger(el, 'Element is hidden');
|
|
265
|
+
return false;
|
|
266
|
+
}
|
|
267
|
+
}
|
|
268
|
+
|
|
269
|
+
const rect = getRect(el, baseZoom, currentWindow);
|
|
270
|
+
|
|
271
|
+
if (rect.width === 0 && rect.height === 0) {
|
|
272
|
+
logger(el, 'Element has no size');
|
|
273
|
+
return false;
|
|
274
|
+
}
|
|
275
|
+
|
|
276
|
+
// check if the element is covered by another element
|
|
277
|
+
// if the element is zoomed, the coverage check should be done with the original zoom
|
|
278
|
+
if (baseZoom === 1 && isElementCovered(el, rect, currentWindow)) {
|
|
279
|
+
return false;
|
|
280
|
+
}
|
|
281
|
+
|
|
282
|
+
const isVisible = isElementPartiallyInViewport(
|
|
283
|
+
rect,
|
|
284
|
+
currentWindow,
|
|
285
|
+
currentDocument,
|
|
286
|
+
);
|
|
287
|
+
|
|
288
|
+
// check if the element is hidden by an ancestor
|
|
289
|
+
let parent: HTMLElement | Node | null = el;
|
|
290
|
+
const parentUntilNonStatic = (currentNode: HTMLElement | Node | null) => {
|
|
291
|
+
// find a parent element that is not static
|
|
292
|
+
let parent = currentNode?.parentElement;
|
|
293
|
+
while (parent) {
|
|
294
|
+
const style = currentWindow.getComputedStyle(parent);
|
|
295
|
+
if (style.position !== 'static') {
|
|
296
|
+
return parent;
|
|
297
|
+
}
|
|
298
|
+
parent = parent.parentElement;
|
|
299
|
+
}
|
|
300
|
+
return null;
|
|
301
|
+
};
|
|
302
|
+
|
|
303
|
+
while (parent && parent !== currentDocument.body) {
|
|
304
|
+
if (!(parent instanceof currentWindow.HTMLElement)) {
|
|
305
|
+
parent = parent.parentElement;
|
|
306
|
+
continue;
|
|
307
|
+
}
|
|
308
|
+
const parentStyle = currentWindow.getComputedStyle(parent);
|
|
309
|
+
if (parentStyle.overflow === 'hidden') {
|
|
310
|
+
const parentRect = getRect(parent, 1, currentWindow);
|
|
311
|
+
const tolerance = 10;
|
|
312
|
+
|
|
313
|
+
if (
|
|
314
|
+
rect.right < parentRect.left - tolerance ||
|
|
315
|
+
rect.left > parentRect.right + tolerance ||
|
|
316
|
+
rect.bottom < parentRect.top - tolerance ||
|
|
317
|
+
rect.top > parentRect.bottom + tolerance
|
|
318
|
+
) {
|
|
319
|
+
logger(el, 'element is partially or totally hidden by an ancestor', {
|
|
320
|
+
rect,
|
|
321
|
+
parentRect,
|
|
322
|
+
});
|
|
323
|
+
return false;
|
|
324
|
+
}
|
|
325
|
+
}
|
|
326
|
+
// if the parent is a fixed element, stop the search
|
|
327
|
+
if (parentStyle.position === 'fixed' || parentStyle.position === 'sticky') {
|
|
328
|
+
break;
|
|
329
|
+
}
|
|
330
|
+
|
|
331
|
+
if (parentStyle.position === 'absolute') {
|
|
332
|
+
parent = parentUntilNonStatic(parent);
|
|
333
|
+
} else {
|
|
334
|
+
parent = parent.parentElement;
|
|
335
|
+
}
|
|
336
|
+
}
|
|
337
|
+
|
|
338
|
+
return {
|
|
339
|
+
left: Math.round(rect.left),
|
|
340
|
+
top: Math.round(rect.top),
|
|
341
|
+
width: Math.round(rect.width),
|
|
342
|
+
height: Math.round(rect.height),
|
|
343
|
+
zoom: rect.zoom,
|
|
344
|
+
isVisible,
|
|
345
|
+
};
|
|
346
|
+
}
|
|
347
|
+
|
|
348
|
+
export function validTextNodeContent(node: globalThis.Node): string | false {
|
|
349
|
+
if (!node) {
|
|
350
|
+
return false;
|
|
351
|
+
}
|
|
352
|
+
if (
|
|
353
|
+
node.nodeType !== Node.ELEMENT_NODE &&
|
|
354
|
+
node.nodeType !== Node.TEXT_NODE &&
|
|
355
|
+
(node as any).nodeName !== '#text'
|
|
356
|
+
) {
|
|
357
|
+
return false;
|
|
358
|
+
}
|
|
359
|
+
|
|
360
|
+
const content = node.textContent || (node as HTMLElement).innerText;
|
|
361
|
+
if (content && !/^\s*$/.test(content)) {
|
|
362
|
+
return content.trim();
|
|
363
|
+
}
|
|
364
|
+
|
|
365
|
+
return false;
|
|
366
|
+
}
|
|
367
|
+
|
|
368
|
+
export function getNodeAttributes(
|
|
369
|
+
node: globalThis.HTMLElement | globalThis.Node,
|
|
370
|
+
currentWindow: typeof globalThis.window,
|
|
371
|
+
): Record<string, string> {
|
|
372
|
+
if (
|
|
373
|
+
!node ||
|
|
374
|
+
!(node instanceof currentWindow.HTMLElement) ||
|
|
375
|
+
!node.attributes
|
|
376
|
+
) {
|
|
377
|
+
return {};
|
|
378
|
+
}
|
|
379
|
+
|
|
380
|
+
const attributesList = Array.from(node.attributes).map((attr) => {
|
|
381
|
+
if (attr.name === 'class') {
|
|
382
|
+
return [attr.name, `.${attr.value.split(' ').join('.')}`];
|
|
383
|
+
}
|
|
384
|
+
|
|
385
|
+
let value = attr.value;
|
|
386
|
+
if (value.startsWith('data:image')) {
|
|
387
|
+
value = 'image';
|
|
388
|
+
}
|
|
389
|
+
|
|
390
|
+
if (value.length > MAX_VALUE_LENGTH) {
|
|
391
|
+
value = `${value.slice(0, MAX_VALUE_LENGTH)}...`;
|
|
392
|
+
}
|
|
393
|
+
return [attr.name, value];
|
|
394
|
+
});
|
|
395
|
+
|
|
396
|
+
return Object.fromEntries(attributesList);
|
|
397
|
+
}
|
|
398
|
+
|
|
399
|
+
/** Maximum number of cached node entries to prevent memory leaks */
|
|
400
|
+
const NODE_CACHE_MAX_SIZE = 2000;
|
|
401
|
+
|
|
402
|
+
/**
|
|
403
|
+
* Reset the node hash cache. Call at the beginning of each extraction cycle
|
|
404
|
+
* to prevent stale DOM references from accumulating.
|
|
405
|
+
*/
|
|
406
|
+
export function setNodeHashCacheListOnWindow() {
|
|
407
|
+
if (typeof window !== 'undefined') {
|
|
408
|
+
(window as any).midsceneNodeHashCache = new Map<string, globalThis.Node>();
|
|
409
|
+
}
|
|
410
|
+
}
|
|
411
|
+
|
|
412
|
+
function getNodeCacheMap(): Map<string, globalThis.Node> | undefined {
|
|
413
|
+
if (typeof window === 'undefined') return undefined;
|
|
414
|
+
return (window as any).midsceneNodeHashCache as
|
|
415
|
+
| Map<string, globalThis.Node>
|
|
416
|
+
| undefined;
|
|
417
|
+
}
|
|
418
|
+
|
|
419
|
+
export function setNodeToCacheList(node: globalThis.Node, id: string): void {
|
|
420
|
+
const cache = getNodeCacheMap();
|
|
421
|
+
if (!cache) return;
|
|
422
|
+
if (cache.has(id)) return;
|
|
423
|
+
|
|
424
|
+
if (cache.size >= NODE_CACHE_MAX_SIZE) {
|
|
425
|
+
const firstKey = cache.keys().next().value;
|
|
426
|
+
if (firstKey !== undefined) cache.delete(firstKey);
|
|
427
|
+
}
|
|
428
|
+
cache.set(id, node);
|
|
429
|
+
}
|
|
430
|
+
|
|
431
|
+
export function getNodeFromCacheList(id: string): globalThis.Node | undefined {
|
|
432
|
+
return getNodeCacheMap()?.get(id);
|
|
433
|
+
}
|
|
434
|
+
|
|
435
|
+
export function midsceneGenerateHash(
|
|
436
|
+
node: globalThis.Node | null,
|
|
437
|
+
content: string,
|
|
438
|
+
rect: Rect,
|
|
439
|
+
): string {
|
|
440
|
+
const slicedHash = generateHashId(rect, content);
|
|
441
|
+
|
|
442
|
+
if (node) {
|
|
443
|
+
if (typeof window !== 'undefined' && !getNodeCacheMap()) {
|
|
444
|
+
setNodeHashCacheListOnWindow();
|
|
445
|
+
}
|
|
446
|
+
setNodeToCacheList(node, slicedHash);
|
|
447
|
+
}
|
|
448
|
+
|
|
449
|
+
return slicedHash;
|
|
450
|
+
}
|
|
451
|
+
|
|
452
|
+
export function generateId(numberId: number) {
|
|
453
|
+
// const letters = 'ABCDEFGHIJKLMNPRSTUVXYZ';
|
|
454
|
+
// const numbers = '0123456789';
|
|
455
|
+
// const randomLetter = letters.charAt(Math.floor(Math.random() * letters.length)).toUpperCase();
|
|
456
|
+
// const randomNumber = numbers.charAt(Math.floor(Math.random() * numbers.length));
|
|
457
|
+
// return randomLetter + numberId;
|
|
458
|
+
return `${numberId}`;
|
|
459
|
+
}
|
|
460
|
+
|
|
461
|
+
export function setGenerateHashOnWindow() {
|
|
462
|
+
if (typeof window !== 'undefined') {
|
|
463
|
+
(window as any).midsceneGenerateHash = midsceneGenerateHash;
|
|
464
|
+
}
|
|
465
|
+
}
|
|
466
|
+
|
|
467
|
+
export function setMidsceneVisibleRectOnWindow() {
|
|
468
|
+
if (typeof window !== 'undefined') {
|
|
469
|
+
(window as any).midsceneVisibleRect = elementRect;
|
|
470
|
+
}
|
|
471
|
+
}
|
|
472
|
+
|
|
473
|
+
export function setExtractTextWithPositionOnWindow() {
|
|
474
|
+
if (typeof window !== 'undefined') {
|
|
475
|
+
(window as any).extractTextWithPosition = extractTextWithPosition;
|
|
476
|
+
}
|
|
477
|
+
}
|
|
478
|
+
|
|
479
|
+
export function getTopDocument(): globalThis.HTMLElement {
|
|
480
|
+
const container: globalThis.HTMLElement = document.body || document;
|
|
481
|
+
return container;
|
|
482
|
+
}
|