feat(ui): helpers pos-utils.js (barcode feedback, saved filters, resizable columns, density/touch toggles, notifications dropdown, ticket preview, image comparator, infinite scroll, sparklines) + inventory.html modals + pos-ui.css timeline & kanban

This commit is contained in:
2026-05-26 09:28:35 +00:00
parent 61bf84b2dc
commit 68d6f81671
4 changed files with 403 additions and 0 deletions

View File

@@ -5,6 +5,40 @@
* Load AFTER tokens.css and common.css, BEFORE page-specific CSS.
*/
/* ═══════════════════════════════════════════════════════════════
0. ICON BUTTONS (header bar)
═══════════════════════════════════════════════════════════════ */
.icon-btn {
display: inline-flex;
align-items: center;
justify-content: center;
width: 32px;
height: 32px;
border-radius: var(--radius-md, 8px);
background: var(--color-surface-2, #222);
border: 1px solid var(--color-border, #2a2a2a);
color: var(--color-text-secondary, #aaa);
cursor: pointer;
transition: all 0.15s;
position: relative;
}
.icon-btn:hover {
background: var(--color-surface-3, #333);
color: var(--color-text-primary, #eee);
border-color: var(--color-primary, #F5A623);
}
.notif-dot {
position: absolute;
top: 4px;
right: 4px;
width: 8px;
height: 8px;
border-radius: 50%;
background: var(--color-error, #ef4444);
box-shadow: 0 0 4px var(--color-error, #ef4444);
}
.notif-dot:empty { display: none; }
/* ═══════════════════════════════════════════════════════════════
1. CUSTOM SCROLLBAR (global)
═══════════════════════════════════════════════════════════════ */
@@ -720,6 +754,36 @@ input:disabled, select:disabled, textarea:disabled {
.nx-loader--sm .nx-loader__ring:nth-child(2) { inset: 4px; }
.nx-loader--sm .nx-loader__ring:nth-child(3) { inset: 8px; }
/* ═══════════════════════════════════════════════════════════════
21. TIMELINE
═══════════════════════════════════════════════════════════════ */
.timeline { position: relative; padding-left: 24px; }
.timeline::before { content: ''; position: absolute; left: 7px; top: 4px; bottom: 4px; width: 2px; background: var(--color-border, #2a2a2a); }
.timeline__item { position: relative; margin-bottom: var(--space-4, 1rem); display: flex; gap: 12px; align-items: flex-start; }
.timeline__dot { width: 14px; height: 14px; border-radius: 50%; background: var(--color-primary, #F5A623); border: 3px solid var(--color-surface-1, #1a1a1a); flex-shrink: 0; margin-left: -24px; margin-top: 3px; z-index: 1; }
.timeline__dot--green { background: var(--color-success, #22c55e); }
.timeline__dot--red { background: var(--color-error, #ef4444); }
.timeline__dot--blue { background: #3b82f6; }
.timeline__content { flex: 1; }
.timeline__date { font-size: 11px; color: var(--color-text-muted, #888); margin-bottom: 2px; }
.timeline__title { font-size: 13px; font-weight: 600; color: var(--color-text-primary, #eee); }
.timeline__desc { font-size: 12px; color: var(--color-text-secondary, #aaa); margin-top: 2px; }
/* ═══════════════════════════════════════════════════════════════
22. KANBAN BOARD
═══════════════════════════════════════════════════════════════ */
.kanban { display: flex; gap: var(--space-4, 1rem); overflow-x: auto; padding-bottom: var(--space-2, 0.5rem); }
.kanban__col { min-width: 280px; max-width: 320px; flex: 1; background: var(--color-surface-2, #222); border-radius: var(--radius-lg, 12px); border: 1px solid var(--color-border, #2a2a2a); display: flex; flex-direction: column; max-height: 70vh; }
.kanban__col-header { padding: 12px 16px; border-bottom: 1px solid var(--color-border, #2a2a2a); font-size: 13px; font-weight: 700; display: flex; justify-content: space-between; align-items: center; }
.kanban__col-count { font-size: 11px; padding: 2px 8px; border-radius: var(--radius-full, 999px); background: var(--color-surface-3, #333); color: var(--color-text-muted, #888); }
.kanban__cards { flex: 1; overflow-y: auto; padding: var(--space-3, 0.75rem); display: flex; flex-direction: column; gap: var(--space-2, 0.5rem); }
.kanban__card { background: var(--color-surface-1, #1a1a1a); border: 1px solid var(--color-border, #2a2a2a); border-radius: var(--radius-md, 8px); padding: 12px; cursor: grab; transition: all 0.15s; }
.kanban__card:hover { border-color: var(--color-primary, #F5A623); transform: translateY(-1px); }
.kanban__card-title { font-size: 13px; font-weight: 600; margin-bottom: 4px; }
.kanban__card-meta { font-size: 11px; color: var(--color-text-muted, #888); }
.kanban__card.dragging { opacity: 0.5; cursor: grabbing; }
.kanban__col.drag-over { background: var(--color-surface-3, #333); border-color: var(--color-primary, #F5A623); }
/* ═══════════════════════════════════════════════════════════════
25. SAVED FILTERS CHIPS
═══════════════════════════════════════════════════════════════ */