import {Component, OnDestroy, OnInit} from '@angular/core';
import {CloudData, CloudOptions} from 'angular-tag-cloud-module';
import {LecturerInfoService} from 'src/app/services/lecturer-info.service';
import {LecturerDataService} from 'src/app/services/lecturer-data.service';
import {WordDetailsDao} from 'src/app/dao/word-details.dao';
import {QuestionDao} from 'src/app/dao/question.dao';
import {el} from '@angular/platform-browser/testing/src/browser_util';

@Component({
  selector:  'app-sentiment-cloud',
  templateUrl: './sentiment-cloud.component.html',
  styleUrls: ['./sentiment-cloud.component.css']
})
export class SentimentCloudComponent implements OnInit, OnDestroy {

  private maxOccurrences: number;
  private wordClouds: any[][];
  public loading: boolean;
  public options: CloudOptions;
  public questions: QuestionDao[];
  public wordcloudData: CloudData[];
  public currentQuestion: QuestionDao;

  constructor(private lecturerInfoService: LecturerInfoService,
              private lecturerDataService: LecturerDataService) {
  }

  ngOnInit(): void {
    this.questions = [];
    this.wordClouds = [];
    this.wordcloudData = [];
    this.maxOccurrences = 0;
    this.loading = true;
    this.options = {
      width : 1000,
      height : 400,
      overflow: false,
    };
    this.lecturerInfoService.getPaperQuestions(this.lecturerDataService.currentPaper.paperId)
      .subscribe((data: QuestionDao[]) => {
        this.questions = data;
        this.currentQuestion = this.questions[0];
      });
    this.lecturerInfoService.getSentimentCloud(this.lecturerDataService.currentPaper.paperId)
      .subscribe((data: WordDetailsDao[]) => {
        if (data) {
          if (data.length > 0) {
            this.sortData(data);
            this.wordcloudData = this.createCloud(data);
          } else {
            this.wordcloudData = [];
          }
        }
        this.loading = false;
      });
  }

  ngOnDestroy(): void {
    this.questions = [];
    this.wordClouds = [];
    this.wordcloudData = [];
  }

  private sortData(data: WordDetailsDao[]) {
    this.questions.forEach(question => {
      this.wordClouds.push(data.filter(word => word.questionId === parseInt(question.questionId.toString(), 10)));
    });
  }

  private createCloud(data: WordDetailsDao[]): CloudData[] {
    const words: any = [];
    data.forEach(word => {
        words.push({text: word.word, weight: word.numberOfOccurrences, color: this.getColour(word.polarity) });
    });
    return words;
  }

  private getAllData() {
    const data = [];
    const allWords = new Set();
    this.wordClouds.forEach((list: WordDetailsDao[]) => {
      list.forEach((word: WordDetailsDao) => {
        if (!allWords.has(word.word)) {
          allWords.add(word.word);
          data.push(word);
        } else {
          this.updateWord(data, word);
        }
      });
    });

    return data;
  }

  private updateWord(wordDetails: WordDetailsDao[], word: WordDetailsDao): any {
    wordDetails.forEach((elem: WordDetailsDao) => {
      if (elem.word === word.word) {
        elem.numberOfOccurrences = elem.numberOfOccurrences + 1;
        elem.polarity = this.calculateScore(elem.polarity, word.polarity);
      }
    });
  }

  private calculateScore(currentScore: number, score: number): number {
    if (score === currentScore) {
      return currentScore;
    }

    if (score < currentScore) {
      return currentScore - 1;
    } else {
      return currentScore + 1;
    }
  }

  private getColour(polarity: number): String {
    switch (polarity) {
      case 0: return '#FF0000';
      case 1: return '#CA6F1E';
      case 2: return '#7e7e7e';
      case 3: return '#37ff48';
      case 4: return '#009b13';
      default: return '#000000';
    }
  }

  public setCloud() {
    this.wordcloudData = [];
    if (this.currentQuestion === undefined) {
      this.wordcloudData = this.createCloud(this.getAllData());
    } else {
      this.wordClouds.forEach(list => {
        if (list[0].questionId === parseInt(this.currentQuestion.questionId.toString(), 10)) {
          this.wordcloudData = this.createCloud(list);
        }
      });
    }
  }

}