[object Object]

← back to Dw Activation Calendar

calendar viewer: mat_tier texture pill/tooltip passthrough (unified schedule); back-compat with legacy fix_type fallback

1dcdfc5e4a9dffe9a2657828a2382ed16ecc6824 · 2026-07-21 13:00:35 -0700 · Steve Abrams

Files touched

Diff

commit 1dcdfc5e4a9dffe9a2657828a2382ed16ecc6824
Author: Steve Abrams <steve@designerwallcoverings.com>
Date:   Tue Jul 21 13:00:35 2026 -0700

    calendar viewer: mat_tier texture pill/tooltip passthrough (unified schedule); back-compat with legacy fix_type fallback
---
 public/index.html | 10 ++++++----
 server.js         |  8 ++++++--
 2 files changed, 12 insertions(+), 6 deletions(-)

diff --git a/public/index.html b/public/index.html
index 1770d23..af36612 100644
--- a/public/index.html
+++ b/public/index.html
@@ -590,7 +590,7 @@ function openVendorList(vendor){
       : `<div class="ph" style="background:${vcolor(vendor)}">${esc(vendor.slice(0,3).toUpperCase())}</div>`;
     return `<div class="vrow"><div class="vthumb">${img}</div>
       <div class="vmeta"><div class="vlabel">${esc(s.title||skuLabel(s))}</div>
-        <div class="vsub">${esc(skuLabel(s))} · ${esc(s.fix_type)}</div></div>
+        <div class="vsub">${esc(skuLabel(s))}${s.mat_tier===0?' · texture':(s.fix_type?' · '+esc(s.fix_type):'')}</div></div>
       <input type="date" class="vdate" data-key="${esc(key)}" value="${esc((s.go_live_at||'').slice(0,10))}" title="reschedule go-live"></div>`;
   }).join('');
   const body=`<div class="mform vlist"><div class="mhead"><div class="mtitle">${esc(vendor)} — ${items.length.toLocaleString()} staged</div><button type="button" class="mclose" id="vl_x" aria-label="Close">✕</button></div>
@@ -635,7 +635,9 @@ function openSkuModal(s){
       <dt>Vendor</dt><dd>${esc(s.vendor)}</dd>
       ${s.dw_sku?`<dt>DW SKU</dt><dd><code>${esc(s.dw_sku)}</code></dd>`:''}
       ${s.mfr_sku?`<dt>Mfr SKU</dt><dd><code>${esc(s.mfr_sku)}</code></dd>`:''}
-      <dt>Build step</dt><dd><span class="fxpill ${fx}"><span class="d"></span>${esc(s.fix_type)}</span></dd>
+      ${s.mat_tier!=null
+        ? `<dt>Tier</dt><dd><span class="fxpill ${s.mat_tier===0?'s':'r'}"><span class="d"></span>${s.mat_tier===0?'texture (goes first)':'standard'}</span></dd>`
+        : (s.fix_type?`<dt>Build step</dt><dd><span class="fxpill ${fx}"><span class="d"></span>${esc(s.fix_type)}</span></dd>`:'')}
       <dt>Goes active</dt><dd title="${esc(s.go_live_at||'')}">⏱ ${fmtGoLive(s.go_live_at)}${s.slot_hour!=null?' · '+slotLabel(s.slot_hour)+' slot':''}</dd>
       ${idNum?`<dt>Shopify ID</dt><dd><code>${esc(idNum)}</code></dd>`:''}
     </dl>
@@ -705,8 +707,8 @@ function renderSchedMonth(containerId, monthDate, data){
         else { el.setAttribute('role','button'); }
         el.tabIndex=0;
         el.onkeydown=(e)=>{if(e.key==='Enter'||e.key===' '){e.preventDefault();openSkuModal(s);}};
-        el.title=`${skuLabel(s)} · ${s.vendor}${s.title?' · '+s.title:''} · ${s.fix_type}\n⏱ goes active ${fmtGoLive(s.go_live_at)}${prodUrl?'\n↗ opens the staged product in Shopify admin':''}`;
-        const fx=s.fix_type==='add-sample'?'s':'r';
+        el.title=`${skuLabel(s)} · ${s.vendor}${s.title?' · '+s.title:''}${s.mat_tier===0?' · texture':(s.fix_type?' · '+s.fix_type:'')}\n⏱ goes active ${fmtGoLive(s.go_live_at)}${prodUrl?'\n↗ opens the staged product in Shopify admin':''}`;
+        const fx=(s.mat_tier!=null)?(s.mat_tier===0?'s':'r'):(s.fix_type==='add-sample'?'s':'r');
         const abbr=s.vendor.slice(0,3).toUpperCase();
         if(s.image_url && /^https?:/.test(s.image_url)){
           el.innerHTML=`<span class="fx ${fx}"></span><img loading="lazy" src="${s.image_url}" onerror="this.replaceWith(Object.assign(document.createElement('div'),{className:'ph',style:'background:${vcolor(s.vendor)}',textContent:'${abbr}'}))"><span class="vn">${s.vendor}</span>`;
diff --git a/server.js b/server.js
index 8b7bff4..bbb0b2a 100644
--- a/server.js
+++ b/server.js
@@ -80,9 +80,13 @@ async function scheduleFromFile() {
     if (!byDate.has(s.go_live_date)) byDate.set(s.go_live_date, []);
     byDate.get(s.go_live_date).push({
       dw_sku: s.dw_sku || sp.dw_sku || '', mfr_sku: s.mfr_sku || '',
-      vendor: s.vendor, fix_type: s.fix_type,
+      vendor: s.vendor,
+      // fix_type is legacy (worklist-only); the unified schedule uses mat_tier
+      // (0 = textures/naturals, activated first). Keep fix_type for back-compat
+      // (undefined on unified rows) and expose mat_tier for the UI's texture pill.
+      fix_type: s.fix_type, mat_tier: (s.mat_tier != null ? s.mat_tier : null),
       slot_hour: s.slot_hour, go_live_at: s.go_live_at,
-      image_url: sp.image_url || null, title: sp.title || null,
+      image_url: sp.image_url || null, title: sp.title || s.title || null,
       shopify_id: s.shopify_id || null, handle: sp.handle || null,
     });
   }

← 295fb99 calendar: mirror unified textures-first + vendor round-robin  ·  back to Dw Activation Calendar  ·  chore: v1.0.3 (session close) 7062f2a →