private void onAppClosing() {
    final MessageBus messageBus = ApplicationManager.getApplication().getMessageBus();

    messageBus
        .connect()
        .subscribe(
            AppLifecycleListener.TOPIC,
            new AppLifecycleListener() {
              @Override
              public void appFrameCreated(
                  String[] commandLineArgs, @NotNull Ref<Boolean> willOpenProject) {}

              @Override
              public void appStarting(Project projectFromCommandLine) {}

              @Override
              public void projectFrameClosed() {}

              @Override
              public void projectOpenFailed() {}

              @Override
              public void welcomeScreenDisplayed() {}

              @Override
              public void appClosing() {
                for (Project project : ProjectManager.getInstance().getOpenProjects()) {
                  if (project.isInitialized()) {
                    doPersistProjectUsages(project);
                  }
                }
                persistOnClosing = false;
              }
            });
  }
 @Override
 public void apply(CodeStyleSettings settings) {
   boolean newValue = myEnabled.isSelected();
   settings.getCustomSettings(EditorConfigSettings.class).ENABLED = newValue;
   MessageBus bus = ApplicationManager.getApplication().getMessageBus();
   bus.syncPublisher(EditorConfigSettings.EDITOR_CONFIG_ENABLED_TOPIC).valueChanged(newValue);
 }
  public void initComponent() {
    log.info("Initializing WakaTime plugin v" + VERSION + " (https://wakatime.com/)");
    // System.out.println("Initializing WakaTime plugin v" + VERSION + " (https://wakatime.com/)");

    // Set runtime constants
    IDE_NAME = PlatformUtils.getPlatformPrefix();
    IDE_VERSION = ApplicationInfo.getInstance().getFullVersion();

    if (!Dependencies.isCLIInstalled()) {
      log.info("Downloading and installing wakatime-cli ...");
      Dependencies.installCLI();
    } else if (Dependencies.isCLIOld()) {
      log.info("Upgrading wakatime-cli ...");
      Dependencies.upgradeCLI();
    }

    if (Dependencies.isPythonInstalled()) {

      WakaTime.DEBUG = WakaTime.isDebugEnabled();
      if (WakaTime.DEBUG) {
        log.setLevel(Level.DEBUG);
        log.debug("Logging level set to DEBUG");
      }

      log.debug("Python location: " + Dependencies.getPythonLocation());
      log.debug("CLI location: " + Dependencies.getCLILocation());

      // prompt for apiKey if it does not already exist
      if (ApiKey.getApiKey().equals("")) {
        Project project = ProjectManager.getInstance().getDefaultProject();
        ApiKey apiKey = new ApiKey(project);
        apiKey.promptForApiKey();
      }
      log.debug("Api Key: " + ApiKey.getApiKey());

      // add WakaTime item to File menu
      ActionManager am = ActionManager.getInstance();
      PluginMenu action = new PluginMenu();
      am.registerAction("WakaTimeApiKey", action);
      DefaultActionGroup fileMenu = (DefaultActionGroup) am.getAction("FileMenu");
      fileMenu.addSeparator();
      fileMenu.add(action);

      // Setup message listeners
      MessageBus bus = ApplicationManager.getApplication().getMessageBus();
      connection = bus.connect();
      connection.subscribe(AppTopics.FILE_DOCUMENT_SYNC, new CustomSaveListener());
      EditorFactory.getInstance()
          .getEventMulticaster()
          .addDocumentListener(new CustomDocumentListener());

      log.debug("Finished initializing WakaTime plugin");

    } else {
      Messages.showErrorDialog(
          "WakaTime requires Python to be installed.\nYou can install it from https://www.python.org/downloads/\nAfter installing Python, restart your IDE.",
          "Error");
    }
  }
  public boolean commitTransaction(final Document document) {
    ApplicationManager.getApplication().assertIsDispatchThread();
    final DocumentChangeTransaction documentChangeTransaction = removeTransaction(document);
    if (documentChangeTransaction == null) return false;
    final PsiFile changeScope = documentChangeTransaction.myChangeScope;
    try {
      mySyncDocument = document;

      final PsiTreeChangeEventImpl fakeEvent = new PsiTreeChangeEventImpl(changeScope.getManager());
      fakeEvent.setParent(changeScope);
      fakeEvent.setFile(changeScope);
      checkPsiModificationAllowed(fakeEvent);
      doSync(
          fakeEvent,
          true,
          new DocSyncAction() {
            @Override
            public void syncDocument(
                @NotNull Document document, @NotNull PsiTreeChangeEventImpl event) {
              doCommitTransaction(document, documentChangeTransaction);
            }
          });
      myBus
          .syncPublisher(PsiDocumentTransactionListener.TOPIC)
          .transactionCompleted(document, changeScope);
    } catch (Throwable e) {
      myPsiDocumentManager.forceReload(
          changeScope.getViewProvider().getVirtualFile(), changeScope.getViewProvider());
      ExceptionUtil.rethrowAllAsUnchecked(e);
    } finally {
      mySyncDocument = null;
    }
    return true;
  }
  @SuppressWarnings("OverlyBroadCatchBlock")
  private void multiCast(@NotNull Method method, Object[] args) {
    try {
      method.invoke(myBus.syncPublisher(AppTopics.FILE_DOCUMENT_SYNC), args);
    } catch (ClassCastException e) {
      LOG.error("Arguments: " + Arrays.toString(args), e);
    } catch (Exception e) {
      LOG.error(e);
    }

    // Allows pre-save document modification
    for (FileDocumentManagerListener listener : getListeners()) {
      try {
        method.invoke(listener, args);
      } catch (Exception e) {
        LOG.error(e);
      }
    }

    // stripping trailing spaces
    try {
      method.invoke(myTrailingSpacesStripper, args);
    } catch (Exception e) {
      LOG.error(e);
    }
  }
  public ExternalAnnotationsManagerImpl(
      @NotNull final Project project, final PsiManager psiManager) {
    super(psiManager);
    myBus = project.getMessageBus();
    final MessageBusConnection connection = myBus.connect(project);
    connection.subscribe(
        ProjectTopics.PROJECT_ROOTS,
        new ModuleRootAdapter() {
          @Override
          public void rootsChanged(ModuleRootEvent event) {
            dropCache();
          }
        });

    final MyVirtualFileListener fileListener = new MyVirtualFileListener();
    VirtualFileManager.getInstance().addVirtualFileListener(fileListener);
    Disposer.register(
        myPsiManager.getProject(),
        new Disposable() {
          @Override
          public void dispose() {
            VirtualFileManager.getInstance().removeVirtualFileListener(fileListener);
          }
        });
  }
  private void upgradeIfNeeded(final MessageBus bus) {
    final MessageBusConnection connection = bus.connect();
    connection.subscribe(
        ChangeListManagerImpl.LISTS_LOADED,
        new LocalChangeListsLoadedListener() {
          @Override
          public void processLoadedLists(final List<LocalChangeList> lists) {
            if (lists.isEmpty()) return;
            SvnConfiguration.SvnSupportOptions supportOptions = null;
            try {
              ChangeListManager.getInstance(myProject)
                  .setReadOnly(SvnChangeProvider.ourDefaultListName, true);
              supportOptions = myConfiguration.getSupportOptions(myProject);

              if (!supportOptions.changeListsSynchronized()) {
                processChangeLists(lists);
              }
            } catch (ProcessCanceledException e) {
              //
            } finally {
              if (supportOptions != null) {
                supportOptions.upgrade();
              }
            }

            connection.disconnect();
          }
        });
  }
  public boolean commitTransaction(final Document document) {
    ApplicationManager.getApplication().assertIsDispatchThread();
    final DocumentChangeTransaction documentChangeTransaction = removeTransaction(document);
    if (documentChangeTransaction == null) return false;
    final PsiElement changeScope = documentChangeTransaction.getChangeScope();
    try {
      mySyncDocument = document;

      final PsiTreeChangeEventImpl fakeEvent = new PsiTreeChangeEventImpl(changeScope.getManager());
      fakeEvent.setParent(changeScope);
      fakeEvent.setFile(changeScope.getContainingFile());
      doSync(
          fakeEvent,
          true,
          new DocSyncAction() {
            @Override
            public void syncDocument(Document document, PsiTreeChangeEventImpl event) {
              doCommitTransaction(document, documentChangeTransaction);
            }
          });
      myBus
          .syncPublisher(PsiDocumentTransactionListener.TOPIC)
          .transactionCompleted(document, (PsiFile) changeScope);
    } finally {
      mySyncDocument = null;
    }
    return true;
  }
  public void addRequest(final Runnable request, final int delay, boolean runWithActiveFrameOnly) {
    if (runWithActiveFrameOnly && !ApplicationManager.getApplication().isActive()) {
      final MessageBus bus = ApplicationManager.getApplication().getMessageBus();
      final MessageBusConnection connection = bus.connect(this);
      connection.subscribe(
          ApplicationActivationListener.TOPIC,
          new ApplicationActivationListener() {
            @Override
            public void applicationActivated(IdeFrame ideFrame) {
              connection.disconnect();
              addRequest(request, delay);
            }

            @Override
            public void applicationDeactivated(IdeFrame ideFrame) {}
          });
    } else {
      addRequest(request, delay);
    }
  }
 VirtualFilePointerManagerImpl(
     @NotNull VirtualFileManager virtualFileManager,
     @NotNull MessageBus bus,
     @NotNull TempFileSystem tempFileSystem,
     @NotNull LocalFileSystem localFileSystem) {
   myVirtualFileManager = virtualFileManager;
   myBus = bus;
   bus.connect().subscribe(VirtualFileManager.VFS_CHANGES, this);
   myTempFileSystem = tempFileSystem;
   myLocalFileSystem = localFileSystem;
 }
 public TodoIndex(MessageBus messageBus) {
   messageBus
       .connect()
       .subscribe(
           IndexPatternProvider.INDEX_PATTERNS_CHANGED,
           new PropertyChangeListener() {
             @Override
             public void propertyChange(PropertyChangeEvent evt) {
               FileBasedIndex.requestRebuild(NAME);
             }
           });
 }
 VirtualFilePointerManagerImpl(
     @NotNull VirtualFileManager virtualFileManager,
     @NotNull MessageBus bus,
     @NotNull TempFileSystem tempFileSystem,
     @NotNull LocalFileSystem localFileSystem,
     @NotNull JarFileSystem jarFileSystem) {
   myVirtualFileManager = virtualFileManager;
   myBus = bus;
   bus.connect().subscribe(VirtualFileManager.VFS_CHANGES, this);
   TEMP_FILE_SYSTEM = tempFileSystem;
   LOCAL_FILE_SYSTEM = localFileSystem;
   JAR_FILE_SYSTEM = jarFileSystem;
 }
  @Override
  public void after(@NotNull final List<? extends VFileEvent> events) {
    incModificationCount();

    for (FilePointerPartNode node : myPointersToUpdateUrl) {
      synchronized (this) {
        VirtualFilePointerImpl pointer = node.leaf;
        String urlBefore = pointer.getUrlNoUpdate();
        Pair<VirtualFile, String> after = node.update();
        String urlAfter = after.second;
        if (URL_COMPARATOR.compare(urlBefore, urlAfter) != 0) {
          // url has changed, reinsert
          FilePointerPartNode root = myPointers.get(pointer.getListener());
          int useCount = node.useCount;
          node.remove();
          FilePointerPartNode newNode =
              root.findPointerOrCreate(VfsUtilCore.urlToPath(urlAfter), 0, after);
          VirtualFilePointerImpl existingPointer = newNode.leaf;
          if (existingPointer != null) {
            // can happen when e.g. file renamed to the existing file
            // merge two pointers
            pointer.myNode = newNode;
          } else {
            newNode.associate(pointer, after);
          }
          newNode.incrementUsageCount(useCount);
        }
      }
    }

    VirtualFilePointer[] pointersToFireArray = toPointers(myPointersToFire);
    for (VirtualFilePointer pointer : pointersToFireArray) {
      ((VirtualFilePointerImpl) pointer).myNode.update();
    }

    for (EventDescriptor event : myEvents) {
      event.fireAfter();
    }

    if (pointersToFireArray.length != 0) {
      myBus.syncPublisher(VirtualFilePointerListener.TOPIC).validityChanged(pointersToFireArray);
    }

    myPointersToUpdateUrl = Collections.emptyList();
    myEvents = Collections.emptyList();
    myPointersToFire = Collections.emptyList();
    for (FilePointerPartNode root : myPointers.values()) {
      root.checkConsistency();
    }
  }
  public KotlinJavaPsiFacade(@NotNull Project project) {
    this.project = project;

    final PsiModificationTracker modificationTracker =
        PsiManager.getInstance(project).getModificationTracker();
    MessageBus bus = project.getMessageBus();

    bus.connect()
        .subscribe(
            PsiModificationTracker.TOPIC,
            new PsiModificationTracker.Listener() {
              private long lastTimeSeen = -1L;

              @Override
              public void modificationCountChanged() {
                long now = modificationTracker.getJavaStructureModificationCount();
                if (lastTimeSeen != now) {
                  lastTimeSeen = now;

                  packageCache = null;
                }
              }
            });
  }
 public ResolveCache(@NotNull MessageBus messageBus) {
   for (int i = 0; i < myMaps.length; i++) {
     myMaps[i] = createWeakMap();
   }
   messageBus
       .connect()
       .subscribe(
           PsiManagerImpl.ANY_PSI_CHANGE_TOPIC,
           new AnyPsiChangeListener.Adapter() {
             @Override
             public void beforePsiChanged(boolean isPhysical) {
               clearCache(isPhysical);
             }
           });
 }
Exemple #16
0
  @RequiredWriteAction
  @Override
  public void processEvents(@NotNull List<VFileEvent> events) {
    ApplicationManager.getApplication().assertWriteAccessAllowed();

    List<VFileEvent> validated = validateEvents(events);

    BulkFileListener publisher = myEventBus.syncPublisher(VirtualFileManager.VFS_CHANGES);
    publisher.before(validated);

    THashMap<VirtualFile, List<VFileEvent>> parentToChildrenEventsChanges = null;
    for (VFileEvent event : validated) {
      VirtualFile changedParent = null;
      if (event instanceof VFileCreateEvent) {
        changedParent = ((VFileCreateEvent) event).getParent();
        ((VFileCreateEvent) event).resetCache();
      } else if (event instanceof VFileDeleteEvent) {
        changedParent = ((VFileDeleteEvent) event).getFile().getParent();
      }

      if (changedParent != null) {
        if (parentToChildrenEventsChanges == null)
          parentToChildrenEventsChanges = new THashMap<VirtualFile, List<VFileEvent>>();
        List<VFileEvent> parentChildrenChanges = parentToChildrenEventsChanges.get(changedParent);
        if (parentChildrenChanges == null) {
          parentToChildrenEventsChanges.put(
              changedParent, parentChildrenChanges = new SmartList<VFileEvent>());
        }
        parentChildrenChanges.add(event);
      } else {
        applyEvent(event);
      }
    }

    if (parentToChildrenEventsChanges != null) {
      parentToChildrenEventsChanges.forEachEntry(
          new TObjectObjectProcedure<VirtualFile, List<VFileEvent>>() {
            @Override
            public boolean execute(VirtualFile parent, List<VFileEvent> childrenEvents) {
              applyChildrenChangeEvents(parent, childrenEvents);
              return true;
            }
          });
      parentToChildrenEventsChanges.clear();
    }

    publisher.after(validated);
  }
  public ProjectLevelVcsManagerImpl(
      Project project,
      final FileStatusManager manager,
      MessageBus messageBus,
      final FileIndexFacade excludedFileIndex) {
    myProject = project;
    myMessageBus = messageBus;
    mySerialization = new ProjectLevelVcsManagerSerialization();
    myOptionsAndConfirmations = new OptionsAndConfirmations();

    myDefaultVcsRootPolicy = DefaultVcsRootPolicy.getInstance(project);

    myBackgroundableActionHandlerMap =
        new EnumMap<VcsBackgroundableActions, BackgroundableActionEnabledHandler>(
            VcsBackgroundableActions.class);
    myInitialization = new VcsInitialization(myProject);
    myMappings = new NewMappings(myProject, myMessageBus, this, manager);
    myMappingsToRoots = new MappingsToRoots(myMappings, myProject);

    if (!myProject.isDefault()) {
      myVcsEventListenerManager = new VcsEventsListenerManagerImpl();
    }

    myVcsHistoryCache = new VcsHistoryCache();
    myContentRevisionCache = new ContentRevisionCache();
    myConnect = myMessageBus.connect();
    myVcsFileListenerContextHelper = VcsFileListenerContextHelper.getInstance(myProject);
    VcsListener vcsListener =
        new VcsListener() {
          @Override
          public void directoryMappingChanged() {
            myVcsHistoryCache.clear();
            myVcsFileListenerContextHelper.possiblySwitchActivation(hasActiveVcss());
          }
        };
    myExcludedIndex = excludedFileIndex;
    myConnect.subscribe(ProjectLevelVcsManager.VCS_CONFIGURATION_CHANGED, vcsListener);
    myConnect.subscribe(ProjectLevelVcsManager.VCS_CONFIGURATION_CHANGED_IN_PLUGIN, vcsListener);
    myConnect.subscribe(
        UpdatedFilesListener.UPDATED_FILES,
        new UpdatedFilesListener() {
          @Override
          public void consume(Set<String> strings) {
            myContentRevisionCache.clearCurrent(strings);
          }
        });
    myAnnotationLocalChangesListener = new VcsAnnotationLocalChangesListenerImpl(myProject, this);
  }
  @Override
  public void registerRunnableToRunOnChange(@NotNull final Runnable runnable) {
    myMessageBus
        .connect()
        .subscribe(
            ANY_PSI_CHANGE_TOPIC,
            new AnyPsiChangeListener() {
              @Override
              public void beforePsiChanged(boolean isPhysical) {
                if (isPhysical) runnable.run();
              }

              @Override
              public void afterPsiChanged(boolean isPhysical) {}
            });
  }
 public void startTransaction(@NotNull Project project, Document doc, PsiElement scope) {
   LOG.assertTrue(!project.isDisposed());
   Pair<DocumentChangeTransaction, Integer> pair = myTransactionsMap.get(doc);
   if (pair == null) {
     final PsiFile psiFile = scope != null ? scope.getContainingFile() : null;
     pair =
         new Pair<DocumentChangeTransaction, Integer>(
             new DocumentChangeTransaction(doc, scope != null ? psiFile : null), 0);
     myBus.syncPublisher(PsiDocumentTransactionListener.TOPIC).transactionStarted(doc, psiFile);
   } else {
     pair =
         new Pair<DocumentChangeTransaction, Integer>(
             pair.getFirst(), pair.getSecond().intValue() + 1);
   }
   myTransactionsMap.put(doc, pair);
 }
  @Override
  public void registerRunnableToRunAfterAnyChange(
      @NotNull final Runnable runnable) { // includes non-physical changes
    myMessageBus
        .connect()
        .subscribe(
            ANY_PSI_CHANGE_TOPIC,
            new AnyPsiChangeListener() {
              @Override
              public void beforePsiChanged(boolean isPhysical) {}

              @Override
              public void afterPsiChanged(boolean isPhysical) {
                runnable.run();
              }
            });
  }
  public JavaResolveCache(
      @Nullable(
              "can be null in com.intellij.core.JavaCoreApplicationEnvironment.JavaCoreApplicationEnvironment")
          MessageBus messageBus) {
    if (messageBus != null) {
      messageBus
          .connect()
          .subscribe(
              PsiManagerImpl.ANY_PSI_CHANGE_TOPIC,
              new AnyPsiChangeListener() {
                @Override
                public void beforePsiChanged(boolean isPhysical) {
                  clearCaches(isPhysical);
                }

                @Override
                public void afterPsiChanged(boolean isPhysical) {}
              });
    }
  }
  private void installListeners() {
    FileStatusManager.getInstance(myProject)
        .addFileStatusListener(myFileStatusListener = new FileStatusChangeListener());
    VirtualFileManager.getInstance()
        .addVirtualFileListener(myFileListener = new FileChangesListener());
    VirtualFileManager.getInstance()
        .addVirtualFileManagerListener(myVirtualFileManagerListener = new RefreshListener());
    myDirectoryMappingListener =
        new VcsListener() {
          public void directoryMappingChanged() {
            rebuildTreeLater();
          }
        };
    myProject.getComponent(ProjectLevelVcsManager.class).addVcsListener(myDirectoryMappingListener);
    ChangeListManager.getInstance(myProject)
        .addChangeListListener(myChangeListListener = new ChangeListUpdateListener());
    myMessageBusConnection = myBus.connect();
    myMessageBusConnection.subscribe(
        FileEditorManagerListener.FILE_EDITOR_MANAGER,
        new FileEditorManagerAdapter() {
          @Override
          public void fileOpened(FileEditorManager source, VirtualFile file) {
            if (myProjectView.isAutoscrollFromSource(getId())) {
              selectNode(file, false);
            }
          }

          @Override
          public void selectionChanged(FileEditorManagerEvent event) {
            if (myProjectView.isAutoscrollFromSource(getId())) {
              VirtualFile newFile = event.getNewFile();
              if (newFile != null) {
                selectNode(newFile, false);
              }
            }
          }
        });
  }
  protected PsiDocumentManagerBase(
      @NotNull final Project project,
      @NotNull PsiManager psiManager,
      @NotNull MessageBus bus,
      @NonNls @NotNull final DocumentCommitProcessor documentCommitProcessor) {
    myProject = project;
    myPsiManager = psiManager;
    myDocumentCommitProcessor = documentCommitProcessor;
    mySynchronizer = new PsiToDocumentSynchronizer(this, bus);
    myPsiManager.addPsiTreeChangeListener(mySynchronizer);
    bus.connect()
        .subscribe(
            PsiDocumentTransactionListener.TOPIC,
            new PsiDocumentTransactionListener() {
              @Override
              public void transactionStarted(@NotNull Document document, @NotNull PsiFile file) {
                myUncommittedDocuments.remove(document);
              }

              @Override
              public void transactionCompleted(@NotNull Document document, @NotNull PsiFile file) {}
            });
  }
 @Override
 public void addVcsListener(VcsListener listener) {
   final MessageBusConnection connection = myMessageBus.connect();
   connection.subscribe(VCS_CONFIGURATION_CHANGED, listener);
   myAdapters.put(listener, connection);
 }
  /** @noinspection UnusedParameters */
  public PyCharmEduInitialConfigurator(
      MessageBus bus,
      CodeInsightSettings codeInsightSettings,
      final PropertiesComponent propertiesComponent,
      FileTypeManager fileTypeManager,
      final ProjectManagerEx projectManager) {
    if (!propertiesComponent.getBoolean(CONFIGURED, false)) {
      propertiesComponent.setValue(CONFIGURED, "true");
      propertiesComponent.setValue("toolwindow.stripes.buttons.info.shown", "true");
      UISettings uiSettings = UISettings.getInstance();
      uiSettings.HIDE_TOOL_STRIPES = false;
      uiSettings.SHOW_MEMORY_INDICATOR = false;
      uiSettings.SHOW_DIRECTORY_FOR_NON_UNIQUE_FILENAMES = true;
      uiSettings.SHOW_MAIN_TOOLBAR = false;
      uiSettings.SHOW_NAVIGATION_BAR = false;
      codeInsightSettings.REFORMAT_ON_PASTE = CodeInsightSettings.NO_REFORMAT;

      Registry.get("ide.new.settings.dialog").setValue(true);

      GeneralSettings.getInstance().setShowTipsOnStartup(false);

      EditorSettingsExternalizable.getInstance().setVirtualSpace(false);
      EditorSettingsExternalizable.getInstance().getOptions().ARE_LINE_NUMBERS_SHOWN = true;
      final CodeStyleSettings settings =
          CodeStyleSettingsManager.getInstance().getCurrentSettings();
      settings.ALIGN_MULTILINE_PARAMETERS_IN_CALLS = true;
      settings.getCommonSettings(PythonLanguage.getInstance()).ALIGN_MULTILINE_PARAMETERS_IN_CALLS =
          true;
      uiSettings.SHOW_DIRECTORY_FOR_NON_UNIQUE_FILENAMES = true;
      uiSettings.SHOW_MEMORY_INDICATOR = false;
      final String ignoredFilesList = fileTypeManager.getIgnoredFilesList();
      ApplicationManager.getApplication()
          .invokeLater(
              new Runnable() {
                @Override
                public void run() {
                  ApplicationManager.getApplication()
                      .runWriteAction(
                          new Runnable() {
                            @Override
                            public void run() {
                              FileTypeManager.getInstance()
                                  .setIgnoredFilesList(ignoredFilesList + ";*$py.class");
                            }
                          });
                }
              });
      PyCodeInsightSettings.getInstance().SHOW_IMPORT_POPUP = false;
    }

    if (!propertiesComponent.isValueSet(DISPLAYED_PROPERTY)) {

      bus.connect()
          .subscribe(
              AppLifecycleListener.TOPIC,
              new AppLifecycleListener.Adapter() {
                @Override
                public void welcomeScreenDisplayed() {

                  ApplicationManager.getApplication()
                      .invokeLater(
                          new Runnable() {
                            @Override
                            public void run() {
                              if (!propertiesComponent.isValueSet(DISPLAYED_PROPERTY)) {
                                GeneralSettings.getInstance().setShowTipsOnStartup(false);
                                propertiesComponent.setValue(DISPLAYED_PROPERTY, "true");

                                patchKeymap();
                              }
                            }
                          });
                }
              });
    }

    bus.connect()
        .subscribe(
            ProjectManager.TOPIC,
            new ProjectManagerAdapter() {
              @Override
              public void projectOpened(final Project project) {
                if (project.isDefault()) return;
                if (FileChooserUtil.getLastOpenedFile(project) == null) {
                  FileChooserUtil.setLastOpenedFile(project, VfsUtil.getUserHomeDir());
                }

                patchProjectAreaExtensions(project);

                StartupManager.getInstance(project)
                    .runWhenProjectIsInitialized(
                        new DumbAwareRunnable() {
                          @Override
                          public void run() {
                            if (project.isDisposed()) return;

                            ToolWindowManager.getInstance(project)
                                .invokeLater(
                                    new Runnable() {
                                      int count = 0;

                                      public void run() {
                                        if (project.isDisposed()) return;
                                        if (count++
                                            < 3) { // we need to call this after
                                                   // ToolWindowManagerImpl.registerToolWindowsFromBeans
                                          ToolWindowManager.getInstance(project).invokeLater(this);
                                          return;
                                        }
                                        ToolWindow toolWindow =
                                            ToolWindowManager.getInstance(project)
                                                .getToolWindow("Project");
                                        if (toolWindow.getType() != ToolWindowType.SLIDING) {
                                          toolWindow.activate(null);
                                        }
                                      }
                                    });
                          }
                        });
              }
            });
  }
 private void notifyChangedExternally() {
   myBus.syncPublisher(TOPIC).externalAnnotationsChangedExternally();
 }
 private void notifyAfterAnnotationChanging(
     @NotNull PsiModifierListOwner owner, @NotNull String annotationFQName, boolean successful) {
   myBus.syncPublisher(TOPIC).afterExternalAnnotationChanging(owner, annotationFQName, successful);
 }
 @Override
 public void afterChange(boolean isPhysical) {
   myMessageBus.syncPublisher(ANY_PSI_CHANGE_TOPIC).afterPsiChanged(isPhysical);
 }
 private void severitiesChanged() {
   myMessageBus.syncPublisher(SEVERITIES_CHANGED_TOPIC).run();
 }
 @Override
 public void notifyDirectoryMappingChanged() {
   myMessageBus.syncPublisher(VCS_CONFIGURATION_CHANGED).directoryMappingChanged();
 }