from PySide6.QtCore import QObject, QThread, Signal from datetime import datetime, timedelta from pathlib import Path import shutil import tempfile from models.api_model import HelioviewerAPI from utils.video_creator import VideoCreator class TimelapseWorker(QThread): log = Signal(str) progress = Signal(int, int) finished = Signal(bool, str) def __init__(self, source_id, start_date, end_date, output_path, fps=10): super().__init__() self.source_id = source_id self.start_date = start_date self.end_date = end_date self.output_path = output_path self.fps = fps self.cancelled = False self.temp_dir = None def cancel(self): self.cancelled = True self.log.emit("⏹️ Отмена процесса...") def run(self): try: # Создаем временную папку self.temp_dir = Path(tempfile.mkdtemp(prefix="timelapse_")) self.log.emit(f"📁 Временная папка: {self.temp_dir}") # Генерируем даты dates = [] current = self.start_date.replace(hour=12, minute=0, second=0) while current <= self.end_date: dates.append(current) current += timedelta(days=1) total = len(dates) self.log.emit(f"📊 Всего файлов: {total}") downloaded = [] # Скачиваем for i, date in enumerate(dates): if self.cancelled: self.cleanup() self.finished.emit(False, "Отменено") return percent = int((i + 1) / total * 100) self.progress.emit(i + 1, total) self.log.emit(f"📥 [{i + 1}/{total}] {percent}% - {date.strftime('%Y-%m-%d')}") filepath = HelioviewerAPI.download_image(self.source_id, date, self.temp_dir) if filepath: downloaded.append(filepath) self.log.emit(f"✅ [{i + 1}/{total}] Успешно") else: self.log.emit(f"❌ [{i + 1}/{total}] Ошибка") if self.cancelled: self.cleanup() self.finished.emit(False, "Отменено") return if not downloaded: self.cleanup() self.finished.emit(False, "Нет файлов") return # Создаем видео self.log.emit("🎬 Создание видео...") self.progress.emit(total, total) video_path = VideoCreator.create_timelapse(downloaded, self.output_path, self.fps) # Очистка self.cleanup() if video_path and video_path.exists(): self.finished.emit(True, str(video_path)) else: self.finished.emit(False, "Ошибка создания видео") except Exception as e: self.cleanup() self.finished.emit(False, str(e)) def cleanup(self): if self.temp_dir and self.temp_dir.exists(): shutil.rmtree(self.temp_dir) self.log.emit("🗑️ Временные файлы удалены") class TimelapseController(QObject): def __init__(self): super().__init__() self.worker = None self.log = Signal(str) self.progress = Signal(int, int) self.finished = Signal(bool, str) def create(self, source_id, start_date, end_date, output_path, fps=10): self.worker = TimelapseWorker(source_id, start_date, end_date, output_path, fps) self.worker.log.connect(self.log) self.worker.progress.connect(self.progress) self.worker.finished.connect(self.finished) self.worker.start() return self.worker def cancel(self): if self.worker: self.worker.cancel()