diff --git a/packages/web/i18n/en/common.json b/packages/web/i18n/en/common.json
index 0a11bc546d54..39bd7edf6527 100644
--- a/packages/web/i18n/en/common.json
+++ b/packages/web/i18n/en/common.json
@@ -286,6 +286,11 @@
"core.app.outLink.Select Mode": "Start Using",
"core.app.outLink.Select Using Way": "Select Usage Method",
"core.app.outLink.Show History": "Show Chat History",
+ "core.app.outLink.HeightPercent": "Height",
+ "core.app.outLink.AspectRatio": "Aspect Ratio",
+ "core.app.outLink.AspectRatio.Mobile": "9:16",
+ "core.app.outLink.AspectRatio.Desktop": "12:16",
+ "core.app.outLink.AspectRatio.Wide": "15:16",
"core.app.publish.Fei shu bot": "Feishu",
"core.app.publish.Fei shu bot publish": "Publish to Feishu Bot",
"core.app.schedule.Default prompt": "Default Question",
diff --git a/packages/web/i18n/zh-CN/common.json b/packages/web/i18n/zh-CN/common.json
index 9d5590285153..3d41e52ff48f 100644
--- a/packages/web/i18n/zh-CN/common.json
+++ b/packages/web/i18n/zh-CN/common.json
@@ -286,6 +286,11 @@
"core.app.outLink.Select Mode": "开始使用",
"core.app.outLink.Select Using Way": "选择使用方式",
"core.app.outLink.Show History": "展示历史对话",
+ "core.app.outLink.HeightPercent": "高度",
+ "core.app.outLink.AspectRatio": "宽高比",
+ "core.app.outLink.AspectRatio.Mobile": "9:16",
+ "core.app.outLink.AspectRatio.Desktop": "12:16",
+ "core.app.outLink.AspectRatio.Wide": "15:16",
"core.app.publish.Fei shu bot": "飞书",
"core.app.publish.Fei shu bot publish": "发布到飞书机器人",
"core.app.schedule.Default prompt": "默认问题",
diff --git a/packages/web/i18n/zh-Hant/common.json b/packages/web/i18n/zh-Hant/common.json
index 0a3ee744ad26..77910e2089b8 100644
--- a/packages/web/i18n/zh-Hant/common.json
+++ b/packages/web/i18n/zh-Hant/common.json
@@ -286,6 +286,11 @@
"core.app.outLink.Select Mode": "開始使用",
"core.app.outLink.Select Using Way": "選擇使用方式",
"core.app.outLink.Show History": "顯示歷史對話",
+ "core.app.outLink.HeightPercent": "高度",
+ "core.app.outLink.AspectRatio": "寬高比",
+ "core.app.outLink.AspectRatio.Mobile": "9:16",
+ "core.app.outLink.AspectRatio.Desktop": "12:16",
+ "core.app.outLink.AspectRatio.Wide": "15:16",
"core.app.publish.Fei shu bot": "飛書",
"core.app.publish.Fei shu bot publish": "發布到飛書機器人",
"core.app.schedule.Default prompt": "預設問題",
diff --git a/projects/app/public/js/iframe.js b/projects/app/public/js/iframe.js
index a1af0cc131b8..242eeb91a7ac 100644
--- a/projects/app/public/js/iframe.js
+++ b/projects/app/public/js/iframe.js
@@ -5,6 +5,8 @@ function embedChatbot() {
const botSrc = script?.getAttribute('data-bot-src');
const defaultOpen = script?.getAttribute('data-default-open') === 'true';
const canDrag = script?.getAttribute('data-drag') === 'true';
+ const heightPercent = script?.getAttribute('data-height-percent') || '80';
+ const aspectRatio = script?.getAttribute('data-aspect-ratio') || '9:16';
const MessageIcon =
script?.getAttribute('data-open-icon') ||
`data:image/svg+xml;base64,PHN2ZyB0PSIxNjkwNTMyNzg1NjY0IiBjbGFzcz0iaWNvbiIgdmlld0JveD0iMCAwIDEwMjQgMTAyNCIgdmVyc2lvbj0iMS4xIiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHAtaWQ9IjQxMzIiIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIj48cGF0aCBkPSJNNTEyIDMyQzI0Ny4wNCAzMiAzMiAyMjQgMzIgNDY0QTQxMC4yNCA0MTAuMjQgMCAwIDAgMTcyLjQ4IDc2OEwxNjAgOTY1LjEyYTI1LjI4IDI1LjI4IDAgMCAwIDM5LjA0IDIyLjRsMTY4LTExMkE1MjguNjQgNTI4LjY0IDAgMCAwIDUxMiA4OTZjMjY0Ljk2IDAgNDgwLTE5MiA0ODAtNDMyUzc3Ni45NiAzMiA1MTIgMzJ6IG0yNDQuOCA0MTZsLTM2MS42IDMwMS43NmExMi40OCAxMi40OCAwIDAgMS0xOS44NC0xMi40OGw1OS4yLTIzMy45MmgtMTYwYTEyLjQ4IDEyLjQ4IDAgMCAxLTcuMzYtMjMuMzZsMzYxLjYtMzAxLjc2YTEyLjQ4IDEyLjQ4IDAgMCAxIDE5Ljg0IDEyLjQ4bC01OS4yIDIzMy45MmgxNjBhMTIuNDggMTIuNDggMCAwIDEgOCAyMi4wOHoiIGZpbGw9IiM0ZTgzZmQiIHAtaWQ9IjQxMzMiPjwvcGF0aD48L3N2Zz4=`;
@@ -37,8 +39,31 @@ function embedChatbot() {
iframe.title = 'FastGPT Chat Window';
iframe.id = chatWindowId;
iframe.src = botSrc;
- iframe.style.cssText =
- 'border: none; position: fixed; flex-direction: column; justify-content: space-between; box-shadow: rgba(150, 150, 150, 0.2) 0px 10px 30px 0px, rgba(150, 150, 150, 0.2) 0px 0px 0px 1px; width: 375px; height: 667px; max-width: 90vw; max-height: 85vh; border-radius: 0.75rem; display: flex; z-index: 2147483647; overflow: hidden; left: unset; background-color: #F3F4F6;';
+ // 计算实际尺寸
+ const calculateDimensions = () => {
+ const vh = window.innerHeight;
+ const vw = window.innerWidth;
+ const [ratioWidth, ratioHeight] = aspectRatio.split(':').map(Number);
+
+ // 根据窗口高度百分比计算高度
+ const height = Math.floor(vh * (parseInt(heightPercent) / 100));
+
+ // 根据宽高比计算宽度
+ const width = Math.floor(height * (ratioWidth / ratioHeight));
+
+ // 确保不超过视窗限制
+ const maxWidth = Math.floor(vw * 0.9);
+ const maxHeight = Math.floor(vh * 0.85);
+
+ const finalWidth = Math.min(width, maxWidth);
+ const finalHeight = Math.min(height, maxHeight);
+
+ return { width: finalWidth, height: finalHeight };
+ };
+
+ const { width: iframeWidth, height: iframeHeight } = calculateDimensions();
+
+ iframe.style.cssText = `border: none; position: fixed; flex-direction: column; justify-content: space-between; box-shadow: rgba(150, 150, 150, 0.2) 0px 10px 30px 0px, rgba(150, 150, 150, 0.2) 0px 0px 0px 1px; width: ${iframeWidth}px; height: ${iframeHeight}px; border-radius: 0.75rem; display: flex; z-index: 2147483647; overflow: hidden; left: unset; background-color: #F3F4F6;`;
iframe.style.visibility = defaultOpen ? 'unset' : 'hidden';
document.body.appendChild(iframe);
@@ -66,12 +91,12 @@ function embedChatbot() {
const updateChatWindowPosition = () => {
const chatWindow = document.getElementById(chatWindowId);
const btn = ChatBtn.getBoundingClientRect();
- const [vw, vh, ww, wh] = [
- window.innerWidth,
- window.innerHeight,
- chatWindow.offsetWidth,
- chatWindow.offsetHeight
- ];
+ const [vw, vh] = [window.innerWidth, window.innerHeight];
+
+ // 重新计算窗口尺寸(响应式)
+ const { width: ww, height: wh } = calculateDimensions();
+ chatWindow.style.width = `${ww}px`;
+ chatWindow.style.height = `${wh}px`;
let right = 0;
if (btn.left >= ww) {
@@ -145,5 +170,8 @@ function embedChatbot() {
ChatBtn.appendChild(ChatBtnDiv);
document.body.appendChild(ChatBtn);
updateChatWindowPosition();
+
+ // 监听窗口大小变化,响应式调整
+ window.addEventListener('resize', updateChatWindowPosition);
}
window.addEventListener('load', embedChatbot);
diff --git a/projects/app/src/pageComponents/app/detail/Publish/Link/SelectUsingWayModal.tsx b/projects/app/src/pageComponents/app/detail/Publish/Link/SelectUsingWayModal.tsx
index 4d9eb2b80650..3e3f338f56d6 100644
--- a/projects/app/src/pageComponents/app/detail/Publish/Link/SelectUsingWayModal.tsx
+++ b/projects/app/src/pageComponents/app/detail/Publish/Link/SelectUsingWayModal.tsx
@@ -2,7 +2,17 @@ import { type OutLinkSchema } from '@fastgpt/global/support/outLink/type';
import React, { useCallback, useState } from 'react';
import MyModal from '@fastgpt/web/components/common/MyModal';
import { useTranslation } from 'next-i18next';
-import { Box, Flex, type FlexProps, Grid, ModalBody, Switch, useTheme } from '@chakra-ui/react';
+import {
+ Box,
+ Flex,
+ type FlexProps,
+ Grid,
+ Input,
+ ModalBody,
+ Select,
+ Switch,
+ useTheme
+} from '@chakra-ui/react';
import MyRadio from '@/components/common/MyRadio';
import { useForm } from 'react-hook-form';
import MyIcon from '@fastgpt/web/components/common/Icon';
@@ -46,12 +56,21 @@ const SelectUsingWayModal = ({ share, onClose }: { share: OutLinkSchema; onClose
const [refresh, setRefresh] = useState(false);
+ // 宽高比配置选项
+ const aspectRatioOptions = [
+ { label: t('common:core.app.outLink.AspectRatio.Mobile'), value: '9:16' },
+ { label: t('common:core.app.outLink.AspectRatio.Desktop'), value: '12:16' },
+ { label: t('common:core.app.outLink.AspectRatio.Wide'), value: '15:16' }
+ ];
+
const { getValues, setValue, register, watch } = useForm({
defaultValues: {
usingWay: UsingWayEnum.link,
showHistory: true,
scriptIconCanDrag: false,
scriptDefaultOpen: false,
+ scriptHeightPercent: 80,
+ scriptAspectRatio: '9:16',
scriptOpenIcon:
'data:image/svg+xml;base64,PHN2ZyB0PSIxNjkwNTMyNzg1NjY0IiBjbGFzcz0iaWNvbiIgdmlld0JveD0iMCAwIDEwMjQgMTAyNCIgdmVyc2lvbj0iMS4xIiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHAtaWQ9IjQxMzIiIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIj48cGF0aCBkPSJNNTEyIDMyQzI0Ny4wNCAzMiAzMiAyMjQgMzIgNDY0QTQxMC4yNCA0MTAuMjQgMCAwIDAgMTcyLjQ4IDc2OEwxNjAgOTY1LjEyYTI1LjI4IDI1LjI4IDAgMCAwIDM5LjA0IDIyLjRsMTY4LTExMkE1MjguNjQgNTI4LjY0IDAgMCAwIDUxMiA4OTZjMjY0Ljk2IDAgNDgwLTE5MiA0ODAtNDMyUzc3Ni45NiAzMiA1MTIgMzJ6IG0yNDQuOCA0MTZsLTM2MS42IDMwMS43NmExMi40OCAxMi40OCAwIDAgMS0xOS44NC0xMi40OGw1OS4yLTIzMy45MmgtMTYwYTEyLjQ4IDEyLjQ4IDAgMCAxLTcuMzYtMjMuMzZsMzYxLjYtMzAxLjc2YTEyLjQ4IDEyLjQ4IDAgMCAxIDE5Ljg0IDEyLjQ4bC01OS4yIDIzMy45MmgxNjBhMTIuNDggMTIuNDggMCAwIDEgOCAyMi4wOHoiIGZpbGw9IiM0ZTgzZmQiIHAtaWQ9IjQxMzMiPjwvcGF0aD48L3N2Zz4=',
scriptCloseIcon:
@@ -102,6 +121,8 @@ const SelectUsingWayModal = ({ share, onClose }: { share: OutLinkSchema; onClose
data-bot-src="${linkUrl}"
data-default-open="${getValues('scriptDefaultOpen') ? 'true' : 'false'}"
data-drag="${getValues('scriptIconCanDrag') ? 'true' : 'false'}"
+ data-height-percent="${getValues('scriptHeightPercent') || 80}"
+ data-aspect-ratio="${getValues('scriptAspectRatio') || '9:16'}"
data-open-icon="${getValues('scriptOpenIcon')}"
data-close-icon="${getValues('scriptCloseIcon')}"
defer
@@ -160,6 +181,29 @@ const SelectUsingWayModal = ({ share, onClose }: { share: OutLinkSchema; onClose
{t('common:core.app.outLink.Default open')}
+
+ {t('common:core.app.outLink.HeightPercent')} (%)
+
+
+
+ {t('common:core.app.outLink.AspectRatio')}
+
+
{t('common:core.app.outLink.Script Open Icon')}