2 * Copyright 2000-2015 JetBrains s.r.o.
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
16 package com.jetbrains.edu.learning.ui;
18 import com.intellij.openapi.Disposable;
19 import com.intellij.openapi.actionSystem.ActionManager;
20 import com.intellij.openapi.actionSystem.ActionToolbar;
21 import com.intellij.openapi.actionSystem.DataProvider;
22 import com.intellij.openapi.actionSystem.DefaultActionGroup;
23 import com.intellij.openapi.diagnostic.Logger;
24 import com.intellij.openapi.editor.colors.EditorColorsManager;
25 import com.intellij.openapi.editor.colors.EditorColorsScheme;
26 import com.intellij.openapi.fileEditor.FileEditorManager;
27 import com.intellij.openapi.fileEditor.FileEditorManagerEvent;
28 import com.intellij.openapi.fileEditor.FileEditorManagerListener;
29 import com.intellij.openapi.project.Project;
30 import com.intellij.openapi.ui.SimpleToolWindowPanel;
31 import com.intellij.openapi.util.io.FileUtil;
32 import com.intellij.openapi.vfs.VirtualFile;
33 import com.intellij.ui.BrowserHyperlinkListener;
34 import com.intellij.ui.components.JBScrollPane;
35 import com.intellij.util.ui.JBUI;
36 import com.intellij.util.ui.UIUtil;
37 import com.jetbrains.edu.EduNames;
38 import com.jetbrains.edu.courseFormat.Task;
39 import com.jetbrains.edu.courseFormat.TaskFile;
40 import com.jetbrains.edu.learning.StudyUtils;
41 import com.jetbrains.edu.learning.actions.*;
42 import com.jetbrains.edu.learning.editor.StudyEditor;
43 import org.jetbrains.annotations.NotNull;
44 import org.jetbrains.annotations.Nullable;
47 import javax.swing.border.EmptyBorder;
48 import javax.swing.text.html.HTMLDocument;
49 import javax.swing.text.html.HTMLEditorKit;
51 import java.io.IOException;
53 public class StudyToolWindow extends SimpleToolWindowPanel implements DataProvider, Disposable {
55 private static final String EMPTY_TASK_TEXT = "Please, open any task to see task description";
57 public StudyToolWindow(final Project project) {
59 JPanel toolbarPanel = createToolbarPanel();
60 setToolbar(toolbarPanel);
62 final StudyEditor studyEditor = StudyUtils.getSelectedStudyEditor(project);
63 final JTextPane taskTextPane = createTaskTextPane();
65 if (studyEditor == null) {
66 taskTextPane.setText(EMPTY_TASK_TEXT);
67 setContent(taskTextPane);
70 final Task task = studyEditor.getTaskFile().getTask();
73 final String taskText = task.getText();
74 JBScrollPane scrollPane = new JBScrollPane(taskTextPane);
75 taskTextPane.setText(taskText);
76 taskTextPane.addHyperlinkListener(BrowserHyperlinkListener.INSTANCE);
78 setContent(scrollPane);
80 final FileEditorManagerListener listener = new StudyFileEditorManagerListener(project, taskTextPane);
81 project.getMessageBus().connect().subscribe(FileEditorManagerListener.FILE_EDITOR_MANAGER, listener);
86 private JTextPane createTaskTextPane() {
87 final JTextPane taskTextPane = new JTextPane();
88 taskTextPane.setContentType(new HTMLEditorKit().getContentType());
89 final EditorColorsScheme editorColorsScheme = EditorColorsManager.getInstance().getGlobalScheme();
90 int fontSize = editorColorsScheme.getEditorFontSize();
91 final String fontName = editorColorsScheme.getEditorFontName();
92 final Font font = new Font(fontName, Font.PLAIN, fontSize);
93 String bodyRule = "body { font-family: " + font.getFamily() + "; " +
94 "font-size: " + font.getSize() + "pt; }";
95 ((HTMLDocument)taskTextPane.getDocument()).getStyleSheet().addRule(bodyRule);
96 taskTextPane.setEditable(false);
97 if (!UIUtil.isUnderDarcula()) {
98 taskTextPane.setBackground(EditorColorsManager.getInstance().getGlobalScheme().getDefaultBackground());
100 taskTextPane.setBorder(new EmptyBorder(15, 20, 0, 100));
104 public void dispose() {
107 private static JPanel createToolbarPanel() {
108 final DefaultActionGroup group = new DefaultActionGroup();
109 group.add(new StudyCheckAction());
110 group.add(new StudyPreviousStudyTaskAction());
111 group.add(new StudyNextStudyTaskAction());
112 group.add(new StudyRefreshTaskFileAction());
113 group.add(new StudyShowHintAction());
115 group.add(new StudyRunAction());
116 group.add(new StudyEditInputAction());
118 final ActionToolbar actionToolBar = ActionManager.getInstance().createActionToolbar("Study", group, true);
119 return JBUI.Panels.simplePanel(actionToolBar.getComponent());
122 static class StudyFileEditorManagerListener implements FileEditorManagerListener {
123 private static final Logger LOG = Logger.getInstance(StudyFileEditorManagerListener.class);
124 private Project myProject;
125 private JTextPane myTaskTextPane;
127 StudyFileEditorManagerListener(@NotNull final Project project, JTextPane taskTextPane) {
129 myTaskTextPane = taskTextPane;
133 public void fileOpened(@NotNull FileEditorManager source, @NotNull VirtualFile file) {
134 Task task = getTask(file);
135 setTaskText(task, file.getParent());
139 public void fileClosed(@NotNull FileEditorManager source, @NotNull VirtualFile file) {
140 myTaskTextPane.setText(EMPTY_TASK_TEXT);
144 public void selectionChanged(@NotNull FileEditorManagerEvent event) {
145 VirtualFile file = event.getNewFile();
147 Task task = getTask(file);
148 setTaskText(task, file);
153 private Task getTask(@NotNull VirtualFile file) {
154 TaskFile taskFile = StudyUtils.getTaskFile(myProject, file);
155 if (taskFile != null) {
156 return taskFile.getTask();
163 private void setTaskText(@Nullable final Task task, @Nullable final VirtualFile taskDirectory) {
165 myTaskTextPane.setText(EMPTY_TASK_TEXT);
168 String text = task.getText();
169 if (text == null && taskDirectory != null) {
170 VirtualFile taskTextFile = taskDirectory.findChild(EduNames.TASK_HTML);
171 if (taskTextFile != null) {
173 text = FileUtil.loadTextAndClose(taskTextFile.getInputStream());
175 catch (IOException e) {
180 myTaskTextPane.setText(text);