feat: 第6布局改为左品右聊(聊天通高整列,chatFullHeight 几何)

This commit is contained in:
Aisland
2026-08-17 11:37:46 +08:00
parent 9afcc91e25
commit 9731c9b7f0
5 changed files with 37 additions and 18 deletions
+13 -9
View File
@@ -66,12 +66,12 @@ const OVER_SIDE_PX = 80
/** 拓扑预设(聊天窗恒贴右,PRD §13.2 硬约束):左右/三栏/上一下二/井字 */
const PRESET_DEFS = [
{ id: '2h', leftCount: 0, topCount: 0, contentCount: 1 },
{ id: '3h', leftCount: 0, topCount: 0, contentCount: 2 },
{ id: 'l2', leftCount: 1, topCount: 1, contentCount: 0 },
{ id: 't2', leftCount: 0, topCount: 1, contentCount: 1 },
{ id: 'grid', leftCount: 0, topCount: 2, contentCount: 1 },
{ id: 't3', leftCount: 0, topCount: 1, contentCount: 2 },
{ id: '2h', leftCount: 0, topCount: 0, contentCount: 1, chatFull: false },
{ id: '3h', leftCount: 0, topCount: 0, contentCount: 2, chatFull: false },
{ id: 'l2', leftCount: 1, topCount: 1, contentCount: 0, chatFull: false },
{ id: 't2', leftCount: 0, topCount: 1, contentCount: 1, chatFull: false },
{ id: 'grid', leftCount: 0, topCount: 2, contentCount: 1, chatFull: false },
{ id: 't3', leftCount: 0, topCount: 1, contentCount: 2, chatFull: true },
] as const
function buildLayout(presetId: string, name: string): LayoutSpec {
@@ -95,6 +95,7 @@ function buildLayout(presetId: string, name: string): LayoutSpec {
chatWidth: { default: 360, min: 240, max: 600 },
topHeight: { default: 200, min: 120, max: 480 },
chatSide: 'right',
chatFullHeight: def.chatFull === true,
}
}
@@ -137,9 +138,12 @@ function presetThumb(defId: string) {
)
}
return (
<span className="dsh-wt_thumb">
<span className="dsh-wt_thumbRow">{cell(false, 'a')}</span>
<span className="dsh-wt_thumbRow">{cell(false, 'b')}{cell(false, 'c')}{cell(true, 'd')}</span>
<span className="dsh-wt_thumb dsh-wt_thumbCols">
<span className="dsh-wt_thumbCol">
<span className="dsh-wt_thumbRow">{cell(false, 'a')}</span>
<span className="dsh-wt_thumbRow">{cell(false, 'b')}{cell(false, 'c')}</span>
</span>
<span className="dsh-wt_thumbCol">{cell(true, 'd')}</span>
</span>
)
}
+2 -2
View File
@@ -50,7 +50,7 @@ export const zh = {
'preset.l2': '左一右二',
'preset.t2': '上一下二',
'preset.grid': '井字四栏',
'preset.t3': '上一下三',
'preset.t3': '左品右聊',
'manage.deleteLayout': '删除布局',
'pane.browser': '浏览器',
'pane.explorer': '资源管理器',
@@ -115,7 +115,7 @@ export const en = {
'preset.l2': 'Left + stacked',
'preset.t2': 'Top + two',
'preset.grid': '2×2 grid',
'preset.t3': 'Top + three',
'preset.t3': 'Pin + chat',
'manage.deleteLayout': 'Delete layout',
'pane.browser': 'Browser',
'pane.explorer': 'Explorer',
+10 -6
View File
@@ -30,6 +30,8 @@ export type LayoutSpec = {
topHeight?: { default: number; min: number; max: number }
/** 聊天窗贴边位置:'right'(右列/右下,默认)| 'left'(左列/左下) */
chatSide?: 'left' | 'right'
/** 聊天窗通高(整列):为 true 时聊天占整条右/左列,内容区(含 top 行)全部排在其另一侧 */
chatFullHeight?: boolean
}
type Geom = { left: number; top: number; right: number; bottom: number }
@@ -310,8 +312,9 @@ export const splitStore: SplitState = {
const leftW = hasLeft
? clamp(this.leftW, spec.leftWidth?.min ?? 160, Math.max(spec.leftWidth?.min ?? 160, colW - 260))
: 0
const chatFull = spec.chatFullHeight === true
const gap = Math.max(0, colW - chatW) + 'px'
const mt = (BAR_H + topH) + 'px'
const mt = (BAR_H + (hasTop && !chatFull ? topH : 0)) + 'px'
const chatLeft = !hasLeft && spec.chatSide === 'left'
this.lastMarginLeft = hasLeft ? leftW + 'px' : (chatLeft ? '' : gap)
this.lastMarginRight = hasLeft ? '' : (chatLeft ? gap : '')
@@ -691,10 +694,11 @@ function SplitWorkspace() {
const leftW = hasLeft
? clamp(snap.leftW, spec.leftWidth?.min ?? 160, Math.max(spec.leftWidth?.min ?? 160, colW - 260))
: 0
const chatFull = spec.chatFullHeight === true
const contentW = Math.max(0, colW - chatW)
const contentX = hasLeft ? g.left + leftW : (chatLeft ? g.left + chatW : g.left)
const topRowX = hasLeft ? g.left + leftW : g.left
const topRowW = hasLeft ? Math.max(0, colW - leftW) : colW
const topRowX = hasLeft ? g.left + leftW : contentX
const topRowW = hasLeft ? Math.max(0, colW - leftW) : (chatFull ? contentW : colW)
const topItems = allocate(top, snap.topWs, topRowW)
const mainItems = allocate(main, snap.paneWs, contentW)
@@ -731,7 +735,7 @@ function SplitWorkspace() {
return (
<>
{/* 标题栏 */}
<div className="dsh-wt_splitBar" style={{ position: 'fixed', left: g.left, top: barTop, width: hasLeft ? colW : (hasTop ? colW : contentW), zIndex: 70 }}>
<div className="dsh-wt_splitBar" style={{ position: 'fixed', left: g.left, top: barTop, width: hasLeft || chatFull ? contentW : (hasTop ? colW : contentW), zIndex: 70 }}>
<span className="dsh-wt_splitTitle">{spec.title}</span>
{!hasLeft && (
<button
@@ -789,9 +793,9 @@ function SplitWorkspace() {
style={{
position: 'fixed',
left: (hasLeft ? g.left + leftW : (chatLeft ? g.left + chatW : g.right - chatW)) - DIVIDER / 2,
top: hasLeft ? barTop + BAR_H : bodyTop,
top: hasLeft || chatFull ? barTop + BAR_H : bodyTop,
width: DIVIDER,
height: hasLeft ? g.bottom - barTop - BAR_H : mainH,
height: hasLeft || chatFull ? g.bottom - barTop - BAR_H : mainH,
zIndex: 72,
}}
onPointerDown={makeDividerHandler(hasLeft ? 'left' : 'chat')}