mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
EA-37556 - assert: RemoteProcessSupport.acquire
1. DocumentationProvider.generateDoc() contract is clarified; 2. Don't call DocumentationProvider.generateDoc() from EDT;
This commit is contained in:
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2009 JetBrains s.r.o.
|
||||
* Copyright 2000-2012 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.
|
||||
@@ -40,6 +40,15 @@ public interface DocumentationProvider {
|
||||
@Nullable
|
||||
List<String> getUrlFor(PsiElement element, PsiElement originalElement);
|
||||
|
||||
/**
|
||||
* Callback for asking the doc provider for the complete documentation.
|
||||
* <p/>
|
||||
* Underlying implementation may be time-consuming, that's why this method is expected not to be called from EDT.
|
||||
*
|
||||
* @param element target element which documentation is being requested
|
||||
* @param originalElement element initially picked up from the current context
|
||||
* @return target element's documentation (if any)
|
||||
*/
|
||||
@Nullable
|
||||
String generateDoc(PsiElement element, PsiElement originalElement);
|
||||
|
||||
|
||||
@@ -72,7 +72,10 @@ import com.intellij.psi.util.PsiUtilBase;
|
||||
import com.intellij.ui.LightweightHint;
|
||||
import com.intellij.usageView.UsageViewShortNameLocation;
|
||||
import com.intellij.usageView.UsageViewTypeLocation;
|
||||
import com.intellij.util.Alarm;
|
||||
import com.intellij.util.Consumer;
|
||||
import com.intellij.util.Processor;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
import org.intellij.lang.annotations.JdkConstants;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -168,7 +171,7 @@ public class CtrlMouseHandler extends AbstractProjectComponent {
|
||||
return;
|
||||
}
|
||||
MouseEvent mouseEvent = e.getMouseEvent();
|
||||
|
||||
|
||||
if (isMouseOverTooltip(mouseEvent.getLocationOnScreen()) || isMouseMovedTowardTooltip(mouseEvent.getLocationOnScreen())) {
|
||||
myPrevMouseLocation = mouseEvent.getLocationOnScreen();
|
||||
return;
|
||||
@@ -212,6 +215,8 @@ public class CtrlMouseHandler extends AbstractProjectComponent {
|
||||
TextAttributesKey
|
||||
.createTextAttributesKey("CTRL_CLICKABLE", new TextAttributes(Color.blue, null, Color.blue, EffectType.LINE_UNDERSCORE, 0));
|
||||
|
||||
@NotNull private final Alarm myDocAlarm;
|
||||
|
||||
public CtrlMouseHandler(final Project project, StartupManager startupManager, EditorColorsManager colorsManager,
|
||||
FileEditorManager fileEditorManager, @NotNull DocumentationManager documentationManager,
|
||||
@NotNull final EditorFactory editorFactory, @NotNull IdeTooltipManager tooltipManager)
|
||||
@@ -234,6 +239,7 @@ public class CtrlMouseHandler extends AbstractProjectComponent {
|
||||
myFileEditorManager = fileEditorManager;
|
||||
myDocumentationManager = documentationManager;
|
||||
myTooltipManager = tooltipManager;
|
||||
myDocAlarm = new Alarm(Alarm.ThreadToUse.OWN_THREAD, myProject);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@@ -265,7 +271,7 @@ public class CtrlMouseHandler extends AbstractProjectComponent {
|
||||
if (dx == 0) {
|
||||
return mouseLocationOnScreen.x > bounds.x && mouseLocationOnScreen.x < bounds.x + bounds.width;
|
||||
}
|
||||
|
||||
|
||||
// Check if the mouse goes out of the control.
|
||||
if (mouseLocationOnScreen.x < prevLocation.x && bounds.x > prevLocation.x) return false;
|
||||
if (mouseLocationOnScreen.y < prevLocation.y && bounds.y > prevLocation.y) return false;
|
||||
@@ -341,13 +347,7 @@ public class CtrlMouseHandler extends AbstractProjectComponent {
|
||||
private static DocInfo generateInfo(PsiElement element, PsiElement atPointer) {
|
||||
final DocumentationProvider documentationProvider = DocumentationManager.getProviderFromElement(element, atPointer);
|
||||
String result = doGenerateInfo(element, atPointer, documentationProvider);
|
||||
if (result != null) {
|
||||
String fullText = documentationProvider.generateDoc(element, atPointer);
|
||||
String qName = element instanceof PsiQualifiedNamedElement ? ((PsiQualifiedNamedElement)element).getQualifiedName() : null;
|
||||
String text = DocPreviewUtil.buildPreview(result, qName, fullText);
|
||||
return new DocInfo(text, documentationProvider, element);
|
||||
}
|
||||
return DocInfo.EMPTY;
|
||||
return result == null ? DocInfo.EMPTY : new DocInfo(result, documentationProvider, element);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@@ -611,6 +611,40 @@ public class CtrlMouseHandler extends AbstractProjectComponent {
|
||||
}
|
||||
}
|
||||
|
||||
private void fulfillDocInfo(@NotNull final String header,
|
||||
@NotNull final DocumentationProvider provider,
|
||||
@NotNull final PsiElement originalElement,
|
||||
@NotNull final PsiElement anchorElement,
|
||||
@NotNull final Consumer<String> newTextConsumer)
|
||||
{
|
||||
myDocAlarm.cancelAllRequests();
|
||||
myDocAlarm.addRequest(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
final Ref<String> fullTextRef = new Ref<String>();
|
||||
ApplicationManager.getApplication().runReadAction(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
fullTextRef.set(provider.generateDoc(anchorElement, originalElement));
|
||||
}
|
||||
});
|
||||
String fullText = fullTextRef.get();
|
||||
if (fullText == null) {
|
||||
return;
|
||||
}
|
||||
String qName = anchorElement instanceof PsiQualifiedNamedElement ? ((PsiQualifiedNamedElement)anchorElement).getQualifiedName()
|
||||
: null;
|
||||
final String updatedText = DocPreviewUtil.buildPreview(header, qName, fullText);
|
||||
UIUtil.invokeLaterIfNeeded(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
newTextConsumer.consume(updatedText);
|
||||
}
|
||||
});
|
||||
}
|
||||
}, 0);
|
||||
}
|
||||
|
||||
private class TooltipProvider {
|
||||
private final Editor myEditor;
|
||||
private final LogicalPosition myPosition;
|
||||
@@ -727,8 +761,14 @@ public class CtrlMouseHandler extends AbstractProjectComponent {
|
||||
pane.mouseExited(e);
|
||||
}
|
||||
}
|
||||
};
|
||||
JComponent label = HintUtil.createInformationLabel(docInfo.text, hyperlinkListener, mouseListener);
|
||||
};
|
||||
Ref<Consumer<String>> newTextConsumerRef = new Ref<Consumer<String>>();
|
||||
JComponent label = HintUtil.createInformationLabel(docInfo.text, hyperlinkListener, mouseListener, newTextConsumerRef);
|
||||
Consumer<String> newTextConsumer = newTextConsumerRef.get();
|
||||
myDocAlarm.cancelAllRequests();
|
||||
if (newTextConsumer != null && docInfo.docProvider != null && docInfo.documentationAnchor != null) {
|
||||
fulfillDocInfo(docInfo.text, docInfo.docProvider, info.myElementAtPointer, docInfo.documentationAnchor, newTextConsumer);
|
||||
}
|
||||
QuickDocInfoPane quickDocPane = null;
|
||||
if (docInfo.documentationAnchor != null) {
|
||||
quickDocPane = new QuickDocInfoPane(docInfo.documentationAnchor, info.myElementAtPointer, label);
|
||||
@@ -744,7 +784,7 @@ public class CtrlMouseHandler extends AbstractProjectComponent {
|
||||
0, false, HintManagerImpl.createHintHint(myEditor, p, hint, HintManager.ABOVE).setContentActive(false));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private HighlightersSet installHighlighterSet(Info info, Editor editor) {
|
||||
final JComponent internalComponent = editor.getContentComponent();
|
||||
internalComponent.addKeyListener(myEditorKeyListener);
|
||||
@@ -875,7 +915,7 @@ public class CtrlMouseHandler extends AbstractProjectComponent {
|
||||
if (myDocumentationManager.hasActiveDockedDocWindow()) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
// Skip event triggered when mouse leaves action button area.
|
||||
if (!mouseEntered && new Rectangle(getLocationOnScreen(), getSize()).contains(mouseScreenLocation)) {
|
||||
return;
|
||||
|
||||
@@ -17,10 +17,12 @@ package com.intellij.codeInsight.hint;
|
||||
|
||||
import com.intellij.icons.AllIcons;
|
||||
import com.intellij.ide.IdeTooltipManager;
|
||||
import com.intellij.openapi.util.Ref;
|
||||
import com.intellij.ui.ColoredSideBorder;
|
||||
import com.intellij.ui.HintHint;
|
||||
import com.intellij.ui.SimpleColoredComponent;
|
||||
import com.intellij.ui.SimpleColoredText;
|
||||
import com.intellij.util.Consumer;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
import org.intellij.lang.annotations.JdkConstants;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -29,12 +31,8 @@ import org.jetbrains.annotations.Nullable;
|
||||
import javax.swing.*;
|
||||
import javax.swing.border.Border;
|
||||
import javax.swing.border.CompoundBorder;
|
||||
import javax.swing.border.EmptyBorder;
|
||||
import javax.swing.event.HyperlinkEvent;
|
||||
import javax.swing.event.HyperlinkListener;
|
||||
import java.awt.*;
|
||||
import java.awt.event.MouseAdapter;
|
||||
import java.awt.event.MouseEvent;
|
||||
import java.awt.event.MouseListener;
|
||||
|
||||
public class HintUtil {
|
||||
@@ -52,16 +50,17 @@ public class HintUtil {
|
||||
}
|
||||
|
||||
public static JComponent createInformationLabel(@NotNull String text) {
|
||||
return createInformationLabel(text, null, null);
|
||||
return createInformationLabel(text, null, null, null);
|
||||
}
|
||||
|
||||
public static JComponent createInformationLabel(@NotNull String text,
|
||||
@Nullable HyperlinkListener hyperlinkListener,
|
||||
@Nullable MouseListener mouseListener)
|
||||
@Nullable MouseListener mouseListener,
|
||||
@Nullable Ref<Consumer<String>> updatedTextConsumer)
|
||||
{
|
||||
HintHint hintHint = new HintHint().setTextBg(INFORMATION_COLOR).setTextFg(Color.black).setFont(getBoldFont()).setAwtTooltip(true);
|
||||
|
||||
HintLabel label = new HintLabel();
|
||||
final HintLabel label = new HintLabel();
|
||||
label.setText(text, hintHint);
|
||||
label.setIcon(INFORMATION_ICON);
|
||||
|
||||
@@ -79,6 +78,14 @@ public class HintUtil {
|
||||
if (mouseListener != null) {
|
||||
label.myPane.addMouseListener(mouseListener);
|
||||
}
|
||||
if (updatedTextConsumer != null) {
|
||||
updatedTextConsumer.set(new Consumer<String>() {
|
||||
@Override
|
||||
public void consume(String s) {
|
||||
label.myPane.setText(s);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
return label;
|
||||
}
|
||||
@@ -148,18 +155,6 @@ public class HintUtil {
|
||||
return UIUtil.getLabelFont().deriveFont(Font.BOLD);
|
||||
}
|
||||
|
||||
public static JLabel createAdComponent(final String bottomText) {
|
||||
return createAdComponent(bottomText, getDefaultAdComponentBorder());
|
||||
}
|
||||
|
||||
public static EmptyBorder getDefaultAdComponentBorder() {
|
||||
return new EmptyBorder(1, 2, 1, 2);
|
||||
}
|
||||
|
||||
public static JLabel createAdComponent(final String bottomText, final Border border) {
|
||||
return createAdComponent(bottomText, border, SwingUtilities.LEFT);
|
||||
}
|
||||
|
||||
public static JLabel createAdComponent(final String bottomText, final Border border, @JdkConstants.HorizontalAlignment int alignment) {
|
||||
JLabel label = new JLabel();
|
||||
label.setText(bottomText);
|
||||
@@ -227,8 +222,8 @@ public class HintUtil {
|
||||
remove(myIcon);
|
||||
}
|
||||
|
||||
myIcon = new JLabel(icon, JLabel.CENTER);
|
||||
myIcon.setVerticalAlignment(JLabel.TOP);
|
||||
myIcon = new JLabel(icon, SwingConstants.CENTER);
|
||||
myIcon.setVerticalAlignment(SwingConstants.TOP);
|
||||
|
||||
add(myIcon, BorderLayout.WEST);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user