/*
 * Copyright 2000-2016 JetBrains s.r.o.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.intellij.codeInsight.daemon.impl;

import com.intellij.codeInsight.daemon.DaemonCodeAnalyzer;
import com.intellij.lang.annotation.HighlightSeverity;
import com.intellij.openapi.Disposable;
import com.intellij.openapi.application.Application;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.editor.Document;
import com.intellij.openapi.editor.Editor;
import com.intellij.openapi.fileEditor.FileEditorManager;
import com.intellij.openapi.fileEditor.FileEditorManagerEvent;
import com.intellij.openapi.fileEditor.FileEditorManagerListener;
import com.intellij.openapi.project.DumbAwareRunnable;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.wm.StatusBar;
import com.intellij.openapi.wm.WindowManager;
import com.intellij.util.Alarm;
import org.jetbrains.annotations.NotNull;

public class StatusBarUpdater implements Disposable {
  private final Project myProject;
  private final DumbAwareRunnable myUpdateStatusRunnable = new DumbAwareRunnable() {
    @Override
    public void run() {
      if (!myProject.isDisposed()) {
        updateStatus();
      }
    }
  };
  private final Alarm updateStatusAlarm = new Alarm();

  StatusBarUpdater(Project project) {
    myProject = project;

    project.getMessageBus().connect(this).subscribe(FileEditorManagerListener.FILE_EDITOR_MANAGER, new FileEditorManagerListener() {
      @Override
      public void selectionChanged(@NotNull FileEditorManagerEvent event) {
        updateLater();
      }
    });

    project.getMessageBus().connect(this).subscribe(DaemonCodeAnalyzer.DAEMON_EVENT_TOPIC, new DaemonCodeAnalyzer.DaemonListener() {
      @Override
      public void daemonFinished() {
        updateLater();
      }
    });
  }

  private void updateLater() {
    final Application application = ApplicationManager.getApplication();
    if (application.isUnitTestMode()) {
      myUpdateStatusRunnable.run();
    }
    else {
      updateStatusAlarm.cancelAllRequests();
      updateStatusAlarm.addRequest(myUpdateStatusRunnable, 100);
    }
  }

  @Override
  public void dispose() {
  }

  private static final HighlightSeverity MIN = new HighlightSeverity("min", HighlightSeverity.INFORMATION.myVal + 1);
  private void updateStatus() {
    Editor editor = FileEditorManager.getInstance(myProject).getSelectedTextEditor();
    if (editor == null || !editor.getContentComponent().hasFocus()){
      return;
    }

    final Document document = editor.getDocument();
    if (document.isInBulkUpdate()) return;

    int offset = editor.getCaretModel().getOffset();
    DaemonCodeAnalyzer codeAnalyzer = DaemonCodeAnalyzer.getInstance(myProject);
    HighlightInfo info = ((DaemonCodeAnalyzerImpl)codeAnalyzer).findHighlightByOffset(document, offset, false, MIN);
    String text = info != null && info.getDescription() != null ? info.getDescription() : "";

    StatusBar statusBar = WindowManager.getInstance().getStatusBar(editor.getContentComponent(), myProject);
    if (statusBar != null && !text.equals(statusBar.getInfo())) {
      statusBar.setInfo(text, "updater");
    }
  }
}

@@ -800,121 +800,8 @@
 le;%0A
-import com.intellij.openapi.application.Application;%0Aimport com.intellij.openapi.application.ApplicationManager;%0A
 impo
@@ -1075,63 +1075,8 @@
 er;%0A
-import com.intellij.openapi.project.DumbAwareRunnable;%0A
 impo
@@ -1229,16 +1229,22 @@
 ij.util.
+Single
 Alarm;%0Ai
@@ -1285,23 +1285,16 @@
 tNull;%0A%0A
-public 
 class St
@@ -1387,119 +1387,72 @@
 nal 
-DumbAwareRunnable myUpdateStatusRunnable = new DumbAwareRunnable() %7B%0A    @Override%0A    public void run(
+SingleAlarm myAlarm;%0A%0A  StatusBarUpdater(Project project
 ) %7B%0A    
   if
@@ -1451,15 +1451,8 @@
     
-  if (!
 myPr
@@ -1460,185 +1460,82 @@
 ject
-.isDisposed()) %7B%0A        updateStatus();%0A      %7D%0A    %7D%0A  %7D;%0A  private final Alarm updateStatusAlarm = new Alarm();%0A%0A  StatusBarUpdater(Project project) %7B%0A    myProject = project
+ = project;%0A    myAlarm = new SingleAlarm(() -%3E updateStatus(), 100, this)
 ;%0A%0A 
@@ -2067,285 +2067,35 @@
     
-final Application application = ApplicationManager.getApplication();%0A    if (application.isUnitTestMode()) %7B%0A      myUpdateStatusRunnable.run();%0A    %7D%0A    else %7B%0A      updateStatusAlarm.cancelAllRequests();%0A      updateStatusAlarm.addRequest(myUpdateStatusRunnable, 100);%0A    %7D
+myAlarm.cancelAndRequest();
 %0A  %7D

simplify StatusBarUpdater