import {
  Component,
  ElementRef,
  Input,
  OnInit,
  ViewChild,
  OnDestroy,
} from '@angular/core';
import { EditorView, basicSetup } from 'codemirror';
import { FormControl } from '@angular/forms';
import { EditorState } from '@codemirror/state';
import { java } from '@codemirror/lang-java';
import { FormsModule, ReactiveFormsModule } from '@angular/forms';

@Component({
  standalone: true,
  selector: 'code-mirror-field',
  template: `<div #editorContainer style="border: 1px solid #ccc; max-height: 300px; overflow: auto; resize: vertical;"></div>`,
})
export class CodeMirrorFieldComponent implements OnInit, OnDestroy {
  @ViewChild('editorContainer', { static: true }) editorContainer!: ElementRef;
  @Input() formControl!: FormControl; // FormControl vindo do formulário reativo

  private editor!: EditorView;

  ngOnInit(): void {
    this.initializeEditor();

    // Atualizar o editor quando o valor do FormControl muda
    this.formControl.valueChanges.subscribe((value) => {
      if (this.editor.state.doc.toString() !== value) {
        this.updateEditorContent(value);
      }
    });
  }

  ngOnDestroy(): void {
    // Destruir o editor ao sair do componente
    this.editor.destroy();
  }

  private initializeEditor(): void {
    const cursorListener = EditorView.updateListener.of((update) => {
      if (update.selectionSet) {
        const cursorPosition = update.state.selection.main.head;
        const word = this.getCurrentWord(update.state, cursorPosition);
        console.log('Current word:', word);
      }
    });
    
    const updateListener = EditorView.updateListener.of((update) => {
      if (update.docChanged) {
        const content = update.state.doc.toString();
        this.formControl.setValue(content, { emitEvent: false }); // Atualizar FormControl
      }
    });

    this.editor = new EditorView({
      state: EditorState.create({
        doc: this.formControl.value || '', // Inicializa com o valor do FormControl
        extensions: [basicSetup, java(), updateListener, cursorListener],
      }),
      parent: this.editorContainer.nativeElement,
    });
  }

  private updateEditorContent(value: string): void {
    this.editor.dispatch({
      changes: { from: 0, to: this.editor.state.doc.length, insert: value },
    });
  }
  
  /**
   * Get the current word based on cursor position
   */
  private getCurrentWord(state: EditorState, position: number): string | null {
    const line = state.doc.lineAt(position); // Get the current line
    const lineText = line.text;
    const cursorIndex = position - line.from; // Cursor position within the line

    // Find the word around the cursor
    const left = lineText.slice(0, cursorIndex).match(/\b\w+$/);
    const right = lineText.slice(cursorIndex).match(/^\w+\b/);

    const leftWord = left ? left[0] : '';
    const rightWord = right ? right[0] : '';

    return leftWord + rightWord; // Combine both parts to get the full word
  }
}
