This commit is contained in:
parent
7d297ad2d9
commit
2467cc5fce
3 changed files with 110 additions and 4 deletions
|
|
@ -6,7 +6,7 @@ services:
|
|||
ports:
|
||||
- "${APP_PORT:-3000}:3000"
|
||||
volumes:
|
||||
- ./data:/data
|
||||
- /opt/intra_monitor/data:/data
|
||||
environment:
|
||||
NODE_ENV: production
|
||||
PORT: 3000
|
||||
|
|
|
|||
|
|
@ -1368,9 +1368,36 @@ html.dark .stats-card { background:var(--surface); }
|
|||
padding:6px;
|
||||
}
|
||||
.adv-filter-panel.open{display:block;}
|
||||
.adv-filter-actions{
|
||||
display:flex;
|
||||
gap:6px;
|
||||
padding:2px 2px 8px;
|
||||
margin:0 0 4px;
|
||||
border-bottom:1px solid var(--border);
|
||||
}
|
||||
.adv-filter-action-btn{
|
||||
flex:1;
|
||||
border:1px solid var(--border);
|
||||
background:var(--surface2);
|
||||
color:var(--text2);
|
||||
border-radius:6px;
|
||||
font-family:inherit;
|
||||
font-size:11px;
|
||||
padding:4px 6px;
|
||||
cursor:pointer;
|
||||
transition:border-color .15s,color .15s,background .15s;
|
||||
}
|
||||
.adv-filter-action-btn:hover:not(:disabled){
|
||||
border-color:var(--accent);
|
||||
color:var(--accent);
|
||||
}
|
||||
.adv-filter-action-btn:disabled{
|
||||
opacity:.5;
|
||||
cursor:not-allowed;
|
||||
}
|
||||
.adv-filter-item{
|
||||
display:flex;
|
||||
align-items:flex-start;
|
||||
align-items:center;
|
||||
gap:8px;
|
||||
padding:6px 7px;
|
||||
border-radius:6px;
|
||||
|
|
@ -1381,11 +1408,18 @@ html.dark .stats-card { background:var(--surface); }
|
|||
}
|
||||
.adv-filter-item:hover{background:var(--surface2);}
|
||||
.adv-filter-item input{
|
||||
margin-top:2px;
|
||||
margin-top:0;
|
||||
accent-color:var(--accent);
|
||||
cursor:pointer;
|
||||
}
|
||||
.adv-filter-item span{
|
||||
.adv-filter-dot{
|
||||
width:8px;
|
||||
height:8px;
|
||||
border-radius:50%;
|
||||
flex-shrink:0;
|
||||
box-shadow:0 0 0 1px rgba(0,0,0,.08);
|
||||
}
|
||||
.adv-filter-text{
|
||||
flex:1;
|
||||
min-width:0;
|
||||
line-height:1.35;
|
||||
|
|
|
|||
|
|
@ -90,6 +90,44 @@ function updateAdvancedFilterLabel(selectId){
|
|||
lbl.textContent=`${cfg.shortLabel}: ${selected.length}`;
|
||||
}
|
||||
|
||||
function getIntraStatusFilterColor(label){
|
||||
const lc=String(label||'').toLowerCase();
|
||||
if(lc.includes('открыт')||lc.includes('нов')||lc.includes('назнач')) return 'var(--blue)';
|
||||
if(lc.includes('работ')||lc.includes('ожид')||lc.includes('progress')) return 'var(--orange)';
|
||||
if(lc.includes('выполн')||lc.includes('закрыт')||lc.includes('реш')) return 'var(--green)';
|
||||
if(lc.includes('hold')||lc.includes('пауза')||lc.includes('приост')) return '#faad14';
|
||||
return 'var(--text3)';
|
||||
}
|
||||
|
||||
function getAdvancedFilterOptionColor(selectId,opt){
|
||||
const value=String(opt?.value||'');
|
||||
const label=String(opt?.textContent||'');
|
||||
if(selectId==='filter-who-select'){
|
||||
if(value==='internal') return 'var(--green)';
|
||||
if(value==='external') return 'var(--red)';
|
||||
return 'var(--text3)';
|
||||
}
|
||||
if(selectId==='filter-internal-select'){
|
||||
const m=MARKS_CONFIG.find((x)=>String(x.key)===value);
|
||||
return m?.colorDot||m?.chipDotColor||m?.ispColor||'var(--text3)';
|
||||
}
|
||||
if(selectId==='filter-intra-select') return getIntraStatusFilterColor(label);
|
||||
return avatarColor(label||value);
|
||||
}
|
||||
|
||||
function setAdvancedFilterSelection(selectId,selected){
|
||||
const sel=document.getElementById(selectId);
|
||||
if(!sel) return;
|
||||
[...sel.options].forEach((opt)=>{
|
||||
if(opt.disabled) return;
|
||||
if(String(opt.value).trim()==='') return;
|
||||
opt.selected=!!selected;
|
||||
});
|
||||
updateAdvancedFilterLabel(selectId);
|
||||
buildAdvancedFilterPanel(selectId);
|
||||
renderTable();
|
||||
}
|
||||
|
||||
function buildAdvancedFilterPanel(selectId){
|
||||
const cfg=ADV_FILTER_CONFIG[selectId];
|
||||
if(!cfg) return;
|
||||
|
|
@ -106,6 +144,34 @@ function buildAdvancedFilterPanel(selectId){
|
|||
return;
|
||||
}
|
||||
|
||||
const selectedCount=opts.filter((o)=>o.selected).length;
|
||||
const actions=document.createElement('div');
|
||||
actions.className='adv-filter-actions';
|
||||
|
||||
const btnAll=document.createElement('button');
|
||||
btnAll.type='button';
|
||||
btnAll.className='adv-filter-action-btn';
|
||||
btnAll.textContent='Выбрать все';
|
||||
btnAll.disabled=selectedCount===opts.length;
|
||||
btnAll.addEventListener('click',(e)=>{
|
||||
e.stopPropagation();
|
||||
setAdvancedFilterSelection(selectId,true);
|
||||
});
|
||||
|
||||
const btnNone=document.createElement('button');
|
||||
btnNone.type='button';
|
||||
btnNone.className='adv-filter-action-btn';
|
||||
btnNone.textContent='Снять все';
|
||||
btnNone.disabled=selectedCount===0;
|
||||
btnNone.addEventListener('click',(e)=>{
|
||||
e.stopPropagation();
|
||||
setAdvancedFilterSelection(selectId,false);
|
||||
});
|
||||
|
||||
actions.appendChild(btnAll);
|
||||
actions.appendChild(btnNone);
|
||||
panel.appendChild(actions);
|
||||
|
||||
const frag=document.createDocumentFragment();
|
||||
opts.forEach((opt)=>{
|
||||
const item=document.createElement('label');
|
||||
|
|
@ -120,10 +186,16 @@ function buildAdvancedFilterPanel(selectId){
|
|||
renderTable();
|
||||
});
|
||||
|
||||
const dot=document.createElement('span');
|
||||
dot.className='adv-filter-dot';
|
||||
dot.style.background=getAdvancedFilterOptionColor(selectId,opt);
|
||||
|
||||
const text=document.createElement('span');
|
||||
text.className='adv-filter-text';
|
||||
text.textContent=opt.textContent;
|
||||
|
||||
item.appendChild(cb);
|
||||
item.appendChild(dot);
|
||||
item.appendChild(text);
|
||||
frag.appendChild(item);
|
||||
});
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue