f9b3f172cf655ac8e730a70a91e9194f32e9c6dd
[idea/community.git] / python / edu / src / com / jetbrains / python / edu / debugger / PyEduStackFrame.java
1 package com.jetbrains.python.edu.debugger;
2
3 import com.intellij.icons.AllIcons;
4 import com.intellij.openapi.project.Project;
5 import com.intellij.openapi.vfs.VirtualFile;
6 import com.intellij.ui.ColoredTextContainer;
7 import com.intellij.ui.SimpleTextAttributes;
8 import com.intellij.xdebugger.XSourcePosition;
9 import com.intellij.xdebugger.frame.XCompositeNode;
10 import com.intellij.xdebugger.frame.XValue;
11 import com.intellij.xdebugger.frame.XValueChildrenList;
12 import com.intellij.xdebugger.frame.XValueGroup;
13 import com.jetbrains.python.debugger.PyFrameAccessor;
14 import com.jetbrains.python.debugger.PyStackFrame;
15 import com.jetbrains.python.debugger.PyStackFrameInfo;
16 import org.jetbrains.annotations.NotNull;
17 import org.jetbrains.annotations.Nullable;
18
19 import javax.swing.*;
20 import java.util.HashMap;
21 import java.util.Map;
22
23 public class PyEduStackFrame extends PyStackFrame {
24   public static final String MODULE = "<module>";
25   public static final String GLOBAL_FRAME = "Globals";
26   public static final String DOUBLE_UNDERSCORE = "__";
27   public static final String BUILTINS_VALUE_NAME = "__builtins__";
28
29   private final PyStackFrameInfo myFrameInfo;
30   private final XSourcePosition myPosition;
31
32   public PyEduStackFrame(@NotNull Project project,
33                          @NotNull PyFrameAccessor debugProcess,
34                          @NotNull PyStackFrameInfo frameInfo,
35                          XSourcePosition position) {
36     super(project, debugProcess, frameInfo, position);
37     myFrameInfo = frameInfo;
38     myPosition = position;
39   }
40
41   @Override
42   public void customizePresentation(@NotNull ColoredTextContainer component) {
43     if (myPosition == null) {
44       component.append("<frame not available>", SimpleTextAttributes.GRAY_ATTRIBUTES);
45       return;
46     }
47     final VirtualFile file = myPosition.getFile();
48     String frameName = myFrameInfo.getName();
49     //TODO: get icons from designers
50     component.setIcon(MODULE.equals(frameName) ? AllIcons.FileTypes.Text : AllIcons.Nodes.Field);
51     if (MODULE.equals(frameName)) {
52       component.append(GLOBAL_FRAME, SimpleTextAttributes.REGULAR_ATTRIBUTES);
53       component.append(" (" + file.getName() + ")", getGrayAttributes(SimpleTextAttributes.REGULAR_ATTRIBUTES));
54     }
55     else {
56       component.append(frameName, SimpleTextAttributes.REGULAR_ATTRIBUTES);
57     }
58   }
59
60   @Override
61   protected void addChildren(@NotNull final XCompositeNode node,
62                              @Nullable final XValueChildrenList children) {
63     if (children == null) {
64       node.addChildren(XValueChildrenList.EMPTY, true);
65       return;
66     }
67     final Map<String, XValue> specialValues = new HashMap<String, XValue>();
68     XValueChildrenList filteredChildren = new XValueChildrenList();
69     for (int i = 0; i < children.size(); i++) {
70       String name = children.getName(i);
71       XValue value = children.getValue(i);
72       if (name.startsWith(DOUBLE_UNDERSCORE) && name.endsWith(DOUBLE_UNDERSCORE)) {
73         specialValues.put(name, value);
74         continue;
75       }
76       filteredChildren.add(name, value);
77     }
78     node.addChildren(filteredChildren, specialValues.isEmpty());
79     if (specialValues.isEmpty()) {
80       return;
81     }
82     addSpecialVars(node, specialValues);
83   }
84
85   private static void addSpecialVars(@NotNull XCompositeNode node, Map<String, XValue> specialValues) {
86       XValue builtins = specialValues.get(BUILTINS_VALUE_NAME);
87       if (builtins != null) {
88         specialValues.remove(BUILTINS_VALUE_NAME);
89         node.addChildren(XValueChildrenList.singleton("Builtins", builtins), false);
90       }
91       node.addChildren(XValueChildrenList.bottomGroup(createSpecialVarsGroup(specialValues)), true);
92   }
93
94   @NotNull
95   private static XValueGroup createSpecialVarsGroup(final Map<String, XValue> specialValues) {
96     return new XValueGroup("Special Variables") {
97       @Nullable
98       @Override
99       public Icon getIcon() {
100         //TODO: get icon from designers
101         return AllIcons.Nodes.Artifact;
102       }
103
104       @Override
105       public void computeChildren(@NotNull XCompositeNode node) {
106         XValueChildrenList list = new XValueChildrenList();
107         for (Map.Entry<String, XValue> entry : specialValues.entrySet()) {
108           list.add(entry.getKey(), entry.getValue());
109         }
110         node.addChildren(list, true);
111       }
112     };
113   }
114 }