mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
action to switch to scientific view in pycharm
- part of PY-23595 - documentation docked on the right - documentation is auto updated from source - data view as toolwindow is shown only in scientific view - console is opened - restore scientific view after restart
This commit is contained in:
+3
-5
@@ -47,7 +47,6 @@ import java.awt.*;
|
||||
|
||||
public abstract class DockablePopupManager<T extends JComponent & Disposable> {
|
||||
protected ToolWindow myToolWindow;
|
||||
private boolean myAutoUpdateDocumentation = PropertiesComponent.getInstance().isTrueValue(getAutoUpdateEnabledProperty());
|
||||
private Runnable myAutoUpdateRequest;
|
||||
@NotNull protected final Project myProject;
|
||||
|
||||
@@ -119,7 +118,7 @@ public abstract class DockablePopupManager<T extends JComponent & Disposable> {
|
||||
new UiNotifyConnector(component, new Activatable() {
|
||||
@Override
|
||||
public void showNotify() {
|
||||
restartAutoUpdate(myAutoUpdateDocumentation);
|
||||
restartAutoUpdate(PropertiesComponent.getInstance().getBoolean(getAutoUpdateEnabledProperty()));
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -144,13 +143,12 @@ public abstract class DockablePopupManager<T extends JComponent & Disposable> {
|
||||
AllIcons.General.AutoscrollFromSource) {
|
||||
@Override
|
||||
public boolean isSelected(AnActionEvent e) {
|
||||
return myAutoUpdateDocumentation;
|
||||
return PropertiesComponent.getInstance().getBoolean(getAutoUpdateEnabledProperty());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setSelected(AnActionEvent e, boolean state) {
|
||||
PropertiesComponent.getInstance().setValue(getAutoUpdateEnabledProperty(), state);
|
||||
myAutoUpdateDocumentation = state;
|
||||
restartAutoUpdate(state);
|
||||
}
|
||||
};
|
||||
@@ -222,7 +220,7 @@ public abstract class DockablePopupManager<T extends JComponent & Disposable> {
|
||||
}
|
||||
|
||||
|
||||
protected void restorePopupBehavior() {
|
||||
public void restorePopupBehavior() {
|
||||
if (myToolWindow != null) {
|
||||
PropertiesComponent.getInstance().setValue(getShowInToolWindowProperty(), Boolean.FALSE.toString());
|
||||
ToolWindowManagerEx toolWindowManagerEx = ToolWindowManagerEx.getInstanceEx(myProject);
|
||||
|
||||
+1
-1
@@ -145,7 +145,7 @@ public class DocumentationManager extends DockablePopupManager<DocumentationComp
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void restorePopupBehavior() {
|
||||
public void restorePopupBehavior() {
|
||||
if (myPreviouslyFocused != null) {
|
||||
IdeFocusManager.getInstance(myProject).requestFocus(myPreviouslyFocused, true);
|
||||
}
|
||||
|
||||
@@ -860,6 +860,10 @@
|
||||
<add-to-group group-id="DebugMainMenu" relative-to-action="StepInto" anchor="after"/>
|
||||
<add-to-group group-id="XDebugger.ToolWindow.TopToolbar" relative-to-action="StepInto" anchor="after"/>
|
||||
</action>
|
||||
|
||||
<action id="PySciView" class="com.jetbrains.python.actions.PySciViewAction">
|
||||
<add-to-group group-id="ViewMenu" anchor="before" relative-to-action="ToggleFullScreenGroup"/>
|
||||
</action>
|
||||
</actions>
|
||||
|
||||
<extensions defaultExtensionNs="com.intellij.spellchecker">
|
||||
@@ -867,6 +871,12 @@
|
||||
<bundledDictionaryProvider implementation="com.jetbrains.python.spellchecker.PythonBundledDictionaryProvider"/>
|
||||
</extensions>
|
||||
|
||||
<project-components>
|
||||
<component>
|
||||
<implementation-class>com.jetbrains.python.actions.PySciProjectComponent</implementation-class>
|
||||
</component>
|
||||
</project-components>
|
||||
|
||||
<application-components>
|
||||
<component>
|
||||
<implementation-class>com.jetbrains.python.testing.VFSTestFrameworkListener</implementation-class>
|
||||
|
||||
@@ -0,0 +1,151 @@
|
||||
/*
|
||||
* Copyright 2000-2017 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.jetbrains.python.actions;
|
||||
|
||||
import com.intellij.codeInsight.documentation.DocumentationManager;
|
||||
import com.intellij.ide.DataManager;
|
||||
import com.intellij.notification.NotificationDisplayType;
|
||||
import com.intellij.notification.NotificationGroup;
|
||||
import com.intellij.notification.NotificationListener;
|
||||
import com.intellij.notification.NotificationType;
|
||||
import com.intellij.openapi.actionSystem.ActionManager;
|
||||
import com.intellij.openapi.actionSystem.ActionPlaces;
|
||||
import com.intellij.openapi.actionSystem.AnAction;
|
||||
import com.intellij.openapi.actionSystem.AnActionEvent;
|
||||
import com.intellij.openapi.components.AbstractProjectComponent;
|
||||
import com.intellij.openapi.components.PersistentStateComponent;
|
||||
import com.intellij.openapi.components.State;
|
||||
import com.intellij.openapi.components.Storage;
|
||||
import com.intellij.openapi.module.Module;
|
||||
import com.intellij.openapi.module.ModuleUtilCore;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.projectRoots.Sdk;
|
||||
import com.intellij.openapi.startup.StartupManager;
|
||||
import com.intellij.psi.PsiDirectory;
|
||||
import com.intellij.psi.PsiManager;
|
||||
import com.jetbrains.python.packaging.PyPackage;
|
||||
import com.jetbrains.python.packaging.PyPackageUtil;
|
||||
import com.jetbrains.python.sdk.PythonSdkType;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import static com.jetbrains.python.actions.PySciViewAction.ACTION_ID;
|
||||
|
||||
@State(name = "PySciProjectComponent", storages = @Storage("other.xml"))
|
||||
public class PySciProjectComponent extends AbstractProjectComponent implements PersistentStateComponent<PySciProjectComponent.State> {
|
||||
private static final NotificationGroup BALLOON_NOTIFICATIONS = new NotificationGroup("Python Scientific View Advertiser",
|
||||
NotificationDisplayType.STICKY_BALLOON,
|
||||
false);
|
||||
private State myState = new State();
|
||||
|
||||
protected PySciProjectComponent(Project project) {
|
||||
super(project);
|
||||
}
|
||||
|
||||
public static PySciProjectComponent getInstance(Project project) {
|
||||
return project.getComponent(PySciProjectComponent.class);
|
||||
}
|
||||
|
||||
public void useSciView(boolean useSciView) {
|
||||
myState.PY_SCI_VIEW = useSciView;
|
||||
}
|
||||
|
||||
public boolean useSciView() {
|
||||
return myState.PY_SCI_VIEW;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void projectOpened() {
|
||||
if (myState.PY_SCI_VIEW) {
|
||||
StartupManager.getInstance(myProject).runWhenProjectIsInitialized(() -> {
|
||||
final PsiDirectory directory = PsiManager.getInstance(myProject).findDirectory(myProject.getBaseDir());
|
||||
if (directory != null) {
|
||||
DocumentationManager.getInstance(myProject).showJavaDocInfo(directory, directory);
|
||||
}
|
||||
});
|
||||
}
|
||||
else if (!myState.PY_SCI_VIEW_SUGGESTED) {
|
||||
StartupManager.getInstance(myProject).runWhenProjectIsInitialized(() -> {
|
||||
final PsiDirectory directory = PsiManager.getInstance(myProject).findDirectory(myProject.getBaseDir());
|
||||
if (directory != null) {
|
||||
final Module module = ModuleUtilCore.findModuleForPsiElement(directory);
|
||||
if (module != null) {
|
||||
final Sdk sdk = PythonSdkType.findPythonSdk(module);
|
||||
if (sdk != null) {
|
||||
final List<PyPackage> packages = PyPackageUtil.refreshAndGetPackagesModally(sdk);
|
||||
final PyPackage numpy = PyPackageUtil.findPackage(packages, "numpy");
|
||||
|
||||
if (numpy != null) {
|
||||
showInspectionAdvertisement(myProject);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
private void showInspectionAdvertisement(@NotNull Project project) {
|
||||
final String msg = "Your source code imports the 'numpy' package." +
|
||||
"<br/>Would you like to enable Scientific View?<br/>" +
|
||||
"<a href=\"#yes\">Yes</a> <a href=\"#no\">No</a>";
|
||||
showSingletonNotification(project, msg, NotificationType.INFORMATION, (notification, event) -> {
|
||||
myState.PY_SCI_VIEW_SUGGESTED = true;
|
||||
final boolean enabled = "#yes".equals(event.getDescription());
|
||||
if (enabled) {
|
||||
final AnAction action = ActionManager.getInstance().getAction(ACTION_ID);
|
||||
if (action instanceof PySciViewAction) {
|
||||
final AnActionEvent anActionEvent = AnActionEvent.createFromDataContext(
|
||||
ActionPlaces.UNKNOWN, null, DataManager.getInstance().getDataContextFromFocus().getResult());
|
||||
((PySciViewAction)action).setSelected(anActionEvent, true);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private static void showSingletonNotification(@NotNull Project project,
|
||||
@NotNull String htmlContent,
|
||||
@NotNull NotificationType type,
|
||||
@NotNull NotificationListener listener) {
|
||||
BALLOON_NOTIFICATIONS.createNotification("Scientific View", htmlContent, type, (notification, event) -> {
|
||||
try {
|
||||
listener.hyperlinkUpdate(notification, event);
|
||||
}
|
||||
finally {
|
||||
notification.expire();
|
||||
}
|
||||
}).notify(project);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public PySciProjectComponent.State getState() {
|
||||
return myState;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void loadState(PySciProjectComponent.State state) {
|
||||
myState.PY_SCI_VIEW = state.PY_SCI_VIEW;
|
||||
myState.PY_SCI_VIEW_SUGGESTED = state.PY_SCI_VIEW_SUGGESTED;
|
||||
}
|
||||
|
||||
public static class State {
|
||||
public boolean PY_SCI_VIEW = false;
|
||||
public boolean PY_SCI_VIEW_SUGGESTED = false;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,151 @@
|
||||
/*
|
||||
* Copyright 2000-2017 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.jetbrains.python.actions;
|
||||
|
||||
import com.intellij.codeInsight.documentation.DocumentationManager;
|
||||
import com.intellij.ide.util.PropertiesComponent;
|
||||
import com.intellij.openapi.actionSystem.AnActionEvent;
|
||||
import com.intellij.openapi.actionSystem.CommonDataKeys;
|
||||
import com.intellij.openapi.actionSystem.Presentation;
|
||||
import com.intellij.openapi.actionSystem.ToggleAction;
|
||||
import com.intellij.openapi.project.DumbAware;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.ui.popup.JBPopup;
|
||||
import com.intellij.openapi.wm.*;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.PsiManager;
|
||||
import com.jetbrains.python.console.PythonConsoleToolWindow;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import static com.jetbrains.python.debugger.containerview.PyDataView.DATA_VIEWER_ID;
|
||||
|
||||
public class PySciViewAction extends ToggleAction implements DumbAware {
|
||||
private static final String TEXT_SCI_VIEW = "Scientific Mode";
|
||||
|
||||
private boolean wasConsoleVisible = false;
|
||||
private ToolWindowType myDocumentationType = ToolWindowType.FLOATING;
|
||||
private boolean myDocumentationAutoHide = true;
|
||||
|
||||
public static final String ACTION_ID = "PySciView";
|
||||
private ToolWindowType myDataViewType = ToolWindowType.FLOATING;
|
||||
|
||||
public PySciViewAction() {
|
||||
super(TEXT_SCI_VIEW);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isSelected(AnActionEvent e) {
|
||||
return e.getProject() != null && PySciProjectComponent.getInstance(e.getProject()).useSciView();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setSelected(AnActionEvent e, boolean state) {
|
||||
final Project project = e.getProject();
|
||||
if (project == null) return;
|
||||
PySciProjectComponent.getInstance(project).useSciView(state);
|
||||
|
||||
final PsiElement element = getPsiElement(e, project);
|
||||
|
||||
if (state) {
|
||||
showConsoleToolwindow(project);
|
||||
showDocumentationToolwindow(project, element);
|
||||
showDataViewAsToolwindow(project);
|
||||
}
|
||||
else {
|
||||
hideConsoleToolwindow(project);
|
||||
restoreDocumentationPopup(project);
|
||||
hideDataViewer(project);
|
||||
}
|
||||
}
|
||||
|
||||
private void showConsoleToolwindow(@NotNull final Project project) {
|
||||
final ToolWindow consoleToolWindow = PythonConsoleToolWindow.getInstance(project).getToolWindow();
|
||||
wasConsoleVisible = consoleToolWindow.isVisible();
|
||||
consoleToolWindow.show(null);
|
||||
}
|
||||
|
||||
private void hideConsoleToolwindow(@NotNull final Project project) {
|
||||
if (!wasConsoleVisible) {
|
||||
PythonConsoleToolWindow.getInstance(project).getToolWindow().hide(null);
|
||||
}
|
||||
}
|
||||
|
||||
private void showDocumentationToolwindow(Project project, PsiElement element) {
|
||||
final String showInToolWindowProperty = DocumentationManager.getInstance(project).getShowInToolWindowProperty();
|
||||
|
||||
PropertiesComponent.getInstance().setValue(showInToolWindowProperty, true);
|
||||
PropertiesComponent.getInstance().setValue(DocumentationManager.getInstance(project).getAutoUpdateEnabledProperty(), true);
|
||||
|
||||
if (element != null) {
|
||||
DocumentationManager.getInstance(project).showJavaDocInfo(element, element);
|
||||
}
|
||||
final ToolWindow window = ToolWindowManager.getInstance(project).getToolWindow(ToolWindowId.DOCUMENTATION);
|
||||
if (window != null) {
|
||||
window.setAnchor(ToolWindowAnchor.RIGHT, null);
|
||||
myDocumentationType = window.getType();
|
||||
myDocumentationAutoHide = window.isAutoHide();
|
||||
window.setType(ToolWindowType.DOCKED, null);
|
||||
window.setAutoHide(false);
|
||||
}
|
||||
}
|
||||
|
||||
private void restoreDocumentationPopup(Project project) {
|
||||
PropertiesComponent.getInstance().setValue(DocumentationManager.getInstance(project).getAutoUpdateEnabledProperty(), false);
|
||||
|
||||
final ToolWindow window = ToolWindowManager.getInstance(project).getToolWindow(ToolWindowId.DOCUMENTATION);
|
||||
if (window != null) {
|
||||
window.setType(myDocumentationType, null);
|
||||
window.setAutoHide(myDocumentationAutoHide);
|
||||
DocumentationManager.getInstance(project).restorePopupBehavior();
|
||||
final JBPopup hint = DocumentationManager.getInstance(project).getDocInfoHint();
|
||||
if (hint != null) {
|
||||
hint.cancel();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void showDataViewAsToolwindow(@NotNull final Project project) {
|
||||
ToolWindow dataViewToolWindow = ToolWindowManager.getInstance(project).getToolWindow(DATA_VIEWER_ID);
|
||||
myDataViewType = dataViewToolWindow.getType();
|
||||
dataViewToolWindow.setType(ToolWindowType.DOCKED, null);
|
||||
dataViewToolWindow.setShowStripeButton(true);
|
||||
}
|
||||
|
||||
private void hideDataViewer(Project project) {
|
||||
final ToolWindow dataViewer = ToolWindowManager.getInstance(project).getToolWindow(DATA_VIEWER_ID);
|
||||
dataViewer.setType(myDataViewType, null);
|
||||
dataViewer.setShowStripeButton(false);
|
||||
}
|
||||
|
||||
private static PsiElement getPsiElement(AnActionEvent e, Project project) {
|
||||
PsiElement element = CommonDataKeys.PSI_ELEMENT.getData(e.getDataContext());
|
||||
if (element == null) {
|
||||
element = CommonDataKeys.PSI_FILE.getData(e.getDataContext());
|
||||
}
|
||||
if (element == null) {
|
||||
element = PsiManager.getInstance(project).findDirectory(project.getBaseDir());
|
||||
}
|
||||
return element;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void update(@NotNull AnActionEvent e) {
|
||||
super.update(e);
|
||||
final Project project = e.getProject();
|
||||
final Presentation presentation = e.getPresentation();
|
||||
presentation.setEnabledAndVisible(project != null);
|
||||
}
|
||||
}
|
||||
@@ -95,6 +95,7 @@ public class PythonConsoleView extends LanguageConsoleImpl implements Observable
|
||||
|
||||
private XStandaloneVariablesView mySplitView;
|
||||
private ActionCallback myInitialized = new ActionCallback();
|
||||
private boolean isShowVars = true;
|
||||
|
||||
public PythonConsoleView(final Project project, final String title, final Sdk sdk) {
|
||||
super(project, title, PythonLanguage.getInstance());
|
||||
@@ -115,6 +116,10 @@ public class PythonConsoleView extends LanguageConsoleImpl implements Observable
|
||||
|
||||
public void setConsoleCommunication(final ConsoleCommunication communication) {
|
||||
getFile().putCopyableUserData(PydevConsoleRunner.CONSOLE_KEY, communication);
|
||||
|
||||
if (isShowVars && communication instanceof PydevConsoleCommunication) {
|
||||
showVariables((PydevConsoleCommunication)communication);
|
||||
}
|
||||
}
|
||||
|
||||
private PyConsoleStartFolding createConsoleFolding() {
|
||||
@@ -491,4 +496,12 @@ public class PythonConsoleView extends LanguageConsoleImpl implements Observable
|
||||
public void initialized() {
|
||||
myInitialized.setDone();
|
||||
}
|
||||
|
||||
public void setShowVars(boolean showVars) {
|
||||
isShowVars = showVars;
|
||||
}
|
||||
|
||||
public boolean isShowVars() {
|
||||
return isShowVars;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -26,16 +26,15 @@ import com.jetbrains.python.console.PythonConsoleView
|
||||
* Created by Yuli Fiterman on 9/18/2016.
|
||||
*/
|
||||
class ShowVarsAction(private val consoleView: PythonConsoleView, private val consoleComm: PydevConsoleCommunication) : ToggleAction("Show Variables", "Shows active console variables", AllIcons.Debugger.Watches), DumbAware {
|
||||
private var mySelected = false
|
||||
|
||||
override fun isSelected(e: AnActionEvent): Boolean {
|
||||
return mySelected
|
||||
return consoleView.isShowVars
|
||||
}
|
||||
|
||||
override fun setSelected(e: AnActionEvent, state: Boolean) {
|
||||
mySelected = state
|
||||
consoleView.isShowVars = state
|
||||
|
||||
if (mySelected) {
|
||||
if (state) {
|
||||
consoleView.showVariables(consoleComm)
|
||||
}
|
||||
else {
|
||||
|
||||
Reference in New Issue
Block a user