remove code related to subtasks
[idea/community.git] / python / educational-core / student / src / com / jetbrains / edu / learning / actions / StudyRefreshTaskFileAction.java
1 package com.jetbrains.edu.learning.actions;
2
3 import com.intellij.ide.projectView.ProjectView;
4 import com.intellij.openapi.actionSystem.AnActionEvent;
5 import com.intellij.openapi.actionSystem.KeyboardShortcut;
6 import com.intellij.openapi.actionSystem.Presentation;
7 import com.intellij.openapi.application.ApplicationManager;
8 import com.intellij.openapi.command.CommandProcessor;
9 import com.intellij.openapi.diagnostic.Logger;
10 import com.intellij.openapi.editor.Document;
11 import com.intellij.openapi.editor.Editor;
12 import com.intellij.openapi.extensions.Extensions;
13 import com.intellij.openapi.keymap.KeymapUtil;
14 import com.intellij.openapi.project.Project;
15 import com.intellij.openapi.ui.MessageType;
16 import com.intellij.openapi.ui.Messages;
17 import com.intellij.openapi.ui.popup.Balloon;
18 import com.intellij.openapi.ui.popup.BalloonBuilder;
19 import com.intellij.openapi.ui.popup.JBPopupFactory;
20 import com.intellij.openapi.util.Disposer;
21 import com.intellij.openapi.wm.IdeFocusManager;
22 import com.intellij.problems.WolfTheProblemSolver;
23 import com.jetbrains.edu.learning.StudyActionListener;
24 import com.jetbrains.edu.learning.StudyState;
25 import com.jetbrains.edu.learning.StudyTaskManager;
26 import com.jetbrains.edu.learning.StudyUtils;
27 import com.jetbrains.edu.learning.core.EduAnswerPlaceholderPainter;
28 import com.jetbrains.edu.learning.core.EduNames;
29 import com.jetbrains.edu.learning.courseFormat.AnswerPlaceholder;
30 import com.jetbrains.edu.learning.courseFormat.Course;
31 import com.jetbrains.edu.learning.courseFormat.StudyStatus;
32 import com.jetbrains.edu.learning.courseFormat.TaskFile;
33 import com.jetbrains.edu.learning.editor.StudyEditor;
34 import com.jetbrains.edu.learning.navigation.StudyNavigator;
35 import icons.InteractiveLearningIcons;
36 import org.jetbrains.annotations.NotNull;
37 import org.jetbrains.annotations.Nullable;
38
39 import javax.swing.*;
40
41 public class StudyRefreshTaskFileAction extends StudyActionWithShortcut {
42   public static final String ACTION_ID = "RefreshTaskAction";
43   public static final String SHORTCUT = "ctrl shift pressed X";
44   private static final Logger LOG = Logger.getInstance(StudyRefreshTaskFileAction.class.getName());
45
46   public StudyRefreshTaskFileAction() {
47     super("Reset Task File (" + KeymapUtil.getShortcutText(new KeyboardShortcut(KeyStroke.getKeyStroke(SHORTCUT), null)) + ")", "Refresh current task",
48           InteractiveLearningIcons.ResetTaskFile);
49   }
50
51   public static void refresh(@NotNull final Project project) {
52     ApplicationManager.getApplication().invokeLater(() -> ApplicationManager.getApplication().runWriteAction(() -> {
53       StudyEditor studyEditor = StudyUtils.getSelectedStudyEditor(project);
54       StudyState studyState = new StudyState(studyEditor);
55       if (studyEditor == null || !studyState.isValid()) {
56         LOG.info("RefreshTaskFileAction was invoked outside of Study Editor");
57         return;
58       }
59       refreshFile(studyState, project);
60     }));
61   }
62
63   private static void refreshFile(@NotNull final StudyState studyState, @NotNull final Project project) {
64     final Editor editor = studyState.getEditor();
65     final TaskFile taskFile = studyState.getTaskFile();
66     if (!resetTaskFile(editor.getDocument(), project, taskFile, studyState.getVirtualFile().getName())) {
67       Messages.showInfoMessage("The initial text of task file is unavailable", "Failed to Refresh Task File");
68       return;
69     }
70     WolfTheProblemSolver.getInstance(project).clearProblems(studyState.getVirtualFile());
71     taskFile.setHighlightErrors(false);
72     StudyUtils.drawAllWindows(editor, taskFile);
73     EduAnswerPlaceholderPainter.createGuardedBlocks(editor, taskFile);
74     ApplicationManager.getApplication().invokeLater(
75       () -> IdeFocusManager.getInstance(project).requestFocus(editor.getContentComponent(), true));
76
77     StudyNavigator.navigateToFirstAnswerPlaceholder(editor, taskFile);
78     showBalloon(project, "You can start again now", MessageType.INFO);
79   }
80
81   private static boolean resetTaskFile(@NotNull final Document document,
82                                        @NotNull final Project project,
83                                        TaskFile taskFile,
84                                        String name) {
85     if (!resetDocument(document, taskFile, name)) {
86       return false;
87     }
88     taskFile.getTask().setStatus(StudyStatus.Unchecked);
89     resetAnswerPlaceholders(taskFile, project);
90     ProjectView.getInstance(project).refresh();
91     StudyUtils.updateToolWindows(project);
92     return true;
93   }
94
95   private static void showBalloon(@NotNull final Project project, String text, @NotNull final MessageType messageType) {
96     BalloonBuilder balloonBuilder =
97       JBPopupFactory.getInstance().createHtmlTextBalloonBuilder(text, messageType, null);
98     final Balloon balloon = balloonBuilder.createBalloon();
99     StudyEditor selectedStudyEditor = StudyUtils.getSelectedStudyEditor(project);
100     assert selectedStudyEditor != null;
101     balloon.show(StudyUtils.computeLocation(selectedStudyEditor.getEditor()), Balloon.Position.above);
102     Disposer.register(project, balloon);
103   }
104
105   private static void resetAnswerPlaceholders(TaskFile selectedTaskFile, Project project) {
106     final StudyTaskManager taskManager = StudyTaskManager.getInstance(project);
107     for (AnswerPlaceholder answerPlaceholder : selectedTaskFile.getAnswerPlaceholders()) {
108       answerPlaceholder.reset();
109       taskManager.setStatus(answerPlaceholder, StudyStatus.Unchecked);
110     }
111   }
112
113
114   private static boolean resetDocument(@NotNull final Document document,
115                                        @NotNull final TaskFile taskFile,
116                                        String fileName) {
117     final Document patternDocument = StudyUtils.getPatternDocument(taskFile, fileName);
118     if (patternDocument == null) {
119       return false;
120     }
121     StudyUtils.deleteGuardedBlocks(document);
122     taskFile.setTrackChanges(false);
123     clearDocument(document);
124     document.setText(patternDocument.getCharsSequence());
125     taskFile.setTrackChanges(true);
126     return true;
127   }
128
129   private static void clearDocument(@NotNull final Document document) {
130     final int lineCount = document.getLineCount();
131     if (lineCount != 0) {
132       CommandProcessor.getInstance().runUndoTransparentAction(() -> document.deleteString(0, document.getLineEndOffset(lineCount - 1)));
133     }
134   }
135
136   public void actionPerformed(@NotNull AnActionEvent event) {
137     final Project project = event.getProject();
138     if (project != null) {
139       for (StudyActionListener listener : Extensions.getExtensions(StudyActionListener.EP_NAME)) {
140         listener.beforeCheck(event);
141       }
142       refresh(project);
143     }
144   }
145
146   @Override
147   public void update(AnActionEvent event) {
148     StudyUtils.updateAction(event);
149     final Project project = event.getProject();
150     if (project != null) {
151       StudyEditor studyEditor = StudyUtils.getSelectedStudyEditor(project);
152       StudyState studyState = new StudyState(studyEditor);
153       Presentation presentation = event.getPresentation();
154       if (!studyState.isValid()) {
155         presentation.setEnabled(false);
156         return;
157       }
158
159       Course course = StudyTaskManager.getInstance(project).getCourse();
160       if (course == null) {
161         return;
162       }
163       if (!EduNames.STUDY.equals(course.getCourseMode())) {
164         presentation.setVisible(true);
165         presentation.setEnabled(false);
166       }
167     }
168   }
169
170   @NotNull
171   @Override
172   public String getActionId() {
173     return ACTION_ID;
174   }
175
176   @Nullable
177   @Override
178   public String[] getShortcuts() {
179     return new String[]{SHORTCUT};
180   }
181 }