Spaces:
No application file
No application file
// Global variables for sorting and filtering | |
let currentSortColumn = -1; | |
let isAscending = true; | |
let columnFilters = {}; | |
let columnValues = {}; | |
// Function to update the table based on filters | |
async function updateTable() { | |
const navigation = document.getElementById('navigation').value; | |
const embdType = document.getElementById('embdType').value; | |
const similarity = document.getElementById('similarity').value; | |
// Get all checked embedding dimensions | |
const embdDims = Array.from(document.querySelectorAll('input[name="embdDim"]:checked')) | |
.map(checkbox => checkbox.value); | |
// Prepare filter data | |
const filters = { | |
navigation: navigation, | |
embd_type: embdType, | |
embd_dims: embdDims, | |
similarity: similarity | |
}; | |
try { | |
const response = await fetch('/api/filter', { | |
method: 'POST', | |
headers: { | |
'Content-Type': 'application/json' | |
}, | |
body: JSON.stringify(filters) | |
}); | |
if (!response.ok) { | |
throw new Error(`HTTP error! status: ${response.status}`); | |
} | |
const data = await response.json(); | |
updateTableContent(data); | |
} catch (error) { | |
console.error('Error updating table:', error); | |
alert('Failed to update table. Please try again.'); | |
} | |
} | |
// Function to update table content | |
function updateTableContent(data) { | |
const tbody = document.querySelector('#leaderboardTable tbody'); | |
tbody.innerHTML = ''; | |
data.forEach(row => { | |
const tr = document.createElement('tr'); | |
row.forEach(cell => { | |
const td = document.createElement('td'); | |
td.innerHTML = cell; // Use innerHTML instead of textContent to handle HTML content | |
tr.appendChild(td); | |
}); | |
tbody.appendChild(tr); | |
}); | |
} | |
// Initialize when document is ready | |
document.addEventListener('DOMContentLoaded', () => { | |
initializeColumnValues(); | |
document.addEventListener('click', handleClickOutside); | |
}); | |
// Initialize unique values for each column | |
function initializeColumnValues() { | |
const table = document.getElementById('leaderboardTable'); | |
const headers = Array.from(table.querySelectorAll('th')); | |
const rows = Array.from(table.querySelectorAll('tbody tr')); | |
headers.forEach((header, columnIndex) => { | |
const columnName = header.querySelector('span').textContent; | |
const values = new Set(); | |
rows.forEach(row => { | |
const cell = row.cells[columnIndex]; | |
const value = cell.textContent.trim(); | |
if (value) values.add(value); | |
}); | |
columnValues[columnName] = Array.from(values).sort(); | |
}); | |
} | |
// Handle clicking outside filter dropdowns | |
function handleClickOutside(event) { | |
const dropdowns = document.querySelectorAll('.filter-dropdown'); | |
dropdowns.forEach(dropdown => { | |
const filterBtn = dropdown.parentElement.querySelector('.filter-btn'); | |
if (!dropdown.contains(event.target) && !filterBtn.contains(event.target)) { | |
dropdown.style.display = 'none'; | |
} | |
}); | |
} | |
// Toggle filter dropdown | |
function toggleFilter(event, columnName) { | |
event.stopPropagation(); | |
const dropdown = document.getElementById(`filter-${columnName}`); | |
const options = document.getElementById(`options-${columnName}`); | |
// Close other dropdowns | |
document.querySelectorAll('.filter-dropdown').forEach(d => { | |
if (d !== dropdown) d.style.display = 'none'; | |
}); | |
if (dropdown.style.display === 'none') { | |
dropdown.style.display = 'block'; | |
if (!options.children.length) { | |
populateFilterOptions(columnName); | |
} | |
} else { | |
dropdown.style.display = 'none'; | |
} | |
} | |
// Populate filter options | |
function populateFilterOptions(columnName) { | |
const options = document.getElementById(`options-${columnName}`); | |
options.innerHTML = ''; | |
columnValues[columnName].forEach(value => { | |
const option = document.createElement('div'); | |
option.className = 'filter-option'; | |
const checkbox = document.createElement('input'); | |
checkbox.type = 'checkbox'; | |
checkbox.value = value; | |
checkbox.checked = columnFilters[columnName]?.includes(value) || false; | |
const label = document.createElement('span'); | |
label.textContent = value; | |
option.appendChild(checkbox); | |
option.appendChild(label); | |
options.appendChild(option); | |
}); | |
} | |
// Filter options based on search input | |
function filterOptions(columnName) { | |
const searchInput = document.querySelector(`#filter-${columnName} .filter-search`); | |
const searchTerm = searchInput.value.toLowerCase(); | |
const options = document.getElementById(`options-${columnName}`); | |
Array.from(options.children).forEach(option => { | |
const text = option.textContent.toLowerCase(); | |
option.style.display = text.includes(searchTerm) ? '' : 'none'; | |
}); | |
} | |
// Apply filter | |
function applyFilter(columnName) { | |
const options = document.getElementById(`options-${columnName}`); | |
const checkedValues = Array.from(options.querySelectorAll('input[type="checkbox"]:checked')) | |
.map(cb => cb.value); | |
columnFilters[columnName] = checkedValues; | |
updateTableVisibility(); | |
document.getElementById(`filter-${columnName}`).style.display = 'none'; | |
} | |
// Clear filter | |
function clearFilter(columnName) { | |
const options = document.getElementById(`options-${columnName}`); | |
options.querySelectorAll('input[type="checkbox"]').forEach(cb => cb.checked = false); | |
delete columnFilters[columnName]; | |
updateTableVisibility(); | |
document.getElementById(`filter-${columnName}`).style.display = 'none'; | |
} | |
// Update table visibility based on filters | |
function updateTableVisibility() { | |
const table = document.getElementById('leaderboardTable'); | |
const rows = Array.from(table.querySelectorAll('tbody tr')); | |
const headers = Array.from(table.querySelectorAll('th')); | |
rows.forEach(row => { | |
let visible = true; | |
Object.entries(columnFilters).forEach(([columnName, selectedValues]) => { | |
if (!selectedValues.length) return; | |
const columnIndex = headers.findIndex(header => | |
header.querySelector('span').textContent === columnName | |
); | |
const cellValue = row.cells[columnIndex].textContent.trim(); | |
if (!selectedValues.includes(cellValue)) { | |
visible = false; | |
} | |
}); | |
row.style.display = visible ? '' : 'none'; | |
}); | |
} | |
// Sort table | |
function sortTable(columnIndex) { | |
const table = document.getElementById('leaderboardTable'); | |
const tbody = table.querySelector('tbody'); | |
const rows = Array.from(tbody.querySelectorAll('tr')); | |
// Update sort direction | |
if (currentSortColumn === columnIndex) { | |
isAscending = !isAscending; | |
} else { | |
currentSortColumn = columnIndex; | |
isAscending = true; | |
} | |
// Sort rows | |
rows.sort((a, b) => { | |
let aValue = a.cells[columnIndex].textContent; | |
let bValue = b.cells[columnIndex].textContent; | |
// Remove HTML tags for comparison | |
aValue = aValue.replace(/<[^>]*>/g, '').trim(); | |
bValue = bValue.replace(/<[^>]*>/g, '').trim(); | |
// Check if the values are numbers | |
const aNum = parseFloat(aValue); | |
const bNum = parseFloat(bValue); | |
if (!isNaN(aNum) && !isNaN(bNum)) { | |
return isAscending ? aNum - bNum : bNum - aNum; | |
} | |
// Sort as strings | |
return isAscending | |
? aValue.localeCompare(bValue) | |
: bValue.localeCompare(aValue); | |
}); | |
// Update table | |
tbody.innerHTML = ''; | |
rows.forEach(row => tbody.appendChild(row)); | |
// Update sort indicators | |
const headers = table.querySelectorAll('.sort-icon'); | |
headers.forEach((icon, index) => { | |
icon.textContent = index === columnIndex | |
? (isAscending ? '↑' : '↓') | |
: '↕'; | |
}); | |
} | |
// Initialize table sorting and filtering | |
document.addEventListener('DOMContentLoaded', () => { | |
// Add event listener for checkboxes | |
const checkboxes = document.querySelectorAll('input[name="embdDim"]'); | |
checkboxes.forEach(checkbox => { | |
checkbox.addEventListener('change', updateTable); | |
}); | |
}); | |