{% extends "mainapp/base.html" %}
{% load static %}

{% block title %}Усреднение точек{% endblock %}

{% block extra_css %}
<link href="{% static 'tabulator/css/tabulator_bootstrap5.min.css' %}" rel="stylesheet">
<style>
    .averaging-container {
        padding: 20px;
    }
    .form-section {
        background: white;
        padding: 20px;
        border-radius: 8px;
        box-shadow: 0 2px 4px rgba(0,0,0,0.1);
        margin-bottom: 20px;
    }
    .table-section {
        background: white;
        padding: 20px;
        border-radius: 8px;
        box-shadow: 0 2px 4px rgba(0,0,0,0.1);
    }
    #sources-table {
        margin-top: 15px;
        font-size: 12px;
    }
    #sources-table .tabulator-header {
        font-size: 12px;
    }
    #sources-table .tabulator-cell {
        font-size: 12px;
        padding: 6px 4px;
    }
    .btn-group-custom {
        margin-top: 15px;
    }
    .loading-overlay {
        position: fixed;
        top: 0;
        left: 0;
        width: 100%;
        height: 100%;
        background: rgba(255,255,255,0.8);
        display: none;
        justify-content: center;
        align-items: center;
        z-index: 9999;
    }
    .loading-overlay.active {
        display: flex;
    }
    .modal-xl {
        max-width: 95%;
    }
    .group-card {
        border: 1px solid #e9ecef;
        border-radius: 6px;
        margin-bottom: 10px;
        background: #fff;
    }
    .group-header {
        background: #f8f9fa;
        padding: 10px 12px;
        border-bottom: 1px solid #e9ecef;
        display: flex;
        justify-content: space-between;
        align-items: center;
        flex-wrap: wrap;
        gap: 10px;
    }
    .group-header.has-outliers {
        background: #fff3cd;
    }
    .group-info {
        display: flex;
        flex-wrap: wrap;
        gap: 15px;
        align-items: center;
    }
    .group-info-item {
        font-size: 13px;
    }
    .group-info-item strong {
        color: #495057;
    }
    .group-actions {
        display: flex;
        gap: 5px;
    }
    .group-body {
        padding: 10px;
    }
    .points-table {
        font-size: 11px;
        width: 100%;
    }
    .points-table th, .points-table td {
        padding: 5px 6px;
        border: 1px solid #dee2e6;
    }
    .points-table th {
        background: #f8f9fa;
        font-weight: 600;
    }
    .points-table tr.outlier {
        background-color: #ffcccc !important;
    }
    .points-table tr.valid {
        background-color: #d4edda !important;
    }
    .source-has-outliers {
        background-color: #fff3cd !important;
    }
</style>
{% endblock %}

{% block content %}
<div class="loading-overlay" id="loading-overlay">
    <div class="spinner-border text-primary" role="status">
        <span class="visually-hidden">Загрузка...</span>
    </div>
</div>

<div class="averaging-container">
    <h2>Усреднение точек по объектам</h2>
    
    <div class="form-section">
        <div class="row">
            <div class="col-md-3 mb-3">
                <label for="satellite-select" class="form-label">Спутник</label>
                <select id="satellite-select" class="form-select">
                    <option value="">Выберите спутник</option>
                    {% for satellite in satellites %}
                    <option value="{{ satellite.id }}">{{ satellite.name }}</option>
                    {% endfor %}
                </select>
            </div>
            <div class="col-md-3 mb-3">
                <label for="date-from" class="form-label">Дата с</label>
                <input type="date" id="date-from" class="form-control">
            </div>
            <div class="col-md-3 mb-3">
                <label for="date-to" class="form-label">Дата по</label>
                <input type="date" id="date-to" class="form-control">
            </div>
            <div class="col-md-3 mb-3 d-flex align-items-end">
                <button id="btn-process" class="btn btn-primary w-100">
                    <i class="bi bi-play-fill"></i> Загрузить данные
                </button>
            </div>
        </div>
    </div>
    
    <div class="table-section">
        <div class="d-flex justify-content-between align-items-center">
            <div>
                <h5>Объекты <span id="source-count" class="badge bg-primary">0</span></h5>
            </div>
            <div class="btn-group-custom">
                <button id="export-xlsx" class="btn btn-success" disabled>
                    <i class="bi bi-file-earmark-excel"></i> Сохранить в Excel
                </button>
                <button id="export-json" class="btn btn-info ms-2" disabled>
                    <i class="bi bi-filetype-json"></i> Сохранить в JSON
                </button>
                <button id="clear-all" class="btn btn-danger ms-2">
                    <i class="bi bi-trash"></i> Очистить всё
                </button>
            </div>
        </div>
        
        <div id="sources-table"></div>
    </div>
</div>

<!-- Modal for source details -->
<div class="modal fade" id="sourceDetailsModal" tabindex="-1" aria-labelledby="sourceDetailsModalLabel" aria-hidden="true">
    <div class="modal-dialog modal-xl">
        <div class="modal-content">
            <div class="modal-header">
                <h5 class="modal-title" id="sourceDetailsModalLabel">Детали объекта</h5>
                <button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
            </div>
            <div class="modal-body" id="modal-body-content">
                <!-- Groups will be rendered here -->
            </div>
            <div class="modal-footer">
                <button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Закрыть</button>
            </div>
        </div>
    </div>
</div>
{% endblock %}

{% block extra_js %}
<script src="{% static 'tabulator/js/tabulator.min.js' %}"></script>
<script src="{% static 'sheetjs/xlsx.full.min.js' %}"></script>

<script>
document.addEventListener('DOMContentLoaded', function() {
    let allSourcesData = [];
    let currentSourceIdx = null;
    let sourcesTable = null;
    
    function showLoading() {
        document.getElementById('loading-overlay').classList.add('active');
    }
    function hideLoading() {
        document.getElementById('loading-overlay').classList.remove('active');
    }
    
    function getCookie(name) {
        let cookieValue = null;
        if (document.cookie && document.cookie !== '') {
            const cookies = document.cookie.split(';');
            for (let i = 0; i < cookies.length; i++) {
                const cookie = cookies[i].trim();
                if (cookie.substring(0, name.length + 1) === (name + '=')) {
                    cookieValue = decodeURIComponent(cookie.substring(name.length + 1));
                    break;
                }
            }
        }
        return cookieValue;
    }
    
    function generateUUID() {
        return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, function(c) {
            const r = Math.random() * 16 | 0;
            const v = c === 'x' ? r : (r & 0x3 | 0x8);
            return v.toString(16);
        });
    }
    
    function updateCounts() {
        document.getElementById('source-count').textContent = allSourcesData.length;
        const hasData = allSourcesData.length > 0;
        document.getElementById('export-xlsx').disabled = !hasData;
        document.getElementById('export-json').disabled = !hasData;
    }
    
    // Prepare table data from sources
    function getTableData() {
        const data = [];
        allSourcesData.forEach((source, sourceIdx) => {
            const totalPoints = source.groups.reduce((sum, g) => sum + g.valid_points_count, 0);
            const hasOutliers = source.groups.some(g => g.has_outliers);
            
            // Get first group's params as representative
            const firstGroup = source.groups[0] || {};
            
            data.push({
                _sourceIdx: sourceIdx,
                source_name: source.source_name,
                source_id: source.source_id,
                groups_count: source.groups.length,
                total_points: totalPoints,
                has_outliers: hasOutliers,
                frequency: firstGroup.frequency || '-',
                modulation: firstGroup.modulation || '-',
                mirrors: firstGroup.mirrors || '-',
            });
        });
        return data;
    }
    
    // Initialize or update sources table
    function updateSourcesTable() {
        const data = getTableData();
        
        if (!sourcesTable) {
            sourcesTable = new Tabulator("#sources-table", {
                layout: "fitDataStretch",
                height: "500px",
                placeholder: "Нет данных. Выберите спутник и диапазон дат, затем нажмите 'Загрузить данные'.",
                initialSort: [
                    {column: "frequency", dir: "asc"}
                ],
                columns: [
                    {title: "Объект", field: "source_name", minWidth: 180, widthGrow: 2},
                    {title: "Групп", field: "groups_count", minWidth: 70, hozAlign: "center"},
                    {title: "Точек", field: "total_points", minWidth: 70, hozAlign: "center"},
                    {title: "Частота", field: "frequency", minWidth: 100, sorter: "number"},
                    {title: "Модуляция", field: "modulation", minWidth: 90},
                    {title: "Зеркала", field: "mirrors", minWidth: 130},
                    {
                        title: "Действия",
                        field: "actions",
                        minWidth: 150,
                        hozAlign: "center",
                        formatter: function(cell) {
                            const data = cell.getRow().getData();
                            const outlierBadge = data.has_outliers ? '<span class="badge bg-warning me-1">!</span>' : '';
                            return `${outlierBadge}
                                <button class="btn btn-sm btn-primary btn-view-source" title="Открыть детали">
                                    <i class="bi bi-eye"></i>
                                </button>
                                <button class="btn btn-sm btn-danger btn-delete-source ms-1" title="Удалить">
                                    <i class="bi bi-trash"></i>
                                </button>`;
                        },
                        cellClick: function(e, cell) {
                            const data = cell.getRow().getData();
                            if (e.target.closest('.btn-view-source')) {
                                openSourceModal(data._sourceIdx);
                            } else if (e.target.closest('.btn-delete-source')) {
                                deleteSource(data._sourceIdx);
                            }
                        }
                    }
                ],
                data: data,
                rowFormatter: function(row) {
                    if (row.getData().has_outliers) {
                        row.getElement().classList.add('source-has-outliers');
                    }
                }
            });
        } else {
            sourcesTable.setData(data);
        }
        
        updateCounts();
    }
    
    // Delete source
    function deleteSource(sourceIdx) {
        //if (!confirm('Удалить этот объект со всеми группами?')) return;
        allSourcesData.splice(sourceIdx, 1);
        updateSourcesTable();
    }
    
    // Open source modal
    function openSourceModal(sourceIdx) {
        currentSourceIdx = sourceIdx;
        const source = allSourcesData[sourceIdx];
        if (!source) return;
        
        document.getElementById('sourceDetailsModalLabel').textContent = `Объект: ${source.source_name}`;
        renderModalContent();
        
        const modal = new bootstrap.Modal(document.getElementById('sourceDetailsModal'));
        modal.show();
    }
    
    // Render modal content
    function renderModalContent() {
        const source = allSourcesData[currentSourceIdx];
        if (!source) return;
        
        let html = '';
        source.groups.forEach((group, groupIdx) => {
            html += renderGroupCard(group, groupIdx);
        });
        
        if (source.groups.length === 0) {
            html = '<div class="alert alert-info">Нет групп для отображения</div>';
        }
        
        document.getElementById('modal-body-content').innerHTML = html;
        addModalEventListeners();
    }
    
    // Render group card
    function renderGroupCard(group, groupIdx) {
        const headerClass = group.has_outliers ? 'has-outliers' : '';
        
        let pointsHtml = '';
        group.points.forEach((point, pointIdx) => {
            const rowClass = point.is_outlier ? 'outlier' : 'valid';
            pointsHtml += `
                <tr class="${rowClass}">
                    <td>${point.id}</td>
                    <td>${point.name}</td>
                    <td>${point.frequency}</td>
                    <td>${point.freq_range}</td>
                    <td>${point.bod_velocity}</td>
                    <td>${point.modulation}</td>
                    <td>${point.snr}</td>
                    <td>${point.timestamp}</td>
                    <td>${point.mirrors}</td>
                    <td>${point.coordinates}</td>
                    <td>${point.distance_from_avg}</td>
                    <td>
                        <button class="btn btn-sm btn-outline-danger btn-delete-point" 
                                data-group-idx="${groupIdx}" 
                                data-point-idx="${pointIdx}"
                                title="Удалить точку">
                            <i class="bi bi-x"></i>
                        </button>
                    </td>
                </tr>
            `;
        });
        
        return `
            <div class="group-card" data-group-idx="${groupIdx}">
                <div class="group-header ${headerClass}">
                    <div class="group-info">
                        <span class="group-info-item"><strong>Интервал:</strong> ${group.interval_label}</span>
                        <span class="group-info-item"><strong>Усреднённые координаты:</strong> ${group.avg_coordinates} <span class="badge bg-secondary">${group.avg_type || 'ГК'}</span></span>
                        <span class="group-info-item"><strong>Медианное время:</strong> ${group.avg_time}</span>
                        <span class="group-info-item"><strong>Точек:</strong> ${group.valid_points_count}/${group.total_points}</span>
                        ${group.has_outliers ? `<span class="badge bg-warning">Выбросов: ${group.outliers_count}</span>` : ''}
                    </div>
                    <div class="group-actions">
                        <button class="btn btn-sm btn-primary btn-average-group" data-group-idx="${groupIdx}" title="Пересчитать усреднение">
                            <i class="bi bi-calculator"></i> Усреднить
                        </button>
                        ${group.has_outliers ? `
                        <button class="btn btn-sm btn-warning btn-average-all" data-group-idx="${groupIdx}" title="Усреднить все точки">
                            <i class="bi bi-arrow-repeat"></i> Все точки
                        </button>
                        ` : ''}
                        <button class="btn btn-sm btn-danger btn-delete-group" data-group-idx="${groupIdx}" title="Удалить группу">
                            <i class="bi bi-trash"></i>
                        </button>
                    </div>
                </div>
                <div class="group-body">
                    <table class="points-table">
                        <thead>
                            <tr>
                                <th>ID</th>
                                <th>Имя</th>
                                <th>Частота</th>
                                <th>Полоса</th>
                                <th>Симв. скорость</th>
                                <th>Модуляция</th>
                                <th>ОСШ</th>
                                <th>Дата/Время</th>
                                <th>Зеркала</th>
                                <th>Координаты</th>
                                <th>Расст., км</th>
                                <th></th>
                            </tr>
                        </thead>
                        <tbody>${pointsHtml}</tbody>
                    </table>
                </div>
            </div>
        `;
    }
    
    // Add event listeners for modal
    function addModalEventListeners() {
        document.querySelectorAll('.btn-delete-group').forEach(btn => {
            btn.addEventListener('click', function() {
                const groupIdx = parseInt(this.dataset.groupIdx);
                deleteGroup(groupIdx);
            });
        });
        
        document.querySelectorAll('.btn-delete-point').forEach(btn => {
            btn.addEventListener('click', function() {
                const groupIdx = parseInt(this.dataset.groupIdx);
                const pointIdx = parseInt(this.dataset.pointIdx);
                deletePoint(groupIdx, pointIdx);
            });
        });
        
        document.querySelectorAll('.btn-average-group').forEach(btn => {
            btn.addEventListener('click', function() {
                const groupIdx = parseInt(this.dataset.groupIdx);
                recalculateGroup(groupIdx, false);
            });
        });
        
        document.querySelectorAll('.btn-average-all').forEach(btn => {
            btn.addEventListener('click', function() {
                const groupIdx = parseInt(this.dataset.groupIdx);
                recalculateGroup(groupIdx, true);
            });
        });
    }
    
    // Delete group
    function deleteGroup(groupIdx) {
        if (!confirm('Удалить эту группу точек?')) return;
        
        const source = allSourcesData[currentSourceIdx];
        source.groups.splice(groupIdx, 1);
        
        if (source.groups.length === 0) {
            allSourcesData.splice(currentSourceIdx, 1);
            bootstrap.Modal.getInstance(document.getElementById('sourceDetailsModal')).hide();
            updateSourcesTable();
        } else {
            renderModalContent();
            updateSourcesTable();
        }
    }
    
    // Delete point
    function deletePoint(groupIdx, pointIdx) {
        const source = allSourcesData[currentSourceIdx];
        const group = source.groups[groupIdx];
        
        if (group.points.length <= 1) {
            alert('Нельзя удалить последнюю точку. Удалите группу целиком.');
            return;
        }
        
        if (!confirm('Удалить эту точку и пересчитать усреднение?')) return;
        
        group.points.splice(pointIdx, 1);
        group.total_points = group.points.length;
        recalculateGroup(groupIdx, true);
    }
    
    // Recalculate group
    async function recalculateGroup(groupIdx, includeAll) {
        const source = allSourcesData[currentSourceIdx];
        const group = source.groups[groupIdx];
        
        showLoading();
        
        try {
            const response = await fetch('/api/points-averaging/recalculate/', {
                method: 'POST',
                headers: {
                    'Content-Type': 'application/json',
                    'X-CSRFToken': getCookie('csrftoken')
                },
                body: JSON.stringify({
                    points: group.points,
                    include_all: includeAll
                })
            });
            
            const data = await response.json();
            
            if (!response.ok) {
                alert(data.error || 'Ошибка при пересчёте');
                return;
            }
            
            // Update group data
            Object.assign(group, {
                avg_coordinates: data.avg_coordinates,
                avg_coord_tuple: data.avg_coord_tuple,
                avg_type: data.avg_type,
                total_points: data.total_points,
                valid_points_count: data.valid_points_count,
                outliers_count: data.outliers_count,
                has_outliers: data.has_outliers,
                mirrors: data.mirrors || group.mirrors,
                avg_time: data.avg_time || group.avg_time,
                points: data.points,
            });
            
            renderModalContent();
            updateSourcesTable();
            
        } catch (error) {
            console.error('Error:', error);
            alert('Произошла ошибка при пересчёте');
        } finally {
            hideLoading();
        }
    }
    
    // Process button click
    document.getElementById('btn-process').addEventListener('click', async function() {
        const satelliteId = document.getElementById('satellite-select').value;
        const dateFrom = document.getElementById('date-from').value;
        const dateTo = document.getElementById('date-to').value;
        
        if (!satelliteId) { alert('Выберите спутник'); return; }
        if (!dateFrom || !dateTo) { alert('Укажите диапазон дат'); return; }
        
        showLoading();
        
        try {
            const params = new URLSearchParams({ satellite_id: satelliteId, date_from: dateFrom, date_to: dateTo });
            const response = await fetch(`/api/points-averaging/?${params.toString()}`);
            const data = await response.json();
            
            if (!response.ok) { alert(data.error || 'Ошибка при обработке данных'); return; }
            
            data.sources.forEach(source => {
                const existingIdx = allSourcesData.findIndex(s => s.source_id === source.source_id);
                if (existingIdx >= 0) {
                    source.groups.forEach(newGroup => {
                        const existingGroupIdx = allSourcesData[existingIdx].groups.findIndex(g => g.interval_key === newGroup.interval_key);
                        if (existingGroupIdx < 0) {
                            allSourcesData[existingIdx].groups.push(newGroup);
                        }
                    });
                } else {
                    allSourcesData.push(source);
                }
            });
            
            updateSourcesTable();
            
        } catch (error) {
            console.error('Error:', error);
            alert('Произошла ошибка при обработке данных');
        } finally {
            hideLoading();
        }
    });
    
    // Clear all
    document.getElementById('clear-all').addEventListener('click', function() {
        if (!confirm('Очистить все данные?')) return;
        allSourcesData = [];
        updateSourcesTable();
    });
    
    // Export to Excel
    document.getElementById('export-xlsx').addEventListener('click', function() {
        if (allSourcesData.length === 0) { alert('Нет данных для экспорта'); return; }
        
        const summaryData = [];
        allSourcesData.forEach(source => {
            source.groups.forEach(group => {
                summaryData.push({
                    'Объект': source.source_name,
                    'Частота, МГц': group.frequency,
                    'Полоса, МГц': group.freq_range,
                    'Символьная скорость, БОД': group.bod_velocity,
                    'Модуляция': group.modulation,
                    'ОСШ': group.snr,
                    'Зеркала': group.mirrors,
                    'Усреднённые координаты': group.avg_coordinates,
                    // 'Тип усреднения': group.avg_type || 'ГК',
                    'Время': group.avg_time || '-',
                    'Кол-во точек': group.valid_points_count
                });
            });
        });
        
        // Sort by frequency
        summaryData.sort((a, b) => {
            const freqA = parseFloat(a['Частота, МГц']) || 0;
            const freqB = parseFloat(b['Частота, МГц']) || 0;
            return freqA - freqB;
        });
        
        const allPointsData = [];
        allSourcesData.forEach(source => {
            source.groups.forEach(group => {
                group.points.forEach(point => {
                    allPointsData.push({
                        'Объект': source.source_name,
                        'ID точки': point.id,
                        'Имя точки': point.name,
                        'Частота, МГц': point.frequency,
                        'Полоса, МГц': point.freq_range,
                        'Символьная скорость, БОД': point.bod_velocity,
                        'Модуляция': point.modulation,
                        'ОСШ': point.snr,
                        'Дата/Время': point.timestamp,
                        'Зеркала': point.mirrors,
                        'Местоположение': point.location,
                        'Координаты точки': point.coordinates,
                        'Усреднённые координаты': group.avg_coordinates,
                        'Расстояние от среднего, км': point.distance_from_avg,
                        'Статус': point.is_outlier ? 'Выброс' : 'OK'
                    });
                });
            });
        });
        
        // Sort by frequency
        allPointsData.sort((a, b) => {
            const freqA = parseFloat(a['Частота, МГц']) || 0;
            const freqB = parseFloat(b['Частота, МГц']) || 0;
            return freqA - freqB;
        });
        
        const wb = XLSX.utils.book_new();
        XLSX.utils.book_append_sheet(wb, XLSX.utils.json_to_sheet(summaryData), "Усреднение");
        XLSX.utils.book_append_sheet(wb, XLSX.utils.json_to_sheet(allPointsData), "Все точки");
        
        const dateStr = new Date().toISOString().slice(0, 10);
        XLSX.writeFile(wb, `averaging_${dateStr}.xlsx`);
    });

    
    // Export to JSON
    document.getElementById('export-json').addEventListener('click', function() {
        if (allSourcesData.length === 0) { alert('Нет данных для экспорта'); return; }
        
        const CREATOR_ID = '6fd12c90-7f17-43d9-a03e-ee14e880f757';
        
        const pathObject = {
            "tacticObjectType": "path",
            "captionPosition": "right",
            "points": [
                {"id": "b92b9cbb-dd27-49aa-bcb6-e89a147bc02c", "latitude": 57, "longitude": -13, "altitude": 0, "customActions": [], "tags": {"creator": CREATOR_ID}, "tacticObjectType": "point"},
                {"id": "8e3666d4-4990-4cb9-9594-63ad06333489", "latitude": 57, "longitude": 64, "altitude": 0, "customActions": [], "tags": {"creator": CREATOR_ID}, "tacticObjectType": "point"},
                {"id": "5f137485-d2fc-443d-8507-c936f02f3569", "latitude": 11, "longitude": 64, "altitude": 0, "customActions": [], "tags": {"creator": CREATOR_ID}, "tacticObjectType": "point"},
                {"id": "0fb90df7-8eb0-49fa-9d00-336389171bf5", "latitude": 11, "longitude": -13, "altitude": 0, "customActions": [], "tags": {"creator": CREATOR_ID}, "tacticObjectType": "point"},
                {"id": "3ef12637-585e-40a4-b0ee-8f1786c89ce6", "latitude": 57, "longitude": -13, "altitude": 0, "customActions": [], "tags": {"creator": CREATOR_ID}, "tacticObjectType": "point"}
            ],
            "isCycle": false,
            "id": "2f604051-4984-4c2f-8c4c-c0cb64008f5f",
            "draggable": false, "selectable": false, "editable": false,
            "caption": "Ограничение для работы с поверхностями",
            "line": {"color": "rgb(148,0,211)", "thickness": 1, "dash": "solid", "border": null},
            "customActions": [],
            "tags": {"creator": CREATOR_ID}
        };
        
        const result = [pathObject];
        
        const jsonSourceColors = [
            "rgb(0,128,0)", "rgb(0,0,255)", "rgb(255,0,0)", "rgb(255,165,0)", "rgb(128,0,128)",
            "rgb(0,128,128)", "rgb(255,20,147)", "rgb(139,69,19)", "rgb(0,100,0)", "rgb(70,130,180)"
        ];
        
        allSourcesData.forEach((source, sourceIdx) => {
            const sourceColor = jsonSourceColors[sourceIdx % jsonSourceColors.length];
            
            source.groups.forEach(group => {
                const avgCoord = group.avg_coord_tuple;
                const avgLat = avgCoord[1];
                const avgLon = avgCoord[0];
                const avgCaption = `${source.source_name} (усредн) - ${group.avg_time || '-'}`;
                const avgSourceId = generateUUID();
                
                result.push({
                    "tacticObjectType": "source",
                    "captionPosition": "right",
                    "id": avgSourceId,
                    "icon": {"type": "triangle", "color": sourceColor},
                    "caption": avgCaption,
                    "name": avgCaption,
                    "customActions": [],
                    "trackBehavior": {},
                    "bearingStyle": {"color": sourceColor, "thickness": 2, "dash": "solid", "border": null},
                    "bearingBehavior": {},
                    "tags": {"creator": CREATOR_ID}
                });
                
                result.push({
                    "tacticObjectType": "position",
                    "id": generateUUID(),
                    "parentId": avgSourceId,
                    "timeStamp": Date.now() / 1000,
                    "latitude": avgLat,
                    "altitude": 0,
                    "longitude": avgLon,
                    "caption": "",
                    "tooltip": "",
                    "customActions": [],
                    "tags": {"layers": [], "creator": CREATOR_ID}
                });
                
                // group.points.forEach(point => {
                //     if (point.is_outlier) return;
                    
                //     const pointCoord = point.coord_tuple;
                //     const pointCaption = `${point.name || '-'} - ${point.timestamp || '-'}`;
                //     const pointSourceId = generateUUID();
                    
                //     result.push({
                //         "tacticObjectType": "source",
                //         "captionPosition": "right",
                //         "id": pointSourceId,
                //         "icon": {"type": "circle", "color": sourceColor},
                //         "caption": pointCaption,
                //         "name": pointCaption,
                //         "customActions": [],
                //         "trackBehavior": {},
                //         "bearingStyle": {"color": sourceColor, "thickness": 2, "dash": "solid", "border": null},
                //         "bearingBehavior": {},
                //         "tags": {"creator": CREATOR_ID}
                //     });
                    
                //     result.push({
                //         "tacticObjectType": "position",
                //         "id": generateUUID(),
                //         "parentId": pointSourceId,
                //         "timeStamp": point.timestamp_unix || (Date.now() / 1000),
                //         "latitude": pointCoord[1],
                //         "altitude": 0,
                //         "longitude": pointCoord[0],
                //         "caption": "",
                //         "tooltip": "",
                //         "customActions": [],
                //         "tags": {"layers": [], "creator": CREATOR_ID}
                //     });
                // });
            });
        });
        
        const jsonString = JSON.stringify(result, null, 2);
        const blob = new Blob(['\uFEFF' + jsonString], {type: 'application/json;charset=utf-8'});
        const dateStr = new Date().toISOString().slice(0, 10);
        
        const a = document.createElement('a');
        a.href = URL.createObjectURL(blob);
        a.download = `averaging_${dateStr}.json`;
        document.body.appendChild(a);
        a.click();
        document.body.removeChild(a);
        URL.revokeObjectURL(a.href);
    });
    
    // Initialize
    updateSourcesTable();
});
</script>
{% endblock %}
