Calendar/wwwroot/poc-produkt.html

1252 lines
34 KiB
HTML
Raw Permalink Normal View History

<!DOCTYPE html>
<html lang="da">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Produkt - Redken Acidic Bonding Concentrate Serum</title>
<link href="https://fonts.googleapis.com/css2?family=JetBrains+Mono:wght@400;500;600;700&display=swap" rel="stylesheet">
<style>
/* ==========================================
FONT FACE (Poppins)
========================================== */
@font-face {
font-family: 'Poppins';
src: url('fonts/Poppins-Regular.woff') format('woff');
font-weight: 400;
font-style: normal;
font-display: swap;
}
@font-face {
font-family: 'Poppins';
src: url('fonts/Poppins-Medium.woff') format('woff');
font-weight: 500;
font-style: normal;
font-display: swap;
}
@font-face {
font-family: 'Poppins';
src: url('fonts/Poppins-SemiBold.woff') format('woff');
font-weight: 600;
font-style: normal;
font-display: swap;
}
@font-face {
font-family: 'Poppins';
src: url('fonts/Poppins-Bold.woff') format('woff');
font-weight: 700;
font-style: normal;
font-display: swap;
}
/* ==========================================
CSS VARIABLES (Design System)
========================================== */
:root {
--color-surface: #fff;
--color-background: #f5f5f5;
--color-background-hover: #f0f0f0;
--color-background-alt: #fafafa;
--color-border: #e0e0e0;
--color-text: #333;
--color-text-secondary: #666;
--color-teal: #00897b;
--color-blue: #1976d2;
--color-red: #e53935;
--color-amber: #f59e0b;
--color-purple: #8b5cf6;
--color-green: #43a047;
--font-family: 'Poppins', -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
--font-mono: 'JetBrains Mono', monospace;
}
/* ==========================================
RESET & BASE
========================================== */
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
body {
font-family: var(--font-family);
font-size: 14px;
color: var(--color-text);
background: var(--color-background);
line-height: 1.5;
}
a {
color: var(--color-teal);
text-decoration: none;
}
a:hover {
text-decoration: underline;
}
/* ==========================================
TOPBAR
========================================== */
swp-topbar {
display: flex;
align-items: center;
justify-content: space-between;
padding: 12px 24px;
background: var(--color-surface);
border-bottom: 1px solid var(--color-border);
position: sticky;
top: 0;
z-index: 100;
}
swp-topbar-left {
display: flex;
align-items: center;
gap: 16px;
}
swp-back-link {
display: flex;
align-items: center;
gap: 6px;
color: var(--color-text-secondary);
text-decoration: none;
font-size: 13px;
cursor: pointer;
transition: color 150ms ease;
}
swp-back-link:hover {
color: var(--color-teal);
}
swp-back-link svg {
width: 16px;
height: 16px;
fill: currentColor;
}
swp-page-title {
font-size: 16px;
font-weight: 600;
}
swp-topbar-right {
display: flex;
align-items: center;
gap: 12px;
}
/* ==========================================
LAYOUT
========================================== */
swp-page-container {
display: block;
max-width: 1200px;
margin: 0 auto;
padding: 24px;
}
.grid-2 {
display: grid;
grid-template-columns: 1fr 1fr;
gap: 24px;
}
@media (max-width: 900px) {
.grid-2 { grid-template-columns: 1fr; }
}
/* ==========================================
CARDS
========================================== */
swp-card {
display: block;
background: var(--color-surface);
border-radius: 8px;
border: 1px solid var(--color-border);
margin-bottom: 20px;
overflow: hidden;
}
swp-card-header {
display: flex;
align-items: center;
justify-content: space-between;
padding: 14px 20px;
border-bottom: 1px solid var(--color-border);
}
swp-card-title {
font-size: 14px;
font-weight: 600;
color: var(--color-text);
}
swp-card-hint {
font-size: 12px;
color: var(--color-text-secondary);
}
swp-card-body {
display: block;
padding: 20px;
}
/* ==========================================
BUTTONS
========================================== */
swp-btn {
display: inline-flex;
align-items: center;
gap: 8px;
padding: 10px 18px;
font-size: 13px;
font-weight: 500;
font-family: var(--font-family);
border-radius: 6px;
cursor: pointer;
transition: all 150ms ease;
border: none;
}
swp-btn svg {
width: 16px;
height: 16px;
fill: currentColor;
}
swp-btn.primary {
background: var(--color-teal);
color: white;
}
swp-btn.primary:hover {
background: #00796b;
}
swp-btn.secondary {
background: var(--color-surface);
border: 1px solid var(--color-border);
color: var(--color-text);
}
swp-btn.secondary:hover {
background: var(--color-background-hover);
}
swp-btn.danger {
background: var(--color-surface);
border: 1px solid var(--color-border);
color: var(--color-red);
}
swp-btn.danger:hover {
background: color-mix(in srgb, var(--color-red) 10%, white);
}
swp-btn.small {
padding: 6px 12px;
font-size: 12px;
}
/* ==========================================
FORM ELEMENTS
========================================== */
swp-form-grid {
display: grid;
gap: 16px;
}
swp-form-row {
display: grid;
grid-template-columns: 1fr 1fr;
gap: 16px;
}
swp-form-field {
display: flex;
flex-direction: column;
gap: 6px;
}
swp-form-field.full {
grid-column: 1 / -1;
}
swp-form-label {
font-size: 12px;
font-weight: 500;
color: var(--color-text-secondary);
}
swp-form-field input,
swp-form-field select,
swp-form-field textarea {
padding: 10px 12px;
font-size: 14px;
font-family: var(--font-family);
border: 1px solid var(--color-border);
border-radius: 6px;
background: var(--color-surface);
color: var(--color-text);
}
swp-form-field input:focus,
swp-form-field select:focus,
swp-form-field textarea:focus {
outline: none;
border-color: var(--color-teal);
}
swp-form-field textarea {
min-height: 150px;
resize: vertical;
}
swp-form-field input.mono {
font-family: var(--font-mono);
}
swp-form-field input[readonly] {
background: var(--color-background-alt);
color: var(--color-text-secondary);
}
/* ==========================================
TOGGLE SLIDER (Ja/Nej)
========================================== */
swp-toggle-row {
display: flex;
align-items: center;
justify-content: space-between;
padding: 12px 0;
}
swp-toggle-label {
font-size: 14px;
font-weight: 500;
}
swp-toggle-slider {
display: inline-flex;
width: fit-content;
background: var(--color-background);
border-radius: 6px;
border: 1px solid var(--color-border);
position: relative;
cursor: pointer;
}
swp-toggle-slider::before {
content: '';
position: absolute;
top: 2px;
left: 2px;
width: calc(50% - 4px);
height: calc(100% - 4px);
background: color-mix(in srgb, var(--color-green) 18%, white);
border-radius: 4px;
transition: transform 200ms ease, background 200ms ease;
}
swp-toggle-slider[data-value="no"]::before {
transform: translateX(100%);
background: color-mix(in srgb, var(--color-red) 18%, white);
}
swp-toggle-option {
position: relative;
z-index: 1;
padding: 5px 16px;
font-size: 12px;
font-weight: 500;
color: var(--color-text-secondary);
transition: color 200ms ease;
user-select: none;
}
swp-toggle-slider[data-value="yes"] swp-toggle-option:first-child {
color: var(--color-green);
font-weight: 600;
}
swp-toggle-slider[data-value="no"] swp-toggle-option:last-child {
color: var(--color-red);
font-weight: 600;
}
/* ==========================================
VARIANTS TABLE
========================================== */
swp-variants-table {
display: block;
width: 100%;
}
swp-variants-header,
swp-variants-row {
display: grid;
grid-template-columns: 1fr 120px 80px 100px 80px;
align-items: center;
gap: 12px;
}
swp-variants-header {
padding: 10px 0;
border-bottom: 1px solid var(--color-border);
}
swp-variants-header span {
font-size: 11px;
font-weight: 600;
text-transform: uppercase;
letter-spacing: 0.5px;
color: var(--color-text-secondary);
}
swp-variants-header span.right {
text-align: right;
}
swp-variants-row {
padding: 12px 0;
border-bottom: 1px solid var(--color-border);
}
swp-variants-row:last-child {
border-bottom: none;
}
swp-variants-row span {
font-size: 14px;
}
swp-variants-row span.mono {
font-family: var(--font-mono);
font-size: 13px;
}
swp-variants-row span.right {
text-align: right;
}
swp-variants-row span.muted {
color: var(--color-text-secondary);
}
swp-variants-actions {
display: flex;
gap: 8px;
justify-content: flex-end;
}
swp-variants-actions button {
width: 28px;
height: 28px;
border: none;
background: var(--color-background);
border-radius: 4px;
cursor: pointer;
display: flex;
align-items: center;
justify-content: center;
transition: background 150ms ease;
}
swp-variants-actions button:hover {
background: var(--color-border);
}
swp-variants-actions button svg {
width: 14px;
height: 14px;
fill: var(--color-text-secondary);
}
swp-add-variant {
display: flex;
justify-content: center;
padding-top: 16px;
}
/* ==========================================
PRICE & MARGIN
========================================== */
swp-price-grid {
display: grid;
grid-template-columns: 1fr 1fr;
gap: 16px;
}
swp-margin-display {
display: flex;
gap: 24px;
padding: 16px;
background: var(--color-background-alt);
border-radius: 6px;
margin-top: 16px;
}
swp-margin-item {
display: flex;
flex-direction: column;
gap: 4px;
}
swp-margin-label {
font-size: 11px;
font-weight: 500;
text-transform: uppercase;
letter-spacing: 0.5px;
color: var(--color-text-secondary);
}
swp-margin-value {
font-size: 20px;
font-weight: 600;
font-family: var(--font-mono);
color: var(--color-green);
}
/* ==========================================
SALES STATS
========================================== */
swp-stats-row {
display: grid;
grid-template-columns: repeat(3, 1fr);
gap: 16px;
margin-bottom: 20px;
}
swp-stat-box {
display: flex;
flex-direction: column;
gap: 4px;
padding: 16px;
background: var(--color-background-alt);
border-radius: 6px;
}
swp-stat-box swp-stat-value {
font-size: 22px;
font-weight: 600;
font-family: var(--font-mono);
color: var(--color-text);
}
swp-stat-box swp-stat-label {
font-size: 11px;
font-weight: 500;
text-transform: uppercase;
letter-spacing: 0.5px;
color: var(--color-text-secondary);
}
swp-stat-box.highlight swp-stat-value {
color: var(--color-teal);
}
/* ==========================================
BAR CHART
========================================== */
swp-bar-chart {
display: flex;
align-items: flex-end;
gap: 8px;
height: 120px;
padding: 16px 0;
}
swp-bar-item {
display: flex;
flex-direction: column;
align-items: center;
gap: 8px;
flex: 1;
}
swp-bar {
width: 100%;
max-width: 40px;
background: var(--color-teal);
border-radius: 4px 4px 0 0;
transition: height 300ms ease;
}
swp-bar-label {
font-size: 11px;
color: var(--color-text-secondary);
}
swp-bar-value {
font-size: 11px;
font-weight: 600;
font-family: var(--font-mono);
color: var(--color-text);
}
/* ==========================================
PIE CHART
========================================== */
swp-chart-container {
display: flex;
align-items: center;
gap: 24px;
}
swp-pie-chart {
width: 100px;
height: 100px;
border-radius: 50%;
flex-shrink: 0;
}
swp-pie-legend {
display: flex;
flex-direction: column;
gap: 8px;
}
swp-legend-item {
display: flex;
align-items: center;
gap: 8px;
font-size: 13px;
}
swp-legend-color {
width: 12px;
height: 12px;
border-radius: 2px;
}
swp-legend-value {
font-family: var(--font-mono);
font-size: 12px;
color: var(--color-text-secondary);
margin-left: auto;
}
/* ==========================================
STOCK DISPLAY
========================================== */
swp-stock-display {
display: flex;
align-items: center;
gap: 24px;
margin-bottom: 20px;
}
swp-stock-current {
display: flex;
flex-direction: column;
gap: 4px;
}
swp-stock-number {
font-size: 36px;
font-weight: 700;
font-family: var(--font-mono);
color: var(--color-text);
line-height: 1;
}
swp-stock-number.warning {
color: var(--color-amber);
}
swp-stock-number.critical {
color: var(--color-red);
}
swp-stock-unit {
font-size: 12px;
color: var(--color-text-secondary);
}
swp-stock-status {
display: inline-flex;
align-items: center;
gap: 6px;
padding: 6px 12px;
font-size: 12px;
font-weight: 500;
border-radius: 20px;
}
swp-stock-status.ok {
background: color-mix(in srgb, var(--color-green) 15%, white);
color: var(--color-green);
}
swp-stock-status.warning {
background: color-mix(in srgb, var(--color-amber) 15%, white);
color: #b45309;
}
swp-stock-status.critical {
background: color-mix(in srgb, var(--color-red) 15%, white);
color: var(--color-red);
}
swp-stock-status::before {
content: '';
width: 6px;
height: 6px;
border-radius: 50%;
background: currentColor;
}
swp-stock-grid {
display: grid;
grid-template-columns: 1fr 1fr;
gap: 16px;
}
swp-stock-actions {
display: flex;
justify-content: flex-end;
padding-top: 16px;
border-top: 1px solid var(--color-border);
margin-top: 16px;
}
/* ==========================================
SUPPLIER INFO
========================================== */
swp-supplier-grid {
display: grid;
gap: 16px;
}
/* ==========================================
USAGE LIST
========================================== */
swp-usage-list {
display: flex;
flex-direction: column;
gap: 8px;
}
swp-usage-item {
display: flex;
align-items: center;
justify-content: space-between;
padding: 10px 12px;
background: var(--color-background-alt);
border-radius: 6px;
}
swp-usage-name {
font-size: 14px;
color: var(--color-text);
}
swp-usage-amount {
font-size: 13px;
font-family: var(--font-mono);
color: var(--color-text-secondary);
}
/* ==========================================
MOVEMENT TABLE
========================================== */
swp-movement-table {
display: block;
width: 100%;
}
swp-movement-header,
swp-movement-row {
display: grid;
grid-template-columns: 110px 90px 70px 1fr 140px;
align-items: center;
gap: 12px;
}
swp-movement-header {
padding: 10px 0;
border-bottom: 1px solid var(--color-border);
}
swp-movement-header span {
font-size: 11px;
font-weight: 600;
text-transform: uppercase;
letter-spacing: 0.5px;
color: var(--color-text-secondary);
}
swp-movement-row {
padding: 12px 0;
border-bottom: 1px solid var(--color-border);
}
swp-movement-row:last-child {
border-bottom: none;
}
swp-movement-row span {
font-size: 13px;
}
swp-movement-row span.positive {
color: var(--color-green);
font-family: var(--font-mono);
font-weight: 500;
}
swp-movement-row span.negative {
color: var(--color-red);
font-family: var(--font-mono);
font-weight: 500;
}
swp-movement-type {
display: inline-flex;
align-items: center;
gap: 6px;
padding: 4px 8px;
font-size: 11px;
font-weight: 500;
border-radius: 4px;
}
swp-movement-type.sale {
background: color-mix(in srgb, var(--color-blue) 15%, white);
color: var(--color-blue);
}
swp-movement-type.purchase {
background: color-mix(in srgb, var(--color-green) 15%, white);
color: var(--color-green);
}
swp-movement-type.treatment {
background: color-mix(in srgb, var(--color-purple) 15%, white);
color: var(--color-purple);
}
swp-movement-link {
font-size: 13px;
}
swp-section-title {
font-size: 12px;
font-weight: 600;
text-transform: uppercase;
letter-spacing: 0.5px;
color: var(--color-text-secondary);
margin-bottom: 12px;
display: block;
}
</style>
</head>
<body>
<!-- Topbar -->
<swp-topbar>
<swp-topbar-left>
<swp-back-link>
<svg viewBox="0 0 24 24"><path d="M20 11H7.83l5.59-5.59L12 4l-8 8 8 8 1.41-1.41L7.83 13H20v-2z"/></svg>
Produkter
</swp-back-link>
<swp-page-title>Redken Acidic Bonding Concentrate 24/7 Night & Day Serum</swp-page-title>
</swp-topbar-left>
<swp-topbar-right>
<swp-btn class="danger">
<svg viewBox="0 0 24 24"><path d="M6 19c0 1.1.9 2 2 2h8c1.1 0 2-.9 2-2V7H6v12zM19 4h-3.5l-1-1h-5l-1 1H5v2h14V4z"/></svg>
Slet
</swp-btn>
<swp-btn class="primary">
<svg viewBox="0 0 24 24"><path d="M17 3H5c-1.11 0-2 .9-2 2v14c0 1.1.89 2 2 2h14c1.1 0 2-.9 2-2V7l-4-4zm-5 16c-1.66 0-3-1.34-3-3s1.34-3 3-3 3 1.34 3 3-1.34 3-3 3zm3-10H5V5h10v4z"/></svg>
Gem ændringer
</swp-btn>
</swp-topbar-right>
</swp-topbar>
<swp-page-container>
<div class="grid-2">
<!-- VENSTRE KOLONNE -->
<div>
<!-- Basisoplysninger -->
<swp-card>
<swp-card-header>
<swp-card-title>Basisoplysninger</swp-card-title>
</swp-card-header>
<swp-card-body>
<swp-form-grid>
<swp-form-field class="full">
<swp-form-label>Produktnavn</swp-form-label>
<input type="text" value="Redken Acidic Bonding Concentrate 24/7 Night & Day Serum 100 ml" />
</swp-form-field>
<swp-form-row>
<swp-form-field>
<swp-form-label>Varenummer</swp-form-label>
<input type="text" class="mono" value="RDK-ABC-100" />
</swp-form-field>
<swp-form-field>
<swp-form-label>EAN / Stregkode</swp-form-label>
<input type="text" class="mono" value="884486532879" />
</swp-form-field>
</swp-form-row>
<swp-form-row>
<swp-form-field>
<swp-form-label>Kategori</swp-form-label>
<select>
<option selected>Hårpleje</option>
<option>Styling</option>
<option>Farve</option>
<option>Tilbehør</option>
</select>
</swp-form-field>
<swp-form-field>
<swp-form-label>Brand</swp-form-label>
<select>
<option selected>Redken</option>
<option>Olaplex</option>
<option>Kérastase</option>
<option>Wella</option>
</select>
</swp-form-field>
</swp-form-row>
<swp-form-field class="full">
<swp-form-label>Beskrivelse</swp-form-label>
<textarea>Et plejende og styrkende reparationsserum, der arbejder kontinuerligt for at genopbygge svækket hårstruktur. Tilfører fugt og glans uden at tynge, og efterlader håret mere elastisk og sundt over tid. Særligt effektivt til skadet, farvebehandlet eller kemisk behandlet hår.
Fordel 1-2 pump i håndklædetørt eller tørt hår. Skal ikke skylles ud. Kan bruges dagligt og som natpleje for intensiv reparation.</textarea>
</swp-form-field>
<swp-toggle-row>
<swp-toggle-label>Produkt aktiv</swp-toggle-label>
<swp-toggle-slider data-value="yes">
<swp-toggle-option>Ja</swp-toggle-option>
<swp-toggle-option>Nej</swp-toggle-option>
</swp-toggle-slider>
</swp-toggle-row>
</swp-form-grid>
</swp-card-body>
</swp-card>
<!-- Varianter -->
<swp-card>
<swp-card-header>
<swp-card-title>Varianter</swp-card-title>
<swp-card-hint>Størrelser og variationer</swp-card-hint>
</swp-card-header>
<swp-card-body>
<swp-variants-table>
<swp-variants-header>
<span>Variant</span>
<span>Varenr</span>
<span class="right">Lager</span>
<span class="right">Pris</span>
<span></span>
</swp-variants-header>
<swp-variants-row>
<span>100 ml</span>
<span class="mono muted">RDK-ABC-100</span>
<span class="mono right">6</span>
<span class="mono right">379 kr</span>
<swp-variants-actions>
<button title="Rediger"><svg viewBox="0 0 24 24"><path d="M3 17.25V21h3.75L17.81 9.94l-3.75-3.75L3 17.25zM20.71 7.04c.39-.39.39-1.02 0-1.41l-2.34-2.34c-.39-.39-1.02-.39-1.41 0l-1.83 1.83 3.75 3.75 1.83-1.83z"/></svg></button>
<button title="Slet"><svg viewBox="0 0 24 24"><path d="M6 19c0 1.1.9 2 2 2h8c1.1 0 2-.9 2-2V7H6v12zM19 4h-3.5l-1-1h-5l-1 1H5v2h14V4z"/></svg></button>
</swp-variants-actions>
</swp-variants-row>
<swp-variants-row>
<span>50 ml (rejsestørrelse)</span>
<span class="mono muted">RDK-ABC-050</span>
<span class="mono right">4</span>
<span class="mono right">219 kr</span>
<swp-variants-actions>
<button title="Rediger"><svg viewBox="0 0 24 24"><path d="M3 17.25V21h3.75L17.81 9.94l-3.75-3.75L3 17.25zM20.71 7.04c.39-.39.39-1.02 0-1.41l-2.34-2.34c-.39-.39-1.02-.39-1.41 0l-1.83 1.83 3.75 3.75 1.83-1.83z"/></svg></button>
<button title="Slet"><svg viewBox="0 0 24 24"><path d="M6 19c0 1.1.9 2 2 2h8c1.1 0 2-.9 2-2V7H6v12zM19 4h-3.5l-1-1h-5l-1 1H5v2h14V4z"/></svg></button>
</swp-variants-actions>
</swp-variants-row>
</swp-variants-table>
<swp-add-variant>
<swp-btn class="secondary small">+ Tilføj variant</swp-btn>
</swp-add-variant>
</swp-card-body>
</swp-card>
<!-- Pris & avance -->
<swp-card>
<swp-card-header>
<swp-card-title>Pris & avance</swp-card-title>
</swp-card-header>
<swp-card-body>
<swp-price-grid>
<swp-form-field>
<swp-form-label>Indkøbspris (ekskl. moms)</swp-form-label>
<input type="text" class="mono" value="195,00 kr" />
</swp-form-field>
<swp-form-field>
<swp-form-label>Salgspris (inkl. moms)</swp-form-label>
<input type="text" class="mono" value="379,00 kr" />
</swp-form-field>
</swp-price-grid>
<swp-margin-display>
<swp-margin-item>
<swp-margin-label>Avance</swp-margin-label>
<swp-margin-value>108,20 kr</swp-margin-value>
</swp-margin-item>
<swp-margin-item>
<swp-margin-label>Avance %</swp-margin-label>
<swp-margin-value>35,7%</swp-margin-value>
</swp-margin-item>
</swp-margin-display>
</swp-card-body>
</swp-card>
<!-- Forbrug i behandlinger -->
<swp-card>
<swp-card-header>
<swp-card-title>Bruges i behandlinger</swp-card-title>
</swp-card-header>
<swp-card-body>
<swp-usage-list>
<swp-usage-item>
<swp-usage-name>Acidic Bonding Behandling</swp-usage-name>
<swp-usage-amount>5 ml pr. behandling</swp-usage-amount>
</swp-usage-item>
<swp-usage-item>
<swp-usage-name>Reparerende Hårpleje</swp-usage-name>
<swp-usage-amount>3 ml pr. behandling</swp-usage-amount>
</swp-usage-item>
</swp-usage-list>
</swp-card-body>
</swp-card>
</div>
<!-- HØJRE KOLONNE -->
<div>
<!-- Salgsstatistik -->
<swp-card>
<swp-card-header>
<swp-card-title>Salgsstatistik</swp-card-title>
<swp-card-hint>Sidste 6 måneder</swp-card-hint>
</swp-card-header>
<swp-card-body>
<swp-stats-row>
<swp-stat-box class="highlight">
<swp-stat-value>32</swp-stat-value>
<swp-stat-label>Solgt i alt</swp-stat-label>
</swp-stat-box>
<swp-stat-box>
<swp-stat-value>12.128 kr</swp-stat-value>
<swp-stat-label>Omsætning</swp-stat-label>
</swp-stat-box>
<swp-stat-box>
<swp-stat-value>3.462 kr</swp-stat-value>
<swp-stat-label>Avance</swp-stat-label>
</swp-stat-box>
</swp-stats-row>
<swp-section-title>Salg pr. måned</swp-section-title>
<div id="salesBarChart"></div>
</swp-card-body>
</swp-card>
<!-- Salg pr. variant -->
<swp-card>
<swp-card-header>
<swp-card-title>Salg pr. variant</swp-card-title>
</swp-card-header>
<swp-card-body>
<div id="variantPieChart"></div>
</swp-card-body>
</swp-card>
<!-- Lager -->
<swp-card>
<swp-card-header>
<swp-card-title>Lager</swp-card-title>
</swp-card-header>
<swp-card-body>
<swp-stock-display>
<swp-stock-current>
<swp-stock-number>10</swp-stock-number>
<swp-stock-unit>stk. på lager (alle varianter)</swp-stock-unit>
</swp-stock-current>
<swp-stock-status class="ok">På lager</swp-stock-status>
</swp-stock-display>
<swp-stock-grid>
<swp-form-field>
<swp-form-label>Minimumslager</swp-form-label>
<input type="number" value="5" />
</swp-form-field>
<swp-form-field>
<swp-form-label>Genbestillingspunkt</swp-form-label>
<input type="number" value="10" />
</swp-form-field>
</swp-stock-grid>
<swp-stock-actions>
<swp-btn class="secondary small">
<svg viewBox="0 0 24 24"><path d="M19 3H5c-1.1 0-2 .9-2 2v14c0 1.1.9 2 2 2h14c1.1 0 2-.9 2-2V5c0-1.1-.9-2-2-2zm-2 10h-4v4h-2v-4H7v-2h4V7h2v4h4v2z"/></svg>
Juster lager
</swp-btn>
</swp-stock-actions>
</swp-card-body>
</swp-card>
<!-- Leverandør -->
<swp-card>
<swp-card-header>
<swp-card-title>Leverandør</swp-card-title>
</swp-card-header>
<swp-card-body>
<swp-supplier-grid>
<swp-form-field>
<swp-form-label>Leverandør</swp-form-label>
<select>
<option selected>L'Oréal Professionnel</option>
<option>Beauty Group Denmark</option>
<option>Hairware ApS</option>
</select>
</swp-form-field>
<swp-form-row>
<swp-form-field>
<swp-form-label>Leverandør varenr</swp-form-label>
<input type="text" class="mono" value="E3845600" />
</swp-form-field>
<swp-form-field>
<swp-form-label>Leveringstid</swp-form-label>
<input type="text" value="3-5 dage" />
</swp-form-field>
</swp-form-row>
<swp-form-field>
<swp-form-label>Sidste indkøb</swp-form-label>
<input type="text" readonly value="15. december 2025" />
</swp-form-field>
</swp-supplier-grid>
</swp-card-body>
</swp-card>
</div>
</div>
<!-- Lagerbevægelser (full width) -->
<swp-card>
<swp-card-header>
<swp-card-title>Lagerbevægelser</swp-card-title>
<swp-card-hint>Seneste aktivitet</swp-card-hint>
</swp-card-header>
<swp-card-body>
<swp-movement-table>
<swp-movement-header>
<span>Dato</span>
<span>Type</span>
<span>Antal</span>
<span>Reference</span>
<span></span>
</swp-movement-header>
<swp-movement-row>
<span>28. dec 2025</span>
<swp-movement-type class="sale">Salg</swp-movement-type>
<span class="negative">-1</span>
<span>Faktura #1847</span>
<swp-movement-link><a href="#">Marie Hansen →</a></swp-movement-link>
</swp-movement-row>
<swp-movement-row>
<span>27. dec 2025</span>
<swp-movement-type class="sale">Salg</swp-movement-type>
<span class="negative">-2</span>
<span>Faktura #1842</span>
<swp-movement-link><a href="#">Louise Andersen →</a></swp-movement-link>
</swp-movement-row>
<swp-movement-row>
<span>22. dec 2025</span>
<swp-movement-type class="treatment">Behandling</swp-movement-type>
<span class="negative">-1</span>
<span>Booking #B-2341</span>
<swp-movement-link><a href="#">Se booking →</a></swp-movement-link>
</swp-movement-row>
<swp-movement-row>
<span>15. dec 2025</span>
<swp-movement-type class="purchase">Indkøb</swp-movement-type>
<span class="positive">+12</span>
<span>Ordre #LOR-8834</span>
<swp-movement-link><a href="#">L'Oréal Prof. →</a></swp-movement-link>
</swp-movement-row>
<swp-movement-row>
<span>10. dec 2025</span>
<swp-movement-type class="sale">Salg</swp-movement-type>
<span class="negative">-1</span>
<span>Faktura #1798</span>
<swp-movement-link><a href="#">Camilla Jensen →</a></swp-movement-link>
</swp-movement-row>
</swp-movement-table>
</swp-card-body>
</swp-card>
</swp-page-container>
<script type="module">
import { createChart } from '../node_modules/@sevenweirdpeople/swp-charting/dist/swp-charting.js';
// Toggle slider (Ja/Nej)
document.querySelectorAll('swp-toggle-slider').forEach(slider => {
const options = slider.querySelectorAll('swp-toggle-option');
options.forEach((option, index) => {
option.addEventListener('click', () => {
slider.dataset.value = index === 0 ? 'yes' : 'no';
});
});
});
// Bar chart - Salg pr. måned
const barContainer = document.getElementById('salesBarChart');
createChart(barContainer, {
height: 160,
series: [{
name: 'Salg',
color: '#00897b',
type: 'bar',
unit: 'stk',
data: [
{ x: 'Jul', y: 5 },
{ x: 'Aug', y: 8 },
{ x: 'Sep', y: 6 },
{ x: 'Okt', y: 9 },
{ x: 'Nov', y: 12 },
{ x: 'Dec', y: 7 }
],
bar: { radius: 4 }
}],
xAxis: {
categories: ['Jul', 'Aug', 'Sep', 'Okt', 'Nov', 'Dec']
},
yAxis: {
min: 0,
ticks: 4
},
padding: { top: 20, right: 10, bottom: 30, left: 35 },
tooltip: true,
legend: false,
animation: { duration: 400 }
});
// Pie chart - Salg pr. variant
const pieContainer = document.getElementById('variantPieChart');
createChart(pieContainer, {
height: 200,
series: [
{ name: '100 ml', color: '#00897b', type: 'pie', data: [{ x: '', y: 23 }], unit: 'stk' },
{ name: '50 ml', color: '#8b5cf6', type: 'pie', data: [{ x: '', y: 9 }], unit: 'stk' }
],
tooltip: true,
legend: { position: 'right', align: 'center' },
animation: { duration: 400 }
});
</script>
</body>
</html>