feat: poll voting, location sharing, image captions, message forwarding
- Poll voting: PollContent sends m.poll.response on answer click - Location: MLocation shows OSM map embed + share-location button in toolbar - Image captions: caption field on media uploads sets message body - Message forwarding: ForwardMessageDialog with searchable room picker - Also includes ring timeout fix and earlier session patches
This commit is contained in:
+2
-1
@@ -13,5 +13,6 @@
|
|||||||
"hashRouter": {
|
"hashRouter": {
|
||||||
"enabled": false,
|
"enabled": false,
|
||||||
"basename": "/"
|
"basename": "/"
|
||||||
}
|
},
|
||||||
|
"gifApiKey": "AqqDuQwZNjYttz7Mn6ME4JH1bJIuZ5CO"
|
||||||
}
|
}
|
||||||
Generated
+469
-11
@@ -1,11 +1,11 @@
|
|||||||
{
|
{
|
||||||
"name": "cinny",
|
"name": "lotus-chat",
|
||||||
"version": "4.11.1",
|
"version": "4.11.1",
|
||||||
"lockfileVersion": 3,
|
"lockfileVersion": 3,
|
||||||
"requires": true,
|
"requires": true,
|
||||||
"packages": {
|
"packages": {
|
||||||
"": {
|
"": {
|
||||||
"name": "cinny",
|
"name": "lotus-chat",
|
||||||
"version": "4.11.1",
|
"version": "4.11.1",
|
||||||
"license": "AGPL-3.0-only",
|
"license": "AGPL-3.0-only",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
@@ -13,6 +13,9 @@
|
|||||||
"@atlaskit/pragmatic-drag-and-drop-auto-scroll": "1.3.0",
|
"@atlaskit/pragmatic-drag-and-drop-auto-scroll": "1.3.0",
|
||||||
"@atlaskit/pragmatic-drag-and-drop-hitbox": "1.0.3",
|
"@atlaskit/pragmatic-drag-and-drop-hitbox": "1.0.3",
|
||||||
"@fontsource/inter": "4.5.14",
|
"@fontsource/inter": "4.5.14",
|
||||||
|
"@giphy/js-fetch-api": "5.8.0",
|
||||||
|
"@giphy/js-types": "5.1.0",
|
||||||
|
"@giphy/react-components": "10.1.2",
|
||||||
"@tanstack/react-query": "5.24.1",
|
"@tanstack/react-query": "5.24.1",
|
||||||
"@tanstack/react-query-devtools": "5.24.1",
|
"@tanstack/react-query-devtools": "5.24.1",
|
||||||
"@tanstack/react-virtual": "3.2.0",
|
"@tanstack/react-virtual": "3.2.0",
|
||||||
@@ -63,10 +66,11 @@
|
|||||||
"slate-dom": "0.123.0",
|
"slate-dom": "0.123.0",
|
||||||
"slate-history": "0.113.1",
|
"slate-history": "0.113.1",
|
||||||
"slate-react": "0.123.0",
|
"slate-react": "0.123.0",
|
||||||
|
"styled-components": "6.4.1",
|
||||||
"ua-parser-js": "1.0.35"
|
"ua-parser-js": "1.0.35"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@element-hq/element-call-embedded": "0.16.3",
|
"@element-hq/element-call-embedded": "0.19.3",
|
||||||
"@esbuild-plugins/node-globals-polyfill": "0.2.3",
|
"@esbuild-plugins/node-globals-polyfill": "0.2.3",
|
||||||
"@rollup/plugin-inject": "5.0.3",
|
"@rollup/plugin-inject": "5.0.3",
|
||||||
"@rollup/plugin-wasm": "6.1.1",
|
"@rollup/plugin-wasm": "6.1.1",
|
||||||
@@ -1652,9 +1656,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/@element-hq/element-call-embedded": {
|
"node_modules/@element-hq/element-call-embedded": {
|
||||||
"version": "0.16.3",
|
"version": "0.19.3",
|
||||||
"resolved": "https://registry.npmjs.org/@element-hq/element-call-embedded/-/element-call-embedded-0.16.3.tgz",
|
"resolved": "https://registry.npmjs.org/@element-hq/element-call-embedded/-/element-call-embedded-0.19.3.tgz",
|
||||||
"integrity": "sha512-OViKJonDaDNVBUW9WdV9mk78/Ruh34C7XsEgt3O8D9z+64C39elbIgllHSoH5S12IRlv9RYrrV37FZLo6QWsDQ==",
|
"integrity": "sha512-ZwAK6PrMDiIFf3uDZuYpRR+Ho7OgfCSnENd9hxRH6LhWlRwuo42/4Nhn6wknqRjAeMJtJo/yFIn0Zh+jZ/Gf7Q==",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"node_modules/@emotion/hash": {
|
"node_modules/@emotion/hash": {
|
||||||
@@ -1662,6 +1666,21 @@
|
|||||||
"resolved": "https://registry.npmjs.org/@emotion/hash/-/hash-0.9.2.tgz",
|
"resolved": "https://registry.npmjs.org/@emotion/hash/-/hash-0.9.2.tgz",
|
||||||
"integrity": "sha512-MyqliTZGuOm3+5ZRSaaBGP3USLw6+EGykkwZns2EPC5g8jJ4z9OrdZY9apkl3+UP9+sdz76YYkwCKP5gh8iY3g=="
|
"integrity": "sha512-MyqliTZGuOm3+5ZRSaaBGP3USLw6+EGykkwZns2EPC5g8jJ4z9OrdZY9apkl3+UP9+sdz76YYkwCKP5gh8iY3g=="
|
||||||
},
|
},
|
||||||
|
"node_modules/@emotion/is-prop-valid": {
|
||||||
|
"version": "1.4.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/@emotion/is-prop-valid/-/is-prop-valid-1.4.0.tgz",
|
||||||
|
"integrity": "sha512-QgD4fyscGcbbKwJmqNvUMSE02OsHUa+lAWKdEUIJKgqe5IwRSKd7+KhibEWdaKwgjLj0DRSHA9biAIqGBk05lw==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"@emotion/memoize": "^0.9.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@emotion/memoize": {
|
||||||
|
"version": "0.9.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/@emotion/memoize/-/memoize-0.9.0.tgz",
|
||||||
|
"integrity": "sha512-30FAj7/EoJ5mwVPOWhAyCX+FPfMDrVecJAM+Iw9NRoSl4BBAQeqj4cApHHUXOVvIPgLVDsCFoz/hGD+5QQD1GQ==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
"node_modules/@esbuild-plugins/node-globals-polyfill": {
|
"node_modules/@esbuild-plugins/node-globals-polyfill": {
|
||||||
"version": "0.2.3",
|
"version": "0.2.3",
|
||||||
"resolved": "https://registry.npmjs.org/@esbuild-plugins/node-globals-polyfill/-/node-globals-polyfill-0.2.3.tgz",
|
"resolved": "https://registry.npmjs.org/@esbuild-plugins/node-globals-polyfill/-/node-globals-polyfill-0.2.3.tgz",
|
||||||
@@ -2117,6 +2136,84 @@
|
|||||||
"tslib": "2"
|
"tslib": "2"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/@giphy/colors": {
|
||||||
|
"version": "1.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/@giphy/colors/-/colors-1.0.1.tgz",
|
||||||
|
"integrity": "sha512-CMUY2UR8Ujl/wTRVjwu9spss6Cf2qkQNATKfoWCTWQp7CXdSfPWUDepp0c0/F0n7lYphLFvD9qzOC4NSdBt7nw==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
|
"node_modules/@giphy/js-analytics": {
|
||||||
|
"version": "5.0.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/@giphy/js-analytics/-/js-analytics-5.0.0.tgz",
|
||||||
|
"integrity": "sha512-jBZG6OqyMWB6meLi8Sz3iLplXYnhkbj+DJhS4ChmRX8Y6UA7i5dbbsUN/So1s7tTjhZOvu0rxA6rWJE73S1FvQ==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"@giphy/js-types": "*",
|
||||||
|
"@giphy/js-util": "*",
|
||||||
|
"append-query": "^2.1.0",
|
||||||
|
"throttle-debounce": "^3.0.1"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@giphy/js-fetch-api": {
|
||||||
|
"version": "5.8.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/@giphy/js-fetch-api/-/js-fetch-api-5.8.0.tgz",
|
||||||
|
"integrity": "sha512-DWdNauYaBSLPeAe/O+uzXtPIoUvmSnYV8Q49p+cPjEQ7Ncj1mDg1fuSKyl0OmPxCm6fzGJ4kuJjsWzyWn9ubbA==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"@giphy/js-types": "*",
|
||||||
|
"@giphy/js-util": "*"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@giphy/js-types": {
|
||||||
|
"version": "5.1.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/@giphy/js-types/-/js-types-5.1.0.tgz",
|
||||||
|
"integrity": "sha512-BZYCDtYNRR7cUWkbDLB4wmm3qmWMsVCQdUiBNOfmZ3yAazCgygKJoDI/5Rq4CK5MBaOc5LVdF8viC2WtoBdaPA==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
|
"node_modules/@giphy/js-util": {
|
||||||
|
"version": "5.2.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/@giphy/js-util/-/js-util-5.2.0.tgz",
|
||||||
|
"integrity": "sha512-Qt7pGh2cqiNmXLeWAgb459wK8+BuMLtIxTfg4ZksnPHPsLthiHT9hhzs2QhqUh7Pp/HOq+Cbv2etGDfnq+xiKA==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"@giphy/js-types": "*",
|
||||||
|
"uuid": "^9.0.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@giphy/js-util/node_modules/uuid": {
|
||||||
|
"version": "9.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/uuid/-/uuid-9.0.1.tgz",
|
||||||
|
"integrity": "sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==",
|
||||||
|
"deprecated": "uuid@10 and below is no longer supported. For ESM codebases, update to uuid@latest. For CommonJS codebases, use uuid@11 (but be aware this version will likely be deprecated in 2028).",
|
||||||
|
"funding": [
|
||||||
|
"https://github.com/sponsors/broofa",
|
||||||
|
"https://github.com/sponsors/ctavan"
|
||||||
|
],
|
||||||
|
"license": "MIT",
|
||||||
|
"bin": {
|
||||||
|
"uuid": "dist/bin/uuid"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@giphy/react-components": {
|
||||||
|
"version": "10.1.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/@giphy/react-components/-/react-components-10.1.2.tgz",
|
||||||
|
"integrity": "sha512-DVyIgf5az0uzHwnkS8tUaqO4qNx8DoxJupnRLhOl8M5CcvV9ykeZBLDxLj+jyDTySPYaIIJtrlR+8SeV2dHZwQ==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"@giphy/colors": "*",
|
||||||
|
"@giphy/js-analytics": "*",
|
||||||
|
"@giphy/js-fetch-api": "*",
|
||||||
|
"@giphy/js-types": "*",
|
||||||
|
"@giphy/js-util": "*",
|
||||||
|
"intersection-observer": "^0.12.2",
|
||||||
|
"react-use": "17.6.0",
|
||||||
|
"throttle-debounce": "^3.0.1"
|
||||||
|
},
|
||||||
|
"peerDependencies": {
|
||||||
|
"react": "18 - 19",
|
||||||
|
"styled-components": ">= 5"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/@humanwhocodes/config-array": {
|
"node_modules/@humanwhocodes/config-array": {
|
||||||
"version": "0.11.14",
|
"version": "0.11.14",
|
||||||
"resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.11.14.tgz",
|
"resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.11.14.tgz",
|
||||||
@@ -4582,6 +4679,12 @@
|
|||||||
"dev": true,
|
"dev": true,
|
||||||
"license": "MIT"
|
"license": "MIT"
|
||||||
},
|
},
|
||||||
|
"node_modules/@types/js-cookie": {
|
||||||
|
"version": "2.2.7",
|
||||||
|
"resolved": "https://registry.npmjs.org/@types/js-cookie/-/js-cookie-2.2.7.tgz",
|
||||||
|
"integrity": "sha512-aLkWa0C0vO5b4Sr798E26QgOkss68Un0bLjs7u9qxzPT5CG+8DuNTffWES58YzJs3hrVAOs1wonycqEBqNJubA==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
"node_modules/@types/json-schema": {
|
"node_modules/@types/json-schema": {
|
||||||
"version": "7.0.15",
|
"version": "7.0.15",
|
||||||
"resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz",
|
"resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz",
|
||||||
@@ -4999,6 +5102,12 @@
|
|||||||
"vite": "^4.2.0 || ^5.0.0"
|
"vite": "^4.2.0 || ^5.0.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/@xobotyi/scrollbar-width": {
|
||||||
|
"version": "1.9.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@xobotyi/scrollbar-width/-/scrollbar-width-1.9.5.tgz",
|
||||||
|
"integrity": "sha512-N8tkAACJx2ww8vFMneJmaAgmjAG1tnVBZJRLRcx061tmsLRZHSEZSLuGWnwPtunsSLvSqXQ2wfp7Mgqg1I+2dQ==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
"node_modules/abbrev": {
|
"node_modules/abbrev": {
|
||||||
"version": "1.1.1",
|
"version": "1.1.1",
|
||||||
"resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz",
|
"resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz",
|
||||||
@@ -5111,6 +5220,15 @@
|
|||||||
"url": "https://github.com/sponsors/jonschlinkert"
|
"url": "https://github.com/sponsors/jonschlinkert"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/append-query": {
|
||||||
|
"version": "2.1.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/append-query/-/append-query-2.1.1.tgz",
|
||||||
|
"integrity": "sha512-adm0E8o1o7ay+HbkWvGIpNNeciLB/rxJ0heThHuzSSVq5zcdQ5/ZubFnUoY0imFmk6gZVghSpwoubLVtwi9EHQ==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"extend": "^3.0.2"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/aproba": {
|
"node_modules/aproba": {
|
||||||
"version": "2.0.0",
|
"version": "2.0.0",
|
||||||
"resolved": "https://registry.npmjs.org/aproba/-/aproba-2.0.0.tgz",
|
"resolved": "https://registry.npmjs.org/aproba/-/aproba-2.0.0.tgz",
|
||||||
@@ -5616,6 +5734,15 @@
|
|||||||
"node": ">=6"
|
"node": ">=6"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/camelize": {
|
||||||
|
"version": "1.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/camelize/-/camelize-1.0.1.tgz",
|
||||||
|
"integrity": "sha512-dU+Tx2fsypxTgtLoE36npi3UqcjSSMNYfkqgmoEhtZrraP5VWq0K7FkWVTYa8eMPtnU/G2txVsfdCJTn9uzpuQ==",
|
||||||
|
"license": "MIT",
|
||||||
|
"funding": {
|
||||||
|
"url": "https://github.com/sponsors/ljharb"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/caniuse-lite": {
|
"node_modules/caniuse-lite": {
|
||||||
"version": "1.0.30001692",
|
"version": "1.0.30001692",
|
||||||
"resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001692.tgz",
|
"resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001692.tgz",
|
||||||
@@ -5825,6 +5952,15 @@
|
|||||||
"resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-2.0.0.tgz",
|
"resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-2.0.0.tgz",
|
||||||
"integrity": "sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg=="
|
"integrity": "sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg=="
|
||||||
},
|
},
|
||||||
|
"node_modules/copy-to-clipboard": {
|
||||||
|
"version": "3.3.3",
|
||||||
|
"resolved": "https://registry.npmjs.org/copy-to-clipboard/-/copy-to-clipboard-3.3.3.tgz",
|
||||||
|
"integrity": "sha512-2KV8NhB5JqC3ky0r9PMCAZKbUHSwtEo4CwCs0KXgruG43gX5PMqDEBbVU4OUzw2MuAWUfsuFmWvEKG5QRfSnJA==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"toggle-selection": "^1.0.6"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/core-js-compat": {
|
"node_modules/core-js-compat": {
|
||||||
"version": "3.40.0",
|
"version": "3.40.0",
|
||||||
"resolved": "https://registry.npmjs.org/core-js-compat/-/core-js-compat-3.40.0.tgz",
|
"resolved": "https://registry.npmjs.org/core-js-compat/-/core-js-compat-3.40.0.tgz",
|
||||||
@@ -5872,6 +6008,57 @@
|
|||||||
"node": ">=8"
|
"node": ">=8"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/css-color-keywords": {
|
||||||
|
"version": "1.0.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/css-color-keywords/-/css-color-keywords-1.0.0.tgz",
|
||||||
|
"integrity": "sha512-FyyrDHZKEjXDpNJYvVsV960FiqQyXc/LlYmsxl2BcdMb2WPx0OGRVgTg55rPSyLSNMqP52R9r8geSp7apN3Ofg==",
|
||||||
|
"license": "ISC",
|
||||||
|
"engines": {
|
||||||
|
"node": ">=4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/css-in-js-utils": {
|
||||||
|
"version": "3.1.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/css-in-js-utils/-/css-in-js-utils-3.1.0.tgz",
|
||||||
|
"integrity": "sha512-fJAcud6B3rRu+KHYk+Bwf+WFL2MDCJJ1XG9x137tJQ0xYxor7XziQtuGFbWNdqrvF4Tk26O3H73nfVqXt/fW1A==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"hyphenate-style-name": "^1.0.3"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/css-to-react-native": {
|
||||||
|
"version": "3.2.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/css-to-react-native/-/css-to-react-native-3.2.0.tgz",
|
||||||
|
"integrity": "sha512-e8RKaLXMOFii+02mOlqwjbD00KSEKqblnpO9e++1aXS1fPQOpS1YoqdVHBqPjHNoxeF2mimzVqawm2KCbEdtHQ==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"camelize": "^1.0.0",
|
||||||
|
"css-color-keywords": "^1.0.0",
|
||||||
|
"postcss-value-parser": "^4.0.2"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/css-tree": {
|
||||||
|
"version": "1.1.3",
|
||||||
|
"resolved": "https://registry.npmjs.org/css-tree/-/css-tree-1.1.3.tgz",
|
||||||
|
"integrity": "sha512-tRpdppF7TRazZrjJ6v3stzv93qxRcSsFmW6cX0Zm2NVKpxE1WV1HblnghVv9TreireHkqI/VDEsfolRF1p6y7Q==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"mdn-data": "2.0.14",
|
||||||
|
"source-map": "^0.6.1"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">=8.0.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/css-tree/node_modules/source-map": {
|
||||||
|
"version": "0.6.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz",
|
||||||
|
"integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==",
|
||||||
|
"license": "BSD-3-Clause",
|
||||||
|
"engines": {
|
||||||
|
"node": ">=0.10.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/css-what": {
|
"node_modules/css-what": {
|
||||||
"version": "5.1.0",
|
"version": "5.1.0",
|
||||||
"resolved": "https://registry.npmjs.org/css-what/-/css-what-5.1.0.tgz",
|
"resolved": "https://registry.npmjs.org/css-what/-/css-what-5.1.0.tgz",
|
||||||
@@ -5895,9 +6082,10 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/csstype": {
|
"node_modules/csstype": {
|
||||||
"version": "3.1.3",
|
"version": "3.2.3",
|
||||||
"resolved": "https://registry.npmjs.org/csstype/-/csstype-3.1.3.tgz",
|
"resolved": "https://registry.npmjs.org/csstype/-/csstype-3.2.3.tgz",
|
||||||
"integrity": "sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw=="
|
"integrity": "sha512-z1HGKcYy2xA8AGQfwrn0PAy+PB7X/GSj3UVJW9qKyn43xWa+gl5nXmU4qqLMRzWVLFC8KusUX8T/0kCiOYpAIQ==",
|
||||||
|
"license": "MIT"
|
||||||
},
|
},
|
||||||
"node_modules/damerau-levenshtein": {
|
"node_modules/damerau-levenshtein": {
|
||||||
"version": "1.0.8",
|
"version": "1.0.8",
|
||||||
@@ -6242,6 +6430,15 @@
|
|||||||
"url": "https://github.com/fb55/entities?sponsor=1"
|
"url": "https://github.com/fb55/entities?sponsor=1"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/error-stack-parser": {
|
||||||
|
"version": "2.1.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/error-stack-parser/-/error-stack-parser-2.1.4.tgz",
|
||||||
|
"integrity": "sha512-Sk5V6wVazPhq5MhpO+AUxJn5x7XSXGl1R93Vn7i+zS15KDVxQijejNCrz8340/2bgLBjR9GtEG8ZVKONDjcqGQ==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"stackframe": "^1.3.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/es-abstract": {
|
"node_modules/es-abstract": {
|
||||||
"version": "1.23.9",
|
"version": "1.23.9",
|
||||||
"resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.23.9.tgz",
|
"resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.23.9.tgz",
|
||||||
@@ -6964,11 +7161,16 @@
|
|||||||
"node": ">=0.8.x"
|
"node": ">=0.8.x"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/extend": {
|
||||||
|
"version": "3.0.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz",
|
||||||
|
"integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
"node_modules/fast-deep-equal": {
|
"node_modules/fast-deep-equal": {
|
||||||
"version": "3.1.3",
|
"version": "3.1.3",
|
||||||
"resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz",
|
"resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz",
|
||||||
"integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==",
|
"integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q=="
|
||||||
"dev": true
|
|
||||||
},
|
},
|
||||||
"node_modules/fast-glob": {
|
"node_modules/fast-glob": {
|
||||||
"version": "3.3.3",
|
"version": "3.3.3",
|
||||||
@@ -7010,6 +7212,11 @@
|
|||||||
"integrity": "sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==",
|
"integrity": "sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
|
"node_modules/fast-shallow-equal": {
|
||||||
|
"version": "1.0.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/fast-shallow-equal/-/fast-shallow-equal-1.0.0.tgz",
|
||||||
|
"integrity": "sha512-HPtaa38cPgWvaCFmRNhlc6NG7pv6NUHqjPgVAkWGoB9mQMwYB27/K0CvOM5Czy+qpT3e8XJ6Q4aPAnzpNpzNaw=="
|
||||||
|
},
|
||||||
"node_modules/fast-uri": {
|
"node_modules/fast-uri": {
|
||||||
"version": "3.0.5",
|
"version": "3.0.5",
|
||||||
"resolved": "https://registry.npmjs.org/fast-uri/-/fast-uri-3.0.5.tgz",
|
"resolved": "https://registry.npmjs.org/fast-uri/-/fast-uri-3.0.5.tgz",
|
||||||
@@ -7026,6 +7233,12 @@
|
|||||||
}
|
}
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
|
"node_modules/fastest-stable-stringify": {
|
||||||
|
"version": "2.0.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/fastest-stable-stringify/-/fastest-stable-stringify-2.0.2.tgz",
|
||||||
|
"integrity": "sha512-bijHueCGd0LqqNK9b5oCMHc0MluJAx0cwqASgbWMvkO01lCYgIhacVRLcaDz3QnyYIRNJRDwMb41VuT6pHJ91Q==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
"node_modules/fastq": {
|
"node_modules/fastq": {
|
||||||
"version": "1.18.0",
|
"version": "1.18.0",
|
||||||
"resolved": "https://registry.npmjs.org/fastq/-/fastq-1.18.0.tgz",
|
"resolved": "https://registry.npmjs.org/fastq/-/fastq-1.18.0.tgz",
|
||||||
@@ -7675,6 +7888,12 @@
|
|||||||
"node": ">= 6"
|
"node": ">= 6"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/hyphenate-style-name": {
|
||||||
|
"version": "1.1.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/hyphenate-style-name/-/hyphenate-style-name-1.1.0.tgz",
|
||||||
|
"integrity": "sha512-WDC/ui2VVRrz3jOVi+XtjqkDjiVjTtFaAGiW37k6b+ohyQ5wYDOGkvCZa8+H0nx3gyvv0+BST9xuOgIyGQ00gw==",
|
||||||
|
"license": "BSD-3-Clause"
|
||||||
|
},
|
||||||
"node_modules/i18next": {
|
"node_modules/i18next": {
|
||||||
"version": "23.12.2",
|
"version": "23.12.2",
|
||||||
"resolved": "https://registry.npmjs.org/i18next/-/i18next-23.12.2.tgz",
|
"resolved": "https://registry.npmjs.org/i18next/-/i18next-23.12.2.tgz",
|
||||||
@@ -7812,6 +8031,15 @@
|
|||||||
"resolved": "https://registry.npmjs.org/inline-style-parser/-/inline-style-parser-0.1.1.tgz",
|
"resolved": "https://registry.npmjs.org/inline-style-parser/-/inline-style-parser-0.1.1.tgz",
|
||||||
"integrity": "sha512-7NXolsK4CAS5+xvdj5OMMbI962hU/wvwoxk+LWR9Ek9bVtyuuYScDN6eS0rUm6TxApFpw7CX1o4uJzcd4AyD3Q=="
|
"integrity": "sha512-7NXolsK4CAS5+xvdj5OMMbI962hU/wvwoxk+LWR9Ek9bVtyuuYScDN6eS0rUm6TxApFpw7CX1o4uJzcd4AyD3Q=="
|
||||||
},
|
},
|
||||||
|
"node_modules/inline-style-prefixer": {
|
||||||
|
"version": "7.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/inline-style-prefixer/-/inline-style-prefixer-7.0.1.tgz",
|
||||||
|
"integrity": "sha512-lhYo5qNTQp3EvSSp3sRvXMbVQTLrvGV6DycRMJ5dm2BLMiJ30wpXKdDdgX+GmJZ5uQMucwRKHamXSst3Sj/Giw==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"css-in-js-utils": "^3.1.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/internal-slot": {
|
"node_modules/internal-slot": {
|
||||||
"version": "1.1.0",
|
"version": "1.1.0",
|
||||||
"resolved": "https://registry.npmjs.org/internal-slot/-/internal-slot-1.1.0.tgz",
|
"resolved": "https://registry.npmjs.org/internal-slot/-/internal-slot-1.1.0.tgz",
|
||||||
@@ -7826,6 +8054,13 @@
|
|||||||
"node": ">= 0.4"
|
"node": ">= 0.4"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/intersection-observer": {
|
||||||
|
"version": "0.12.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/intersection-observer/-/intersection-observer-0.12.2.tgz",
|
||||||
|
"integrity": "sha512-7m1vEcPCxXYI8HqnL8CKI6siDyD+eIWSwgB3DZA+ZTogxk9I4CDnj4wilt9x/+/QbHI4YG5YZNmC6458/e9Ktg==",
|
||||||
|
"deprecated": "The Intersection Observer polyfill is no longer needed and can safely be removed. Intersection Observer has been Baseline since 2019.",
|
||||||
|
"license": "Apache-2.0"
|
||||||
|
},
|
||||||
"node_modules/intl-messageformat": {
|
"node_modules/intl-messageformat": {
|
||||||
"version": "10.7.12",
|
"version": "10.7.12",
|
||||||
"resolved": "https://registry.npmjs.org/intl-messageformat/-/intl-messageformat-10.7.12.tgz",
|
"resolved": "https://registry.npmjs.org/intl-messageformat/-/intl-messageformat-10.7.12.tgz",
|
||||||
@@ -8324,6 +8559,12 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/js-cookie": {
|
||||||
|
"version": "2.2.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/js-cookie/-/js-cookie-2.2.1.tgz",
|
||||||
|
"integrity": "sha512-HvdH2LzI/EAZcUwA8+0nKNtWHqS+ZmijLA30RwZA0bo7ToCckjK5MkGhjED9KoRcXO6BaGI3I9UIzSA1FKFPOQ==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
"node_modules/js-sdsl": {
|
"node_modules/js-sdsl": {
|
||||||
"version": "4.4.2",
|
"version": "4.4.2",
|
||||||
"resolved": "https://registry.npmjs.org/js-sdsl/-/js-sdsl-4.4.2.tgz",
|
"resolved": "https://registry.npmjs.org/js-sdsl/-/js-sdsl-4.4.2.tgz",
|
||||||
@@ -8683,6 +8924,12 @@
|
|||||||
"events": "^3.2.0"
|
"events": "^3.2.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/mdn-data": {
|
||||||
|
"version": "2.0.14",
|
||||||
|
"resolved": "https://registry.npmjs.org/mdn-data/-/mdn-data-2.0.14.tgz",
|
||||||
|
"integrity": "sha512-dn6wd0uw5GsdswPFfsgMp5NSB0/aDe6fK94YJV/AJDYXL6HVLWBsxeq7js7Ad+mU2K9LAlwpk6kN2D5mwCPVow==",
|
||||||
|
"license": "CC0-1.0"
|
||||||
|
},
|
||||||
"node_modules/media-query-parser": {
|
"node_modules/media-query-parser": {
|
||||||
"version": "2.0.2",
|
"version": "2.0.2",
|
||||||
"resolved": "https://registry.npmjs.org/media-query-parser/-/media-query-parser-2.0.2.tgz",
|
"resolved": "https://registry.npmjs.org/media-query-parser/-/media-query-parser-2.0.2.tgz",
|
||||||
@@ -8848,6 +9095,26 @@
|
|||||||
"integrity": "sha512-nbajikzWTMwsW+eSsNm3QwlOs7het9gGJU5dDZzRTQGk03vyBOauxgI4VakDzE0PtsGTmXPsXTbbjVhRwR5mpw==",
|
"integrity": "sha512-nbajikzWTMwsW+eSsNm3QwlOs7het9gGJU5dDZzRTQGk03vyBOauxgI4VakDzE0PtsGTmXPsXTbbjVhRwR5mpw==",
|
||||||
"optional": true
|
"optional": true
|
||||||
},
|
},
|
||||||
|
"node_modules/nano-css": {
|
||||||
|
"version": "5.6.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/nano-css/-/nano-css-5.6.2.tgz",
|
||||||
|
"integrity": "sha512-+6bHaC8dSDGALM1HJjOHVXpuastdu2xFoZlC77Jh4cg+33Zcgm+Gxd+1xsnpZK14eyHObSp82+ll5y3SX75liw==",
|
||||||
|
"license": "Unlicense",
|
||||||
|
"dependencies": {
|
||||||
|
"@jridgewell/sourcemap-codec": "^1.4.15",
|
||||||
|
"css-tree": "^1.1.2",
|
||||||
|
"csstype": "^3.1.2",
|
||||||
|
"fastest-stable-stringify": "^2.0.2",
|
||||||
|
"inline-style-prefixer": "^7.0.1",
|
||||||
|
"rtl-css-js": "^1.16.1",
|
||||||
|
"stacktrace-js": "^2.0.2",
|
||||||
|
"stylis": "^4.3.0"
|
||||||
|
},
|
||||||
|
"peerDependencies": {
|
||||||
|
"react": "*",
|
||||||
|
"react-dom": "*"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/nanoid": {
|
"node_modules/nanoid": {
|
||||||
"version": "3.3.8",
|
"version": "3.3.8",
|
||||||
"resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.8.tgz",
|
"resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.8.tgz",
|
||||||
@@ -9344,6 +9611,12 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/postcss-value-parser": {
|
||||||
|
"version": "4.2.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/postcss-value-parser/-/postcss-value-parser-4.2.0.tgz",
|
||||||
|
"integrity": "sha512-1NNCs6uurfkVbeXG4S8JFT9t19m45ICnif8zWLd5oPSZ50QnwMfK+H3jv408d4jw/7Bttv5axS5IiHoLaVNHeQ==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
"node_modules/prelude-ls": {
|
"node_modules/prelude-ls": {
|
||||||
"version": "1.2.1",
|
"version": "1.2.1",
|
||||||
"resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz",
|
"resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz",
|
||||||
@@ -9647,6 +9920,41 @@
|
|||||||
"react-dom": ">=16.8"
|
"react-dom": ">=16.8"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/react-universal-interface": {
|
||||||
|
"version": "0.6.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/react-universal-interface/-/react-universal-interface-0.6.2.tgz",
|
||||||
|
"integrity": "sha512-dg8yXdcQmvgR13RIlZbTRQOoUrDciFVoSBZILwjE2LFISxZZ8loVJKAkuzswl5js8BHda79bIb2b84ehU8IjXw==",
|
||||||
|
"peerDependencies": {
|
||||||
|
"react": "*",
|
||||||
|
"tslib": "*"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/react-use": {
|
||||||
|
"version": "17.6.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/react-use/-/react-use-17.6.0.tgz",
|
||||||
|
"integrity": "sha512-OmedEScUMKFfzn1Ir8dBxiLLSOzhKe/dPZwVxcujweSj45aNM7BEGPb9BEVIgVEqEXx6f3/TsXzwIktNgUR02g==",
|
||||||
|
"license": "Unlicense",
|
||||||
|
"dependencies": {
|
||||||
|
"@types/js-cookie": "^2.2.6",
|
||||||
|
"@xobotyi/scrollbar-width": "^1.9.5",
|
||||||
|
"copy-to-clipboard": "^3.3.1",
|
||||||
|
"fast-deep-equal": "^3.1.3",
|
||||||
|
"fast-shallow-equal": "^1.0.0",
|
||||||
|
"js-cookie": "^2.2.1",
|
||||||
|
"nano-css": "^5.6.2",
|
||||||
|
"react-universal-interface": "^0.6.2",
|
||||||
|
"resize-observer-polyfill": "^1.5.1",
|
||||||
|
"screenfull": "^5.1.0",
|
||||||
|
"set-harmonic-interval": "^1.0.1",
|
||||||
|
"throttle-debounce": "^3.0.1",
|
||||||
|
"ts-easing": "^0.2.0",
|
||||||
|
"tslib": "^2.1.0"
|
||||||
|
},
|
||||||
|
"peerDependencies": {
|
||||||
|
"react": "*",
|
||||||
|
"react-dom": "*"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/readable-stream": {
|
"node_modules/readable-stream": {
|
||||||
"version": "3.6.2",
|
"version": "3.6.2",
|
||||||
"resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz",
|
"resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz",
|
||||||
@@ -9843,6 +10151,12 @@
|
|||||||
"node": "*"
|
"node": "*"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/resize-observer-polyfill": {
|
||||||
|
"version": "1.5.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/resize-observer-polyfill/-/resize-observer-polyfill-1.5.1.tgz",
|
||||||
|
"integrity": "sha512-LwZrotdHOo12nQuZlHEmtuXdqGoOD0OhaxopaNFxWzInpEgaLWoVuAMbTzixuosCx2nEG58ngzW3vxdWoxIgdg==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
"node_modules/resolve": {
|
"node_modules/resolve": {
|
||||||
"version": "1.22.10",
|
"version": "1.22.10",
|
||||||
"resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.10.tgz",
|
"resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.10.tgz",
|
||||||
@@ -9944,6 +10258,15 @@
|
|||||||
"fsevents": "~2.3.2"
|
"fsevents": "~2.3.2"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/rtl-css-js": {
|
||||||
|
"version": "1.16.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/rtl-css-js/-/rtl-css-js-1.16.1.tgz",
|
||||||
|
"integrity": "sha512-lRQgou1mu19e+Ya0LsTvKrVJ5TYUbqCVPAiImX3UfLTenarvPUl1QFdvu5Z3PYmHT9RCcwIfbjRQBntExyj3Zg==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"@babel/runtime": "^7.1.2"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/run-parallel": {
|
"node_modules/run-parallel": {
|
||||||
"version": "1.2.0",
|
"version": "1.2.0",
|
||||||
"resolved": "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz",
|
"resolved": "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz",
|
||||||
@@ -10060,6 +10383,18 @@
|
|||||||
"loose-envify": "^1.1.0"
|
"loose-envify": "^1.1.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/screenfull": {
|
||||||
|
"version": "5.2.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/screenfull/-/screenfull-5.2.0.tgz",
|
||||||
|
"integrity": "sha512-9BakfsO2aUQN2K9Fdbj87RJIEZ82Q9IGim7FqM5OsebfoFC6ZHXgDq/KvniuLTPdeM8wY2o6Dj3WQ7KeQCj3cA==",
|
||||||
|
"license": "MIT",
|
||||||
|
"engines": {
|
||||||
|
"node": ">=0.10.0"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://github.com/sponsors/sindresorhus"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/scroll-into-view-if-needed": {
|
"node_modules/scroll-into-view-if-needed": {
|
||||||
"version": "3.1.0",
|
"version": "3.1.0",
|
||||||
"resolved": "https://registry.npmjs.org/scroll-into-view-if-needed/-/scroll-into-view-if-needed-3.1.0.tgz",
|
"resolved": "https://registry.npmjs.org/scroll-into-view-if-needed/-/scroll-into-view-if-needed-3.1.0.tgz",
|
||||||
@@ -10137,6 +10472,15 @@
|
|||||||
"node": ">= 0.4"
|
"node": ">= 0.4"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/set-harmonic-interval": {
|
||||||
|
"version": "1.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/set-harmonic-interval/-/set-harmonic-interval-1.0.1.tgz",
|
||||||
|
"integrity": "sha512-AhICkFV84tBP1aWqPwLZqFvAwqEoVA9kxNMniGEUvzOlm4vLmOFLiTT3UZ6bziJTy4bOVpzWGTfSCbmaayGx8g==",
|
||||||
|
"license": "Unlicense",
|
||||||
|
"engines": {
|
||||||
|
"node": ">=6.9"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/set-proto": {
|
"node_modules/set-proto": {
|
||||||
"version": "1.0.0",
|
"version": "1.0.0",
|
||||||
"resolved": "https://registry.npmjs.org/set-proto/-/set-proto-1.0.0.tgz",
|
"resolved": "https://registry.npmjs.org/set-proto/-/set-proto-1.0.0.tgz",
|
||||||
@@ -10424,6 +10768,51 @@
|
|||||||
"deprecated": "Please use @jridgewell/sourcemap-codec instead",
|
"deprecated": "Please use @jridgewell/sourcemap-codec instead",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
|
"node_modules/stack-generator": {
|
||||||
|
"version": "2.0.10",
|
||||||
|
"resolved": "https://registry.npmjs.org/stack-generator/-/stack-generator-2.0.10.tgz",
|
||||||
|
"integrity": "sha512-mwnua/hkqM6pF4k8SnmZ2zfETsRUpWXREfA/goT8SLCV4iOFa4bzOX2nDipWAZFPTjLvQB82f5yaodMVhK0yJQ==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"stackframe": "^1.3.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/stackframe": {
|
||||||
|
"version": "1.3.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/stackframe/-/stackframe-1.3.4.tgz",
|
||||||
|
"integrity": "sha512-oeVtt7eWQS+Na6F//S4kJ2K2VbRlS9D43mAlMyVpVWovy9o+jfgH8O9agzANzaiLjclA0oYzUXEM4PurhSUChw==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
|
"node_modules/stacktrace-gps": {
|
||||||
|
"version": "3.1.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/stacktrace-gps/-/stacktrace-gps-3.1.2.tgz",
|
||||||
|
"integrity": "sha512-GcUgbO4Jsqqg6RxfyTHFiPxdPqF+3LFmQhm7MgCuYQOYuWyqxo5pwRPz5d/u6/WYJdEnWfK4r+jGbyD8TSggXQ==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"source-map": "0.5.6",
|
||||||
|
"stackframe": "^1.3.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/stacktrace-gps/node_modules/source-map": {
|
||||||
|
"version": "0.5.6",
|
||||||
|
"resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.6.tgz",
|
||||||
|
"integrity": "sha512-MjZkVp0NHr5+TPihLcadqnlVoGIoWo4IBHptutGh9wI3ttUYvCG26HkSuDi+K6lsZ25syXJXcctwgyVCt//xqA==",
|
||||||
|
"license": "BSD-3-Clause",
|
||||||
|
"engines": {
|
||||||
|
"node": ">=0.10.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/stacktrace-js": {
|
||||||
|
"version": "2.0.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/stacktrace-js/-/stacktrace-js-2.0.2.tgz",
|
||||||
|
"integrity": "sha512-Je5vBeY4S1r/RnLydLl0TBTi3F2qdfWmYsGvtfZgEI+SCprPppaIhQf5nGcal4gI4cGpCV/duLcAzT1np6sQqg==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"error-stack-parser": "^2.0.6",
|
||||||
|
"stack-generator": "^2.0.5",
|
||||||
|
"stacktrace-gps": "^3.0.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/string_decoder": {
|
"node_modules/string_decoder": {
|
||||||
"version": "1.3.0",
|
"version": "1.3.0",
|
||||||
"resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz",
|
"resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz",
|
||||||
@@ -10605,6 +10994,54 @@
|
|||||||
"inline-style-parser": "0.1.1"
|
"inline-style-parser": "0.1.1"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/styled-components": {
|
||||||
|
"version": "6.4.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/styled-components/-/styled-components-6.4.1.tgz",
|
||||||
|
"integrity": "sha512-ADu2dF53esUzzM4I0ewxhxFtsDd6v4V6dNkg3vG0iFKhnt06sJneTZnRvujAosZwW0XD58IKgGMQoqri4wHRqg==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"@emotion/is-prop-valid": "1.4.0",
|
||||||
|
"css-to-react-native": "3.2.0",
|
||||||
|
"csstype": "3.2.3",
|
||||||
|
"stylis": "4.3.6"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">= 16"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"type": "opencollective",
|
||||||
|
"url": "https://opencollective.com/styled-components"
|
||||||
|
},
|
||||||
|
"peerDependencies": {
|
||||||
|
"css-to-react-native": ">= 3.2.0",
|
||||||
|
"react": ">= 16.8.0",
|
||||||
|
"react-dom": ">= 16.8.0",
|
||||||
|
"react-native": ">= 0.68.0"
|
||||||
|
},
|
||||||
|
"peerDependenciesMeta": {
|
||||||
|
"css-to-react-native": {
|
||||||
|
"optional": true
|
||||||
|
},
|
||||||
|
"react-dom": {
|
||||||
|
"optional": true
|
||||||
|
},
|
||||||
|
"react-native": {
|
||||||
|
"optional": true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/styled-components/node_modules/stylis": {
|
||||||
|
"version": "4.3.6",
|
||||||
|
"resolved": "https://registry.npmjs.org/stylis/-/stylis-4.3.6.tgz",
|
||||||
|
"integrity": "sha512-yQ3rwFWRfwNUY7H5vpU0wfdkNSnvnJinhF9830Swlaxl03zsOjCfmX0ugac+3LtK0lYSgwL/KXc8oYL3mG4YFQ==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
|
"node_modules/stylis": {
|
||||||
|
"version": "4.4.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/stylis/-/stylis-4.4.0.tgz",
|
||||||
|
"integrity": "sha512-5Z9ZpRzfuH6l/UAvCPAPUo3665Nk2wLaZU3x+TLHKVzIz33+sbJqbtrYoC3KD4/uVOr2Zp+L0LySezP9OHV9yA==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
"node_modules/supports-color": {
|
"node_modules/supports-color": {
|
||||||
"version": "7.2.0",
|
"version": "7.2.0",
|
||||||
"resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz",
|
"resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz",
|
||||||
@@ -10707,6 +11144,15 @@
|
|||||||
"integrity": "sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw==",
|
"integrity": "sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw==",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
|
"node_modules/throttle-debounce": {
|
||||||
|
"version": "3.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/throttle-debounce/-/throttle-debounce-3.0.1.tgz",
|
||||||
|
"integrity": "sha512-dTEWWNu6JmeVXY0ZYoPuH5cRIwc0MeGbJwah9KUNYSJwommQpCzTySTpEe8Gs1J23aeWEuAobe4Ag7EHVt/LOg==",
|
||||||
|
"license": "MIT",
|
||||||
|
"engines": {
|
||||||
|
"node": ">=10"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/tiny-invariant": {
|
"node_modules/tiny-invariant": {
|
||||||
"version": "1.3.1",
|
"version": "1.3.1",
|
||||||
"resolved": "https://registry.npmjs.org/tiny-invariant/-/tiny-invariant-1.3.1.tgz",
|
"resolved": "https://registry.npmjs.org/tiny-invariant/-/tiny-invariant-1.3.1.tgz",
|
||||||
@@ -10738,11 +11184,23 @@
|
|||||||
"node": ">=8.0"
|
"node": ">=8.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/toggle-selection": {
|
||||||
|
"version": "1.0.6",
|
||||||
|
"resolved": "https://registry.npmjs.org/toggle-selection/-/toggle-selection-1.0.6.tgz",
|
||||||
|
"integrity": "sha512-BiZS+C1OS8g/q2RRbJmy59xpyghNBqrr6k5L/uKBGRsTfxmu3ffiRnd8mlGPUVayg8pvfi5urfnu8TU7DVOkLQ==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
"node_modules/tr46": {
|
"node_modules/tr46": {
|
||||||
"version": "0.0.3",
|
"version": "0.0.3",
|
||||||
"resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz",
|
"resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz",
|
||||||
"integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw=="
|
"integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw=="
|
||||||
},
|
},
|
||||||
|
"node_modules/ts-easing": {
|
||||||
|
"version": "0.2.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/ts-easing/-/ts-easing-0.2.0.tgz",
|
||||||
|
"integrity": "sha512-Z86EW+fFFh/IFB1fqQ3/+7Zpf9t2ebOAxNI/V6Wo7r5gqiqtxmgTlQ1qbqQcjLKYeSHPTsEmvlJUDg/EuL0uHQ==",
|
||||||
|
"license": "Unlicense"
|
||||||
|
},
|
||||||
"node_modules/tsconfig-paths": {
|
"node_modules/tsconfig-paths": {
|
||||||
"version": "3.15.0",
|
"version": "3.15.0",
|
||||||
"resolved": "https://registry.npmjs.org/tsconfig-paths/-/tsconfig-paths-3.15.0.tgz",
|
"resolved": "https://registry.npmjs.org/tsconfig-paths/-/tsconfig-paths-3.15.0.tgz",
|
||||||
|
|||||||
+6
-2
@@ -1,7 +1,7 @@
|
|||||||
{
|
{
|
||||||
"name": "lotus-chat",
|
"name": "lotus-chat",
|
||||||
"version": "4.11.1",
|
"version": "4.11.1",
|
||||||
"description": "Lotus Chat \u2014 Matrix client for Lotus Guild",
|
"description": "Lotus Chat — Matrix client for Lotus Guild",
|
||||||
"main": "index.js",
|
"main": "index.js",
|
||||||
"type": "module",
|
"type": "module",
|
||||||
"engines": {
|
"engines": {
|
||||||
@@ -25,6 +25,9 @@
|
|||||||
"@atlaskit/pragmatic-drag-and-drop-auto-scroll": "1.3.0",
|
"@atlaskit/pragmatic-drag-and-drop-auto-scroll": "1.3.0",
|
||||||
"@atlaskit/pragmatic-drag-and-drop-hitbox": "1.0.3",
|
"@atlaskit/pragmatic-drag-and-drop-hitbox": "1.0.3",
|
||||||
"@fontsource/inter": "4.5.14",
|
"@fontsource/inter": "4.5.14",
|
||||||
|
"@giphy/js-fetch-api": "5.8.0",
|
||||||
|
"@giphy/js-types": "5.1.0",
|
||||||
|
"@giphy/react-components": "10.1.2",
|
||||||
"@tanstack/react-query": "5.24.1",
|
"@tanstack/react-query": "5.24.1",
|
||||||
"@tanstack/react-query-devtools": "5.24.1",
|
"@tanstack/react-query-devtools": "5.24.1",
|
||||||
"@tanstack/react-virtual": "3.2.0",
|
"@tanstack/react-virtual": "3.2.0",
|
||||||
@@ -75,10 +78,11 @@
|
|||||||
"slate-dom": "0.123.0",
|
"slate-dom": "0.123.0",
|
||||||
"slate-history": "0.113.1",
|
"slate-history": "0.113.1",
|
||||||
"slate-react": "0.123.0",
|
"slate-react": "0.123.0",
|
||||||
|
"styled-components": "6.4.1",
|
||||||
"ua-parser-js": "1.0.35"
|
"ua-parser-js": "1.0.35"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@element-hq/element-call-embedded": "0.16.3",
|
"@element-hq/element-call-embedded": "0.19.3",
|
||||||
"@esbuild-plugins/node-globals-polyfill": "0.2.3",
|
"@esbuild-plugins/node-globals-polyfill": "0.2.3",
|
||||||
"@rollup/plugin-inject": "5.0.3",
|
"@rollup/plugin-inject": "5.0.3",
|
||||||
"@rollup/plugin-wasm": "6.1.1",
|
"@rollup/plugin-wasm": "6.1.1",
|
||||||
|
|||||||
+2
-1
@@ -13,5 +13,6 @@
|
|||||||
"hashRouter": {
|
"hashRouter": {
|
||||||
"enabled": false,
|
"enabled": false,
|
||||||
"basename": "/"
|
"basename": "/"
|
||||||
}
|
},
|
||||||
|
"gifApiKey": "AqqDuQwZNjYttz7Mn6ME4JH1bJIuZ5CO"
|
||||||
}
|
}
|
||||||
@@ -0,0 +1,152 @@
|
|||||||
|
import React, { useCallback } from 'react';
|
||||||
|
import FocusTrap from 'focus-trap-react';
|
||||||
|
import { Grid, SearchBar, SearchContext, SearchContextManager } from '@giphy/react-components';
|
||||||
|
import { IGif } from '@giphy/js-types';
|
||||||
|
import { Box } from 'folds';
|
||||||
|
import { useSetting } from '../state/hooks/settings';
|
||||||
|
import { settingsAtom } from '../state/settings';
|
||||||
|
|
||||||
|
const PICKER_WIDTH = 312;
|
||||||
|
|
||||||
|
const TERMINAL_CSS = `
|
||||||
|
[data-gif-terminal] input,
|
||||||
|
[data-gif-terminal] form {
|
||||||
|
background: #030c14 !important;
|
||||||
|
color: #e8edf5 !important;
|
||||||
|
font-family: 'JetBrains Mono', 'Cascadia Code', 'Fira Code', monospace !important;
|
||||||
|
border: 1px solid rgba(255,107,0,0.35) !important;
|
||||||
|
border-radius: 4px !important;
|
||||||
|
font-size: 12px !important;
|
||||||
|
box-shadow: none !important;
|
||||||
|
}
|
||||||
|
[data-gif-terminal] input:focus {
|
||||||
|
border-color: rgba(255,107,0,0.7) !important;
|
||||||
|
box-shadow: 0 0 0 2px rgba(255,107,0,0.12) !important;
|
||||||
|
outline: none !important;
|
||||||
|
}
|
||||||
|
[data-gif-terminal] input::placeholder {
|
||||||
|
color: rgba(255,107,0,0.4) !important;
|
||||||
|
font-family: 'JetBrains Mono', monospace !important;
|
||||||
|
}
|
||||||
|
[data-gif-terminal] svg,
|
||||||
|
[data-gif-terminal] button[type="reset"] {
|
||||||
|
display: none !important;
|
||||||
|
}
|
||||||
|
[data-gif-terminal] ::-webkit-scrollbar {
|
||||||
|
width: 4px;
|
||||||
|
}
|
||||||
|
[data-gif-terminal] ::-webkit-scrollbar-track {
|
||||||
|
background: #030508;
|
||||||
|
}
|
||||||
|
[data-gif-terminal] ::-webkit-scrollbar-thumb {
|
||||||
|
background: rgba(255,107,0,0.4);
|
||||||
|
border-radius: 2px;
|
||||||
|
}
|
||||||
|
`;
|
||||||
|
|
||||||
|
type GifPickerInnerProps = {
|
||||||
|
onSelect: (url: string, width: number, height: number) => void;
|
||||||
|
requestClose: () => void;
|
||||||
|
lotusTerminal: boolean;
|
||||||
|
};
|
||||||
|
|
||||||
|
function GifPickerInner({ onSelect, requestClose, lotusTerminal }: GifPickerInnerProps) {
|
||||||
|
const { fetchGifs, searchKey } = React.useContext(SearchContext);
|
||||||
|
|
||||||
|
const handleClick = useCallback(
|
||||||
|
(gif: IGif, e: React.SyntheticEvent) => {
|
||||||
|
e.preventDefault();
|
||||||
|
const r = gif.images.downsized ?? gif.images.original;
|
||||||
|
const url = r.url;
|
||||||
|
const width = Number(r.width) || 200;
|
||||||
|
const height = Number(r.height) || 200;
|
||||||
|
onSelect(url, width, height);
|
||||||
|
requestClose();
|
||||||
|
},
|
||||||
|
[onSelect, requestClose]
|
||||||
|
);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Box direction="Column" style={{ width: `${PICKER_WIDTH}px` }}>
|
||||||
|
{lotusTerminal && (
|
||||||
|
<div style={{
|
||||||
|
padding: '5px 10px 4px',
|
||||||
|
borderBottom: '1px solid rgba(255,107,0,0.2)',
|
||||||
|
fontFamily: "'JetBrains Mono', 'Cascadia Code', monospace",
|
||||||
|
fontSize: '10px',
|
||||||
|
fontWeight: 700,
|
||||||
|
letterSpacing: '0.1em',
|
||||||
|
color: '#FF6B00',
|
||||||
|
userSelect: 'none',
|
||||||
|
}}>
|
||||||
|
// GIF_SEARCH
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
<Box style={{ padding: '8px 8px 4px' }}>
|
||||||
|
<SearchBar style={{ width: '100%', borderRadius: lotusTerminal ? '4px' : '8px' }} />
|
||||||
|
</Box>
|
||||||
|
<div style={{ overflowY: 'auto', overflowX: 'hidden', maxHeight: '340px', padding: '0 8px 8px' }}>
|
||||||
|
<Grid
|
||||||
|
key={searchKey}
|
||||||
|
fetchGifs={fetchGifs}
|
||||||
|
width={PICKER_WIDTH - 16}
|
||||||
|
columns={2}
|
||||||
|
gutter={4}
|
||||||
|
onGifClick={handleClick}
|
||||||
|
hideAttribution={false}
|
||||||
|
noLink
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</Box>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
type GifPickerProps = {
|
||||||
|
apiKey: string;
|
||||||
|
onSelect: (url: string, width: number, height: number) => void;
|
||||||
|
requestClose: () => void;
|
||||||
|
};
|
||||||
|
|
||||||
|
export function GifPicker({ apiKey, onSelect, requestClose }: GifPickerProps) {
|
||||||
|
const [lotusTerminal] = useSetting(settingsAtom, 'lotusTerminal');
|
||||||
|
|
||||||
|
const containerStyle = lotusTerminal
|
||||||
|
? {
|
||||||
|
background: '#060c14',
|
||||||
|
border: '1px solid rgba(255,107,0,0.35)',
|
||||||
|
borderRadius: '4px',
|
||||||
|
overflow: 'hidden',
|
||||||
|
boxShadow: '0 4px 24px rgba(255,107,0,0.10), 0 0 0 1px rgba(255,107,0,0.08)',
|
||||||
|
width: `${PICKER_WIDTH}px`,
|
||||||
|
}
|
||||||
|
: {
|
||||||
|
background: 'var(--bg-surface)',
|
||||||
|
border: '1px solid rgba(255,255,255,0.08)',
|
||||||
|
borderRadius: '12px',
|
||||||
|
overflow: 'hidden',
|
||||||
|
boxShadow: '0 8px 32px rgba(0,0,0,0.4)',
|
||||||
|
width: `${PICKER_WIDTH}px`,
|
||||||
|
};
|
||||||
|
|
||||||
|
return (
|
||||||
|
<FocusTrap
|
||||||
|
focusTrapOptions={{
|
||||||
|
initialFocus: false,
|
||||||
|
onDeactivate: requestClose,
|
||||||
|
clickOutsideDeactivates: true,
|
||||||
|
allowOutsideClick: true,
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<Box
|
||||||
|
direction="Column"
|
||||||
|
data-gif-terminal={lotusTerminal ? '' : undefined}
|
||||||
|
style={containerStyle}
|
||||||
|
>
|
||||||
|
{lotusTerminal && <style>{TERMINAL_CSS}</style>}
|
||||||
|
<SearchContextManager apiKey={apiKey} initialTerm="">
|
||||||
|
<GifPickerInner onSelect={onSelect} requestClose={requestClose} lotusTerminal={!!lotusTerminal} />
|
||||||
|
</SearchContextManager>
|
||||||
|
</Box>
|
||||||
|
</FocusTrap>
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -391,9 +391,28 @@ export function MLocation({ content }: MLocationProps) {
|
|||||||
const location = parseGeoUri(geoUri);
|
const location = parseGeoUri(geoUri);
|
||||||
if (!location) return <BrokenContent />;
|
if (!location) return <BrokenContent />;
|
||||||
|
|
||||||
|
const lat = parseFloat(location.latitude);
|
||||||
|
const lon = parseFloat(location.longitude);
|
||||||
|
const mapSrc = `https://www.openstreetmap.org/export/embed.html?bbox=${lon - 0.007},${lat - 0.004},${lon + 0.007},${lat + 0.004}&layer=mapnik&marker=${lat},${lon}`;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Box direction="Column" alignItems="Start" gap="100">
|
<Box direction="Column" alignItems="Start" gap="200">
|
||||||
<Text size="T400">{geoUri}</Text>
|
<iframe
|
||||||
|
title="Location"
|
||||||
|
src={mapSrc}
|
||||||
|
style={{
|
||||||
|
width: '280px',
|
||||||
|
height: '160px',
|
||||||
|
border: '1px solid var(--bg-surface-border)',
|
||||||
|
borderRadius: '8px',
|
||||||
|
display: 'block',
|
||||||
|
}}
|
||||||
|
scrolling="no"
|
||||||
|
loading="lazy"
|
||||||
|
/>
|
||||||
|
<Text size="T300" style={{ opacity: 0.65 }}>
|
||||||
|
{`${lat.toFixed(5)}, ${lon.toFixed(5)}`}
|
||||||
|
</Text>
|
||||||
<Chip
|
<Chip
|
||||||
as="a"
|
as="a"
|
||||||
size="400"
|
size="400"
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
import React from 'react';
|
import React, { useState } from 'react';
|
||||||
import { Box, Text } from 'folds';
|
import { Box, Text } from 'folds';
|
||||||
|
import { useMatrixClient } from '../../../hooks/useMatrixClient';
|
||||||
|
|
||||||
type PollTextValue = Array<{ body: string }> | string;
|
type PollTextValue = Array<{ body: string }> | string;
|
||||||
|
|
||||||
@@ -21,7 +22,19 @@ type PollData = {
|
|||||||
answers?: PollAnswer[];
|
answers?: PollAnswer[];
|
||||||
};
|
};
|
||||||
|
|
||||||
export function PollContent({ content }: { content: Record<string, unknown> }) {
|
export function PollContent({
|
||||||
|
content,
|
||||||
|
roomId,
|
||||||
|
eventId,
|
||||||
|
}: {
|
||||||
|
content: Record<string, unknown>;
|
||||||
|
roomId?: string;
|
||||||
|
eventId?: string;
|
||||||
|
}) {
|
||||||
|
const mx = useMatrixClient();
|
||||||
|
const [myVote, setMyVote] = useState<string | null>(null);
|
||||||
|
const isStable = !!content['m.poll'];
|
||||||
|
|
||||||
const poll = (
|
const poll = (
|
||||||
content['m.poll'] ?? content['org.matrix.msc3381.poll.start']
|
content['m.poll'] ?? content['org.matrix.msc3381.poll.start']
|
||||||
) as PollData | undefined;
|
) as PollData | undefined;
|
||||||
@@ -39,8 +52,30 @@ export function PollContent({ content }: { content: Record<string, unknown> }) {
|
|||||||
(poll.question as any)?.body ||
|
(poll.question as any)?.body ||
|
||||||
'Untitled poll';
|
'Untitled poll';
|
||||||
|
|
||||||
|
const canVote = !!roomId && !!eventId;
|
||||||
|
|
||||||
|
const handleVote = (answerId: string) => {
|
||||||
|
if (!roomId || !eventId) return;
|
||||||
|
setMyVote(answerId);
|
||||||
|
if (isStable) {
|
||||||
|
mx.sendEvent(roomId, 'm.poll.response' as any, {
|
||||||
|
'm.relates_to': { rel_type: 'm.reference', event_id: eventId },
|
||||||
|
'm.responses': [{ 'm.id': answerId }],
|
||||||
|
});
|
||||||
|
} else {
|
||||||
|
mx.sendEvent(roomId, 'org.matrix.msc3381.poll.response' as any, {
|
||||||
|
'm.relates_to': { rel_type: 'm.reference', event_id: eventId },
|
||||||
|
'org.matrix.msc3381.poll.response': { answers: [answerId] },
|
||||||
|
});
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Box direction="Column" gap="200" style={{ maxWidth: '340px', paddingTop: '2px', paddingBottom: '4px' }}>
|
<Box
|
||||||
|
direction="Column"
|
||||||
|
gap="200"
|
||||||
|
style={{ maxWidth: '340px', paddingTop: '2px', paddingBottom: '4px' }}
|
||||||
|
>
|
||||||
<Box
|
<Box
|
||||||
alignItems="Center"
|
alignItems="Center"
|
||||||
gap="100"
|
gap="100"
|
||||||
@@ -65,26 +100,45 @@ export function PollContent({ content }: { content: Record<string, unknown> }) {
|
|||||||
(answer as any)['org.matrix.msc3381.poll.answer']?.body ||
|
(answer as any)['org.matrix.msc3381.poll.answer']?.body ||
|
||||||
`Option ${i + 1}`;
|
`Option ${i + 1}`;
|
||||||
const id = answer['m.id'] ?? answer.id ?? String(i);
|
const id = answer['m.id'] ?? answer.id ?? String(i);
|
||||||
|
const selected = myVote === id;
|
||||||
return (
|
return (
|
||||||
<div
|
<button
|
||||||
key={id}
|
key={id}
|
||||||
|
type="button"
|
||||||
|
onClick={canVote ? () => handleVote(id) : undefined}
|
||||||
style={{
|
style={{
|
||||||
padding: '7px 12px',
|
padding: '7px 12px',
|
||||||
borderRadius: '8px',
|
borderRadius: '8px',
|
||||||
background: 'var(--bg-surface-low)',
|
background: selected ? 'var(--bg-surface-active)' : 'var(--bg-surface-low)',
|
||||||
border: '1px solid var(--bg-surface-border)',
|
border: `1px solid ${selected ? 'var(--text-primary)' : 'var(--bg-surface-border)'}`,
|
||||||
fontSize: '0.88rem',
|
fontSize: '0.88rem',
|
||||||
lineHeight: 1.4,
|
lineHeight: 1.4,
|
||||||
|
textAlign: 'left',
|
||||||
|
cursor: canVote ? 'pointer' : 'default',
|
||||||
|
color: 'var(--text-primary)',
|
||||||
|
display: 'flex',
|
||||||
|
alignItems: 'center',
|
||||||
|
gap: '8px',
|
||||||
|
width: '100%',
|
||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
{text}
|
<span style={{ flexGrow: 1 }}>{text}</span>
|
||||||
</div>
|
{selected && (
|
||||||
|
<span style={{ opacity: 0.8, fontSize: '1rem', flexShrink: 0 }}>✓</span>
|
||||||
|
)}
|
||||||
|
</button>
|
||||||
);
|
);
|
||||||
})}
|
})}
|
||||||
</Box>
|
</Box>
|
||||||
|
{canVote ? (
|
||||||
|
<Text size="T200" style={{ opacity: 0.5, marginTop: '2px' }}>
|
||||||
|
<i>{myVote ? 'Vote cast — click another to change' : 'Click an option to vote'}</i>
|
||||||
|
</Text>
|
||||||
|
) : (
|
||||||
<Text size="T200" style={{ opacity: 0.4, marginTop: '2px' }}>
|
<Text size="T200" style={{ opacity: 0.4, marginTop: '2px' }}>
|
||||||
<i>Open in Element to vote</i>
|
<i>Open in Element to vote</i>
|
||||||
</Text>
|
</Text>
|
||||||
|
)}
|
||||||
</Box>
|
</Box>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -182,6 +182,27 @@ export function UploadCardRenderer({
|
|||||||
<PreviewVideo fileItem={fileItem} />
|
<PreviewVideo fileItem={fileItem} />
|
||||||
</MediaPreview>
|
</MediaPreview>
|
||||||
)}
|
)}
|
||||||
|
{(fileItem.originalFile.type.startsWith('image') ||
|
||||||
|
fileItem.originalFile.type.startsWith('video')) && (
|
||||||
|
<input
|
||||||
|
type="text"
|
||||||
|
placeholder="Add a caption… (optional)"
|
||||||
|
value={metadata.caption ?? ''}
|
||||||
|
onChange={(e) => setMetadata(fileItem, { ...metadata, caption: e.target.value })}
|
||||||
|
style={{
|
||||||
|
marginTop: '6px',
|
||||||
|
width: '100%',
|
||||||
|
background: 'var(--bg-surface-low)',
|
||||||
|
border: '1px solid var(--bg-surface-border)',
|
||||||
|
borderRadius: '6px',
|
||||||
|
padding: '5px 8px',
|
||||||
|
fontSize: '0.85rem',
|
||||||
|
color: 'var(--text-primary)',
|
||||||
|
outline: 'none',
|
||||||
|
boxSizing: 'border-box',
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
)}
|
||||||
{upload.status === UploadStatus.Idle && !fileSizeExceeded && (
|
{upload.status === UploadStatus.Idle && !fileSizeExceeded && (
|
||||||
<UploadCardProgress sentBytes={0} totalBytes={file.size} />
|
<UploadCardProgress sentBytes={0} totalBytes={file.size} />
|
||||||
)}
|
)}
|
||||||
|
|||||||
@@ -57,6 +57,7 @@ export function CallControls({ callEmbed }: CallControlsProps) {
|
|||||||
const [shareConfirm, setShareConfirm] = useState(false);
|
const [shareConfirm, setShareConfirm] = useState(false);
|
||||||
const [pttMode] = useSetting(settingsAtom, 'pttMode');
|
const [pttMode] = useSetting(settingsAtom, 'pttMode');
|
||||||
const [pttKey] = useSetting(settingsAtom, 'pttKey');
|
const [pttKey] = useSetting(settingsAtom, 'pttKey');
|
||||||
|
const [lotusTerminal] = useSetting(settingsAtom, 'lotusTerminal');
|
||||||
const [pttActive, setPttActive] = useState(false);
|
const [pttActive, setPttActive] = useState(false);
|
||||||
|
|
||||||
// Track microphone via ref so the PTT effect doesn't need it as a dep (avoids listener churn)
|
// Track microphone via ref so the PTT effect doesn't need it as a dep (avoids listener churn)
|
||||||
@@ -159,6 +160,24 @@ export function CallControls({ callEmbed }: CallControlsProps) {
|
|||||||
alignItems="Center"
|
alignItems="Center"
|
||||||
>
|
>
|
||||||
{pttMode && (
|
{pttMode && (
|
||||||
|
lotusTerminal ? (
|
||||||
|
<Box style={{
|
||||||
|
position: 'absolute',
|
||||||
|
top: '-2.5rem',
|
||||||
|
left: '50%',
|
||||||
|
transform: 'translateX(-50%)',
|
||||||
|
background: pttActive ? 'rgba(0,255,136,0.18)' : 'rgba(255,107,0,0.12)',
|
||||||
|
border: `1px solid ${pttActive ? 'rgba(0,255,136,0.55)' : 'rgba(255,107,0,0.35)'}`,
|
||||||
|
borderRadius: '99px',
|
||||||
|
padding: '0.2rem 0.9rem',
|
||||||
|
pointerEvents: 'none',
|
||||||
|
whiteSpace: 'nowrap',
|
||||||
|
}}>
|
||||||
|
<Text size="T200" style={{ color: pttActive ? '#00FF88' : '#FF6B00', fontWeight: 700, letterSpacing: '0.08em', fontFamily: 'JetBrains Mono, monospace' }}>
|
||||||
|
{pttActive ? '● LIVE' : `PTT — Hold ${pttKeyLabel}`}
|
||||||
|
</Text>
|
||||||
|
</Box>
|
||||||
|
) : (
|
||||||
<Chip
|
<Chip
|
||||||
variant={pttActive ? 'Success' : 'Warning'}
|
variant={pttActive ? 'Success' : 'Warning'}
|
||||||
fill="Soft"
|
fill="Soft"
|
||||||
@@ -177,6 +196,7 @@ export function CallControls({ callEmbed }: CallControlsProps) {
|
|||||||
{pttActive ? '● Live' : `PTT — Hold ${pttKeyLabel}`}
|
{pttActive ? '● Live' : `PTT — Hold ${pttKeyLabel}`}
|
||||||
</Text>
|
</Text>
|
||||||
</Chip>
|
</Chip>
|
||||||
|
)
|
||||||
)}
|
)}
|
||||||
{shareConfirm && (
|
{shareConfirm && (
|
||||||
<Box
|
<Box
|
||||||
|
|||||||
@@ -9,14 +9,14 @@ import { ScreenSize, useScreenSizeContext } from '../../hooks/useScreenSize';
|
|||||||
import { useSetting } from '../../state/hooks/settings';
|
import { useSetting } from '../../state/hooks/settings';
|
||||||
import { settingsAtom } from '../../state/settings';
|
import { settingsAtom } from '../../state/settings';
|
||||||
import { PowerLevelsContextProvider, usePowerLevels } from '../../hooks/usePowerLevels';
|
import { PowerLevelsContextProvider, usePowerLevels } from '../../hooks/usePowerLevels';
|
||||||
import { useRoom } from '../../hooks/useRoom';
|
import { useRoom, useIsDirectRoom } from '../../hooks/useRoom';
|
||||||
import { useKeyDown } from '../../hooks/useKeyDown';
|
import { useKeyDown } from '../../hooks/useKeyDown';
|
||||||
import { markAsRead } from '../../utils/notifications';
|
import { markAsRead } from '../../utils/notifications';
|
||||||
import { useMatrixClient } from '../../hooks/useMatrixClient';
|
import { useMatrixClient } from '../../hooks/useMatrixClient';
|
||||||
import { useRoomMembers } from '../../hooks/useRoomMembers';
|
import { useRoomMembers } from '../../hooks/useRoomMembers';
|
||||||
import { CallView } from '../call/CallView';
|
import { CallView } from '../call/CallView';
|
||||||
import { RoomViewHeader } from './RoomViewHeader';
|
import { RoomViewHeader } from './RoomViewHeader';
|
||||||
import { callChatAtom } from '../../state/callEmbed';
|
import { callChatAtom, callEmbedAtom } from '../../state/callEmbed';
|
||||||
import { CallChatView } from './CallChatView';
|
import { CallChatView } from './CallChatView';
|
||||||
|
|
||||||
export function Room() {
|
export function Room() {
|
||||||
@@ -30,6 +30,8 @@ export function Room() {
|
|||||||
const powerLevels = usePowerLevels(room);
|
const powerLevels = usePowerLevels(room);
|
||||||
const members = useRoomMembers(mx, room.roomId);
|
const members = useRoomMembers(mx, room.roomId);
|
||||||
const chat = useAtomValue(callChatAtom);
|
const chat = useAtomValue(callChatAtom);
|
||||||
|
const callEmbed = useAtomValue(callEmbedAtom);
|
||||||
|
const isDirect = useIsDirectRoom();
|
||||||
|
|
||||||
useKeyDown(
|
useKeyDown(
|
||||||
window,
|
window,
|
||||||
@@ -43,7 +45,7 @@ export function Room() {
|
|||||||
)
|
)
|
||||||
);
|
);
|
||||||
|
|
||||||
const callView = room.isCallRoom();
|
const callView = room.isCallRoom() || (isDirect && !!callEmbed && callEmbed.roomId === room.roomId);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<PowerLevelsContextProvider value={powerLevels}>
|
<PowerLevelsContextProvider value={powerLevels}>
|
||||||
|
|||||||
@@ -30,6 +30,8 @@ import {
|
|||||||
} from 'folds';
|
} from 'folds';
|
||||||
|
|
||||||
import { useMatrixClient } from '../../hooks/useMatrixClient';
|
import { useMatrixClient } from '../../hooks/useMatrixClient';
|
||||||
|
import { GifPicker } from '../../components/GifPicker';
|
||||||
|
import { useClientConfig } from '../../hooks/useClientConfig';
|
||||||
import {
|
import {
|
||||||
CustomEditor,
|
CustomEditor,
|
||||||
Toolbar,
|
Toolbar,
|
||||||
@@ -171,6 +173,26 @@ export const RoomInput = forwardRef<HTMLDivElement, RoomInputProps>(
|
|||||||
const imagePackRooms: Room[] = useImagePackRooms(roomId, roomToParents);
|
const imagePackRooms: Room[] = useImagePackRooms(roomId, roomToParents);
|
||||||
|
|
||||||
const [toolbar, setToolbar] = useSetting(settingsAtom, 'editorToolbar');
|
const [toolbar, setToolbar] = useSetting(settingsAtom, 'editorToolbar');
|
||||||
|
const [locating, setLocating] = React.useState(false);
|
||||||
|
const handleShareLocation = () => {
|
||||||
|
if (!navigator.geolocation) return;
|
||||||
|
setLocating(true);
|
||||||
|
navigator.geolocation.getCurrentPosition(
|
||||||
|
(pos) => {
|
||||||
|
setLocating(false);
|
||||||
|
const { latitude, longitude } = pos.coords;
|
||||||
|
const geoUri = `geo:${latitude.toFixed(6)},${longitude.toFixed(6)}`;
|
||||||
|
mx.sendMessage(roomId, {
|
||||||
|
msgtype: 'm.location',
|
||||||
|
body: `Location: ${geoUri}`,
|
||||||
|
geo_uri: geoUri,
|
||||||
|
} as any);
|
||||||
|
},
|
||||||
|
() => setLocating(false),
|
||||||
|
{ timeout: 10000 }
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
const [autocompleteQuery, setAutocompleteQuery] =
|
const [autocompleteQuery, setAutocompleteQuery] =
|
||||||
useState<AutocompleteQuery<AutocompletePrefix>>();
|
useState<AutocompleteQuery<AutocompletePrefix>>();
|
||||||
|
|
||||||
@@ -216,6 +238,8 @@ export const RoomInput = forwardRef<HTMLDivElement, RoomInputProps>(
|
|||||||
const pickFile = useFilePicker(handleFiles, true);
|
const pickFile = useFilePicker(handleFiles, true);
|
||||||
const handlePaste = useFilePasteHandler(handleFiles);
|
const handlePaste = useFilePasteHandler(handleFiles);
|
||||||
const dropZoneVisible = useFileDropZone(fileDropContainerRef, handleFiles);
|
const dropZoneVisible = useFileDropZone(fileDropContainerRef, handleFiles);
|
||||||
|
const { gifApiKey } = useClientConfig();
|
||||||
|
const gifBtnRef = useRef<HTMLButtonElement>(null);
|
||||||
const [hideStickerBtn, setHideStickerBtn] = useState(document.body.clientWidth < 500);
|
const [hideStickerBtn, setHideStickerBtn] = useState(document.body.clientWidth < 500);
|
||||||
|
|
||||||
const isComposing = useComposingCheck();
|
const isComposing = useComposingCheck();
|
||||||
@@ -430,6 +454,30 @@ export const RoomInput = forwardRef<HTMLDivElement, RoomInputProps>(
|
|||||||
moveCursor(editor);
|
moveCursor(editor);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const handleGifSelect = useCallback(
|
||||||
|
async (gifUrl: string, w: number, h: number) => {
|
||||||
|
try {
|
||||||
|
const res = await fetch(gifUrl);
|
||||||
|
const blob = await res.blob();
|
||||||
|
const uploadRes = await mx.uploadContent(
|
||||||
|
new File([blob], 'image.gif', { type: 'image/gif' }),
|
||||||
|
{ type: 'image/gif', name: 'image.gif', includeFilename: false }
|
||||||
|
);
|
||||||
|
const mxcUrl = (uploadRes as any).content_uri;
|
||||||
|
if (!mxcUrl) return;
|
||||||
|
mx.sendMessage(roomId, {
|
||||||
|
msgtype: MsgType.Image,
|
||||||
|
body: 'image.gif',
|
||||||
|
url: mxcUrl,
|
||||||
|
info: { mimetype: 'image/gif', w, h, size: blob.size },
|
||||||
|
});
|
||||||
|
} catch (e) {
|
||||||
|
console.error('GIF send failed', e);
|
||||||
|
}
|
||||||
|
},
|
||||||
|
[mx, roomId]
|
||||||
|
);
|
||||||
|
|
||||||
const handleStickerSelect = async (mxc: string, shortcode: string, label: string) => {
|
const handleStickerSelect = async (mxc: string, shortcode: string, label: string) => {
|
||||||
const stickerUrl = mxcUrlToHttp(mx, mxc, useAuthentication);
|
const stickerUrl = mxcUrlToHttp(mx, mxc, useAuthentication);
|
||||||
if (!stickerUrl) return;
|
if (!stickerUrl) return;
|
||||||
@@ -669,6 +717,67 @@ export const RoomInput = forwardRef<HTMLDivElement, RoomInputProps>(
|
|||||||
</PopOut>
|
</PopOut>
|
||||||
)}
|
)}
|
||||||
</UseStateProvider>
|
</UseStateProvider>
|
||||||
|
{!!gifApiKey && (
|
||||||
|
<UseStateProvider initial={false}>
|
||||||
|
{(gifOpen: boolean, setGifOpen) => (
|
||||||
|
<PopOut
|
||||||
|
offset={16}
|
||||||
|
alignOffset={-44}
|
||||||
|
position="Top"
|
||||||
|
align="End"
|
||||||
|
anchor={
|
||||||
|
gifOpen
|
||||||
|
? gifBtnRef.current?.getBoundingClientRect() ?? undefined
|
||||||
|
: undefined
|
||||||
|
}
|
||||||
|
content={
|
||||||
|
<GifPicker
|
||||||
|
apiKey={gifApiKey}
|
||||||
|
onSelect={handleGifSelect}
|
||||||
|
requestClose={() => setGifOpen(false)}
|
||||||
|
/>
|
||||||
|
}
|
||||||
|
>
|
||||||
|
<IconButton
|
||||||
|
ref={gifBtnRef}
|
||||||
|
aria-pressed={gifOpen}
|
||||||
|
onClick={() => setGifOpen(!gifOpen)}
|
||||||
|
variant="SurfaceVariant"
|
||||||
|
size="300"
|
||||||
|
radii="300"
|
||||||
|
>
|
||||||
|
<Text
|
||||||
|
size="T200"
|
||||||
|
style={{
|
||||||
|
fontWeight: 800,
|
||||||
|
fontSize: '11px',
|
||||||
|
letterSpacing: '0.04em',
|
||||||
|
lineHeight: 1,
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
GIF
|
||||||
|
</Text>
|
||||||
|
</IconButton>
|
||||||
|
</PopOut>
|
||||||
|
)}
|
||||||
|
</UseStateProvider>
|
||||||
|
)}
|
||||||
|
<IconButton
|
||||||
|
onClick={handleShareLocation}
|
||||||
|
variant="SurfaceVariant"
|
||||||
|
size="300"
|
||||||
|
radii="300"
|
||||||
|
aria-label="Share location"
|
||||||
|
title="Share location"
|
||||||
|
>
|
||||||
|
{locating ? (
|
||||||
|
<Text size="T200" style={{ fontWeight: 800, fontSize: '10px', letterSpacing: '0.04em', lineHeight: 1 }}>
|
||||||
|
...
|
||||||
|
</Text>
|
||||||
|
) : (
|
||||||
|
<Icon src={Icons.Pin} size="100" />
|
||||||
|
)}
|
||||||
|
</IconButton>
|
||||||
<IconButton onClick={submit} variant="SurfaceVariant" size="300" radii="300">
|
<IconButton onClick={submit} variant="SurfaceVariant" size="300" radii="300">
|
||||||
<Icon src={Icons.Send} />
|
<Icon src={Icons.Send} />
|
||||||
</IconButton>
|
</IconButton>
|
||||||
|
|||||||
@@ -1222,7 +1222,7 @@ export function RoomTimeline({ room, eventId, roomInputRef, editor }: RoomTimeli
|
|||||||
mEvent.getType() === 'm.poll.start' ||
|
mEvent.getType() === 'm.poll.start' ||
|
||||||
mEvent.getType() === 'org.matrix.msc3381.poll.start'
|
mEvent.getType() === 'org.matrix.msc3381.poll.start'
|
||||||
)
|
)
|
||||||
return <PollContent content={mEvent.getContent()} />;
|
return <PollContent content={mEvent.getContent()} roomId={room.roomId} eventId={mEvent.getId() ?? undefined} />;
|
||||||
if (mEvent.getType() === MessageEvent.RoomMessageEncrypted)
|
if (mEvent.getType() === MessageEvent.RoomMessageEncrypted)
|
||||||
return (
|
return (
|
||||||
<Text>
|
<Text>
|
||||||
@@ -1351,7 +1351,7 @@ export function RoomTimeline({ room, eventId, roomInputRef, editor }: RoomTimeli
|
|||||||
{mEvent.isRedacted() ? (
|
{mEvent.isRedacted() ? (
|
||||||
<RedactedContent reason={mEvent.getUnsigned().redacted_because?.content.reason} />
|
<RedactedContent reason={mEvent.getUnsigned().redacted_because?.content.reason} />
|
||||||
) : (
|
) : (
|
||||||
<PollContent content={mEvent.getContent()} />
|
<PollContent content={mEvent.getContent()} roomId={room.roomId} eventId={mEvent.getId() ?? undefined} />
|
||||||
)}
|
)}
|
||||||
</Message>
|
</Message>
|
||||||
);
|
);
|
||||||
@@ -1404,7 +1404,7 @@ export function RoomTimeline({ room, eventId, roomInputRef, editor }: RoomTimeli
|
|||||||
{mEvent.isRedacted() ? (
|
{mEvent.isRedacted() ? (
|
||||||
<RedactedContent reason={mEvent.getUnsigned().redacted_because?.content.reason} />
|
<RedactedContent reason={mEvent.getUnsigned().redacted_because?.content.reason} />
|
||||||
) : (
|
) : (
|
||||||
<PollContent content={mEvent.getContent()} />
|
<PollContent content={mEvent.getContent()} roomId={room.roomId} eventId={mEvent.getId() ?? undefined} />
|
||||||
)}
|
)}
|
||||||
</Message>
|
</Message>
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -0,0 +1,129 @@
|
|||||||
|
import React, { ChangeEvent, useState } from 'react';
|
||||||
|
import FocusTrap from 'focus-trap-react';
|
||||||
|
import {
|
||||||
|
Box,
|
||||||
|
config,
|
||||||
|
Input,
|
||||||
|
Line,
|
||||||
|
MenuItem,
|
||||||
|
Modal,
|
||||||
|
Overlay,
|
||||||
|
OverlayBackdrop,
|
||||||
|
OverlayCenter,
|
||||||
|
Scroll,
|
||||||
|
Text,
|
||||||
|
} from 'folds';
|
||||||
|
import { MatrixEvent } from 'matrix-js-sdk';
|
||||||
|
import { useMatrixClient } from '../../../hooks/useMatrixClient';
|
||||||
|
import { stopPropagation } from '../../../utils/keyboard';
|
||||||
|
|
||||||
|
type Props = {
|
||||||
|
mEvent: MatrixEvent;
|
||||||
|
onClose: () => void;
|
||||||
|
};
|
||||||
|
|
||||||
|
export function ForwardMessageDialog({ mEvent, onClose }: Props) {
|
||||||
|
const mx = useMatrixClient();
|
||||||
|
const [query, setQuery] = useState('');
|
||||||
|
const [sentTo, setSentTo] = useState<string | null>(null);
|
||||||
|
|
||||||
|
const allRooms = mx
|
||||||
|
.getRooms()
|
||||||
|
.filter((r) => r.getMyMembership() === 'join' && !r.isSpaceRoom())
|
||||||
|
.sort((a, b) => (b.getLastActiveTimestamp() ?? 0) - (a.getLastActiveTimestamp() ?? 0));
|
||||||
|
|
||||||
|
const filtered = query
|
||||||
|
? allRooms.filter((r) => r.name.toLowerCase().includes(query.toLowerCase()))
|
||||||
|
: allRooms;
|
||||||
|
|
||||||
|
const forward = (roomId: string, roomName: string) => {
|
||||||
|
const fwdContent: Record<string, unknown> = { ...mEvent.getContent() };
|
||||||
|
delete fwdContent['m.relates_to'];
|
||||||
|
mx.sendMessage(roomId, fwdContent as any);
|
||||||
|
setSentTo(roomName);
|
||||||
|
setTimeout(onClose, 1200);
|
||||||
|
};
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Overlay open backdrop={<OverlayBackdrop />}>
|
||||||
|
<OverlayCenter>
|
||||||
|
<FocusTrap
|
||||||
|
focusTrapOptions={{
|
||||||
|
initialFocus: false,
|
||||||
|
onDeactivate: onClose,
|
||||||
|
clickOutsideDeactivates: true,
|
||||||
|
escapeDeactivates: stopPropagation,
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<Modal
|
||||||
|
size="400"
|
||||||
|
style={{ maxHeight: '440px', borderRadius: config.radii.R500, display: 'flex', flexDirection: 'column' }}
|
||||||
|
>
|
||||||
|
<Box
|
||||||
|
direction="Column"
|
||||||
|
gap="200"
|
||||||
|
shrink="No"
|
||||||
|
style={{ padding: config.space.S400, paddingBottom: config.space.S200 }}
|
||||||
|
>
|
||||||
|
<Text size="H5">Forward message</Text>
|
||||||
|
<Input
|
||||||
|
variant="Background"
|
||||||
|
size="400"
|
||||||
|
radii="400"
|
||||||
|
outlined
|
||||||
|
placeholder="Search rooms…"
|
||||||
|
value={query}
|
||||||
|
onChange={(e: ChangeEvent<HTMLInputElement>) => setQuery(e.target.value)}
|
||||||
|
/>
|
||||||
|
</Box>
|
||||||
|
<Line size="300" />
|
||||||
|
{sentTo ? (
|
||||||
|
<Box
|
||||||
|
grow="Yes"
|
||||||
|
alignItems="Center"
|
||||||
|
justifyContent="Center"
|
||||||
|
style={{ padding: config.space.S400 }}
|
||||||
|
>
|
||||||
|
<Text size="T300">✓ Forwarded to {sentTo}</Text>
|
||||||
|
</Box>
|
||||||
|
) : (
|
||||||
|
<Box grow="Yes" style={{ minHeight: 0 }}>
|
||||||
|
<Scroll size="300" hideTrack visibility="Hover">
|
||||||
|
<Box
|
||||||
|
direction="Column"
|
||||||
|
gap="100"
|
||||||
|
style={{ padding: config.space.S200 }}
|
||||||
|
>
|
||||||
|
{filtered.slice(0, 60).map((room) => (
|
||||||
|
<MenuItem
|
||||||
|
key={room.roomId}
|
||||||
|
size="300"
|
||||||
|
radii="300"
|
||||||
|
onClick={() => forward(room.roomId, room.name)}
|
||||||
|
>
|
||||||
|
<Text size="T300" truncate>
|
||||||
|
{room.name}
|
||||||
|
</Text>
|
||||||
|
</MenuItem>
|
||||||
|
))}
|
||||||
|
{filtered.length === 0 && (
|
||||||
|
<Box
|
||||||
|
alignItems="Center"
|
||||||
|
justifyContent="Center"
|
||||||
|
style={{ padding: config.space.S400 }}
|
||||||
|
>
|
||||||
|
<Text size="T300" priority="300">
|
||||||
|
No rooms found
|
||||||
|
</Text>
|
||||||
|
</Box>
|
||||||
|
)}
|
||||||
|
</Box>
|
||||||
|
</Scroll>
|
||||||
|
</Box>
|
||||||
|
)}
|
||||||
|
</Modal>
|
||||||
|
</FocusTrap>
|
||||||
|
</OverlayCenter>
|
||||||
|
</Overlay>
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -727,6 +727,7 @@ export const Message = as<'div', MessageProps>(
|
|||||||
const { focusWithinProps } = useFocusWithin({ onFocusWithinChange: setHover });
|
const { focusWithinProps } = useFocusWithin({ onFocusWithinChange: setHover });
|
||||||
const [menuAnchor, setMenuAnchor] = useState<RectCords>();
|
const [menuAnchor, setMenuAnchor] = useState<RectCords>();
|
||||||
const [emojiBoardAnchor, setEmojiBoardAnchor] = useState<RectCords>();
|
const [emojiBoardAnchor, setEmojiBoardAnchor] = useState<RectCords>();
|
||||||
|
const [forwardOpen, setForwardOpen] = useState(false);
|
||||||
|
|
||||||
const senderDisplayName =
|
const senderDisplayName =
|
||||||
getMemberDisplayName(room, senderId) ?? getMxIdLocalPart(senderId) ?? senderId;
|
getMemberDisplayName(room, senderId) ?? getMxIdLocalPart(senderId) ?? senderId;
|
||||||
@@ -1028,6 +1029,26 @@ export const Message = as<'div', MessageProps>(
|
|||||||
Reply
|
Reply
|
||||||
</Text>
|
</Text>
|
||||||
</MenuItem>
|
</MenuItem>
|
||||||
|
{!mEvent.isRedacted() && (
|
||||||
|
<MenuItem
|
||||||
|
size="300"
|
||||||
|
after={<Icon src={Icons.ArrowRight} />}
|
||||||
|
radii="300"
|
||||||
|
onClick={() => {
|
||||||
|
setForwardOpen(true);
|
||||||
|
closeMenu();
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<Text
|
||||||
|
className={css.MessageMenuItemText}
|
||||||
|
as="span"
|
||||||
|
size="T300"
|
||||||
|
truncate
|
||||||
|
>
|
||||||
|
Forward
|
||||||
|
</Text>
|
||||||
|
</MenuItem>
|
||||||
|
)}
|
||||||
{!isThreadedMessage && (
|
{!isThreadedMessage && (
|
||||||
<MenuItem
|
<MenuItem
|
||||||
size="300"
|
size="300"
|
||||||
@@ -1145,6 +1166,9 @@ export const Message = as<'div', MessageProps>(
|
|||||||
{msgContentJSX}
|
{msgContentJSX}
|
||||||
</ModernLayout>
|
</ModernLayout>
|
||||||
)}
|
)}
|
||||||
|
{forwardOpen && (
|
||||||
|
<ForwardMessageDialog mEvent={mEvent} onClose={() => setForwardOpen(false)} />
|
||||||
|
)}
|
||||||
</MessageBase>
|
</MessageBase>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -55,7 +55,7 @@ export const getImageMsgContent = async (
|
|||||||
const content: IContent = {
|
const content: IContent = {
|
||||||
msgtype: MsgType.Image,
|
msgtype: MsgType.Image,
|
||||||
filename: file.name,
|
filename: file.name,
|
||||||
body: file.name,
|
body: metadata.caption?.trim() || file.name,
|
||||||
[MATRIX_SPOILER_PROPERTY_NAME]: metadata.markedAsSpoiler,
|
[MATRIX_SPOILER_PROPERTY_NAME]: metadata.markedAsSpoiler,
|
||||||
};
|
};
|
||||||
if (imgEl) {
|
if (imgEl) {
|
||||||
@@ -90,7 +90,7 @@ export const getVideoMsgContent = async (
|
|||||||
const content: IContent = {
|
const content: IContent = {
|
||||||
msgtype: MsgType.Video,
|
msgtype: MsgType.Video,
|
||||||
filename: file.name,
|
filename: file.name,
|
||||||
body: file.name,
|
body: metadata.caption?.trim() || file.name,
|
||||||
[MATRIX_SPOILER_PROPERTY_NAME]: metadata.markedAsSpoiler,
|
[MATRIX_SPOILER_PROPERTY_NAME]: metadata.markedAsSpoiler,
|
||||||
};
|
};
|
||||||
if (videoEl) {
|
if (videoEl) {
|
||||||
|
|||||||
@@ -18,6 +18,7 @@ export type ClientConfig = {
|
|||||||
};
|
};
|
||||||
|
|
||||||
hashRouter?: HashRouterConfig;
|
hashRouter?: HashRouterConfig;
|
||||||
|
gifApiKey?: string;
|
||||||
};
|
};
|
||||||
|
|
||||||
const ClientConfigContext = createContext<ClientConfig | null>(null);
|
const ClientConfigContext = createContext<ClientConfig | null>(null);
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ import { createListAtom } from '../list';
|
|||||||
|
|
||||||
export type TUploadMetadata = {
|
export type TUploadMetadata = {
|
||||||
markedAsSpoiler: boolean;
|
markedAsSpoiler: boolean;
|
||||||
|
caption?: string;
|
||||||
};
|
};
|
||||||
|
|
||||||
export type TUploadItem = {
|
export type TUploadItem = {
|
||||||
|
|||||||
Reference in New Issue
Block a user