Metric bar and CPU bar improvements

This commit is contained in:
rcourtman 2025-12-07 00:27:47 +00:00
parent fc8d88a7c7
commit c0da4768bb
5 changed files with 28 additions and 41 deletions

View file

@ -47,6 +47,7 @@ export function EnhancedCPUBar(props: EnhancedCPUBarProps) {
<Show <Show
when={viewMode() === 'sparklines' && props.resourceId} when={viewMode() === 'sparklines' && props.resourceId}
fallback={ fallback={
// Progress bar mode - full width, flex centered like stacked bars
<div ref={containerRef} class="metric-text w-full h-4 flex items-center justify-center"> <div ref={containerRef} class="metric-text w-full h-4 flex items-center justify-center">
<div <div
class="relative w-full h-full overflow-hidden bg-gray-200 dark:bg-gray-600 rounded cursor-help" class="relative w-full h-full overflow-hidden bg-gray-200 dark:bg-gray-600 rounded cursor-help"
@ -112,21 +113,14 @@ export function EnhancedCPUBar(props: EnhancedCPUBarProps) {
</div> </div>
} }
> >
{/* Sparkline mode - scales to fill column width, matching bar mode */} {/* Sparkline mode - full width, flex centered like stacked bars */}
<div class="metric-text w-full h-6 flex items-center justify-center"> <div class="metric-text w-full h-4 flex items-center justify-center">
<div class="flex items-center gap-1.5 w-full"> <Sparkline
<div class="flex-1 min-w-0 h-6"> data={metricHistory()}
<Sparkline metric="cpu"
data={metricHistory()} width={0}
metric="cpu" height={16}
width={0} />
height={24}
/>
</div>
<span class="text-[10px] font-medium text-gray-800 dark:text-gray-100 whitespace-nowrap flex-shrink-0 w-[35px] text-right">
{formatPercent(props.usage)}
</span>
</div>
</div> </div>
</Show> </Show>
); );

View file

@ -979,7 +979,7 @@ export function GuestRow(props: GuestRowProps) {
{/* CPU */} {/* CPU */}
<Show when={isColVisible('cpu')}> <Show when={isColVisible('cpu')}>
<td class="px-2 py-1 align-middle" style={{ "min-width": "140px" }}> <td class="px-2 py-1 align-middle" style={{ width: "140px", "min-width": "140px", "max-width": "140px" }}>
<Show when={isMobile()}> <Show when={isMobile()}>
<div class="md:hidden flex justify-center"> <div class="md:hidden flex justify-center">
<ResponsiveMetricCell <ResponsiveMetricCell
@ -1015,7 +1015,7 @@ export function GuestRow(props: GuestRowProps) {
{/* Memory */} {/* Memory */}
<Show when={isColVisible('memory')}> <Show when={isColVisible('memory')}>
<td class="px-2 py-1 align-middle" style={{ "min-width": "140px" }}> <td class="px-2 py-1 align-middle" style={{ width: "140px", "min-width": "140px", "max-width": "140px" }}>
<div title={memoryTooltip() ?? undefined}> <div title={memoryTooltip() ?? undefined}>
<Show when={isMobile()}> <Show when={isMobile()}>
<div class="md:hidden flex justify-center"> <div class="md:hidden flex justify-center">
@ -1058,7 +1058,7 @@ export function GuestRow(props: GuestRowProps) {
{/* Disk */} {/* Disk */}
<Show when={isColVisible('disk')}> <Show when={isColVisible('disk')}>
<td class="px-2 py-1 align-middle" style={{ "min-width": "140px" }}> <td class="px-2 py-1 align-middle" style={{ width: "140px", "min-width": "140px", "max-width": "140px" }}>
<Show <Show
when={hasDiskUsage()} when={hasDiskUsage()}
fallback={ fallback={

View file

@ -102,7 +102,7 @@ export function MetricBar(props: MetricBarProps) {
<Show <Show
when={viewMode() === 'sparklines' && props.resourceId} when={viewMode() === 'sparklines' && props.resourceId}
fallback={ fallback={
// Progress bar mode - scales to fill column width // Progress bar mode - full width, flex centered like stacked bars
<div ref={containerRef} class="metric-text w-full h-4 flex items-center justify-center"> <div ref={containerRef} class="metric-text w-full h-4 flex items-center justify-center">
<div class={`relative w-full h-full overflow-hidden bg-gray-200 dark:bg-gray-600 rounded ${props.class || ''}`}> <div class={`relative w-full h-full overflow-hidden bg-gray-200 dark:bg-gray-600 rounded ${props.class || ''}`}>
<div class={`absolute top-0 left-0 h-full ${progressColorClass()}`} style={{ width: `${width()}%` }} /> <div class={`absolute top-0 left-0 h-full ${progressColorClass()}`} style={{ width: `${width()}%` }} />
@ -120,21 +120,14 @@ export function MetricBar(props: MetricBarProps) {
</div> </div>
} }
> >
{/* Sparkline mode - scales to fill column width, matching bar mode sizing */} {/* Sparkline mode - full width, flex centered like stacked bars */}
<div class="metric-text w-full h-6 flex items-center justify-center"> <div class="metric-text w-full h-4 flex items-center justify-center">
<div class="flex items-center gap-1.5 w-full"> <Sparkline
<div class="flex-1 min-w-0 h-6"> data={metricHistory()}
<Sparkline metric={sparklineMetric()}
data={metricHistory()} width={0}
metric={sparklineMetric()} height={16}
width={0} />
height={24}
/>
</div>
<span class="text-[10px] font-medium text-gray-800 dark:text-gray-100 whitespace-nowrap flex-shrink-0 w-[35px] text-right">
{props.label}
</span>
</div>
</div> </div>
</Show> </Show>
); );

View file

@ -354,13 +354,13 @@ export const NodeSummaryTable: Component<NodeSummaryTableProps> = (props) => {
<th class={thClass} style={{ "min-width": '80px' }} onClick={() => handleSort('uptime')}> <th class={thClass} style={{ "min-width": '80px' }} onClick={() => handleSort('uptime')}>
Uptime {renderSortIndicator('uptime')} Uptime {renderSortIndicator('uptime')}
</th> </th>
<th class={thClass} style={{ "min-width": '140px' }} onClick={() => handleSort('cpu')}> <th class={thClass} style={{ width: "200px", "min-width": "200px", "max-width": "200px" }} onClick={() => handleSort('cpu')}>
CPU {renderSortIndicator('cpu')} CPU {renderSortIndicator('cpu')}
</th> </th>
<th class={thClass} style={{ "min-width": '140px' }} onClick={() => handleSort('memory')}> <th class={thClass} style={{ width: "200px", "min-width": "200px", "max-width": "200px" }} onClick={() => handleSort('memory')}>
Memory {renderSortIndicator('memory')} Memory {renderSortIndicator('memory')}
</th> </th>
<th class={thClass} style={{ "min-width": '140px' }} onClick={() => handleSort('disk')}> <th class={thClass} style={{ width: "200px", "min-width": "200px", "max-width": "200px" }} onClick={() => handleSort('disk')}>
Disk {renderSortIndicator('disk')} Disk {renderSortIndicator('disk')}
</th> </th>
<Show when={hasAnyTemperatureData()}> <Show when={hasAnyTemperatureData()}>
@ -561,7 +561,7 @@ export const NodeSummaryTable: Component<NodeSummaryTableProps> = (props) => {
</td> </td>
{/* CPU */} {/* CPU */}
<td class="px-2 py-1 align-middle" style={{ "min-width": "140px" }}> <td class="px-2 py-1 align-middle" style={{ width: "200px", "min-width": "200px", "max-width": "200px" }}>
<Show when={isMobile()}> <Show when={isMobile()}>
<div class="md:hidden flex justify-center"> <div class="md:hidden flex justify-center">
<MetricText value={cpuPercentValue} type="cpu" /> <MetricText value={cpuPercentValue} type="cpu" />
@ -589,7 +589,7 @@ export const NodeSummaryTable: Component<NodeSummaryTableProps> = (props) => {
</td> </td>
{/* Memory */} {/* Memory */}
<td class="px-2 py-1 align-middle" style={{ "min-width": "140px" }}> <td class="px-2 py-1 align-middle" style={{ width: "200px", "min-width": "200px", "max-width": "200px" }}>
<Show when={isMobile()}> <Show when={isMobile()}>
<div class="md:hidden flex justify-center"> <div class="md:hidden flex justify-center">
<MetricText value={memoryPercentValue} type="memory" /> <MetricText value={memoryPercentValue} type="memory" />
@ -631,7 +631,7 @@ export const NodeSummaryTable: Component<NodeSummaryTableProps> = (props) => {
</td> </td>
{/* Disk */} {/* Disk */}
<td class="px-2 py-1 align-middle" style={{ "min-width": "140px" }}> <td class="px-2 py-1 align-middle" style={{ width: "200px", "min-width": "200px", "max-width": "200px" }}>
<ResponsiveMetricCell <ResponsiveMetricCell
value={diskPercentValue} value={diskPercentValue}
type="disk" type="disk"

View file

@ -41,7 +41,7 @@ export const Sparkline: Component<SparklineProps> = (props) => {
} }
return props.width || 120; return props.width || 120;
}; };
const height = () => props.height || 24; const height = () => props.height || 16;
// Default thresholds based on metric type // Default thresholds based on metric type
const getDefaultThresholds = () => { const getDefaultThresholds = () => {