Files
Genarrative/src/components/common/floatingFeedbackEntryModel.ts
T
kdletters 071faa482c 统一 Rust 与 TypeScript 格式化门禁
纳入 AGC Cargo workspace 的统一 rustfmt 检查与格式化入口

完成项目 TypeScript/Prettier 与 Rust 全量格式化

修复 Pingora expected executable 门禁的空白敏感误报

同步开发运维文档与 AGC skill pack 格式化忽略规则
2026-09-01 16:28:34 +08:00

83 lines
2.3 KiB
TypeScript

export const FLOATING_FEEDBACK_FORM_URL =
'https://kcnz41bksl1c.feishu.cn/share/base/form/shrcn1p9WpuZMDxrI5ysLLJhw7k';
export const FLOATING_FEEDBACK_DESKTOP_QUERY = '(min-width: 1024px)';
export const FLOATING_FEEDBACK_SIZE = 57.6;
export const FLOATING_FEEDBACK_MARGIN = 20;
export const FLOATING_FEEDBACK_INITIAL_LEFT = 24;
export const FLOATING_FEEDBACK_INITIAL_BOTTOM = 96;
export const FLOATING_FEEDBACK_DRAG_CLICK_THRESHOLD = 4;
export const FLOATING_FEEDBACK_DRAG_CLICK_SUPPRESS_MS = 250;
export const FLOATING_FEEDBACK_CONTACT_PANEL_WIDTH = 348;
export type FloatingFeedbackPosition = {
left: number;
top: number;
};
function roundFloatingFeedbackCoordinate(value: number) {
return Math.round(value * 10) / 10;
}
export function clampFloatingFeedbackPosition(
position: FloatingFeedbackPosition,
viewport: { width: number; height: number },
) {
const minLeft = FLOATING_FEEDBACK_MARGIN;
const minTop = FLOATING_FEEDBACK_MARGIN;
const maxLeft = Math.max(
minLeft,
viewport.width - FLOATING_FEEDBACK_SIZE - FLOATING_FEEDBACK_MARGIN,
);
const maxTop = Math.max(
minTop,
viewport.height - FLOATING_FEEDBACK_SIZE - FLOATING_FEEDBACK_MARGIN,
);
return {
left: roundFloatingFeedbackCoordinate(
Math.min(maxLeft, Math.max(minLeft, position.left)),
),
top: roundFloatingFeedbackCoordinate(
Math.min(maxTop, Math.max(minTop, position.top)),
),
};
}
export function resolveInitialFloatingFeedbackPosition(viewport: {
width: number;
height: number;
}) {
return clampFloatingFeedbackPosition(
{
left: FLOATING_FEEDBACK_INITIAL_LEFT,
top:
viewport.height -
FLOATING_FEEDBACK_SIZE -
FLOATING_FEEDBACK_INITIAL_BOTTOM,
},
viewport,
);
}
export function resolveFloatingFeedbackContactPanelOffset(
position: FloatingFeedbackPosition,
viewport: { width: number },
) {
const entryCenter = position.left + FLOATING_FEEDBACK_SIZE / 2;
const minCenter =
FLOATING_FEEDBACK_MARGIN + FLOATING_FEEDBACK_CONTACT_PANEL_WIDTH / 2;
const maxCenter =
viewport.width -
FLOATING_FEEDBACK_MARGIN -
FLOATING_FEEDBACK_CONTACT_PANEL_WIDTH / 2;
if (maxCenter < minCenter) {
return 0;
}
return roundFloatingFeedbackCoordinate(
Math.min(maxCenter, Math.max(minCenter, entryCenter)) - entryCenter,
);
}