Skip to content

Commit

Permalink
[Feat] Optimize UI (#3)
Browse files Browse the repository at this point in the history
- Disable closing `support window`
- Layout setting according to the position of the toolWindow
- Embed console view on `Result Area`
- Refactoring for Clean Code and Object-oriented Coding

Signed-off-by: Hyeon-Uk <[email protected]>
  • Loading branch information
Hyeon-Uk committed Jan 14, 2024
1 parent b8a7e0c commit 7eb966b
Show file tree
Hide file tree
Showing 15 changed files with 240 additions and 82 deletions.
2 changes: 1 addition & 1 deletion build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ intellij {
version.set("2022.2.5")
type.set("IC") // Target IDE Platform

plugins.set(listOf("com.intellij.java"))
plugins.set(listOf("com.intellij.java","org.jetbrains.plugins.terminal"))
}

dependencies{
Expand Down
57 changes: 26 additions & 31 deletions src/main/java/com/example/pssupporter/MyToolWindowFactory.java
Original file line number Diff line number Diff line change
Expand Up @@ -4,58 +4,53 @@

package com.example.pssupporter;

import com.example.pssupporter.ui.MyTestListPanel;
import com.example.pssupporter.ui.MyToolbarPanel;
import com.example.pssupporter.utils.ComponentManager;
import com.intellij.openapi.actionSystem.ActionGroup;
import com.intellij.openapi.actionSystem.ActionManager;
import com.example.pssupporter.ui.MyMainView;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.wm.ToolWindow;
import com.intellij.openapi.wm.ToolWindowAnchor;
import com.intellij.openapi.wm.ToolWindowFactory;
import com.intellij.ui.components.JBPanel;
import com.intellij.ui.components.JBScrollPane;
import com.intellij.openapi.wm.ToolWindowManager;
import com.intellij.openapi.wm.ex.ToolWindowManagerListener;
import com.intellij.ui.content.Content;
import com.intellij.ui.content.ContentFactory;
import com.intellij.ui.content.ContentManager;
import com.intellij.util.messages.MessageBusConnection;
import org.jetbrains.annotations.NotNull;

import javax.swing.*;
import java.awt.*;

public class MyToolWindowFactory implements ToolWindowFactory {
private ActionGroup getActionGroup(String actionGroupId) {
ActionManager actionManager = ActionManager.getInstance();
return (ActionGroup) actionManager.getAction(actionGroupId);
}
private MyMainView myMainView;

@Override
public void createToolWindowContent(@NotNull Project project, @NotNull ToolWindow toolWindow) {
ApplicationManager.getApplication().invokeLater(() -> {
ContentManager contentManager = toolWindow.getContentManager();
ContentFactory contentFactory = ContentFactory.getInstance();

JBPanel myMainView = new JBPanel(new BorderLayout());

JBScrollPane scrollPane = new JBScrollPane(MyTestListPanel.getInstance());

scrollPane.setHorizontalScrollBarPolicy(ScrollPaneConstants.HORIZONTAL_SCROLLBAR_AS_NEEDED);
scrollPane.setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED);

JBPanel myEditorPanel = new JBPanel(new GridLayout(1, 1));
ActionGroup myActionGroup = getActionGroup("myActionGroup");
MyToolbarPanel myToolbarPanel = new MyToolbarPanel(myActionGroup, myMainView);

myMainView.add(myToolbarPanel, BorderLayout.NORTH);
myMainView.add(scrollPane, BorderLayout.WEST);
myMainView.add(myEditorPanel, BorderLayout.CENTER);

ComponentManager.getInstance().addComponent("myTestListPanel", MyTestListPanel.getInstance());
ComponentManager.getInstance().addComponent("myEditorPanel", myEditorPanel);
myMainView = new MyMainView(project, toolWindow.getAnchor().isHorizontal());

Content content = contentFactory.createContent(myMainView, "Supporter", false);

contentManager.addContent(content);
setupToolWindowEventListener(project);
});
}

private void setupToolWindowEventListener(@NotNull Project project) {
MessageBusConnection connect = project.getMessageBus().connect();
connect.subscribe(ToolWindowManagerListener.TOPIC, new ToolWindowManagerListener() {
@Override
public void stateChanged(@NotNull ToolWindowManager toolWindowManager, @NotNull ToolWindowManagerEventType changeType) {
ToolWindowManagerListener.super.stateChanged(toolWindowManager, changeType);
if (ToolWindowManagerEventType.SetSideToolAndAnchor.equals(changeType)) {
ToolWindow baekjoonSupporter = toolWindowManager.getToolWindow("BaekjoonSupporter");

if (baekjoonSupporter.getAnchor() != null) {
ToolWindowAnchor anchor = baekjoonSupporter.getAnchor();
myMainView.setLayoutBasedOnOrientation(anchor.isHorizontal());
}
}
}
});
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
package com.example.pssupporter.actions;

import com.example.pssupporter.ui.MyTestListPanel;
import com.example.pssupporter.utils.ComponentManager;
import com.example.pssupporter.utils.thread.GlobalThreadStore;
import com.example.pssupporter.utils.thread.vo.ThreadGroupName;
import com.intellij.openapi.actionSystem.AnAction;
Expand All @@ -22,7 +23,7 @@ public void update(@NotNull AnActionEvent e) {

@Override
public void actionPerformed(@NotNull AnActionEvent e) {
MyTestListPanel myTestListPanel = MyTestListPanel.getInstance();
MyTestListPanel myTestListPanel = ComponentManager.getInstance().getComponent("myTestListPanel", MyTestListPanel.class);
myTestListPanel.addTest();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ public void update(@NotNull AnActionEvent e) {

@Override
public void actionPerformed(@NotNull AnActionEvent e) {
MyTestListPanel myTestListPanel = ComponentManager.getInstance().getComponent("myTestListPanel", MyTestListPanel.class);
String selected = Messages.showInputDialog(e.getProject(), "Input Baekjoon number", "Load Test Data", null);
if (!StringUtils.isBlank(selected)) {
ComponentManager.getInstance().removeChildrenComponentsByName("myEditorPanel");
Expand All @@ -38,10 +39,10 @@ public void actionPerformed(@NotNull AnActionEvent e) {
long number = Long.parseLong(selected);
List<TestData> examples = CrawlerProvider.getCrawler(Site.BAEKJOON_OJ).getExamples(number);

MyTestListPanel.getInstance().removeAllTests();
myTestListPanel.removeAllTests();

for (TestData testData : examples) {
MyTestListPanel.getInstance().addTest(testData);
myTestListPanel.addTest(testData);
}

} catch (NumberFormatException ne) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,13 +23,13 @@ public void update(@NotNull AnActionEvent e) {

@Override
public void actionPerformed(@NotNull AnActionEvent e) {
MyTestListPanel instance = MyTestListPanel.getInstance();
int selectedIndex = instance.getSelectedIndex();
MyTestListPanel myTestListPanel = ComponentManager.getInstance().getComponent("myTestListPanel", MyTestListPanel.class);
int selectedIndex = myTestListPanel.getSelectedIndex();
if (selectedIndex != -1) {
ComponentManager.getInstance().removeChildrenComponentsByName("myEditorPanel");

instance.removeTest(selectedIndex);
instance.repaint();
myTestListPanel.removeTest(selectedIndex);
myTestListPanel.repaint();
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -30,16 +30,17 @@ public void update(@NotNull AnActionEvent e) {
boolean isRunning = GlobalThreadStore.getInstance()
.hasRunningThreads(ThreadGroupName.TEST_RUNNING);
e.getPresentation().setEnabled(!isRunning);

MyTestListPanel.getInstance().setEnabled(!isRunning);
MyTestListPanel myTestListPanel = ComponentManager.getInstance().getComponent("myTestListPanel", MyTestListPanel.class);
myTestListPanel.setEnabled(!isRunning);
}

@Override
public void actionPerformed(@NotNull AnActionEvent e) {
ComponentManager.getInstance().removeChildrenComponentsByName("myEditorPanel");
MyTestListPanel.getInstance().clearSelection();
MyTestListPanel myTestListPanel = ComponentManager.getInstance().getComponent("myTestListPanel", MyTestListPanel.class);
myTestListPanel.clearSelection();

List<MyTestListItem> myTestListItems = MyTestListPanel.getInstance().getMyTestListItems();
List<MyTestListItem> myTestListItems = myTestListPanel.getMyTestListItems();
IntellijUtils.getSelectedFile(Objects.requireNonNull(e.getProject()))
.ifPresentOrElse(selectedFile -> {
IntellijUtils.autoSaveFile(selectedFile);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -30,19 +30,21 @@ public void update(@NotNull AnActionEvent e) {
.hasRunningThreads(ThreadGroupName.TEST_RUNNING);
e.getPresentation().setEnabled(!isRunning);

MyTestListPanel.getInstance().setEnabled(!isRunning);
MyTestListPanel myTestListPanel = ComponentManager.getInstance().getComponent("myTestListPanel", MyTestListPanel.class);
myTestListPanel.setEnabled(!isRunning);
}

@Override
public void actionPerformed(@NotNull AnActionEvent e) {
int selectedIndex = MyTestListPanel.getInstance().getSelectedIndex();
MyTestListPanel myTestListPanel = ComponentManager.getInstance().getComponent("myTestListPanel", MyTestListPanel.class);
int selectedIndex = myTestListPanel.getSelectedIndex();
if (selectedIndex == -1) {
return;
}
ComponentManager.getInstance().removeChildrenComponentsByName("myEditorPanel");
MyTestListPanel.getInstance().clearSelection();
myTestListPanel.clearSelection();

MyTestListItem selectedItem = MyTestListPanel.getInstance().getMyTestListItem(selectedIndex);
MyTestListItem selectedItem = myTestListPanel.getMyTestListItem(selectedIndex);
IntellijUtils.getSelectedFile(Objects.requireNonNull(e.getProject()))
.ifPresentOrElse(selectedFile -> {
IntellijUtils.autoSaveFile(selectedFile);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
package com.example.pssupporter.actions;

import com.example.pssupporter.ui.MyTestListPanel;
import com.example.pssupporter.utils.ComponentManager;
import com.example.pssupporter.utils.thread.GlobalThreadStore;
import com.example.pssupporter.utils.thread.vo.ThreadGroupName;
import com.intellij.openapi.actionSystem.AnAction;
Expand All @@ -19,7 +20,8 @@ public void update(@NotNull AnActionEvent e) {
.hasRunningThreads(ThreadGroupName.TEST_RUNNING);
e.getPresentation().setEnabled(isRunning);

MyTestListPanel.getInstance().setEnabled(!isRunning);
MyTestListPanel myTestListPanel = ComponentManager.getInstance().getComponent("myTestListPanel", MyTestListPanel.class);
myTestListPanel.setEnabled(!isRunning);
}

@Override
Expand Down
50 changes: 33 additions & 17 deletions src/main/java/com/example/pssupporter/ui/MyEditorPanel.java
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,10 @@


import com.example.pssupporter.vo.TestData;
import com.intellij.execution.filters.TextConsoleBuilderFactory;
import com.intellij.execution.ui.ConsoleView;
import com.intellij.execution.ui.ConsoleViewContentType;
import com.intellij.openapi.project.Project;
import com.intellij.ui.JBColor;
import com.intellij.ui.components.JBPanel;
import com.intellij.ui.components.JBScrollPane;
Expand All @@ -18,60 +22,72 @@ public class MyEditorPanel extends JBPanel {

private final JBTextArea myInputTextArea;
private final JBTextArea myOutputTextArea;
private final JBTextArea myLogTextArea;
private final ConsoleView myLogConsoleView;
private final Project project;
private final TestData myTestData;

public MyEditorPanel() {
this(new TestData());
public MyEditorPanel(Project project) {
this(project, new TestData());
}

public MyEditorPanel(TestData myTestData) {
public MyEditorPanel(Project project, TestData myTestData) {
this.myTestData = myTestData;
this.setName("MyLogPanel");
this.setLayout(new GridLayout(3, 1));
this.setLayout(new BorderLayout());
this.setBorder(BorderFactory.createLineBorder(JBColor.DARK_GRAY));
this.project = project;

myInputTextArea = new JBTextArea(10, 10);
JBPanel inputOutputPanel = new JBPanel(new GridLayout(1, 2));

myInputTextArea = new JBTextArea();
myInputTextArea.setText(myTestData.getInput());

JBScrollPane myInputTextScrollPane = new JBScrollPane(myInputTextArea);
myInputTextScrollPane.setBorder(BorderFactory.createTitledBorder(BorderFactory.createLineBorder(JBColor.DARK_GRAY), "Input"));
myInputTextScrollPane.setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED);
myInputTextScrollPane.setHorizontalScrollBarPolicy(ScrollPaneConstants.HORIZONTAL_SCROLLBAR_AS_NEEDED);

myOutputTextArea = new JBTextArea(10, 10);
myOutputTextArea = new JBTextArea();
myOutputTextArea.setText(myTestData.getOutput());

JBScrollPane myOutputTextScrollPane = new JBScrollPane(myOutputTextArea);
myOutputTextScrollPane.setBorder(BorderFactory.createTitledBorder(BorderFactory.createLineBorder(JBColor.DARK_GRAY), "Output"));
myOutputTextScrollPane.setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED);
myOutputTextScrollPane.setHorizontalScrollBarPolicy(ScrollPaneConstants.HORIZONTAL_SCROLLBAR_AS_NEEDED);

myLogTextArea = new JBTextArea();
myLogTextArea.setEditable(false);
myLogTextArea.setDragEnabled(true);
myLogConsoleView = createConsoleView();

setBorder(BorderFactory.createLineBorder(JBColor.LIGHT_GRAY));
JBScrollPane myLogScrollPane = new JBScrollPane(myLogTextArea);
JBScrollPane myLogScrollPane = new JBScrollPane(myLogConsoleView.getComponent());
myLogScrollPane.setBorder(BorderFactory.createTitledBorder(BorderFactory.createLineBorder(JBColor.DARK_GRAY), "Result"));
myLogScrollPane.setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED);
myLogScrollPane.setHorizontalScrollBarPolicy(ScrollPaneConstants.HORIZONTAL_SCROLLBAR_AS_NEEDED);

this.add(myInputTextScrollPane);
this.add(myOutputTextScrollPane);
this.add(myLogScrollPane);
inputOutputPanel.add(myInputTextScrollPane);
inputOutputPanel.add(myOutputTextScrollPane);

this.add(inputOutputPanel, BorderLayout.NORTH);
this.add(myLogScrollPane, BorderLayout.SOUTH);

// JSplitPane
JSplitPane splitPane = new JSplitPane(JSplitPane.VERTICAL_SPLIT, inputOutputPanel, myLogScrollPane);
splitPane.setDividerSize(1);
splitPane.setResizeWeight(0.3);
add(splitPane, BorderLayout.CENTER);
}

public TestData getTestData() {
myTestData.setInput(myInputTextArea.getText());
myTestData.setOutput(myOutputTextArea.getText());
myTestData.setResult(myLogTextArea.getText());
return myTestData;
}

public void setResult(String result) {
myTestData.setResult(result);
myLogTextArea.setText(result);
myLogConsoleView.clear();
myLogConsoleView.print(result, ConsoleViewContentType.SYSTEM_OUTPUT);
}

private ConsoleView createConsoleView() {
return TextConsoleBuilderFactory.getInstance().createBuilder(project).getConsole();
}
}
Loading

0 comments on commit 7eb966b

Please sign in to comment.