"""
Abhängigkeiten:
- pyramids (für den Aufbau der Bildpyramiden)
- heartrate (zur Berechnung der Herzfrequenz)
- preprocessing (für die Video-Vorverarbeitung)
- eulerian (für die Euler'sche Video-Magnifikation)
- tkinter und constants (für die GUI und Konstantenverwaltung)

Autor: Roberto Gelsinger
Datum: 07.12.2023
Version: Modulversion
"""

import pyramids
import heartrate
import facedetection
import eulerian
from constants import freq_max, freq_min
import pandas as pd
from excel_update import color_cells_based_on_deviation
from excel_evaluation import evaluation


def process_video_for_excel(selected_video_name):
    """
    Verarbeitet ein ausgewähltes Video, um die Herzfrequenz der abgebildeten Person zu ermitteln.

    Dieser Prozess umfasst die Vorverarbeitung des Videos, den Aufbau einer Laplace-Pyramide,
    die Anwendung von FFT-Filterung und Euler'scher Magnifikation, und schließlich die Berechnung
    der Herzfrequenz aus den Video-Daten.

    Args:
    selected_video_name (str): Der Name des zu verarbeitenden Videos.

    Returns:
    None: Die Funktion gibt direkt die berechnete Herzfrequenz auf der Konsole aus.
    """

   
   
    print("Reading + preprocessing video...")
    video_frames, frame_ct, fps = facedetection.read_video("code/videos/"+selected_video_name)

    
    print("Building Laplacian video pyramid...")
    lap_video = pyramids.build_video_pyramid(video_frames)

    print(len(lap_video))

    for i, video in enumerate(lap_video):
        print("test")
        if i == 0 or i == len(lap_video)-1:
            continue

        print("Running FFT and Eulerian magnification...")
        result, fft, frequencies = eulerian.fft_filter(video, freq_min, freq_max, fps)
        lap_video[i] += result


        print("Calculating heart rate...")
        heart_rate = heartrate.find_heart_rate(fft, frequencies, freq_min, freq_max)





    print("Heart rate: ", heart_rate*0.7, "bpm")
    return heart_rate *0.7



def process_all_videos_and_save_results(testcase_excel_file_path, testruns_excel_file_path, code_version, kommentar):

    try:
        df_testruns = pd.read_excel(testruns_excel_file_path)
    except FileNotFoundError:
        df_testruns = pd.DataFrame()


    df_testcases = pd.read_excel(testcase_excel_file_path)

    existing_testcases = [col for col in df_testruns.columns if col.startswith('Testcase_')]

    new_testcases = [f'Testcase_{tc}' for tc in df_testcases['Testcase'] if f'Testcase_{tc}' not in existing_testcases]


    if df_testruns.empty:
        df_testruns = pd.DataFrame(columns=['Testnummer', 'Codeversion', 'Kommentar', 'Abweichung'])
    

    for col in new_testcases:
        df_testruns[col] = None 
    

    df_testruns.to_excel(testruns_excel_file_path, index=False)

    if new_testcases:
        print(f"Folgende neue Testcases wurden hinzugefügt: {new_testcases}")
    else:
        print("Keine neuen Testcases zum Hinzufügen gefunden.")

    next_testcase_index = len(df_testruns) + 1


    new_run = {
        'Testnummer': next_testcase_index,
        'Codeversion': code_version,
        'Kommentar': kommentar,
        'Abweichung': 'Wert_für_Abweichung'  
    }


    for index, row in df_testcases.iterrows():
        video_name = row['VideoName']
        heart_rate = process_video_for_excel(video_name)


        testcase_column_name = f'Testcase_{row["Testcase"]}'
        new_run[testcase_column_name] = heart_rate

    try:

        df_testruns = df_testruns._append(new_run, ignore_index=True)
    except TypeError:
        pass


    df_testruns.to_excel(testruns_excel_file_path, index=False)

    print("Testrun wurde verarbeitet und das Ergebnis in der Testruns-Excel-Datei gespeichert.")

    color_cells_based_on_deviation(testruns_excel_file_path, testcase_excel_file_path)

    print("Zellen gefärbt")

    evaluation(testcase_excel_file_path, testruns_excel_file_path)

    print("Testcases sortiert")