import { Component, ElementRef, Inject, OnInit, ViewChild } from '@angular/core';
import { EnviarInfoService } from '../../../Administrador/services/enviar-info.service';
import { MatTableDataSource } from '@angular/material/table';
import { MatPaginator } from '@angular/material/paginator';
import { MAT_DIALOG_DATA, MatDialog, MatDialogModule, MatDialogRef } from '@angular/material/dialog';
import { CommonModule } from '@angular/common';
import { ReactiveFormsModule, FormGroup, FormControl, FormBuilder, Validators } from '@angular/forms';
import { MatAutocompleteModule } from '@angular/material/autocomplete';
import { MatOption } from '@angular/material/core';
import { MatFormFieldModule } from '@angular/material/form-field';
import { MatIconModule, MatIconRegistry } from '@angular/material/icon';
import { MatInputModule } from '@angular/material/input';
import { MatProgressSpinnerModule } from '@angular/material/progress-spinner';
import { MatSelectModule } from '@angular/material/select';
import * as XLSX from 'xlsx';
import { DomSanitizer } from '@angular/platform-browser';
import Swal from 'sweetalert2';
import { RegistroCalificacionesService } from '../../services/registroCalificaciones.service';
import { MatSlideToggleChange } from '@angular/material/slide-toggle';
import { forkJoin, last, lastValueFrom, map, Observable, startWith } from 'rxjs';
import { GradosEducativosService } from '../../../Administrador/services/grados-educativos.service';
import { GruposService } from '../../../Administrador/services/grupos.service';
import { MateriaService } from '../../../Administrador/services/materia.service';
import { ProfesorBitacoraService } from '../../services/profesor-bitacora.service';
import { H } from '@fullcalendar/core/internal-common';
import { HttpClient } from '@angular/common/http';

@Component({
  selector: 'app-registro-calificaciones',
  templateUrl: './registro-calificaciones.component.html',
  styleUrl: './registro-calificaciones.component.css'
})
export class RegistroCalificacionesComponent implements OnInit {
  color: string = '';
  textColor: string = '';
  filtro: string = 'Activo';
  displayedColumns: string[] = ['Periodo', 'MGG', 'Alumno', 'Calificacion', 'UsuarioRegistro', 'UltActualizacion', 'estado', 'Acciones'];
  dataSource = new MatTableDataSource<any>([]);
  isLoading: boolean = true;

  @ViewChild(MatPaginator) paginator!: MatPaginator;
  @ViewChild('TABLE') table!: ElementRef;
  constructor(private _enviarInfo: EnviarInfoService, public dialog: MatDialog, private _DomSanitizer: DomSanitizer, private _MatIconRegister: MatIconRegistry,
    private _registroCalificacionesService: RegistroCalificacionesService) {
    this._MatIconRegister.addSvgIcon('excel', this._DomSanitizer.bypassSecurityTrustResourceUrl('assets/icons/excel.svg'));

  }


  ngOnInit(): void {
    this._enviarInfo.currentTextColor.subscribe(textColor => {
      this.textColor = textColor;
    });
    this._enviarInfo.currentColor.subscribe(color => {
      this.color = color;
    });
    this.getCalificaciones();
    this._registroCalificacionesService.dataUpdated$.subscribe(() => {
      this.getCalificaciones();
    });
  }

  getCalificaciones() {
    this._registroCalificacionesService.getRegistros().subscribe((data: any) => {
      this.dataSource = new MatTableDataSource(data);
      this.dataSource.paginator = this.paginator;
      this.isLoading = false;
      this.Filtro(this.filtro);
    });
  }

  applyFilter(event: Event) {
    const filterValue = (event.target as HTMLInputElement).value;
    this.dataSource.filter = filterValue.trim().toLowerCase();
    if (this.dataSource.paginator) {
      this.dataSource.paginator.firstPage();
    }
  }

  Filtro(event: any) {
    this.filtro = event;
    this.dataSource.filter = this.filtro;
  }

  openDialog() {
    const modal = this.dialog.open(CrearRegistro, {
    });
  }

  openEditar(data: any) {
    const modal = this.dialog.open(CrearRegistro, {
      data: data
    });
  }

  exportAsExcel() {
    const ws: XLSX.WorkSheet = XLSX.utils.table_to_sheet(this.table.nativeElement);
    const wb: XLSX.WorkBook = XLSX.utils.book_new();
    XLSX.utils.book_append_sheet(wb, ws, 'COLEGIOABC-ConsultaTipos');
    XLSX.writeFile(wb, 'Tipos.xlsx');
  }

  exportAll() {
    const dataSource = this.dataSource.data;
    const ws: XLSX.WorkSheet = XLSX.utils.json_to_sheet(dataSource);
    const wb: XLSX.WorkBook = XLSX.utils.book_new();
    XLSX.utils.book_append_sheet(wb, ws, 'COLEGIOABC-ConsultaTipos');
    XLSX.writeFile(wb, 'Tipos.xlsx');
  }

  onToggleChange(event: MatSlideToggleChange, row: any) {
    event.source.checked = !event.checked;
    if (row.estado === 'Activo') {
      this.confirmDelete(row.idBitacora, () => {
        this.delete(row, () => {
          row.estado = 'Eliminado';
          event.source.checked = false;
        });
      });
    } else {
      this.confirmEnable(row, () => {
        this.habilitarEstado(row.idBitacora, () => {
          row.estado = 'Activo';
          event.source.checked = true;
        });
      });
    }
  }

  confirmDelete(id: string, callback: () => void) {
    Swal.fire({
      title: '¿Estas seguro de eliminar este registro?',
      text: "No podras revertir esta acción!",
      icon: 'warning',
      showCancelButton: true,
      confirmButtonColor: '#3085d6',
      cancelButtonColor: '#d33',
      confirmButtonText: 'Si, eliminar!',
    }).then((result) => {
      if (result.isConfirmed) {
        callback();
      }
    });
  }

  confirmEnable(id: string, callback: () => void) {
    Swal.fire({
      title: '¿Estas seguro de habilitar este registro?',
      icon: 'warning',
      showCancelButton: true,
      confirmButtonColor: '#3085d6',
      cancelButtonColor: '#d33',
      confirmButtonText: 'Si, habilitar!',
    }).then((result) => {
      if (result.isConfirmed) {
        callback();
      }
    });
  }
  delete(id: string, callback: () => void) {
    this._registroCalificacionesService.eliminarRegistro(id).subscribe((res: any) => {
      Swal.fire('Exito!', res.message, 'success');
      callback();
    });
  }
  habilitarEstado(id: string, callback: () => void) {
    this._registroCalificacionesService.habilitarRegistro(id).subscribe((res: any) => {
      Swal.fire('Exito!', res.message, 'success');
      callback();
    });
  }

}


@Component({
  selector: 'app-RegistroCalificaciones',
  templateUrl: 'RegistroCalificaciones.html',
  styleUrl: './registro-calificaciones.component.css',
  standalone: true,
  imports: [MatDialogModule, MatIconModule, MatFormFieldModule, ReactiveFormsModule, MatSelectModule, MatInputModule, MatOption, CommonModule, MatIconModule,
    MatProgressSpinnerModule, MatAutocompleteModule]
})
export class CrearRegistro implements OnInit {
  form!: FormGroup;
  isLoading: boolean = true;
  todos: any;
  public materias: any;
  junto: any;
  public filtrados: any;
  public dataUsuarios: any;
  public alumnos: any;
  periodos: any;
  myControl = new FormControl('', [Validators.required]);
  filteredOptions!: Observable<string[]>;
  userRegistro = JSON.parse(localStorage.getItem('userDataS') ? localStorage.getItem('userDataS') || '' : localStorage.getItem('userData') || '');
  constructor(private fb: FormBuilder,
    public dialog: MatDialogRef<CrearRegistro>,
    @Inject(MAT_DIALOG_DATA) public data: any,
    public dialog1: MatDialog,
    private gradosService: GradosEducativosService,
    private gruposService: GruposService,
    private materiasService: MateriaService,
    private profesorService: ProfesorBitacoraService,
    private _registroCalificacionesService: RegistroCalificacionesService
  ) {
    this.gradosGrupos();
    this.materiasS();
    this.getAlumnos();
    this.formulario();
    console.log(data);
  }

  ngOnInit(): void {
    if (this.data) {
      this.form.patchValue({
        gradoGrupo: this.data.idGradoGrupoRelacionado,
        alumno: this.data.idAlumnoBoletaCalificaciones,
        periodo: this.data.idPeriodoBoletaCalificaciones,
        calificacion: this.data.calificacion,

      })
      this.myControl.setValue(this.data.nombreAlumno);
      this.form.get('gradoGrupo')?.disable();
      this.form.get('materia')?.disable();
      this.myControl.disable();
    }
  }

  formulario() {
    this.form = this.fb.group({
      gradoGrupo: ['', Validators.required],
      materia: ['', Validators.required],
      alumno: ['', Validators.required],
      periodo: ['', Validators.required],
      calificacion: ['', Validators.required],
      usuarioRegistro: [this.userRegistro[0]],
    });
  }

  isValidField(field: string, errorType: string) {
    const control = this.form.get(field);
    return control?.hasError(errorType) && control?.touched;
  }

  isValidField1(errorType: string) {
    return this.myControl.hasError(errorType) && this.myControl.touched;
  }

  gradosGrupos() {
    forkJoin({
      grados: this.gradosService.getHabilitados(),
      grupos: this.gruposService.getHabilitados()
    }).subscribe(({ grados, grupos }: any) => {
      this.todos = grados.concat(grupos);

      this.junto = this.todos.map((data: any) => {
        return {
          id: data.nombreGrado || data.idGrupo,
          nombre: data.nombreGrado || data.nombreGrupo
        }
      })
    });
  }

  materiasS() {
    this.materiasService.getHabilitados().subscribe((response: any) => {
      this.materias = response;
      if (this.data) {
        this.filtrados = this.materias.filter((materia: any) => materia.idGradoGrupoRelacionado === this.data.idGradoGrupoRelacionado);
        this.form.get('materia')?.setValue(this.data.idMateriaBoletaCalificaciones);
      }
    });
    this._registroCalificacionesService.getPeriodos().subscribe((data: any) => {
      this.periodos = data;
      this.isLoading = false;
    });
  }

  // onGradoGrupo(event: any) {
  //   this.filtrados = this.materias.filter((materia: any) => materia.idGradoGrupoRelacionado === event);
  //   this.alumnos = this.dataUsuarios.filter((alumno: any) => alumno.grado == event || alumno.idGrupo == event);
  //   console.log("🚀 ~ CrearRegistro ~ onGradoGrupo ~ this.alumnos:", this.alumnos)



  //   this.filteredOptions = this.myControl.valueChanges.pipe(
  //     startWith(''),
  //     map(value => this._filter(value || '')),
  //   );
  // }

  onGradoGrupo(event: any) {
    this.filtrados = this.materias.filter((materia: any) => materia.idGradoGrupoRelacionado === event);

    // Filtrar alumnos y agrupar por idUsuario (evitar duplicados)
    const alumnosFiltrados = this.dataUsuarios.filter(
      (alumno: any) => alumno.grado == event || alumno.idGrupo == event
    );

    // Agrupar por idUsuario usando reduce
    this.alumnos = alumnosFiltrados.reduce((acc: any[], curr: any) => {
      if (!acc.some(a => a.idUsuario === curr.idUsuario)) {
        acc.push(curr);
      }
      return acc;
    }, []);

    // console.log("🚀 ~ CrearRegistro ~ onGradoGrupo ~ this.alumnos:", this.alumnos);

    this.filteredOptions = this.myControl.valueChanges.pipe(
      startWith(''),
      map(value => this._filter(value || '')),
    );
  }

  nombreAlum(event: any) {
    const idAlum = this.dataUsuarios.filter((alumno: any) => alumno.nombreAlumno == event);
    this.form.get('alumno')?.setValue(idAlum[0].idUsuario);
  }


  private _filter(value: string): string[] {
    const filterValue = value.toLowerCase();
    return this.alumnos.map((option: any) => option.nombreAlumno).filter((nombre: string) => nombre.toLowerCase().includes(filterValue));
  }

  getAlumnos() {
    this.profesorService.getAlum().subscribe((data: any) => {
      this.dataUsuarios = data;
    });
  }

  onSave() {
    if (this.form.invalid || this.myControl.invalid) {
      return Object.values(this.form.controls).forEach(control => {
        control.markAsTouched();
        this.myControl.markAsTouched();
        Swal.fire({
          icon: 'error',
          title: 'Oops...',
          text: 'Faltan campos por llenar',
        });
      });
    }
    console.log(this.form.value);
    if (this.data) {
      console.log(this.form.getRawValue());
      this._registroCalificacionesService.editarRegistro(this.form.getRawValue()).subscribe((data: any) => {
      });
    } else {
      this._registroCalificacionesService.crearRegistro(this.form.value).subscribe((data: any) => {
        console.log(data);
      });
    }

  }

  limpiar() {
    this.form.reset();
    this.myControl.reset();
  }

  openCargaMasiva(data: any) {
    console.log(this.form.value.materia);

    if (this.form.value.gradoGrupo == '' || this.form.value.materias == '' || this.myControl.value != '') {
      return;
    } else {
      // console.log(data);
      const modal = this.dialog1.open(CargaMasiva, {

        data: {
          alumnos: this.alumnos,
          periodos: this.periodos,
          materia: this.form.value.materia,
          gradoGrupo: this.form.value.gradoGrupo,
        }
      });
    }
  }
}

@Component({
  selector: 'app-CargaMasiva',
  templateUrl: './cargaMasiva.html',
  styleUrl: './registro-calificaciones.component.css',
  standalone: true,
  imports: [MatDialogModule, MatIconModule, MatFormFieldModule, ReactiveFormsModule, MatSelectModule, MatInputModule, MatOption, CommonModule, MatIconModule,
    MatProgressSpinnerModule, MatAutocompleteModule]
})
export class CargaMasiva implements OnInit {
  public alumnosConCalificaciones: any[] = []; 
  public isLoading: boolean = true;

  constructor(private fb: FormBuilder, public dialog: MatDialogRef<CargaMasiva>, @Inject(MAT_DIALOG_DATA) public data: any, private calificacionService: RegistroCalificacionesService) {
    console.log(data);
  }

  ngOnInit(): void {
    this.calificacionService.getRegistrosConCalificacion(this.data.gradoGrupo, this.data.materia).subscribe((data: any) => {
      this.alumnosConCalificaciones = data;
      this.procesarCalificaciones(data);
      this.isLoading = false;
    });
  }
  public form: FormGroup = this.fb.group({
    grupo: ['', [Validators.required]],
  });

  isValidField(field: string) {
    return this.form.controls[field].errors && this.form.controls[field].touched;
  }


  // Después de recibir los datos del API, procesalos para facilitar el acceso
  procesarCalificaciones(data: any[]) {
    this.alumnosConCalificaciones = data;
  }

  getCalificacion(alumnoId: string, periodoId: string): string | null {
    const calificacion = this.alumnosConCalificaciones.find(item =>
      item.idUsuario === alumnoId &&
      item.idPeriodoBoletaCalificaciones === periodoId
    );

    return calificacion ? calificacion.calificacion : null;
  }

  guardarCalificaciones() {
    // Validar que hay datos necesarios
    if (!this.data || !this.data.alumnos || !this.data.periodos || !this.data.materia) {
      alert('Datos incompletos para procesar las calificaciones');
      return;
    }

    // Preparar los datos para enviar
    const datosEnvio: any[] = [];

    // Recorrer cada alumno
    this.data.alumnos.forEach((alumno: any) => {
      // Recorrer cada periodo
      this.data.periodos.forEach((periodo: any) => {
        // Obtener el valor del input correspondiente
        // Usamos idUsuario como identificador único del alumno
        const input = document.querySelector(
          `input[data-alumno="${alumno.idUsuario}"][data-periodo="${periodo.idPeriodo}"]`
        ) as HTMLInputElement;

        if (input) {
          const calificacion = input.value.trim();

          // Validar que la calificación sea un número válido
          if (calificacion && !isNaN(Number(calificacion))) {
            datosEnvio.push({
              alumnoId: alumno.idUsuario, // Usamos idUsuario como identificador
              materiaId: this.data.materia, // Usamos el string directamente
              periodoId: periodo.idPeriodo,
              calificacion: Number(calificacion), // Convertir a número
              idGrupo: alumno.idGrupo, // Incluimos el grupo del alumno
              grado: alumno.grado // Incluimos el grado del alumno
            });
          } else if (calificacion) {
            console.warn(`Calificación inválida para ${alumno.nombreAlumno} en ${periodo.nombrePeriodo}: ${calificacion}`);
          }
        }
      });
    });

    console.log('Datos a enviar:', datosEnvio);

    if (datosEnvio.length === 0) {
      alert('No hay calificaciones válidas para guardar');
      return;
    }
    // Enviar al servidor
    this.calificacionService.crearRegistroMasivo(datosEnvio).subscribe({
      next: (response: any) => {
        console.log('Respuesta del servidor:', response);
        if (response.status === 200) {
          alert('Calificaciones guardadas exitosamente');
          this.dialog.close(true); // Cerrar con éxito
        } else {
          alert(response.mensaje || 'Error al guardar calificaciones');
        }
      },
      error: (error) => {
        console.error('Error al enviar datos:', error);
        alert(error.error?.mensaje || 'Error al enviar datos al servidor');
      }
    });
  }

  saveGrupo() {
    if (this.form.invalid) {
      this.form.markAllAsTouched();
      return;
    }
  }

  limpiar() {
    this.form.reset();
  }
}

