{# Logging panel component for experiment run #}
<div class="col-lg-6 col-sm-12 logging-panel d-flex flex-column h-100">
  <div class="d-flex justify-content-between align-items-center flex-shrink-0">
    <h5>Progress：</h5>
    <div class="d-flex gap-2 ms-auto">
      <button id="pause-resume" class="btn btn-info text-white">
        {% if pause_status %}
        <i class="bi bi-play-circle"></i>
        {% else %}
        <i class="bi bi-pause-circle"></i>
        {% endif %}
      </button>
      <button id="abort-current" class="btn btn-danger text-white">
        <i class="bi bi-stop-circle"></i>
      </button>
      <button id="abort-pending" class="btn btn-warning text-white">
        <i class="bi bi-hourglass-split"></i>
      </button>
    </div>
  </div>
  <small class="text-muted mt-2 flex-shrink-0">
    <strong>Note:</strong> The current step cannot be paused or stopped until it completes.
  </small>
  <div class="progress my-3 flex-shrink-0">
    <div id="progress-bar-inner" class="progress-bar progress-bar-striped progress-bar-animated"></div>
  </div>
  <!-- Tabs -->
  <ul class="nav nav-tabs flex-shrink-0" id="logPlotTabs" role="tablist">
    <li class="nav-item" role="presentation">
      <button class="nav-link active" id="log-tab" data-bs-toggle="tab" data-bs-target="#log" type="button"
        role="tab">Log</button>
    </li>
    <li class="nav-item" role="presentation">
      <button class="nav-link" id="queue-tab" data-bs-toggle="tab" data-bs-target="#queue" type="button"
        role="tab">Queue</button>
    </li>
    <li class="nav-item" role="presentation">
      <button class="nav-link" id="plot-tab" data-bs-toggle="tab" data-bs-target="#plot" type="button"
        role="tab">Optimizer Plot</button>
    </li>
  </ul>
  <div class="tab-content mt-3 flex-grow-1 d-flex flex-column" id="logPlotTabsContent" style="min-height: 0;">
    <div class="tab-pane fade show active flex-grow-1 h-100" id="log" role="tabpanel" style="min-height: 0;">
      <div class="d-flex flex-column h-100">
        <div id="logging-panel" class="border p-2 bg-light flex-grow-1 overflow-auto"></div>
      </div>
    </div>
    <div class="tab-pane fade flex-grow-1 h-100" id="queue" role="tabpanel" style="overflow-y: auto; min-height: 0;">
      <div class="d-flex flex-column h-100 justify-content-start">
        <div id="queue-list" class="list-group w-100">
          <!-- Queue items will be inserted here -->
        </div>
      </div>
    </div>
    <div class="tab-pane fade flex-grow-1 h-100" id="plot" role="tabpanel" style="overflow-y: auto;">
      <div class="d-flex flex-column h-100 justify-content-start">
        <button class="btn btn-success mb-2" onclick="showPlot()">Refresh Plot</button>
        <small class="text-muted d-block mt-1" id="plot-info">This function is only available for NIMO
          optimizers.</small>
        <br>
        <img id="optimizerPlot" src="" class="img-fluid rounded shadow-sm d-block mx-auto"
          style="max-width:100%; display:none;">
      </div>
    </div>
  </div>
</div>
<!-- Abort Pending Modal -->
<div class="modal fade" id="abortPendingModal" tabindex="-1" aria-hidden="true">
  <div class="modal-dialog">
    <div class="modal-content">
      <div class="modal-header">
        <h5 class="modal-title">Stop After This Iteration?</h5>
        <button type="button" class="btn-close" data-bs-dismiss="modal"></button>
      </div>

      <div class="modal-body">
        <p>Do you want to stop after this iteration?</p>
        <div class="form-check">
          <input class="form-check-input" type="checkbox" id="cleanup-checkbox">
          <label class="form-check-label" for="cleanup-checkbox">
            Proceed to cleanup steps
          </label>
        </div>
      </div>

      <div class="modal-footer">
        <button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Cancel</button>
        <button type="button" class="btn btn-danger" id="abortPendingConfirm">
          Confirm
        </button>
      </div>
    </div>
  </div>
</div>
</div>
<!-- Input Modal -->
<div class="modal fade" id="inputModal" tabindex="-1" data-bs-backdrop="static" data-bs-keyboard="false"
  aria-hidden="true">
  <div class="modal-dialog">
    <div class="modal-content">
      <div class="modal-header">
        <h5 class="modal-title">User Input Required</h5>
      </div>
      <div class="modal-body">
        <p id="input-prompt"></p>
        <div id="input-container">
          <!-- Dynamic input will be inserted here -->
        </div>
      </div>
      <div class="modal-footer">
        <button type="button" class="btn btn-primary" id="submit-input-btn">Submit</button>
      </div>
    </div>
  </div>
</div>
<!-- Queue Details Modal -->
<div class="modal fade" id="queueDetailsModal" tabindex="-1" aria-hidden="true">
  <div class="modal-dialog modal-lg">
    <div class="modal-content">
      <div class="modal-header">
        <h5 class="modal-title">Task Details</h5>
        <button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
      </div>
      <div class="modal-body">
        <pre id="queue-details-content" class="bg-light p-3 border rounded"></pre>
      </div>
      <div class="modal-footer">
        <button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Close</button>
      </div>
    </div>
  </div>
</div>
<script>
    function showPlot() {
        const img = document.getElementById('optimizerPlot');
        img.src = "{{ url_for('execute.get_optimizer_plot') }}";
        img.style.display = 'block';
    }

  let currentDetailsMsg = null;
  let currentTaskId = null;

  function renderTaskDetails(details, fullConfig = null) {
    const content = document.getElementById('queue-details-content');
    content.innerHTML = '';
    currentDetailsMsg = details; // Store for reloading

    if (!details) {
      content.innerText = "No details available.";
      return;
    }

    const table = document.createElement('table');
    table.className = 'table table-striped table-sm';
    const tbody = document.createElement('tbody');

    for (const [key, value] of Object.entries(details)) {
      if (key === 'Config Preview (First 5)' || key === 'Full Config') continue;

      const row = document.createElement('tr');
      const th = document.createElement('th');
      th.scope = 'row';
      th.innerText = key;
      const td = document.createElement('td');

      if (typeof value === 'object' && value !== null) {
        td.innerHTML = `<pre class="m-0" style="max-height: 200px; overflow: auto;">${JSON.stringify(value, null, 2)}</pre>`;
      } else {
        td.innerText = value;
      }
      row.appendChild(th);
      row.appendChild(td);
      tbody.appendChild(row);
    }
    table.appendChild(tbody);
    content.appendChild(table);

    // Handle Config Display
    if (fullConfig) {
      const configContainer = document.createElement('div');
      configContainer.className = 'mt-3';
      configContainer.innerHTML = `<h6>Full Configuration (${fullConfig.length} entries):</h6>`;
      const pre = document.createElement('pre');
      pre.className = 'bg-white p-2 border rounded';
      pre.style.maxHeight = '400px';
      pre.style.overflow = 'auto';
      pre.innerText = JSON.stringify(fullConfig, null, 2);
      configContainer.appendChild(pre);
      content.appendChild(configContainer);

    } else if (details['Config Preview (First 5)']) {
      const configContainer = document.createElement('div');
      configContainer.className = 'mt-3';
      configContainer.innerHTML = '<h6>Configuration Preview (First 5):</h6>';
      const pre = document.createElement('pre');
      pre.className = 'bg-white p-2 border rounded';
      pre.innerText = JSON.stringify(details['Config Preview (First 5)'], null, 2);
      configContainer.appendChild(pre);

      const loadBtn = document.createElement('button');
      loadBtn.className = 'btn btn-sm btn-primary mt-2';
      loadBtn.innerText = 'Load Full Config';
      loadBtn.onclick = () => loadFullConfig(currentTaskId);
      configContainer.appendChild(loadBtn);

      content.appendChild(configContainer);
    }
  }

  function showQueueDetails(details, taskId) {
    currentTaskId = taskId;
    renderTaskDetails(details);
    const modal = new bootstrap.Modal(document.getElementById('queueDetailsModal'));
    modal.show();
  }

  function loadFullConfig(taskId) {
    if (taskId === null) return;
    const btn = document.querySelector('#queue-details-content button');
    if (btn) {
      btn.disabled = true;
      btn.innerText = 'Loading...';
    }

    // Use a dummy ID 0 to generate the base URL, then replace it with the actual taskId
    const baseUrl = "{{ url_for('execute.get_queue_task_details', task_id=0) }}".slice(0, -1);
    fetch(`${baseUrl}${taskId}`)
      .then(response => response.json())
      .then(data => {
        if (data && data["Full Config"]) {
          renderTaskDetails(currentDetailsMsg, data["Full Config"]);
        } else {
          alert('Failed to load full configuration.');
          if (btn) {
            btn.disabled = false;
            btn.innerText = 'Load Full Config';
          }
        }
      })
      .catch(err => {
        console.error(err);
        alert('Error loading configuration.');
        if (btn) {
          btn.disabled = false;
          btn.innerText = 'Load Full Config';
        }
      });
  }

  function updateQueue() {
    // Add timestamp to prevent caching
    const timestamp = new Date().getTime();
    fetch("{{ url_for('execute.get_queue') }}?t=" + timestamp)
      .then(response => response.json())
      .then(data => {
        const queueList = document.getElementById('queue-list');
        // If element doesn't exist (e.g. if tabs are switched or hidden?), return
        if (!queueList) return;

        queueList.innerHTML = '';
        if (data.length === 0) {
          queueList.innerHTML = '<div class="list-group-item text-center text-muted">No pending tasks</div>';
          return;
        }
        data.forEach((task, index) => {
          const item = document.createElement('div');
          item.className = 'list-group-item d-flex justify-content-between align-items-center';

          const infoDiv = document.createElement('div');
          infoDiv.style.cursor = 'pointer';
          infoDiv.setAttribute('title', 'Click to view details');

          let batchBadge = '';
          if (task.details && task.details['Batch Size']) {
            batchBadge = `<span class="badge bg-info text-dark ms-2">Batch: ${task.details['Batch Size']}</span>`;
          }

          infoDiv.innerHTML = `
              <span class="badge bg-secondary me-2">#${index + 1}</span>
              <span class="fw-bold">${task.name}</span>
              ${batchBadge}
              <br>
              <small class="text-muted ms-4">${task.args}</small>
          `;
          infoDiv.onclick = () => showQueueDetails(task.details, index); // Use index as ID for now, backend uses index
          item.appendChild(infoDiv);

          const controlsDiv = document.createElement('div');
          controlsDiv.innerHTML = `
              <button class="btn btn-sm btn-outline-secondary" onclick="reorderTask(${index}, 'up')" ${index === 0 ? 'disabled' : ''}>
                <i class="bi bi-arrow-up"></i>
              </button>
              <button class="btn btn-sm btn-outline-secondary" onclick="reorderTask(${index}, 'down')" ${index === data.length - 1 ? 'disabled' : ''}>
                <i class="bi bi-arrow-down"></i>
              </button>
              <button class="btn btn-sm btn-outline-danger" onclick="deleteTask(${index})">
                <i class="bi bi-trash"></i>
              </button>
          `;
          item.appendChild(controlsDiv);

          queueList.appendChild(item);
        });
      })
      .catch(error => console.error('Error fetching queue:', error));
  }

  function deleteTask(id) {
    fetch("{{ url_for('execute.delete_queue_task') }}", {
      method: 'POST',
      headers: {
        'Content-Type': 'application/json'
      },
      body: JSON.stringify({ id: id })
    })
      .then(response => response.json())
      .then(data => {
        if (data.status === 'ok') {
          updateQueue();
        } else {
          console.error('Delete failed:', data.error);
        }
      })
      .catch(error => console.error('Error deleting task:', error));
  }

  function reorderTask(id, direction) {
    fetch("{{ url_for('execute.reorder_queue_task') }}", {
      method: 'POST',
      headers: {
        'Content-Type': 'application/json'
      },
      body: JSON.stringify({ id: id, direction: direction })
    })
      .then(response => response.json())
      .then(data => {
        if (data.status === 'ok') {
          updateQueue();
        } else {
          console.error('Reorder failed:', data.error);
        }
      })
      .catch(error => console.error('Error reordering task:', error));
  }

  // Poll queue status every 2 seconds
  // Store interval ID to potentially clear it if needed
  if (!window.queueInterval) {
    window.queueInterval = setInterval(updateQueue, 2000);
  }
  updateQueue(); // Initial call
</script>