refactor: implement collapsable sidebar with integrated stage toggle controls

This commit is contained in:
ws50529
2026-05-27 12:00:42 +08:00
parent 6766df8f5e
commit 5413062eff
5 changed files with 217 additions and 161 deletions
+78 -53
View File
@@ -1,29 +1,5 @@
<template>
<div id="app" class="flex flex-col h-screen overflow-hidden">
<!-- 頂部導覽列 -->
<header
class="bg-white dark:bg-dark border-b border-slate-200 dark:border-gray-800 py-1.5 px-4 shadow-md flex justify-between items-center z-10 flex-shrink-0">
<div class="flex items-center gap-3">
<img :src="'/ui/logo.png'" alt="Logo" style="width: 28px; height: 28px;" class="object-contain rounded-md shadow-sm">
<h1 class="text-xl font-bold text-slate-900 dark:text-gray-100">
級聯差分方程式分析 (Cascade Difference Equation Analyzer)</h1>
</div>
<div class="flex items-center gap-4">
<!-- 模式切換按鈕 -->
<button @click="toggleDarkMode"
class="p-2 rounded-lg bg-slate-100 dark:bg-gray-800 hover:bg-slate-200 dark:hover:bg-gray-700 transition-colors shadow-sm">
<svg v-if="isDarkMode" class="w-5 h-5 role-theme-icon text-yellow-500" fill="currentColor" viewBox="0 0 20 20">
<path d="M10 12a2 2 0 100-4 2 2 0 000 4z" />
<path fill-rule="evenodd"
d="M10 18a8 8 0 100-16 8 8 0 000 16zm1-13a1 1 0 10-2 0 1 1 0 002 0zM2 10a1 1 0 011-1h1a1 1 0 110 2H3a1 1 0 01-1-1zm14 0a1 1 0 011-1h1a1 1 0 110 2h-1a1 1 0 01-1-1zM5.05 5.05a1 1 0 011.414 0l.707.707a1 1 0 11-1.414 1.414l-.707-.707a1 1 0 010-1.414zm9.9 9.9a1 1 0 011.414 0l.707.707a1 1 0 11-1.414 1.414l-.707-.707a1 1 0 010-1.414zM5.05 14.95a1 1 0 010-1.414l.707-.707a1 1 0 011.414 1.414l-.707.707a1 1 0 01-1.414 0zm9.9-9.9a1 1 0 010-1.414l.707-.707a1 1 0 011.414 1.414l-.707.707a1 1 0 01-1.414 0z"
clip-rule="evenodd" />
</svg>
<svg v-else class="w-5 h-5 text-slate-700" fill="currentColor" viewBox="0 0 20 20">
<path d="M17.293 13.293A8 8 0 016.707 2.707a8.001 8.001 0 1010.586 10.586z" />
</svg>
</button>
</div>
</header>
<!-- 手機版頁籤列 (桌面版隱藏) -->
<div
class="lg:hidden flex border-b border-slate-200 dark:border-gray-800 bg-white dark:bg-dark z-10 flex-shrink-0">
@@ -52,10 +28,35 @@
<span v-if="loadingBode" class="w-2 h-2 rounded-full role-dot-primary animate-ping"></span>
</button>
</div>
<div class="flex flex-col lg:flex-row flex-1 overflow-hidden">
<!-- 左側控制面板 (RWD: 手機版=設定頁籤全螢幕桌面版=左側邊欄) -->
<aside :class="mobileTab === 'settings' ? 'flex' : 'hidden'"
class="lg:flex flex-col w-full lg:w-96 h-full bg-white dark:bg-dark border-b lg:border-b-0 lg:border-r border-slate-200 dark:border-gray-800 overflow-y-auto p-5 gap-5 custom-scrollbar transition-colors duration-300">
<div class="flex flex-col lg:flex-row flex-1 overflow-hidden relative">
<!-- 浮動展開側邊欄按鈕 (僅在桌面版且收折時顯示) -->
<button v-show="isSidebarCollapsed" @click="toggleSidebar"
class="hidden lg:flex absolute top-6 left-6 z-30 p-2 rounded-lg bg-white dark:bg-dark border border-slate-200/80 dark:border-gray-800 shadow-md text-slate-500 hover:text-slate-700 dark:text-gray-400 dark:hover:text-gray-200 hover:bg-slate-100 dark:hover:bg-gray-800 transition-all flex-shrink-0"
title="展開側邊欄">
<svg class="w-5 h-5" fill="none" stroke="currentColor" viewBox="0 0 24 24">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4 6h16M4 12h16M4 18h16"></path>
</svg>
</button>
<aside :class="[mobileTab === 'settings' ? 'flex' : 'hidden', isSidebarCollapsed ? 'sidebar-collapsed' : '']"
class="lg:flex flex-col w-full lg:w-96 h-full bg-white dark:bg-dark border-b lg:border-b-0 lg:border-r border-slate-200 dark:border-gray-800 transition-all duration-300 ease-in-out select-none flex-shrink-0 overflow-y-auto p-5 lg:p-4 gap-5 lg:gap-4 custom-scrollbar">
<!-- 側邊欄頂部 Logo 與標題及收折按鈕 -->
<div class="flex items-center justify-between pb-3 border-b border-slate-200 dark:border-gray-800/80 flex-shrink-0">
<div class="flex items-center gap-2 overflow-hidden">
<img :src="'/ui/logo.png'" alt="Logo" style="width: 24px; height: 24px;" class="object-contain rounded-md shadow-sm flex-shrink-0">
<h1 class="text-sm font-extrabold text-slate-800 dark:text-gray-200 tracking-wide truncate">
級聯差分方程式分析
</h1>
</div>
<button @click="toggleSidebar"
class="p-1.5 rounded-lg text-slate-500 hover:text-slate-700 dark:text-gray-400 dark:hover:text-gray-200 hover:bg-slate-100 dark:hover:bg-gray-800/60 transition-colors flex-shrink-0"
title="收折側邊欄">
<svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M15 19l-7-7 7-7"></path>
</svg>
</button>
</div>
<!-- 系統級參數與 MCU 連線 -->
<section class="bg-slate-50 dark:bg-gray-900/40 p-3.5 rounded-xl border border-slate-200 dark:border-gray-800 space-y-3 shadow-sm">
@@ -141,6 +142,15 @@
class="stage-drag-handle px-2 py-1 rounded bg-slate-200 dark:bg-gray-700 text-slate-700 dark:text-gray-300 text-xs touch-none select-none cursor-grab active:cursor-grabbing">
</button>
<span @click.stop="toggleCascadeStage(idx)"
class="h-[2.25rem] rounded text-[11px] font-bold transition-all duration-200 border cursor-pointer inline-flex items-center justify-center w-16 flex-shrink-0 select-none"
:class="stage.isActive
? 'z-10'
: 'bg-slate-200 dark:bg-gray-800 text-slate-400 dark:text-gray-500 border-slate-300 dark:border-gray-700 shadow-inner'"
:style="stage.isActive ? 'color: #052e16 !important; background-color: #4ade80 !important; border-color: #86efac !important;' : ''"
:title="stage.isActive ? '設為 Bypass' : '設為 Active'">
{{ stage.isActive ? 'Active' : 'Bypass' }}
</span>
<button type="button" @click="selectCascadeStage(idx)"
:class="idx === activeCascadeStageIndex ? 'role-bg-primary role-text-on-fill' : 'text-slate-700 dark:text-gray-300'"
class="flex-1 min-w-0 px-3 py-1.5 rounded text-left text-xs font-semibold transition-colors">
@@ -154,15 +164,8 @@
<div v-show="stage.isExpanded && draggingCascadeStageIndex === null" class="px-3 pb-3 text-xs text-slate-600 dark:text-gray-400 border-t border-slate-100 dark:border-gray-700">
<div class="flex items-center justify-between gap-2 pt-2">
<span class="truncate">{{ cascadeStageSummary(stage) }}</span>
<span :class="stage.isActive ? 'text-emerald-600 dark:text-emerald-400' : 'text-slate-500 dark:text-gray-500'">
{{ stage.isActive ? 'Active' : 'Bypass' }}
</span>
</div>
<div class="flex flex-wrap items-center gap-2 pt-2">
<button type="button" @click="toggleCascadeStage(idx)"
class="px-3 py-1 rounded-full bg-slate-200 dark:bg-gray-700 text-slate-700 dark:text-gray-300">
{{ stage.isActive ? '設為 Bypass' : '設為 Active' }}
</button>
<button v-if="idx === activeCascadeStageIndex" type="button" @click="writeToMCU"
:disabled="writingMCU || !mcuConnected"
class="px-3 py-1 rounded-full role-bg-primary role-hover-primary role-text-on-fill disabled:opacity-50 disabled:cursor-not-allowed">
@@ -740,7 +743,7 @@
<!-- 右側主視窗 (RWD: 手機版=圖表頁籤全螢幕桌面版=右側主區) -->
<main :class="mobileTab === 'chart' ? 'flex' : 'hidden'"
class="lg:flex flex-1 flex-col overflow-y-auto bg-slate-50 dark:bg-[#0f0f0f] lg:p-6 gap-0 lg:gap-6 custom-scrollbar relative transition-colors duration-300">
class="lg:flex flex-1 flex-col overflow-y-auto bg-slate-50 dark:bg-[#0f0f0f] lg:py-6 lg:px-20 gap-0 lg:gap-6 custom-scrollbar relative transition-colors duration-300">
<div v-if="globalError"
class="absolute top-4 right-6 role-bg-error-soft border role-border-error role-text-error role-text-on-fill px-4 py-3 rounded-lg shadow-lg text-base z-50 flex items-center gap-2">
<svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
@@ -783,21 +786,13 @@
<div
class="chart-panel bg-white dark:bg-dark lg:rounded-xl border-b lg:border border-slate-100 lg:border-slate-200 dark:border-gray-100 lg:dark:border-gray-800 lg:shadow-md p-0 lg:p-1 flex-shrink-0 relative transition-colors duration-300">
<div
class="chart-panel-header px-5 py-4 border-b border-slate-100 dark:border-gray-800 bg-white dark:bg-dark backdrop-blur-sm z-10 relative">
class="chart-panel-header px-5 py-4 border-b border-slate-100 dark:border-gray-800 bg-white dark:bg-dark backdrop-blur-sm z-10 relative flex justify-between items-center">
<h3 class="font-bold text-slate-800 dark:text-gray-200 tracking-wide flex items-center gap-2">
<svg class="w-5 h-5 role-text-primary" fill="none" stroke="currentColor" viewBox="0 0 24 24">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2"
d="M4 12h4l2-6 4 12 2-6h4"></path>
</svg>
級聯時域訊號模擬 (Multi-Stage Time-Domain Simulation)</h3>
<button v-if="filterDone" @click="downloadCsv"
class="bg-slate-700 hover:bg-slate-600 role-text-on-fill px-4 py-2 rounded-lg text-sm font-semibold transition-all flex items-center gap-2">
<svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2"
d="M4 16v1a3 3 0 003 3h10a3 3 0 003-3v-1m-4-4l-4 4m0 0l-4-4m4 4V4"></path>
</svg>
匯出 4 CSV
</button>
</div>
<div class="p-6 z-10 relative bg-white dark:bg-dark transition-colors duration-300">
<p class="text-base text-slate-600 dark:text-gray-400 mb-4">可上傳時域輸入訊號的 CSV 檔案訊號會依序通過所有啟用的 cascade stages並比較原始輸入Ideal Float Mimic Integer 輸出
@@ -961,12 +956,23 @@
</div>
<!-- 波形比較圖 -->
<h4 v-if="filterDone" class="text-base font-bold text-slate-800 dark:text-gray-200 mb-3">波形比較圖
</h4>
<!-- 只有圖表繪圖區可水平滾動卡片外框不動 -->
<div class="overflow-x-auto bg-white dark:bg-dark">
<div id="timePlot" class="min-w-[580px] w-full h-[400px] bg-white dark:bg-dark"
v-show="filterDone"></div>
<h4 v-if="filterDone" class="text-base font-bold text-slate-800 dark:text-gray-200 mb-3">波形比較圖</h4>
<div class="relative" v-if="filterDone">
<!-- 只有圖表繪圖區可水平滾動卡片外框不動 -->
<div class="overflow-x-auto bg-white dark:bg-dark rounded-lg">
<div id="timePlot" class="min-w-[580px] w-full h-[400px] bg-white dark:bg-dark"></div>
</div>
<!-- 匯出 CSV 按鈕 -->
<button @click="downloadCsv"
class="absolute bottom-4 right-4 z-20 bg-slate-700 hover:bg-slate-600 active:scale-95 text-white px-4 py-2 rounded-lg text-sm font-semibold transition-all flex items-center gap-2 shadow-md border border-slate-600/50"
title="匯出 CSV">
<svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2"
d="M4 16v1a3 3 0 003 3h10a3 3 0 003-3v-1m-4-4l-4 4m0 0l-4-4m4 4V4"></path>
</svg>
匯出 CSV
</button>
</div>
<div v-if="!filterDone && !loadingFilter && csvPreview.length === 0"
@@ -985,8 +991,27 @@
</div>
<!-- 全域置底版權宣告 -->
<footer
class="bg-white dark:bg-dark border-t border-slate-200 dark:border-gray-800 py-2 text-center z-20 transition-colors duration-300">
<p class="text-xs text-slate-500 dark:text-gray-600">© 2026 喆富創新科技股份有限公司. All rights reserved.</p>
class="bg-white dark:bg-dark border-t border-slate-200 dark:border-gray-800 py-2 px-4 z-20 transition-colors duration-300 flex items-center justify-between relative min-h-[44px]">
<button @click="toggleDarkMode"
class="p-2 rounded-lg bg-slate-100 hover:bg-slate-200 dark:bg-gray-800 dark:hover:bg-gray-700 text-slate-700 dark:text-gray-200 transition-colors shadow-sm border border-slate-200/50 dark:border-gray-700/50 flex items-center gap-1.5"
:title="isDarkMode ? '切換淺色模式' : '切換深色模式'">
<svg v-if="isDarkMode" class="w-4 h-4 text-yellow-500" fill="currentColor" viewBox="0 0 20 20">
<path d="M10 12a2 2 0 100-4 2 2 0 000 4z" />
<path fill-rule="evenodd" d="M10 18a8 8 0 100-16 8 8 0 000 16zm1-13a1 1 0 10-2 0 1 1 0 002 0zM2 10a1 1 0 011-1h1a1 1 0 110 2H3a1 1 0 01-1-1zm14 0a1 1 0 011-1h1a1 1 0 110 2h-1a1 1 0 01-1-1zM5.05 5.05a1 1 0 011.414 0l.707.707a1 1 0 11-1.414 1.414l-.707-.707a1 1 0 010-1.414zm9.9 9.9a1 1 0 011.414 0l.707.707a1 1 0 11-1.414 1.414l-.707-.707a1 1 0 010-1.414zM5.05 14.95a1 1 0 010-1.414l.707-.707a1 1 0 011.414 1.414l-.707.707a1 1 0 01-1.414 0zm9.9-9.9a1 1 0 010-1.414l.707-.707a1 1 0 011.414 1.414l-.707.707a1 1 0 01-1.414 0z" clip-rule="evenodd" />
</svg>
<svg v-else class="w-4 h-4 text-slate-700" fill="currentColor" viewBox="0 0 20 20">
<path d="M17.293 13.293A8 8 0 016.707 2.707a8.001 8.001 0 1010.586 10.586z" />
</svg>
<span class="text-xs font-semibold hidden md:inline">{{ isDarkMode ? '切換淺色模式' : '切換深色模式' }}</span>
</button>
<!-- 置中的版權宣告 -->
<p class="text-xs text-slate-500 dark:text-gray-600 absolute left-1/2 transform -translate-x-1/2 pointer-events-none">
© 2026 喆富創新科技股份有限公司. All rights reserved.
</p>
<!-- 右側佔位 -->
<div class="w-[32px] md:w-[120px]"></div>
</footer>
</div>
</template>
+20
View File
@@ -102,6 +102,7 @@ export default {
writingMCU: false,
mcuStatus: '',
saveSettingsTimeout: null,
isSidebarCollapsed: localStorage.getItem('dea_sidebar_collapsed') === 'true',
bodeMagRange: null, // [min, max] for Y-axis
}
},
@@ -334,6 +335,25 @@ export default {
this.stopShiftOutDrag();
},
methods: {
toggleSidebar() {
this.isSidebarCollapsed = !this.isSidebarCollapsed;
localStorage.setItem('dea_sidebar_collapsed', this.isSidebarCollapsed ? 'true' : 'false');
const startTime = Date.now();
const interval = setInterval(() => {
window.dispatchEvent(new Event('resize'));
if (Date.now() - startTime > 400) {
clearInterval(interval);
window.dispatchEvent(new Event('resize'));
this.resizePlots();
}
}, 30);
},
resizePlots() {
const bode = document.getElementById('bodePlot');
const time = document.getElementById('timePlot');
if (bode && window.Plotly) window.Plotly.Plots.resize(bode);
if (time && window.Plotly) window.Plotly.Plots.resize(time);
},
stageTitle(index) {
const stage = this.cascadeStages[index];
return stage?.filterType || `Stage ${index + 1}`;
+116 -105
View File
@@ -123,7 +123,7 @@ body {
header,
aside,
footer,
main > div,
main>div,
section,
details,
.js-plotly-plot,
@@ -227,7 +227,7 @@ details,
}
aside section,
main > div {
main>div {
background: transparent !important;
border-color: transparent !important;
}
@@ -239,20 +239,29 @@ aside section {
@media (min-width: 1024px) {
aside.lg\:w-96 {
width: 28rem !important;
width: 26.25rem !important;
transition: width 0.3s ease-in-out, padding 0.3s ease-in-out, border-color 0.3s ease-in-out, opacity 0.2s ease-in-out !important;
}
aside.lg\:w-96.sidebar-collapsed {
width: 0 !important;
padding: 0 !important;
border-right-color: transparent !important;
overflow: hidden !important;
opacity: 0;
pointer-events: none;
}
}
main > div {
main>div {
border-radius: 30px !important;
overflow: hidden;
}
main > div > div:first-child {
main>div>div:first-child {
border-radius: 30px 30px 0 0;
}
main > div > div:last-child,
main>div>div:last-child,
main .overflow-x-auto:has(#bodePlot),
main .overflow-x-auto:has(#timePlot),
#bodePlot,
@@ -280,7 +289,7 @@ main .overflow-x-auto:has(#timePlot) {
.border-l,
.border-r,
.lg\:border,
.divide-y > :not([hidden]) ~ :not([hidden]) {
.divide-y> :not([hidden])~ :not([hidden]) {
border-color: var(--m3-divider) !important;
}
@@ -724,14 +733,12 @@ label.role-bg-primary {
}
.role-surface-gradient {
background-image: linear-gradient(
135deg,
color-mix(in srgb, var(--m3-primary) 7%, transparent),
color-mix(in srgb, var(--m3-tertiary) 6%, transparent)
) !important;
background-image: linear-gradient(135deg,
color-mix(in srgb, var(--m3-primary) 7%, transparent),
color-mix(in srgb, var(--m3-tertiary) 6%, transparent)) !important;
}
details .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\] > div,
details .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\]>div,
details .grid.grid-cols-\[2rem_1fr_2rem\] input,
details button.touch-none {
background: var(--m3-surface-container-lowest) !important;
@@ -743,8 +750,8 @@ details .grid.grid-cols-\[2rem_1fr_2rem\] button {
color: var(--m3-on-secondary-container) !important;
}
details .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\] > button,
details .grid.grid-cols-\[2rem_1fr_2rem\] > button,
details .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\]>button,
details .grid.grid-cols-\[2rem_1fr_2rem\]>button,
details button.touch-none {
background: var(--m3-secondary-container) !important;
border: 1px solid color-mix(in srgb, var(--m3-secondary) 28%, var(--m3-outline-variant)) !important;
@@ -753,29 +760,29 @@ details button.touch-none {
min-height: 42px;
}
details .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\] > button:hover,
details .grid.grid-cols-\[2rem_1fr_2rem\] > button:hover,
details .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\]>button:hover,
details .grid.grid-cols-\[2rem_1fr_2rem\]>button:hover,
details button.touch-none:hover {
background: color-mix(in srgb, var(--m3-secondary-container) 82%, var(--m3-primary) 18%) !important;
color: var(--m3-on-secondary-container) !important;
}
details .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\] > div,
details .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\]>div,
details .grid.grid-cols-\[2rem_1fr_2rem\] input,
details button.touch-none,
details .grid.grid-cols-2.gap-2 > div {
details .grid.grid-cols-2.gap-2>div {
background: var(--m3-surface-container-lowest) !important;
border-color: var(--m3-soft-outline) !important;
}
details .grid.grid-cols-\[2rem_1fr_2rem\] input,
details button.touch-none span.font-mono,
details .grid.grid-cols-2.gap-2 > div span.font-mono {
details .grid.grid-cols-2.gap-2>div span.font-mono {
color: var(--m3-on-surface) !important;
-webkit-text-fill-color: var(--m3-on-surface);
}
details .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\] > div span.font-mono {
details .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\]>div span.font-mono {
color: var(--m3-on-secondary-container) !important;
-webkit-text-fill-color: var(--m3-on-secondary-container);
}
@@ -785,8 +792,8 @@ details .grid.grid-cols-\[2rem_1fr_2rem\] input:focus {
box-shadow: 0 0 0 3px var(--m3-primary-state) !important;
}
.grid.grid-cols-\[3\.25rem_1fr_3\.25rem\] > button,
.grid.grid-cols-\[2rem_1fr_2rem\] > button,
.grid.grid-cols-\[3\.25rem_1fr_3\.25rem\]>button,
.grid.grid-cols-\[2rem_1fr_2rem\]>button,
button.touch-none {
background: var(--m3-secondary-container) !important;
border: 1px solid color-mix(in srgb, var(--m3-secondary) 28%, var(--m3-outline-variant)) !important;
@@ -798,21 +805,21 @@ button.touch-none {
min-height: 42px;
}
.grid.grid-cols-\[3\.25rem_1fr_3\.25rem\] > button:hover,
.grid.grid-cols-\[2rem_1fr_2rem\] > button:hover,
.grid.grid-cols-\[3\.25rem_1fr_3\.25rem\]>button:hover,
.grid.grid-cols-\[2rem_1fr_2rem\]>button:hover,
button.touch-none:hover {
background: color-mix(in srgb, var(--m3-secondary-container) 82%, var(--m3-primary) 18%) !important;
color: var(--m3-on-secondary-container) !important;
}
.grid.grid-cols-\[2rem_1fr_2rem\] > input,
.grid.grid-cols-\[2rem_1fr_2rem\]>input,
button.touch-none,
.grid.grid-cols-\[3\.25rem_1fr_3\.25rem\] > div {
.grid.grid-cols-\[3\.25rem_1fr_3\.25rem\]>div {
background: var(--m3-surface-container-lowest) !important;
border-color: var(--m3-soft-outline) !important;
}
.grid.grid-cols-\[2rem_1fr_2rem\] > input,
.grid.grid-cols-\[2rem_1fr_2rem\]>input,
button.touch-none span.font-mono,
.grid.grid-cols-\[3\.25rem_1fr_3\.25rem\] span.font-mono,
.grid.grid-cols-2.gap-2 span.font-mono {
@@ -826,13 +833,13 @@ button.touch-none span.font-mono,
font-weight: 400 !important;
}
.grid.grid-cols-\[2rem_1fr_2rem\] > input {
.grid.grid-cols-\[2rem_1fr_2rem\]>input {
text-align: center;
font-size: 0.95rem !important;
min-height: 42px;
}
.grid.grid-cols-\[2rem_1fr_2rem\] > input:focus {
.grid.grid-cols-\[2rem_1fr_2rem\]>input:focus {
border-color: var(--m3-primary) !important;
box-shadow: 0 0 0 3px var(--m3-primary-state) !important;
}
@@ -851,18 +858,18 @@ button.touch-none span.font-mono,
letter-spacing: 0 !important;
}
#app section .flex.flex-wrap.gap-1.mb-2 > div,
#app section .grid.grid-cols-2.gap-2 > div,
#app section .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\] > div,
#app section .flex.flex-wrap.gap-1.mb-2>div,
#app section .grid.grid-cols-2.gap-2>div,
#app section .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\]>div,
#app section button.touch-none {
background: var(--m3-surface-container-lowest) !important;
border-color: color-mix(in srgb, var(--m3-outline) 34%, var(--m3-outline-variant)) !important;
color: var(--m3-on-surface) !important;
}
#app section .flex.flex-wrap.gap-1.mb-2 > div span,
#app section .grid.grid-cols-2.gap-2 > div span,
#app section .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\] > div span,
#app section .flex.flex-wrap.gap-1.mb-2>div span,
#app section .grid.grid-cols-2.gap-2>div span,
#app section .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\]>div span,
#app section button.touch-none span {
color: var(--m3-on-surface) !important;
-webkit-text-fill-color: var(--m3-on-surface);
@@ -871,43 +878,43 @@ button.touch-none span.font-mono,
line-height: 1.25 !important;
}
#app section .flex.flex-wrap.gap-1.mb-2 > div span:first-child,
#app section .grid.grid-cols-2.gap-2 > div span:first-child,
#app section .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\] > div span:first-child,
#app section .flex.flex-wrap.gap-1.mb-2>div span:first-child,
#app section .grid.grid-cols-2.gap-2>div span:first-child,
#app section .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\]>div span:first-child,
#app section button.touch-none span:first-child {
color: var(--m3-on-surface-variant) !important;
-webkit-text-fill-color: var(--m3-on-surface-variant);
font-weight: 400 !important;
}
#app section .flex.flex-wrap.gap-1.mb-2 > div {
#app section .flex.flex-wrap.gap-1.mb-2>div {
gap: 0.3rem !important;
min-height: 1.85rem;
padding: 0.25rem 0.45rem !important;
}
#app section .flex.flex-wrap.gap-1.mb-2 > div span:first-child {
#app section .flex.flex-wrap.gap-1.mb-2>div span:first-child {
font-size: 0.68rem !important;
}
#app section .flex.flex-wrap.gap-1.mb-2 > div span.font-mono {
#app section .flex.flex-wrap.gap-1.mb-2>div span.font-mono {
font-size: 0.78rem !important;
}
#app section .grid.grid-cols-2.gap-2 > div {
#app section .grid.grid-cols-2.gap-2>div {
padding: 0.7rem 0.65rem !important;
}
#app section .grid.grid-cols-2.gap-2 > div span.font-mono {
#app section .grid.grid-cols-2.gap-2>div span.font-mono {
font-size: clamp(0.92rem, 1vw, 1.08rem) !important;
}
#app section .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\] > div span.font-mono,
#app section .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\]>div span.font-mono,
#app section button.touch-none span.font-mono {
font-size: 1rem !important;
}
#app section .grid.grid-cols-\[2rem_1fr_2rem\] > input {
#app section .grid.grid-cols-\[2rem_1fr_2rem\]>input {
color: var(--m3-on-surface) !important;
font-size: 1rem !important;
font-variant-numeric: tabular-nums;
@@ -945,8 +952,8 @@ button.touch-none span.font-mono,
min-width: 0;
}
#app aside label.flex > span:first-child,
#app aside .flex.justify-between > span:first-child {
#app aside label.flex>span:first-child,
#app aside .flex.justify-between>span:first-child {
min-width: 0;
overflow: hidden;
text-overflow: ellipsis;
@@ -960,38 +967,38 @@ button.touch-none span.font-mono,
}
#app aside .space-y-3,
#app aside details > div,
#app aside details>div,
#app aside section {
min-width: 0;
}
#app aside .coeff-section > div.mb-3,
#app aside .fixed-section > div.mb-4,
#app aside .fixed-section > .space-y-4 > div {
#app aside .coeff-section>div.mb-3,
#app aside .fixed-section>div.mb-4,
#app aside .fixed-section>.space-y-4>div {
padding: 1rem !important;
}
#app aside .coeff-section > details,
#app aside .coeff-section>details,
#app aside .fixed-section details {
overflow: hidden;
}
#app aside .coeff-section > details > summary,
#app aside .fixed-section details > summary {
#app aside .coeff-section>details>summary,
#app aside .fixed-section details>summary {
background: transparent !important;
border-bottom: 1px solid transparent;
padding: 0.95rem 1rem !important;
}
#app aside .coeff-section > details[open] > summary,
#app aside .fixed-section details[open] > summary {
#app aside .coeff-section>details[open]>summary,
#app aside .fixed-section details[open]>summary {
border-bottom-color: var(--m3-divider);
}
#app aside .coeff-section > details > div,
#app aside .fixed-section details > div {
#app aside .coeff-section>details>div,
#app aside .fixed-section details>div {
padding: 1rem !important;
}
@@ -1007,10 +1014,10 @@ button.touch-none span.font-mono,
.dark #app aside .coeff-section .flex.flex-wrap.gap-1.mb-2 > div,
.dark #app aside .fixed-section .flex.flex-wrap.gap-1.mb-2 > div,
.dark #app aside .grid.grid-cols-2.gap-2 > div,
.dark #app aside .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\] > div,
.dark #app aside .coeff-section .flex.flex-wrap.gap-1.mb-2>div,
.dark #app aside .fixed-section .flex.flex-wrap.gap-1.mb-2>div,
.dark #app aside .grid.grid-cols-2.gap-2>div,
.dark #app aside .grid.grid-cols-\[3\.25rem_1fr_3\.25rem\]>div,
.dark #app aside button.touch-none {
background: #292a2d !important;
border-color: color-mix(in srgb, var(--m3-outline-variant) 78%, transparent) !important;
@@ -1072,43 +1079,43 @@ button.touch-none span.font-mono,
-webkit-text-fill-color: var(--m3-on-surface);
}
#app aside .fixed-section > div.mb-4 {
#app aside .fixed-section>div.mb-4 {
border-radius: 24px 24px 4px 4px !important;
margin: 0 0 2px !important;
overflow: hidden;
}
#app aside .fixed-section > .space-y-4 {
#app aside .fixed-section>.space-y-4 {
display: flex !important;
flex-direction: column;
gap: 0 !important;
margin-top: 0 !important;
}
#app aside .fixed-section > .space-y-4 > :not([hidden]) ~ :not([hidden]) {
#app aside .fixed-section>.space-y-4> :not([hidden])~ :not([hidden]) {
margin-top: 0 !important;
}
#app aside .fixed-section > .space-y-4 > :is(div, details) {
#app aside .fixed-section>.space-y-4> :is(div, details) {
border-radius: 4px !important;
margin: 0 0 2px !important;
overflow: hidden;
}
#app aside .fixed-section > .space-y-4 > :is(div, details):first-child {
#app aside .fixed-section>.space-y-4> :is(div, details):first-child {
border-radius: 4px !important;
}
#app aside .fixed-section > .space-y-4 > :is(div, details):last-child {
#app aside .fixed-section>.space-y-4> :is(div, details):last-child {
border-radius: 4px 4px 24px 24px !important;
margin-bottom: 0 !important;
}
#app aside .fixed-section > .space-y-4 > :is(div, details):first-child:last-child {
#app aside .fixed-section>.space-y-4> :is(div, details):first-child:last-child {
border-radius: 4px 4px 24px 24px !important;
}
#app aside .fixed-section > div.mb-4 + .space-y-4 {
#app aside .fixed-section>div.mb-4+.space-y-4 {
margin-top: 0 !important;
}
@@ -1186,7 +1193,7 @@ button.touch-none span.font-mono,
align-items: center;
}
#app aside .selector-button-group > span {
#app aside .selector-button-group>span {
flex: 0 0 auto;
color: var(--m3-on-surface-variant) !important;
}
@@ -1249,7 +1256,7 @@ button.touch-none span.font-mono,
box-shadow: none !important;
}
#app main .chart-panel > .role-surface-gradient {
#app main .chart-panel>.role-surface-gradient {
border-radius: inherit !important;
}
@@ -1272,14 +1279,14 @@ button.touch-none span.font-mono,
}
@media (max-width: 1023px) {
#app > header + .lg\:hidden {
#app>header+.lg\:hidden {
gap: 0.25rem !important;
padding: 0.35rem 0.75rem 0.45rem !important;
border-bottom: 0 !important;
background: var(--m3-background) !important;
}
#app > header + .lg\:hidden > button {
#app>header+.lg\:hidden>button {
position: relative;
min-height: 2.75rem;
border: 0 !important;
@@ -1289,12 +1296,12 @@ button.touch-none span.font-mono,
color: var(--m3-on-surface-variant) !important;
}
#app > header + .lg\:hidden > button.role-text-primary {
#app>header+.lg\:hidden>button.role-text-primary {
color: var(--m3-primary) !important;
-webkit-text-fill-color: var(--m3-primary);
}
#app > header + .lg\:hidden > button::after {
#app>header+.lg\:hidden>button::after {
content: "";
position: absolute;
left: 50%;
@@ -1308,7 +1315,7 @@ button.touch-none span.font-mono,
transition: opacity 160ms ease, transform 160ms ease;
}
#app > header + .lg\:hidden > button.role-text-primary::after {
#app>header+.lg\:hidden>button.role-text-primary::after {
opacity: 1;
transform: translateX(-50%) scaleX(1);
}
@@ -1323,25 +1330,25 @@ button.touch-none span.font-mono,
}
}
.dark #app aside .fixed-section > div.mb-4 {
.dark #app aside .fixed-section>div.mb-4 {
border-radius: 24px 24px 4px 4px !important;
margin: 0 0 2px !important;
overflow: hidden;
}
.dark #app aside .fixed-section > div.mb-4 + .space-y-4,
.dark #app aside .fixed-section > .space-y-4 {
.dark #app aside .fixed-section>div.mb-4+.space-y-4,
.dark #app aside .fixed-section>.space-y-4 {
display: flex !important;
flex-direction: column;
gap: 0 !important;
margin-top: 0 !important;
}
.dark #app aside .fixed-section > .space-y-4 > :not([hidden]) ~ :not([hidden]) {
.dark #app aside .fixed-section>.space-y-4> :not([hidden])~ :not([hidden]) {
margin-top: 0 !important;
}
.dark #app aside .fixed-section > .space-y-4 > :is(div, details) {
.dark #app aside .fixed-section>.space-y-4> :is(div, details) {
background: var(--m3-surface-container-high) !important;
border: 0 !important;
border-radius: 4px !important;
@@ -1349,20 +1356,20 @@ button.touch-none span.font-mono,
overflow: hidden;
}
.dark #app aside .fixed-section > .space-y-4 > :is(div, details):first-child {
.dark #app aside .fixed-section>.space-y-4> :is(div, details):first-child {
border-radius: 4px !important;
}
.dark #app aside .fixed-section > .space-y-4 > :is(div, details):last-child {
.dark #app aside .fixed-section>.space-y-4> :is(div, details):last-child {
border-radius: 4px 4px 24px 24px !important;
margin-bottom: 0 !important;
}
.dark #app aside .fixed-section > .space-y-4 > :is(div, details):first-child:last-child {
.dark #app aside .fixed-section>.space-y-4> :is(div, details):first-child:last-child {
border-radius: 4px 4px 24px 24px !important;
}
.dark #app aside .fixed-section > .space-y-4 > details.mt-3 {
.dark #app aside .fixed-section>.space-y-4>details.mt-3 {
margin-top: 0 !important;
}
@@ -1373,11 +1380,11 @@ button.touch-none span.font-mono,
border-color: var(--m3-outline-variant) !important;
}
#app aside .coeff-section > div.mb-3,
#app aside .coeff-section > details,
#app aside .fixed-section > div.mb-4,
#app aside .fixed-section > .space-y-4 > :is(div, details),
#app aside section > .space-y-3.bg-slate-100 {
#app aside .coeff-section>div.mb-3,
#app aside .coeff-section>details,
#app aside .fixed-section>div.mb-4,
#app aside .fixed-section>.space-y-4> :is(div, details),
#app aside section>.space-y-3.bg-slate-100 {
background: var(--m3-surface-container-high) !important;
border: 0 !important;
border-radius: 4px !important;
@@ -1386,38 +1393,38 @@ button.touch-none span.font-mono,
overflow: hidden;
}
#app aside section > .space-y-3.bg-slate-100 {
#app aside section>.space-y-3.bg-slate-100 {
border-radius: 24px !important;
}
#app aside .fixed-section > .space-y-4 {
#app aside .fixed-section>.space-y-4 {
display: flex !important;
flex-direction: column;
gap: 0 !important;
margin-top: 0 !important;
}
#app aside .fixed-section > .space-y-4 > :not([hidden]) ~ :not([hidden]) {
#app aside .fixed-section>.space-y-4> :not([hidden])~ :not([hidden]) {
margin-top: 0 !important;
}
#app aside .coeff-section > div.mb-3:first-of-type,
#app aside .fixed-section > div.mb-4 {
#app aside .coeff-section>div.mb-3:first-of-type,
#app aside .fixed-section>div.mb-4 {
border-radius: 24px 24px 4px 4px !important;
}
#app aside .coeff-section > details:last-of-type,
#app aside .fixed-section > .space-y-4 > :is(div, details):last-child {
#app aside .coeff-section>details:last-of-type,
#app aside .fixed-section>.space-y-4> :is(div, details):last-child {
border-radius: 4px 4px 24px 24px !important;
margin-bottom: 0 !important;
}
#app aside .fixed-section > .space-y-4 > :is(div, details):first-child {
#app aside .fixed-section>.space-y-4> :is(div, details):first-child {
border-radius: 4px !important;
}
#app aside .coeff-section > details.mt-3,
#app aside .fixed-section > .space-y-4 > details.mt-3 {
#app aside .coeff-section>details.mt-3,
#app aside .fixed-section>.space-y-4>details.mt-3 {
margin-top: 0 !important;
}
@@ -1451,14 +1458,17 @@ button.touch-none span.font-mono,
border-radius: 999px !important;
}
button.touch-none, details button.touch-none {
button.touch-none,
details button.touch-none {
background: var(--m3-secondary-container) !important;
border: 1px solid color-mix(in srgb, var(--m3-secondary) 28%, var(--m3-outline-variant)) !important;
color: var(--m3-on-secondary-container) !important;
border-radius: 999px !important;
min-height: 42px;
}
button.touch-none:hover, details button.touch-none:hover {
button.touch-none:hover,
details button.touch-none:hover {
background: color-mix(in srgb, var(--m3-secondary-container) 82%, var(--m3-primary) 18%) !important;
color: var(--m3-on-secondary-container) !important;
}
@@ -1558,6 +1568,7 @@ button.touch-none:hover, details button.touch-none:hover {
top: 0 !important;
right: 0 !important;
}
.modebar-container svg {
display: inline-block !important;
}
@@ -1574,4 +1585,4 @@ button.touch-none:hover, details button.touch-none:hover {
background: transparent !important;
border-color: transparent !important;
box-shadow: none !important;
}
}
+1 -1
View File
File diff suppressed because one or more lines are too long
+2 -2
View File
File diff suppressed because one or more lines are too long