backups/2026-03-28-pre-sidebar-refactor/konfigurator-tak.js

Code: DEV-66B93E0A Size: 7.2 KB Lines: 81 Path: /home/prodconfig.wenesthosting.com/dev.solargroup.wenest.se/backups/2026-03-28-pre-sidebar-refactor/konfigurator-tak.js

Task / Comment

Open report form
// konfigurator-tak.js
// Visar: tak

// === TAK KONFIGURATOR ===
let _takYtor=[], _takTillbehor={}, _takDeduction='rot', _takOwners=1, _takFinYears=15;
const TAK_TYPER=[{v:'Sadeltak',l:'Sadeltak'},{v:'Pulpettak',l:'Pulpettak'},{v:'Mansardtak',l:'Mansardtak'},{v:'Platt tak',l:'Platt tak'}];
const TAK_MATERIAL=[
    {v:'Betongpannor',l:'Betongpannor',price_sqm:850},
    {v:'Tegelpannor',l:'Tegelpannor',price_sqm:1200},
    {v:'Plåttak',l:'Plåttak',price_sqm:650},
    {v:'Papptak',l:'Papptak',price_sqm:450}
];
const TAK_FARGER=['Svart','Tegelröd','Mörkgrå','Brun','Grön'];
const TAK_TILLBEHOR=[
    {id:'takstege',name:'Takstege',price:3500,unit:'st'},
    {id:'snoglidar',name:'Snöglidare',price:180,unit:'löpmeter'},
    {id:'ventilation',name:'Ventilationshuv',price:2800,unit:'st'},
    {id:'takfönster',name:'Takfönster VELUX',price:8900,unit:'st'},
    {id:'hangranna',name:'Hängrännor',price:320,unit:'löpmeter'},
    {id:'stuprör',name:'Stuprör',price:280,unit:'löpmeter'}
];

function initTakConfig(){ var _lbl=document.getElementById('cfgFileLabel');if(_lbl)_lbl.textContent='konfigurator-tak.js';renderTakYtor();renderTakTillbehor();updateTakCalc();}
let _takNextId=1;
function addTakYta(){_takYtor.push({id:_takNextId++,area:0,type:'',material:'',color:''});renderTakYtor();updateTakCalc();}
function removeTakYta(id){_takYtor=_takYtor.filter(y=>y.id!==id);renderTakYtor();updateTakCalc();}
function updateTakYta(id,field,val){const y=_takYtor.find(y=>y.id===id);if(y){y[field]=field==='area'?parseInt(val)||0:val;}updateTakCalc();}
function renderTakYtor(){
    const c=document.getElementById('takYtorContainer');if(!c)return;
    if(!_takYtor.length){c.innerHTML='<div style="text-align:center;padding:30px;border:2px dashed #e5e7eb;border-radius:10px;color:#94a3b8"><p style="font-size:14px;font-weight:600;margin:0 0 8px">Inga takytor tillagda ännu</p><button onclick="addTakYta()" style="padding:8px 16px;background:#f0f9ff;border:1.5px solid #3b82f6;border-radius:8px;color:#3b82f6;font-size:12px;font-weight:600;cursor:pointer;font-family:inherit">+ Lägg till första takytan</button></div>';return;}
    c.innerHTML=_takYtor.map((y,i)=>`
        <div style="border:1px solid #e5e7eb;border-radius:10px;padding:16px;background:#f8fafc">
            <div style="display:flex;justify-content:space-between;align-items:center;margin-bottom:12px">
                <span style="font-weight:600;font-size:14px">Takyta ${i+1}</span>
                <button onclick="removeTakYta(${y.id})" style="background:none;border:none;cursor:pointer;color:#ef4444;font-size:16px">✕</button>
            </div>
            <div style="display:grid;grid-template-columns:1fr 1fr;gap:10px">
                <div><label style="font-size:11px;font-weight:600;color:#64748b;display:block;margin-bottom:3px">Takyta (m²)</label><input type="number" value="${y.area||''}" placeholder="100" oninput="updateTakYta(${y.id},'area',this.value)" style="width:100%;padding:8px 10px;border:1.5px solid #e5e7eb;border-radius:8px;font-size:13px;font-family:inherit;box-sizing:border-box"></div>
                <div><label style="font-size:11px;font-weight:600;color:#64748b;display:block;margin-bottom:3px">Taktyp</label><select onchange="updateTakYta(${y.id},'type',this.value)" style="width:100%;padding:8px 10px;border:1.5px solid #e5e7eb;border-radius:8px;font-size:13px;font-family:inherit;background:#fff"><option value="">Välj...</option>${TAK_TYPER.map(t=>'<option value="'+t.v+'"'+(y.type===t.v?' selected':'')+'>'+t.l+'</option>').join('')}</select></div>
                <div><label style="font-size:11px;font-weight:600;color:#64748b;display:block;margin-bottom:3px">Material</label><select onchange="updateTakYta(${y.id},'material',this.value)" style="width:100%;padding:8px 10px;border:1.5px solid #e5e7eb;border-radius:8px;font-size:13px;font-family:inherit;background:#fff"><option value="">Välj...</option>${TAK_MATERIAL.map(m=>'<option value="'+m.v+'"'+(y.material===m.v?' selected':'')+'>'+m.l+' — '+m.price_sqm+' kr/m²</option>').join('')}</select></div>
                <div><label style="font-size:11px;font-weight:600;color:#64748b;display:block;margin-bottom:3px">Färg</label><select onchange="updateTakYta(${y.id},'color',this.value)" style="width:100%;padding:8px 10px;border:1.5px solid #e5e7eb;border-radius:8px;font-size:13px;font-family:inherit;background:#fff"><option value="">Välj...</option>${TAK_FARGER.map(f=>'<option value="'+f+'"'+(y.color===f?' selected':'')+'>'+f+'</option>').join('')}</select></div>
            </div>
        </div>`).join('');
}
function renderTakTillbehor(){
    const c=document.getElementById('takTillbehorCards');if(!c)return;
    c.innerHTML=TAK_TILLBEHOR.map(t=>`
        <div style="display:flex;align-items:center;gap:12px;padding:12px 14px;border:1.5px solid ${_takTillbehor[t.id]?'#3b82f6':'#e5e7eb'};border-radius:10px;background:${_takTillbehor[t.id]?'#f0f9ff':'#fff'}">
            <input type="checkbox" ${_takTillbehor[t.id]?'checked':''} onchange="toggleTakTillb('${t.id}',this.checked)" style="accent-color:#3b82f6;width:18px;height:18px">
            <div style="flex:1"><div style="font-weight:600;font-size:13px">${t.name}</div><div style="font-size:10px;color:#64748b">${fmt(t.price)}/${t.unit}</div></div>
            ${_takTillbehor[t.id]?'<input type="number" min="1" value="'+(_takTillbehor[t.id]?.qty||1)+'" oninput="updateTakTillbQty(\''+t.id+'\',this.value)" style="width:60px;padding:6px;border:1.5px solid #e5e7eb;border-radius:6px;font-size:13px;text-align:center;font-family:inherit">':''}
        </div>`).join('');
}
function toggleTakTillb(id,checked){
    if(checked){const t=TAK_TILLBEHOR.find(x=>x.id===id);_takTillbehor[id]={price:t.price,qty:1};}else delete _takTillbehor[id];
    renderTakTillbehor();updateTakCalc();
}
function updateTakTillbQty(id,val){if(_takTillbehor[id])_takTillbehor[id].qty=parseInt(val)||1;updateTakCalc();}
function setTakDeduction(t){_takDeduction=t;cfgSetBtns('deduct','tak-deduct-btn',t);updateTakCalc();}
function setTakOwners(n){_takOwners=n;cfgSetBtns('owner','tak-owner-btn',n);updateTakCalc();}
function setTakFinYears(y){_takFinYears=y;cfgSetBtns('fin','tak-fin-btn',y);updateTakCalc();}
function updateTakCalc(){
    let ytorTotal=0;
    _takYtor.forEach(y=>{const m=TAK_MATERIAL.find(x=>x.v===y.material);if(m&&y.area)ytorTotal+=y.area*m.price_sqm;});
    let tillbTotal=0;
    Object.values(_takTillbehor).forEach(t=>{tillbTotal+=t.price*(t.qty||1);});
    const subtotal=ytorTotal+tillbTotal;
    const deduct=cfgDeduct(subtotal,0.50,_takDeduction,_takOwners);
    const total=subtotal-deduct;
    const monthly=cfgMonthly(total,_takFinYears);
    document.getElementById('takPrYtor').textContent=fmt(ytorTotal);
    document.getElementById('takPrTillb').textContent=fmt(tillbTotal);
    document.getElementById('takPrSubtotal').textContent=fmt(subtotal);
    document.getElementById('takDeductLabel').textContent=_takDeduction==='rot'?'ROT-AVDRAG':'INGET AVDRAG';
    document.getElementById('takDeductKr').textContent=deduct?'-'+fmt(deduct):'0 kr';
    document.getElementById('takPrTotal').textContent=fmt(total);
    document.getElementById('takFinInfo').textContent='('+_takFinYears+' år, 4.9%)';
    document.getElementById('takPrMonthly').textContent=fmt(monthly)+'/mån';
}