diff --git a/python/educational-core/student/resources/META-INF/plugin.xml b/python/educational-core/student/resources/META-INF/plugin.xml
index f29b7e7a1c1a..3e10b6a2bb2e 100644
--- a/python/educational-core/student/resources/META-INF/plugin.xml
+++ b/python/educational-core/student/resources/META-INF/plugin.xml
@@ -35,7 +35,7 @@
-
+
@@ -75,11 +75,13 @@
serviceImplementation="com.jetbrains.edu.learning.StudyDocumentationManager" overrides="true"/>
-
+
diff --git a/python/educational-core/student/src/com/jetbrains/edu/learning/StudyBaseToolWindowConfigurator.java b/python/educational-core/student/src/com/jetbrains/edu/learning/StudyBasePluginConfigurator.java
similarity index 93%
rename from python/educational-core/student/src/com/jetbrains/edu/learning/StudyBaseToolWindowConfigurator.java
rename to python/educational-core/student/src/com/jetbrains/edu/learning/StudyBasePluginConfigurator.java
index 7c118af5bccf..e1900e133df5 100644
--- a/python/educational-core/student/src/com/jetbrains/edu/learning/StudyBaseToolWindowConfigurator.java
+++ b/python/educational-core/student/src/com/jetbrains/edu/learning/StudyBasePluginConfigurator.java
@@ -17,7 +17,7 @@ import javax.swing.*;
import java.util.Collections;
import java.util.Map;
-public abstract class StudyBaseToolWindowConfigurator implements StudyToolWindowConfigurator {
+public abstract class StudyBasePluginConfigurator implements StudyPluginConfigurator {
@NotNull
@Override
public DefaultActionGroup getActionGroup(Project project) {
@@ -87,4 +87,10 @@ public abstract class StudyBaseToolWindowConfigurator implements StudyToolWindow
}
};
}
+
+ @Nullable
+ @Override
+ public StudyAfterCheckAction[] getAfterCheckActions() {
+ return null;
+ }
}
diff --git a/python/educational-core/student/src/com/jetbrains/edu/learning/StudyToolWindowConfigurator.java b/python/educational-core/student/src/com/jetbrains/edu/learning/StudyPluginConfigurator.java
similarity index 73%
rename from python/educational-core/student/src/com/jetbrains/edu/learning/StudyToolWindowConfigurator.java
rename to python/educational-core/student/src/com/jetbrains/edu/learning/StudyPluginConfigurator.java
index 9757d4dd0a56..4561c2b903aa 100644
--- a/python/educational-core/student/src/com/jetbrains/edu/learning/StudyToolWindowConfigurator.java
+++ b/python/educational-core/student/src/com/jetbrains/edu/learning/StudyPluginConfigurator.java
@@ -4,14 +4,17 @@ import com.intellij.openapi.actionSystem.DefaultActionGroup;
import com.intellij.openapi.extensions.ExtensionPointName;
import com.intellij.openapi.fileEditor.FileEditorManagerListener;
import com.intellij.openapi.project.Project;
+import com.jetbrains.edu.learning.actions.StudyAfterCheckAction;
+import com.jetbrains.edu.learning.settings.ModifiableSettingsPanel;
import com.jetbrains.edu.learning.ui.StudyToolWindow;
import org.jetbrains.annotations.NotNull;
+import org.jetbrains.annotations.Nullable;
import javax.swing.*;
import java.util.Map;
-public interface StudyToolWindowConfigurator {
- ExtensionPointName EP_NAME = ExtensionPointName.create("Edu.studyToolWindowConfigurator");
+public interface StudyPluginConfigurator {
+ ExtensionPointName EP_NAME = ExtensionPointName.create("Edu.studyPluginConfigurator");
/**
* Provide action group that should be placed on the tool window toolbar.
@@ -37,9 +40,14 @@ public interface StudyToolWindowConfigurator {
* @return parameter for CodeMirror script. Available languages: @see <@linktourl http://codemirror.net/mode/>
*/
@NotNull String getDefaultHighlightingMode();
+
+ @Nullable
+ StudyAfterCheckAction[] getAfterCheckActions();
@NotNull String getLanguageScriptUrl();
boolean accept(@NotNull final Project project);
-
+
+ @Nullable
+ ModifiableSettingsPanel getSettingsPanel();
}
diff --git a/python/educational-core/student/src/com/jetbrains/edu/learning/StudyUtils.java b/python/educational-core/student/src/com/jetbrains/edu/learning/StudyUtils.java
index 00c3518c529b..940d94ce6b53 100644
--- a/python/educational-core/student/src/com/jetbrains/edu/learning/StudyUtils.java
+++ b/python/educational-core/student/src/com/jetbrains/edu/learning/StudyUtils.java
@@ -450,9 +450,9 @@ public class StudyUtils {
}
@Nullable
- public static StudyToolWindowConfigurator getConfigurator(@NotNull final Project project) {
- StudyToolWindowConfigurator[] extensions = StudyToolWindowConfigurator.EP_NAME.getExtensions();
- for (StudyToolWindowConfigurator extension: extensions) {
+ public static StudyPluginConfigurator getConfigurator(@NotNull final Project project) {
+ StudyPluginConfigurator[] extensions = StudyPluginConfigurator.EP_NAME.getExtensions();
+ for (StudyPluginConfigurator extension: extensions) {
if (extension.accept(project)) {
return extension;
}
diff --git a/python/educational-core/student/src/com/jetbrains/edu/learning/actions/StudyAfterCheckAction.java b/python/educational-core/student/src/com/jetbrains/edu/learning/actions/StudyAfterCheckAction.java
new file mode 100644
index 000000000000..a112e4330de7
--- /dev/null
+++ b/python/educational-core/student/src/com/jetbrains/edu/learning/actions/StudyAfterCheckAction.java
@@ -0,0 +1,10 @@
+package com.jetbrains.edu.learning.actions;
+
+import com.intellij.openapi.actionSystem.AnAction;
+import com.intellij.openapi.project.Project;
+import com.jetbrains.edu.courseFormat.Task;
+import org.jetbrains.annotations.NotNull;
+
+public abstract class StudyAfterCheckAction extends AnAction {
+ public abstract void run(@NotNull final Project project, @NotNull final Task solvedTask);
+}
diff --git a/python/educational-core/student/src/com/jetbrains/edu/learning/checker/StudyCheckTask.java b/python/educational-core/student/src/com/jetbrains/edu/learning/checker/StudyCheckTask.java
index 5d332ef3ce31..5de1e25b6725 100644
--- a/python/educational-core/student/src/com/jetbrains/edu/learning/checker/StudyCheckTask.java
+++ b/python/educational-core/student/src/com/jetbrains/edu/learning/checker/StudyCheckTask.java
@@ -14,10 +14,12 @@ import com.intellij.openapi.vfs.VirtualFile;
import com.jetbrains.edu.learning.core.EduUtils;
import com.jetbrains.edu.learning.courseFormat.StudyStatus;
import com.jetbrains.edu.learning.courseFormat.Task;
+import com.jetbrains.edu.learning.StudyPluginConfigurator;
import com.jetbrains.edu.learning.StudyState;
import com.jetbrains.edu.learning.StudyTaskManager;
import com.jetbrains.edu.learning.StudyUtils;
-import com.jetbrains.edu.learning.stepic.EduStepicConnector;
+import com.jetbrains.edu.learning.actions.StudyAfterCheckAction;
+import com.jetbrains.edu.learning.EduStepicConnector;
import com.jetbrains.edu.learning.stepic.StudySettings;
import org.jetbrains.annotations.NotNull;
@@ -110,6 +112,19 @@ public class StudyCheckTask extends com.intellij.openapi.progress.Task.Backgroun
myTaskManger.setStatus(myTask, StudyStatus.Solved);
ApplicationManager.getApplication().invokeLater(
() -> StudyCheckUtils.showTestResultPopUp(testsOutput.getMessage(), MessageType.INFO.getPopupBackground(), myProject));
+ runAfterTaskActions();
+ }
+
+ private void runAfterTaskActions() {
+ StudyPluginConfigurator configurator = StudyUtils.getConfigurator(myProject);
+ if (configurator != null) {
+ StudyAfterCheckAction[] checkActions = configurator.getAfterCheckActions();
+ if (checkActions != null) {
+ for (StudyAfterCheckAction action: checkActions) {
+ action.run(myProject, myTask);
+ }
+ }
+ }
}
protected void postAttemptToStepic(StudyTestsOutputParser.TestsOutput testsOutput) {
diff --git a/python/educational-core/student/src/com/jetbrains/edu/learning/settings/ModifiableSettingsPanel.java b/python/educational-core/student/src/com/jetbrains/edu/learning/settings/ModifiableSettingsPanel.java
new file mode 100644
index 000000000000..101fcb452397
--- /dev/null
+++ b/python/educational-core/student/src/com/jetbrains/edu/learning/settings/ModifiableSettingsPanel.java
@@ -0,0 +1,19 @@
+package com.jetbrains.edu.learning.settings;
+
+
+import org.jetbrains.annotations.NotNull;
+
+import javax.swing.*;
+
+public interface ModifiableSettingsPanel {
+ void apply();
+
+ void reset();
+
+ void resetCredentialsModification();
+
+ boolean isModified();
+
+ @NotNull
+ JComponent getPanel();
+}
diff --git a/python/educational-core/student/src/com/jetbrains/edu/learning/stepic/StudySettingsPanel.form b/python/educational-core/student/src/com/jetbrains/edu/learning/settings/StudyBaseSettingsPanel.form
similarity index 84%
rename from python/educational-core/student/src/com/jetbrains/edu/learning/stepic/StudySettingsPanel.form
rename to python/educational-core/student/src/com/jetbrains/edu/learning/settings/StudyBaseSettingsPanel.form
index d6e802b93d12..5ee9dc512466 100644
--- a/python/educational-core/student/src/com/jetbrains/edu/learning/stepic/StudySettingsPanel.form
+++ b/python/educational-core/student/src/com/jetbrains/edu/learning/settings/StudyBaseSettingsPanel.form
@@ -1,6 +1,6 @@
-
diff --git a/python/educational-core/student/src/com/jetbrains/edu/learning/stepic/StudySettingsPanel.java b/python/educational-core/student/src/com/jetbrains/edu/learning/settings/StudyBaseSettingsPanel.java
similarity index 88%
rename from python/educational-core/student/src/com/jetbrains/edu/learning/stepic/StudySettingsPanel.java
rename to python/educational-core/student/src/com/jetbrains/edu/learning/settings/StudyBaseSettingsPanel.java
index e559463c8cfd..2b3135c9e65b 100644
--- a/python/educational-core/student/src/com/jetbrains/edu/learning/stepic/StudySettingsPanel.java
+++ b/python/educational-core/student/src/com/jetbrains/edu/learning/settings/StudyBaseSettingsPanel.java
@@ -13,10 +13,13 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-package com.jetbrains.edu.learning.stepic;
+package com.jetbrains.edu.learning.settings;
import com.intellij.openapi.util.text.StringUtil;
import com.intellij.ui.DocumentAdapter;
+import com.intellij.util.ui.UIUtil;
+import com.jetbrains.edu.learning.stepic.EduStepicConnector;
+import com.jetbrains.edu.learning.stepic.StudySettings;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@@ -28,16 +31,15 @@ import javax.swing.text.PlainDocument;
import java.awt.event.FocusEvent;
import java.awt.event.FocusListener;
-public class StudySettingsPanel {
+public class StudyBaseSettingsPanel implements ModifiableSettingsPanel{
private static final String DEFAULT_PASSWORD_TEXT = "************";
private JTextField myLoginTextField;
private JPasswordField myPasswordField;
private JPanel myPane;
- private JPanel myCardPanel;
private boolean myCredentialsModified;
- public StudySettingsPanel() {
+ public StudyBaseSettingsPanel() {
myPasswordField.getDocument().addDocumentListener(new DocumentAdapter() {
@Override
protected void textChanged(DocumentEvent e) {
@@ -67,7 +69,7 @@ public class StudySettingsPanel {
public void focusLost(FocusEvent e) {
}
});
-
+ myPane.setBorder(BorderFactory.createMatteBorder(1, 0, 0, 0, UIUtil.getBoundsColor()));
reset();
}
@@ -76,6 +78,8 @@ public class StudySettingsPanel {
myCredentialsModified = true;
}
+ @NotNull
+ @Override
public JComponent getPanel() {
return myPane;
}
@@ -98,6 +102,7 @@ public class StudySettingsPanel {
myPasswordField.setText(StringUtil.isEmpty(password) ? null : password);
}
+ @Override
public void reset() {
final StudySettings studySettings = StudySettings.getInstance();
setLogin(studySettings.getLogin());
@@ -106,6 +111,7 @@ public class StudySettingsPanel {
resetCredentialsModification();
}
+ @Override
public void apply() {
if (myCredentialsModified) {
final StudySettings studySettings = StudySettings.getInstance();
@@ -118,10 +124,12 @@ public class StudySettingsPanel {
resetCredentialsModification();
}
+ @Override
public boolean isModified() {
return myCredentialsModified;
}
+ @Override
public void resetCredentialsModification() {
myCredentialsModified = false;
}
diff --git a/python/educational-core/student/src/com/jetbrains/edu/learning/settings/StudyConfigurable.java b/python/educational-core/student/src/com/jetbrains/edu/learning/settings/StudyConfigurable.java
new file mode 100644
index 000000000000..eff51e506e35
--- /dev/null
+++ b/python/educational-core/student/src/com/jetbrains/edu/learning/settings/StudyConfigurable.java
@@ -0,0 +1,124 @@
+/*
+ * Copyright 2000-2015 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.edu.learning.settings;
+
+import com.intellij.openapi.options.ConfigurationException;
+import com.intellij.openapi.options.SearchableConfigurable;
+import com.intellij.openapi.ui.VerticalFlowLayout;
+import com.jetbrains.edu.learning.StudyPluginConfigurator;
+import org.jetbrains.annotations.Nls;
+import org.jetbrains.annotations.NotNull;
+import org.jetbrains.annotations.Nullable;
+
+import javax.swing.*;
+import java.util.ArrayList;
+
+public class StudyConfigurable implements SearchableConfigurable {
+ public static final String ID = "com.jetbrains.edu.learning.stepic.EduConfigurable";
+ private JPanel myMainPanel;
+ private ArrayList myPluginsSettingsPanels;
+ private StudyBaseSettingsPanel mySettingsPanel;
+
+ public StudyConfigurable() {
+ }
+
+ @NotNull
+ @Override
+ public String getId() {
+ return ID;
+ }
+
+ @Nullable
+ @Override
+ public Runnable enableSearch(String option) {
+ return null;
+ }
+
+ @Nls
+ @Override
+ public String getDisplayName() {
+ return "Educational";
+ }
+
+ @NotNull
+ @Override
+ public String getHelpTopic() {
+ return ID;
+ }
+
+ @Nullable
+ @Override
+ public JComponent createComponent() {
+ if (myMainPanel == null) {
+ myMainPanel = new JPanel(new VerticalFlowLayout());
+ }
+ mySettingsPanel = new StudyBaseSettingsPanel();
+ myMainPanel.add(mySettingsPanel.getPanel());
+
+ myPluginsSettingsPanels = new ArrayList<>();
+ StudyPluginConfigurator[] extensions = StudyPluginConfigurator.EP_NAME.getExtensions();
+ for (StudyPluginConfigurator configurator: extensions) {
+ final ModifiableSettingsPanel settingsPanel = configurator.getSettingsPanel();
+ if (settingsPanel != null) {
+ myPluginsSettingsPanels.add(settingsPanel);
+ myMainPanel.add(settingsPanel.getPanel());
+ }
+ }
+ return myMainPanel;
+ }
+
+ @Override
+ public boolean isModified() {
+ if (mySettingsPanel != null) {
+ boolean isModified = mySettingsPanel.isModified();
+ if (myPluginsSettingsPanels != null && !myPluginsSettingsPanels.isEmpty()) {
+ for (ModifiableSettingsPanel settingsPanel: myPluginsSettingsPanels) {
+ isModified &= settingsPanel.isModified();
+ }
+ }
+ return isModified;
+ }
+ return false;
+ }
+
+ public void apply() throws ConfigurationException {
+ if (myMainPanel != null) {
+ mySettingsPanel.apply();
+ if (myPluginsSettingsPanels != null && !myPluginsSettingsPanels.isEmpty()) {
+ for (ModifiableSettingsPanel settingsPanel: myPluginsSettingsPanels) {
+ settingsPanel.apply();
+ }
+ }
+ }
+ }
+
+ public void reset() {
+ if (myMainPanel != null) {
+ mySettingsPanel.apply();
+ if (myPluginsSettingsPanels != null && !myPluginsSettingsPanels.isEmpty()) {
+ for (ModifiableSettingsPanel settingsPanel: myPluginsSettingsPanels) {
+ settingsPanel.reset();
+ }
+ }
+ }
+ }
+
+ @Override
+ public void disposeUIResources() {
+ myMainPanel = null;
+ }
+}
+
diff --git a/python/educational-core/student/src/com/jetbrains/edu/learning/stepic/StudyConfigurable.java b/python/educational-core/student/src/com/jetbrains/edu/learning/stepic/StudyConfigurable.java
deleted file mode 100644
index f75dc403b37d..000000000000
--- a/python/educational-core/student/src/com/jetbrains/edu/learning/stepic/StudyConfigurable.java
+++ /dev/null
@@ -1,88 +0,0 @@
-/*
- * Copyright 2000-2015 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.edu.learning.stepic;
-
-import com.intellij.openapi.options.ConfigurationException;
-import com.intellij.openapi.options.SearchableConfigurable;
-import org.jetbrains.annotations.Nls;
-import org.jetbrains.annotations.NotNull;
-import org.jetbrains.annotations.Nullable;
-
-import javax.swing.*;
-
-public class StudyConfigurable implements SearchableConfigurable {
- public static final String ID = "com.jetbrains.edu.learning.stepic.EduConfigurable";
- private StudySettingsPanel mySettingsPane;
-
- public StudyConfigurable() {
- }
-
- @NotNull
- @Override
- public String getId() {
- return ID;
- }
-
- @Nullable
- @Override
- public Runnable enableSearch(String option) {
- return null;
- }
-
- @Nls
- @Override
- public String getDisplayName() {
- return "Educational";
- }
-
- @NotNull
- @Override
- public String getHelpTopic() {
- return ID;
- }
-
- @Nullable
- @Override
- public JComponent createComponent() {
- if (mySettingsPane == null) {
- mySettingsPane = new StudySettingsPanel();
- }
- return mySettingsPane.getPanel();
- }
-
- @Override
- public boolean isModified() {
- return mySettingsPane != null && mySettingsPane.isModified();
- }
-
- public void apply() throws ConfigurationException {
- if (mySettingsPane != null) {
- mySettingsPane.apply();
- }
- }
-
- public void reset() {
- if (mySettingsPane != null) {
- mySettingsPane.reset();
- }
- }
-
- @Override
- public void disposeUIResources() {
- mySettingsPane = null;
- }
-}
-
diff --git a/python/educational-core/student/src/com/jetbrains/edu/learning/ui/StudyBrowserWindow.java b/python/educational-core/student/src/com/jetbrains/edu/learning/ui/StudyBrowserWindow.java
index 76ad74a86f26..c0999d9cbae6 100644
--- a/python/educational-core/student/src/com/jetbrains/edu/learning/ui/StudyBrowserWindow.java
+++ b/python/educational-core/student/src/com/jetbrains/edu/learning/ui/StudyBrowserWindow.java
@@ -10,7 +10,7 @@ import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.editor.colors.EditorColorsManager;
import com.intellij.openapi.editor.colors.EditorColorsScheme;
import com.intellij.openapi.util.io.StreamUtil;
-import com.jetbrains.edu.learning.StudyToolWindowConfigurator;
+import com.jetbrains.edu.learning.StudyPluginConfigurator;
import javafx.application.Platform;
import javafx.concurrent.Worker;
import javafx.embed.swing.JFXPanel;
@@ -124,7 +124,7 @@ class StudyBrowserWindow extends JFrame {
});
}
- public void loadContent(@NotNull final String content, StudyToolWindowConfigurator configurator) {
+ public void loadContent(@NotNull final String content, StudyPluginConfigurator configurator) {
String withCodeHighlighting = createHtmlWithCodeHighlighting(content, configurator);
Platform.runLater(()-> {
updateLookWithProgressBarIfNeeded();
@@ -133,7 +133,7 @@ class StudyBrowserWindow extends JFrame {
}
@Nullable
- private String createHtmlWithCodeHighlighting(@NotNull final String content, @NotNull StudyToolWindowConfigurator configurator) {
+ private String createHtmlWithCodeHighlighting(@NotNull final String content, @NotNull StudyPluginConfigurator configurator) {
String template = null;
InputStream stream = getClass().getResourceAsStream("/code-mirror/template.html");
try {
diff --git a/python/educational-core/student/src/com/jetbrains/edu/learning/ui/StudyJavaFxToolWindow.java b/python/educational-core/student/src/com/jetbrains/edu/learning/ui/StudyJavaFxToolWindow.java
index 873c987da77d..c215dc86eed4 100644
--- a/python/educational-core/student/src/com/jetbrains/edu/learning/ui/StudyJavaFxToolWindow.java
+++ b/python/educational-core/student/src/com/jetbrains/edu/learning/ui/StudyJavaFxToolWindow.java
@@ -16,7 +16,7 @@
package com.jetbrains.edu.learning.ui;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.project.ProjectUtil;
-import com.jetbrains.edu.learning.StudyToolWindowConfigurator;
+import com.jetbrains.edu.learning.StudyPluginConfigurator;
import com.jetbrains.edu.learning.StudyUtils;
import javax.swing.*;
@@ -41,7 +41,7 @@ public class StudyJavaFxToolWindow extends StudyToolWindow {
@Override
public void setTaskText(String text) {
- StudyToolWindowConfigurator configurator = StudyUtils.getConfigurator(ProjectUtil.guessCurrentProject(this));
+ StudyPluginConfigurator configurator = StudyUtils.getConfigurator(ProjectUtil.guessCurrentProject(this));
if (configurator != null) {
myBrowserWindow.loadContent(text, configurator);
}
diff --git a/python/educational-core/student/src/com/jetbrains/edu/learning/ui/StudyToolWindow.java b/python/educational-core/student/src/com/jetbrains/edu/learning/ui/StudyToolWindow.java
index 0230fa10c5af..28671186339a 100644
--- a/python/educational-core/student/src/com/jetbrains/edu/learning/ui/StudyToolWindow.java
+++ b/python/educational-core/student/src/com/jetbrains/edu/learning/ui/StudyToolWindow.java
@@ -28,8 +28,10 @@ import com.intellij.ui.JBCardLayout;
import com.intellij.ui.OnePixelSplitter;
import com.intellij.util.ui.JBUI;
import com.jetbrains.edu.learning.courseFormat.Course;
+import com.jetbrains.edu.learning.courseFormat.Task;
+import com.jetbrains.edu.learning.courseFormat.TaskFile;
+import com.jetbrains.edu.learning.StudyPluginConfigurator;
import com.jetbrains.edu.learning.StudyTaskManager;
-import com.jetbrains.edu.learning.StudyToolWindowConfigurator;
import com.jetbrains.edu.learning.StudyUtils;
import org.jetbrains.annotations.NotNull;
@@ -65,14 +67,14 @@ public abstract class StudyToolWindow extends SimpleToolWindowPanel implements D
setContent(mySplitPane);
- StudyToolWindowConfigurator configurator = StudyUtils.getConfigurator(project);
+ StudyPluginConfigurator configurator = StudyUtils.getConfigurator(project);
assert configurator != null;
final FileEditorManagerListener listener = configurator.getFileEditorManagerListener(project, this);
project.getMessageBus().connect().subscribe(FileEditorManagerListener.FILE_EDITOR_MANAGER, listener);
}
private void addAdditionalPanels(Project project) {
- StudyToolWindowConfigurator configurator = StudyUtils.getConfigurator(project);
+ StudyPluginConfigurator configurator = StudyUtils.getConfigurator(project);
assert configurator != null;
Map panels = configurator.getAdditionalPanels(project);
for (Map.Entry entry: panels.entrySet()) {
@@ -129,7 +131,7 @@ public abstract class StudyToolWindow extends SimpleToolWindowPanel implements D
LOG.warn("Course is null");
return new DefaultActionGroup();
}
- StudyToolWindowConfigurator configurator = StudyUtils.getConfigurator(project);
+ StudyPluginConfigurator configurator = StudyUtils.getConfigurator(project);
assert configurator != null;
return configurator.getActionGroup(project);
diff --git a/python/educational-python/student-python/resources/META-INF/plugin.xml b/python/educational-python/student-python/resources/META-INF/plugin.xml
index a6c07367a459..3828c747c81b 100644
--- a/python/educational-python/student-python/resources/META-INF/plugin.xml
+++ b/python/educational-python/student-python/resources/META-INF/plugin.xml
@@ -33,7 +33,7 @@
-
+
+
diff --git a/python/educational-python/student-python/src/com/jetbrains/edu/learning/settings/PySettingsPanel.java b/python/educational-python/student-python/src/com/jetbrains/edu/learning/settings/PySettingsPanel.java
new file mode 100644
index 000000000000..240b567135bb
--- /dev/null
+++ b/python/educational-python/student-python/src/com/jetbrains/edu/learning/settings/PySettingsPanel.java
@@ -0,0 +1,48 @@
+package com.jetbrains.edu.learning.settings;
+import com.intellij.openapi.project.Project;
+import com.intellij.openapi.project.ProjectUtil;
+import com.intellij.ui.components.JBCheckBox;
+import com.intellij.util.ui.UIUtil;
+import org.jetbrains.annotations.NotNull;
+
+import javax.swing.*;
+
+
+public class PySettingsPanel implements ModifiableSettingsPanel{
+ private JBCheckBox myAskToTweetCheckBox;
+ private JPanel myPanel;
+ private boolean myIsModified = false;
+
+ public PySettingsPanel() {
+ myAskToTweetCheckBox.addActionListener(e -> myIsModified = true);
+ myAskToTweetCheckBox.setSelected(PyStudySettings.getInstance(ProjectUtil.guessCurrentProject(myPanel)).askToTweet());
+ myPanel.setBorder(BorderFactory.createMatteBorder(1, 0, 0, 0, UIUtil.getBoundsColor()));
+ }
+
+ @Override
+ public void apply() {
+ Project project = ProjectUtil.guessCurrentProject(myPanel);
+ PyStudySettings.getInstance(project).setAskToTweet(myAskToTweetCheckBox.isSelected());
+ }
+
+ @Override
+ public void reset() {
+ Project project = ProjectUtil.guessCurrentProject(myPanel);
+ PyStudySettings.getInstance(project).setAskToTweet(true);
+ }
+
+ @Override
+ public void resetCredentialsModification() {
+ myIsModified = false;
+ }
+
+ @Override
+ public boolean isModified() {
+ return myIsModified;
+ }
+
+ @NotNull
+ public JPanel getPanel() {
+ return myPanel;
+ }
+}
diff --git a/python/educational-python/student-python/src/com/jetbrains/edu/learning/settings/PyStudySettings.java b/python/educational-python/student-python/src/com/jetbrains/edu/learning/settings/PyStudySettings.java
new file mode 100644
index 000000000000..b2bc22b0d18b
--- /dev/null
+++ b/python/educational-python/student-python/src/com/jetbrains/edu/learning/settings/PyStudySettings.java
@@ -0,0 +1,43 @@
+package com.jetbrains.edu.learning.settings;
+
+import com.intellij.openapi.components.PersistentStateComponent;
+import com.intellij.openapi.components.ServiceManager;
+import com.intellij.openapi.components.State;
+import com.intellij.openapi.components.Storage;
+import com.intellij.openapi.project.Project;
+import org.jetbrains.annotations.NotNull;
+import org.jetbrains.annotations.Nullable;
+
+@SuppressWarnings("MethodMayBeStatic")
+@State(name = "PyStudySettings", storages = @Storage("py_study_settings.xml"))
+public class PyStudySettings implements PersistentStateComponent {
+
+ private State myState = new State();
+
+
+ public static class State {
+ public boolean askToTweet = true;
+ }
+
+ public static PyStudySettings getInstance(@NotNull final Project project) {
+ return ServiceManager.getService(project, PyStudySettings.class);
+ }
+ @Nullable
+ @Override
+ public State getState() {
+ return myState;
+ }
+
+ @Override
+ public void loadState(State state) {
+ myState = state;
+ }
+
+ public boolean askToTweet() {
+ return myState.askToTweet;
+ }
+
+ public void setAskToTweet(final boolean askToTweet) {
+ myState.askToTweet = askToTweet;
+ }
+}
\ No newline at end of file