/* ==========================================================================
   2-components.css — 通用组件
   玻璃面板 / 按钮 / 徽章 / 表单 / 提示 / 终端
   ========================================================================== */

/* ============================================================== 面板 === */
.panel {
	position: relative;
	padding: var(--sp-5);
	border: 1px solid var(--line);
	border-radius: var(--r-md);
	background: var(--panel);
	box-shadow: var(--shadow-md);
}

/* 四角科技感切角 */
.panel::before {
	content: "";
	position: absolute;
	inset: -1px;
	pointer-events: none;
	border-radius: inherit;
	background:
		linear-gradient(var(--cyan), var(--cyan)) left top / 12px 1px no-repeat,
		linear-gradient(var(--cyan), var(--cyan)) left top / 1px 12px no-repeat,
		linear-gradient(var(--cyan), var(--cyan)) right top / 12px 1px no-repeat,
		linear-gradient(var(--cyan), var(--cyan)) right top / 1px 12px no-repeat,
		linear-gradient(var(--cyan), var(--cyan)) left bottom / 12px 1px no-repeat,
		linear-gradient(var(--cyan), var(--cyan)) left bottom / 1px 12px no-repeat,
		linear-gradient(var(--cyan), var(--cyan)) right bottom / 12px 1px no-repeat,
		linear-gradient(var(--cyan), var(--cyan)) right bottom / 1px 12px no-repeat;
	opacity: 0.55;
	transition: opacity var(--dur) var(--ease-out);
}

.panel:hover::before { opacity: 0.95; }

.panel--flush { padding: 0; overflow: hidden; }
.panel--plain::before { display: none; }

.panel-head {
	display: flex;
	align-items: center;
	gap: var(--sp-3);
	margin-bottom: var(--sp-4);
	padding-bottom: var(--sp-3);
	border-bottom: 1px solid var(--line-soft);
}

.panel-head h2,
.panel-head h3 {
	font-size: var(--fs-lg);
	font-weight: 600;
	letter-spacing: 0.05em;
	color: var(--txt-strong);
}

.panel-head .spacer { flex: 1 1 auto; }

/* 小标题（带左侧能量条） */
.sect-title {
	display: flex;
	align-items: center;
	gap: var(--sp-3);
	margin-bottom: var(--sp-4);
	font-size: var(--fs-md);
	font-weight: 600;
	letter-spacing: 0.14em;
	color: var(--txt-soft);
	text-transform: uppercase;
	font-family: var(--font-mono);
}

.sect-title::before {
	content: "";
	width: 3px;
	height: 14px;
	border-radius: 2px;
	background: linear-gradient(180deg, var(--cyan), var(--violet));
	box-shadow: var(--glow-cyan);
}

/* ============================================================== 按钮 === */
.btn {
	position: relative;
	display: inline-flex;
	align-items: center;
	justify-content: center;
	gap: var(--sp-2);

	padding: 8px 16px;
	border: 1px solid var(--line-strong);
	border-radius: var(--r-sm);
	background: rgba(46, 230, 255, 0.07);
	color: var(--cyan);

	font-size: var(--fs-sm);
	font-family: var(--font-ui);
	letter-spacing: 0.06em;
	white-space: nowrap;
	cursor: pointer;
	user-select: none;
	overflow: hidden;

	transition: background var(--dur-fast) var(--ease-out),
		color var(--dur-fast) var(--ease-out),
		border-color var(--dur-fast) var(--ease-out),
		box-shadow var(--dur-fast) var(--ease-out),
		transform var(--dur-fast) var(--ease-out);
}

.btn:hover {
	background: rgba(46, 230, 255, 0.16);
	color: var(--txt-strong);
	box-shadow: var(--glow-cyan);
}

.btn:active { transform: translateY(1px) scale(0.99); }

.btn[disabled],
.btn[aria-disabled="true"] {
	opacity: 0.42;
	cursor: not-allowed;
	box-shadow: none;
	transform: none;
}

.btn--ghost {
	border-color: var(--line);
	background: transparent;
	color: var(--txt-soft);
}

.btn--ghost:hover {
	background: rgba(255, 255, 255, 0.05);
	color: var(--txt-strong);
	box-shadow: none;
}

.btn--primary {
	border-color: rgba(46, 230, 255, 0.55);
	background: linear-gradient(180deg, rgba(46, 230, 255, 0.24), rgba(10, 145, 184, 0.16));
	color: var(--txt-strong);
}

.btn--danger {
	border-color: rgba(255, 90, 122, 0.5);
	background: rgba(255, 90, 122, 0.1);
	color: var(--rose);
}

.btn--danger:hover {
	background: rgba(255, 90, 122, 0.2);
	box-shadow: 0 0 12px rgba(255, 90, 122, 0.4);
	color: #ffd7de;
}

.btn--sm { padding: 5px 11px; font-size: var(--fs-xs); }
.btn--icon { padding: 7px; width: 32px; height: 32px; }

/* 加载中的按钮 */
.btn.is-busy { pointer-events: none; opacity: 0.72; }

.btn.is-busy::after {
	content: "";
	position: absolute;
	inset: 0;
	background: linear-gradient(90deg, transparent, rgba(46, 230, 255, 0.32), transparent);
	animation: btn-sheen 1.1s linear infinite;
}

@keyframes btn-sheen {
	from { transform: translateX(-100%); }
	to { transform: translateX(100%); }
}

/* ============================================================== 徽章 === */
.tag {
	display: inline-flex;
	align-items: center;
	gap: 5px;

	padding: 2px 9px;
	border: 1px solid var(--line);
	border-radius: var(--r-pill);
	background: rgba(46, 230, 255, 0.06);

	font-family: var(--font-mono);
	font-size: var(--fs-xxs);
	letter-spacing: 0.08em;
	color: var(--cyan-soft);
	white-space: nowrap;
}

.tag--violet {
	border-color: rgba(155, 108, 255, 0.36);
	background: rgba(155, 108, 255, 0.09);
	color: #c8b0ff;
}

.tag--muted {
	border-color: var(--line-soft);
	background: rgba(255, 255, 255, 0.03);
	color: var(--txt-dim);
}

.tag--ok { color: var(--green); border-color: rgba(61, 245, 165, 0.35); background: rgba(61, 245, 165, 0.08); }
.tag--warn { color: var(--amber); border-color: rgba(255, 179, 64, 0.35); background: rgba(255, 179, 64, 0.08); }
.tag--danger { color: var(--rose); border-color: rgba(255, 90, 122, 0.35); background: rgba(255, 90, 122, 0.08); }

/* 状态点 */
.dot {
	width: 6px;
	height: 6px;
	border-radius: 50%;
	background: currentColor;
	box-shadow: 0 0 6px currentColor;
	flex: none;
}

/* ============================================================== 表单 === */
.field {
	display: flex;
	flex-direction: column;
	gap: var(--sp-2);
}

.field-label {
	font-family: var(--font-mono);
	font-size: var(--fs-xs);
	letter-spacing: 0.16em;
	color: var(--txt-dim);
	text-transform: uppercase;
}

.input {
	width: 100%;
	padding: 9px 13px;
	border: 1px solid var(--line);
	border-radius: var(--r-sm);
	background: var(--panel-inset);
	color: var(--txt);
	font-size: var(--fs-md);
	transition: border-color var(--dur-fast) var(--ease-out),
		box-shadow var(--dur-fast) var(--ease-out), background var(--dur-fast) var(--ease-out);
}

.input::placeholder { color: var(--txt-faint); }

.input:hover { border-color: var(--line-strong); }

.input:focus {
	outline: none;
	border-color: rgba(46, 230, 255, 0.55);
	background: rgba(4, 10, 20, 0.8);
	box-shadow: 0 0 0 3px rgba(46, 230, 255, 0.12), inset 0 0 18px rgba(46, 230, 255, 0.05);
}

/* 带图标的搜索框 */
.search {
	position: relative;
	display: flex;
	align-items: center;
}

.search .input {
	padding-left: 38px;
	padding-right: 42px;
}

.search .s-icon {
	position: absolute;
	left: 13px;
	width: 15px;
	height: 15px;
	color: var(--txt-faint);
	pointer-events: none;
}

.search .s-count {
	position: absolute;
	right: 40px;
	font-family: var(--font-mono);
	font-size: var(--fs-xs);
	color: var(--txt-faint);
	pointer-events: none;
}

.search .s-clear {
	position: absolute;
	right: 9px;
	width: 22px;
	height: 22px;
	display: none;
	align-items: center;
	justify-content: center;
	border: none;
	border-radius: 50%;
	background: rgba(255, 255, 255, 0.07);
	color: var(--txt-soft);
	cursor: pointer;
	line-height: 1;
}

.search .s-clear:hover { background: rgba(255, 90, 122, 0.25); color: var(--txt-strong); }
.search.has-value .s-clear { display: flex; }

/* ============================================================== 提示 === */
.toast-wrap {
	position: fixed;
	right: var(--sp-5);
	bottom: calc(var(--bottom-h) + var(--sp-5));
	z-index: var(--z-toast);
	display: flex;
	flex-direction: column;
	gap: var(--sp-2);
	pointer-events: none;
}

.toast {
	display: flex;
	align-items: center;
	gap: var(--sp-3);
	max-width: 340px;
	padding: 10px 15px;
	border: 1px solid var(--line-strong);
	border-left-width: 3px;
	border-radius: var(--r-sm);
	background: rgba(8, 14, 26, 0.96);
	backdrop-filter: blur(10px);
	box-shadow: var(--shadow-md);
	font-size: var(--fs-sm);
	color: var(--txt);
	animation: toast-in var(--dur) var(--ease-snap) both;
}

.toast[data-kind="error"] { border-left-color: var(--rose); }
.toast[data-kind="ok"] { border-left-color: var(--green); }
.toast[data-kind="info"] { border-left-color: var(--cyan); }

.toast.is-out { animation: toast-out var(--dur) var(--ease-out) both; }

@keyframes toast-in {
	from { opacity: 0; transform: translateX(24px) scale(0.96); }
	to { opacity: 1; transform: none; }
}

@keyframes toast-out {
	to { opacity: 0; transform: translateX(18px) scale(0.97); }
}

/* 提示条 */
.notice {
	display: flex;
	gap: var(--sp-3);
	padding: var(--sp-3) var(--sp-4);
	border: 1px solid var(--line);
	border-left: 3px solid var(--cyan);
	border-radius: var(--r-sm);
	background: rgba(46, 230, 255, 0.05);
	font-size: var(--fs-sm);
	color: var(--txt-soft);
}

.notice--warn { border-left-color: var(--amber); background: rgba(255, 179, 64, 0.06); }
.notice--danger { border-left-color: var(--rose); background: rgba(255, 90, 122, 0.06); }

/* ========================================================== 空/载状态 === */
.empty {
	padding: var(--sp-8) var(--sp-4);
	text-align: center;
	color: var(--txt-dim);
	font-size: var(--fs-sm);
}

.empty .e-icon {
	width: 46px;
	height: 46px;
	margin: 0 auto var(--sp-3);
	color: var(--txt-faint);
}

.skeleton {
	position: relative;
	overflow: hidden;
	border-radius: var(--r-sm);
	background: rgba(255, 255, 255, 0.045);
}

.skeleton::after {
	content: "";
	position: absolute;
	inset: 0;
	background: linear-gradient(90deg, transparent, rgba(46, 230, 255, 0.11), transparent);
	animation: skeleton-sweep 1.4s ease-in-out infinite;
}

@keyframes skeleton-sweep {
	from { transform: translateX(-100%); }
	to { transform: translateX(100%); }
}

.spinner {
	width: 20px;
	height: 20px;
	border: 2px solid rgba(46, 230, 255, 0.18);
	border-top-color: var(--cyan);
	border-radius: 50%;
	animation: spin 760ms linear infinite;
}

@keyframes spin { to { transform: rotate(360deg); } }

.loading-row {
	display: flex;
	align-items: center;
	justify-content: center;
	gap: var(--sp-3);
	padding: var(--sp-7) 0;
	color: var(--txt-dim);
	font-family: var(--font-mono);
	font-size: var(--fs-sm);
	letter-spacing: 0.1em;
}

/* ========================================================== 数据展示 === */
.kv {
	display: grid;
	grid-template-columns: auto minmax(0, 1fr);
	gap: var(--sp-2) var(--sp-4);
	font-size: var(--fs-sm);
}

.kv dt {
	font-family: var(--font-mono);
	font-size: var(--fs-xs);
	letter-spacing: 0.1em;
	color: var(--txt-dim);
	white-space: nowrap;
}

.kv dd {
	margin: 0;
	color: var(--txt);
	min-width: 0;
	overflow-wrap: anywhere;
}

/* 数值读数块 */
.readout {
	display: flex;
	flex-direction: column;
	gap: 3px;
	padding: var(--sp-3) var(--sp-4);
	border: 1px solid var(--line-soft);
	border-radius: var(--r-sm);
	background: var(--panel-inset);
}

.readout .r-label {
	font-family: var(--font-mono);
	font-size: var(--fs-xxs);
	letter-spacing: 0.18em;
	color: var(--txt-faint);
	text-transform: uppercase;
}

.readout .r-value {
	font-family: var(--font-mono);
	font-size: var(--fs-xl);
	font-variant-numeric: tabular-nums;
	color: var(--txt-strong);
	text-shadow: var(--glow-text);
}

.readout .r-value small { font-size: var(--fs-sm); color: var(--txt-dim); margin-left: 3px; }

/* 进度条（大号） */
.meter {
	position: relative;
	height: 6px;
	border-radius: var(--r-pill);
	background: rgba(255, 255, 255, 0.06);
	overflow: hidden;
}

.meter > i {
	position: absolute;
	inset: 0 auto 0 0;
	width: var(--v, 0%);
	border-radius: inherit;
	background: linear-gradient(90deg, var(--cyan-deep), var(--cyan));
	box-shadow: 0 0 10px rgba(46, 230, 255, 0.45);
	transition: width var(--dur-slow) var(--ease-out);
}

.meter[data-level="warn"] > i { background: linear-gradient(90deg, #b06f10, var(--amber)); box-shadow: 0 0 10px rgba(255, 179, 64, 0.5); }
.meter[data-level="hot"] > i { background: linear-gradient(90deg, #a02540, var(--rose)); box-shadow: 0 0 10px rgba(255, 90, 122, 0.55); }

/* 迷你趋势图 */
.spark {
	width: 100%;
	height: 34px;
	overflow: visible;
}

.spark path.line {
	fill: none;
	stroke: var(--cyan);
	stroke-width: 1.5;
	stroke-linejoin: round;
	stroke-linecap: round;
	filter: drop-shadow(0 0 4px rgba(46, 230, 255, 0.6));
}

.spark path.area { fill: url(#sparkGrad); stroke: none; }

/* ============================================================== 终端 === */
.term {
	position: relative;
	display: flex;
	flex-direction: column;
	height: 100%;
	min-height: 0;
	border: 1px solid var(--line);
	border-radius: var(--r-md);
	background: rgba(3, 6, 12, 0.92);
	box-shadow: inset 0 0 60px rgba(46, 230, 255, 0.04), var(--shadow-md);
	overflow: hidden;
}

.term-bar {
	display: flex;
	align-items: center;
	gap: var(--sp-3);
	flex: none;
	padding: 7px var(--sp-3);
	border-bottom: 1px solid var(--line);
	background: linear-gradient(180deg, rgba(15, 23, 41, 0.9), rgba(9, 14, 26, 0.85));
	font-family: var(--font-mono);
	font-size: var(--fs-xs);
	color: var(--txt-dim);
}

.term-bar .tb-dots { display: flex; gap: 5px; }

.term-bar .tb-dots i {
	width: 9px;
	height: 9px;
	border-radius: 50%;
	background: rgba(255, 255, 255, 0.13);
}

.term-bar .tb-dots i:nth-child(1) { background: rgba(255, 90, 122, 0.65); }
.term-bar .tb-dots i:nth-child(2) { background: rgba(255, 179, 64, 0.65); }
.term-bar .tb-dots i:nth-child(3) { background: rgba(61, 245, 165, 0.65); }

.term-bar .tb-cwd {
	min-width: 0;
	flex: 1 1 auto;
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
	color: var(--cyan-soft);
}

.term-bar .tb-cwd b { color: var(--txt-dim); font-weight: 400; }

.term-bar .tb-actions { display: flex; gap: var(--sp-1); flex: none; }

.term-body {
	position: relative;
	flex: 1 1 auto;
	min-height: 0;
	overflow-y: auto;
	overscroll-behavior: contain;
	padding: var(--sp-3);
	font-family: var(--font-mono);
	font-size: var(--fs-sm);
	line-height: 1.55;
	color: #cfe6f5;
	white-space: pre-wrap;
	overflow-wrap: anywhere;
	tab-size: 4;
	cursor: text;
}

.term-body::-webkit-scrollbar { width: 9px; }

.term-line { display: block; }

.term-echo {
	color: var(--cyan-soft);
	text-shadow: 0 0 8px rgba(46, 230, 255, 0.3);
}

.term-echo .p-sigil { color: var(--green); }
.term-echo .p-path { color: var(--violet); }

.term-meta {
	display: block;
	font-size: var(--fs-xxs);
	color: var(--txt-faint);
	padding: 1px 0 4px;
	letter-spacing: 0.06em;
}

.term-meta[data-exit="0"] { color: rgba(61, 245, 165, 0.5); }
.term-meta[data-exit="err"] { color: rgba(255, 90, 122, 0.7); }

.term-input-row {
	display: flex;
	align-items: flex-start;
	gap: var(--sp-2);
	flex: none;
	padding: var(--sp-2) var(--sp-3);
	border-top: 1px solid var(--line);
	background: linear-gradient(0deg, rgba(12, 20, 36, 0.95), rgba(8, 13, 24, 0.85));
	font-family: var(--font-mono);
	font-size: var(--fs-sm);
}

.term-input-row .ti-sigil {
	flex: none;
	color: var(--green);
	padding-top: 5px;
	text-shadow: 0 0 8px rgba(61, 245, 165, 0.5);
}

.term-input-row .ti-wrap {
	position: relative;
	flex: 1 1 auto;
	min-width: 0;
}

.term-input-row textarea {
	width: 100%;
	min-height: 26px;
	max-height: 132px;
	padding: 5px 0;
	border: none;
	background: transparent;
	color: var(--cyan-soft);
	font-family: inherit;
	font-size: inherit;
	line-height: 1.5;
	resize: none;
	overflow-y: auto;
	caret-color: var(--cyan);
}

.term-input-row textarea:focus { outline: none; }

/* 输入联想 */
.term-hint {
	position: absolute;
	left: 0;
	bottom: 100%;
	max-height: 190px;
	min-width: 190px;
	overflow-y: auto;
	border: 1px solid var(--line-strong);
	border-radius: var(--r-sm);
	background: rgba(6, 11, 22, 0.98);
	box-shadow: var(--shadow-md);
	display: none;
	z-index: 5;
}

.term-hint.show { display: block; }

.term-hint .th-item {
	padding: 3px 11px;
	font-family: var(--font-mono);
	font-size: var(--fs-xs);
	color: var(--txt-soft);
	cursor: pointer;
	white-space: nowrap;
}

.term-hint .th-item.sel,
.term-hint .th-item:hover {
	background: rgba(46, 230, 255, 0.16);
	color: var(--txt-strong);
}

/* 终端 ANSI 配色（与后端 a-* 类名约定一致） */
.term-body .a-b { font-weight: 700; }
.term-body .a-d { opacity: 0.62; }
.term-body .a-i { font-style: italic; }
.term-body .a-u { text-decoration: underline; }
.term-body .a-s { text-decoration: line-through; }
.term-body .a-r { background: #cfe6f5; color: #05070e; }

.term-body .a-fg-0 { color: #4a5a6e; }
.term-body .a-fg-1 { color: #ff6b81; }
.term-body .a-fg-2 { color: #4ee39a; }
.term-body .a-fg-3 { color: #ffc857; }
.term-body .a-fg-4 { color: #5aa9ff; }
.term-body .a-fg-5 { color: #c08bff; }
.term-body .a-fg-6 { color: #46d8e8; }
.term-body .a-fg-7 { color: #cfe6f5; }
.term-body .a-fg-8 { color: #6d7f95; }
.term-body .a-fg-9 { color: #ff92a4; }
.term-body .a-fg-10 { color: #7ff0bb; }
.term-body .a-fg-11 { color: #ffe08a; }
.term-body .a-fg-12 { color: #8cc6ff; }
.term-body .a-fg-13 { color: #d9b8ff; }
.term-body .a-fg-14 { color: #86ecf7; }
.term-body .a-fg-15 { color: #ffffff; }

.term-body .a-bg-0 { background-color: #4a5a6e; }
.term-body .a-bg-1 { background-color: #ff6b81; }
.term-body .a-bg-2 { background-color: #4ee39a; }
.term-body .a-bg-3 { background-color: #ffc857; }
.term-body .a-bg-4 { background-color: #5aa9ff; }
.term-body .a-bg-5 { background-color: #c08bff; }
.term-body .a-bg-6 { background-color: #46d8e8; }
.term-body .a-bg-7 { background-color: #cfe6f5; }

/* 终端内的行内样式（256/真彩色）不需要额外规则，后端直接输出 style */
