feat(ui-refactor 4/4): 表单字段切 bg-field+inset 阴影(替代描边风,宿主/插件组件库统一);流式光标常亮对齐 StreamText

This commit is contained in:
Rick Ye
2026-09-11 13:38:23 +08:00
parent 1a7d79739d
commit 5ee00bd2c4
3 changed files with 10 additions and 22 deletions
@@ -263,7 +263,7 @@ const CUSTOM_API_OPTIONS: Array<{ value: string; label: string }> = [
] ]
const customInputCls = const customInputCls =
'w-full rounded-control border border-line-strong bg-surface px-2.5 py-1.5 text-[12px] text-ink outline-none placeholder:text-ink-3 focus:border-ink-3' 'w-full rounded-control bg-field shadow-inset-field px-2.5 py-1.5 text-[12px] text-ink outline-none placeholder:text-ink-3'
/** 模型设置:搜索/过滤 + @tanstack/react-virtual 虚拟列表(供应商多、模型上千时滚动不卡顿)。 /** 模型设置:搜索/过滤 + @tanstack/react-virtual 虚拟列表(供应商多、模型上千时滚动不卡顿)。
* 卡片视觉按行拼装:provider 头行圆角上盖、模型行接左右边框、末行圆角下盖,行尾留组间距。 * 卡片视觉按行拼装:provider 头行圆角上盖、模型行接左右边框、末行圆角下盖,行尾留组间距。
@@ -423,7 +423,7 @@ function ModelSettings({
value={keyValue} value={keyValue}
onChange={(e) => onKeyChange(e.target.value)} onChange={(e) => onKeyChange(e.target.value)}
placeholder="输入 API Key" placeholder="输入 API Key"
className="flex-1 rounded-control border border-line-strong bg-surface px-2.5 py-1.5 font-mono text-[12px] text-ink outline-none focus:border-ink-3" className="flex-1 rounded-control bg-field shadow-inset-field px-2.5 py-1.5 font-mono text-[12px] text-ink outline-none"
/> />
<button <button
type="button" type="button"
@@ -491,7 +491,7 @@ function ModelSettings({
value={search} value={search}
onChange={(e) => onSearch(e.target.value)} onChange={(e) => onSearch(e.target.value)}
placeholder="搜索模型或提供商" placeholder="搜索模型或提供商"
className="w-full rounded-control border border-line-strong bg-surface py-1.5 pl-8 pr-3 text-[12.5px] text-ink outline-none placeholder:text-ink-3 focus:border-ink-3" className="w-full rounded-control bg-field shadow-inset-field py-1.5 pl-8 pr-3 text-[12.5px] text-ink outline-none placeholder:text-ink-3"
/> />
</div> </div>
{loading && <span className="text-[11px] text-ink-3">加载中…</span>} {loading && <span className="text-[11px] text-ink-3">加载中…</span>}
@@ -909,7 +909,7 @@ function PluginSettingsForm({
// 注意不要写 w-full:string/number 控件要定宽(w-56/w-28)跟 label 同行,w-full 会把 label 挤成竖排 // 注意不要写 w-full:string/number 控件要定宽(w-56/w-28)跟 label 同行,w-full 会把 label 挤成竖排
const inputCls = const inputCls =
'rounded-control border border-line-strong bg-surface px-2.5 py-1.5 text-[12px] text-ink outline-none placeholder:text-ink-3 focus:border-ink-3' 'rounded-control bg-field shadow-inset-field px-2.5 py-1.5 text-[12px] text-ink outline-none placeholder:text-ink-3'
return ( return (
<div className="space-y-1"> <div className="space-y-1">
@@ -1023,7 +1023,7 @@ function PluginSettingsForm({
<select <select
value={typeof value === 'string' ? value : ''} value={typeof value === 'string' ? value : ''}
onChange={(e) => onChange(item.key, e.target.value)} onChange={(e) => onChange(item.key, e.target.value)}
className="w-44 shrink-0 rounded-control border border-line-strong bg-surface px-2 py-1.5 text-[12px] text-ink outline-none focus:border-ink-3" className="w-44 shrink-0 rounded-control bg-field shadow-inset-field px-2 py-1.5 text-[12px] text-ink outline-none"
> >
{!value && <option value="">(未设置)</option>} {!value && <option value="">(未设置)</option>}
{item.options.map((o) => ( {item.options.map((o) => (
@@ -38,20 +38,9 @@ body,
/* ::selection 在 beautifului.css 基座(accent-tint + ink) */ /* ::selection 在 beautifului.css 基座(accent-tint + ink) */
/* 流式输出光标 */
@keyframes caret-blink {
0%,
60% {
opacity: 1;
}
61%,
100% {
opacity: 0;
}
}
/* 流式输出光标:以 ::after 附加到流式正文最后一个文本块的最后一行文字之后 /* 流式输出光标:以 ::after 附加到流式正文最后一个文本块的最后一行文字之后
(inline 随文,而不是孤零零落在新的一行),结束后随容器 data-streaming 消失 */ (inline 随文,而不是孤零零落在新的一行),结束后随容器 data-streaming 消失。
对齐 beautifului StreamText:流式期间光标常亮(不闪烁)。 */
.streaming-body[data-streaming='true'] > *:last-child > :is(p, h1, h2, h3, h4, h5, h6):last-child::after, .streaming-body[data-streaming='true'] > *:last-child > :is(p, h1, h2, h3, h4, h5, h6):last-child::after,
.streaming-body[data-streaming='true'] > *:last-child > :is(ul, ol):last-child > li:last-child::after { .streaming-body[data-streaming='true'] > *:last-child > :is(ul, ol):last-child > li:last-child::after {
content: ''; content: '';
@@ -62,7 +51,6 @@ body,
vertical-align: -0.15em; vertical-align: -0.15em;
background: var(--ink); background: var(--ink);
border-radius: 1px; border-radius: 1px;
animation: caret-blink 0.9s steps(1) infinite;
} }
/* 禁用 textarea 的默认 resize 与滚动条闪烁 */ /* 禁用 textarea 的默认 resize 与滚动条闪烁 */
+3 -3
View File
@@ -159,7 +159,7 @@ export function Input({ className, ...rest }: InputHTMLAttributes<HTMLInputEleme
return ( return (
<input <input
className={cn( className={cn(
'w-full rounded-control border border-line-strong bg-surface px-2.5 py-1.5 text-[12px] text-ink outline-none placeholder:text-ink-3 disabled:opacity-50', 'w-full rounded-control bg-field shadow-inset-field px-2.5 py-1.5 text-[12px] text-ink outline-none placeholder:text-ink-3 disabled:opacity-50',
className className
)} )}
{...rest} {...rest}
@@ -171,7 +171,7 @@ export function Textarea({ className, ...rest }: TextareaHTMLAttributes<HTMLText
return ( return (
<textarea <textarea
className={cn( className={cn(
'w-full resize-y rounded-control border border-line-strong bg-surface px-2.5 py-1.5 text-[12px] leading-4 text-ink outline-none placeholder:text-ink-3 disabled:opacity-50', 'w-full resize-y bg-field shadow-inset-field px-2.5 py-1.5 text-[12px] leading-4 text-ink outline-none placeholder:text-ink-3 disabled:opacity-50',
className className
)} )}
{...rest} {...rest}
@@ -188,7 +188,7 @@ export function Select({ options, className, ...rest }: SelectProps): ReactEleme
return ( return (
<select <select
className={cn( className={cn(
'w-full rounded-control border border-line-strong bg-surface px-2.5 py-1.5 text-[12px] text-ink outline-none disabled:opacity-50', 'w-full rounded-control bg-field shadow-inset-field px-2.5 py-1.5 text-[12px] text-ink outline-none disabled:opacity-50',
className className
)} )}
{...rest} {...rest}