1 package com
.intellij
.ui
.tabs
.impl
;
3 import com
.intellij
.ide
.DataManager
;
4 import com
.intellij
.openapi
.actionSystem
.ActionGroup
;
5 import com
.intellij
.openapi
.actionSystem
.ActionPlaces
;
6 import com
.intellij
.openapi
.actionSystem
.DefaultActionGroup
;
7 import com
.intellij
.openapi
.util
.Pass
;
8 import com
.intellij
.ui
.LayeredIcon
;
9 import com
.intellij
.ui
.SimpleColoredComponent
;
10 import com
.intellij
.ui
.SimpleColoredText
;
11 import com
.intellij
.ui
.components
.panels
.Wrapper
;
12 import com
.intellij
.ui
.tabs
.TabInfo
;
13 import com
.intellij
.ui
.tabs
.UiDecorator
;
14 import com
.intellij
.util
.ui
.Centerizer
;
17 import javax
.swing
.border
.EmptyBorder
;
19 import java
.awt
.event
.MouseAdapter
;
20 import java
.awt
.event
.MouseEvent
;
22 public class TabLabel
extends JPanel
{
23 private SimpleColoredComponent myLabel
= new SimpleColoredComponent();
24 private LayeredIcon myIcon
;
25 private Icon myOverlayedIcon
;
27 private TabInfo myInfo
;
28 private ActionPanel myActionPanel
;
29 private boolean myCentered
;
31 private Wrapper myLabelPlaceholder
= new Wrapper();
32 private JBTabsImpl myTabs
;
34 public TabLabel(JBTabsImpl tabs
, final TabInfo info
) {
37 myLabel
.setOpaque(false);
38 myLabel
.setBorder(null);
39 myLabel
.setIconTextGap(new JLabel().getIconTextGap());
40 myLabel
.setIconOpaque(false);
41 myLabel
.setIpad(new Insets(0, 0, 0, 0));
43 setLayout(new BorderLayout());
46 myLabelPlaceholder
.setOpaque(false);
47 add(myLabelPlaceholder
, BorderLayout
.CENTER
);
49 setAligmentToCenter(true);
51 myIcon
= new LayeredIcon(2);
52 myLabel
.setIcon(myIcon
);
54 addMouseListener(new MouseAdapter() {
55 public void mousePressed(final MouseEvent e
) {
56 if (myTabs
.isSelectionClick(e
, false)) {
57 myTabs
.select(info
, true);
64 public void mouseClicked(final MouseEvent e
) {
68 public void mouseReleased(final MouseEvent e
) {
74 public void setAligmentToCenter(boolean toCenter
) {
75 if (myCentered
== toCenter
&& myLabel
.getParent() != null) return;
77 myLabelPlaceholder
.removeAll();
80 final Centerizer center
= new Centerizer(myLabel
);
81 myLabelPlaceholder
.setContent(center
);
83 myLabelPlaceholder
.setContent(myLabel
);
86 myCentered
= toCenter
;
89 public void paint(final Graphics g
) {
90 if (myTabs
.getSelectedInfo() != myInfo
) {
98 if (myTabs
.getSelectedInfo() != myInfo
) {
105 private void handlePopup(final MouseEvent e
) {
106 if (e
.getClickCount() != 1 || !e
.isPopupTrigger()) return;
108 if (e
.getX() < 0 || e
.getX() >= e
.getComponent().getWidth() || e
.getY() < 0 || e
.getY() >= e
.getComponent().getHeight()) return;
110 String place
= myTabs
.getPopupPlace();
111 place
= place
!= null ? place
: ActionPlaces
.UNKNOWN
;
112 myTabs
.myPopupInfo
= myInfo
;
114 final DefaultActionGroup toShow
= new DefaultActionGroup();
115 if (myTabs
.getPopupGroup() != null) {
116 toShow
.addAll(myTabs
.getPopupGroup());
117 toShow
.addSeparator();
121 DataManager
.getInstance().getDataContext(e
.getComponent(), e
.getX(), e
.getY()).getData(JBTabsImpl
.NAVIGATION_ACTIONS_KEY
.getName());
122 if (tabs
== myTabs
&& myTabs
.myAddNavigationGroup
) {
123 toShow
.addAll(myTabs
.myNavigationActions
);
126 if (toShow
.getChildrenCount() == 0) return;
128 myTabs
.myActivePopup
= myTabs
.myActionManager
.createActionPopupMenu(place
, toShow
).getComponent();
129 myTabs
.myActivePopup
.addPopupMenuListener(myTabs
.myPopupListener
);
131 myTabs
.myActivePopup
.addPopupMenuListener(myTabs
);
132 myTabs
.myActivePopup
.show(e
.getComponent(), e
.getX(), e
.getY());
133 myTabs
.onPopup(myTabs
.myPopupInfo
);
137 public void setText(final SimpleColoredText text
) {
140 text
.appendToComponent(myLabel
);
142 invalidateIfNeeded();
145 private void clear(final boolean invalidate
) {
147 myLabel
.setIcon(myIcon
);
150 invalidateIfNeeded();
154 private void invalidateIfNeeded() {
155 if (myLabel
.getSize() != null && myLabel
.getSize().equals(myLabel
.getPreferredSize())) return;
156 myLabel
.getParent().invalidate();
158 myTabs
.revalidateAndRepaint(false);
161 public void setIcon(final Icon icon
) {
162 getLayeredIcon().setIcon(icon
, 0);
163 invalidateIfNeeded();
166 private LayeredIcon
getLayeredIcon() {
170 public void setAttraction(boolean enabled
) {
171 getLayeredIcon().setLayerEnabled(1, enabled
);
174 public boolean isAttractionEnabled() {
175 return getLayeredIcon().isLayerEnabled(1);
178 public TabInfo
getInfo() {
182 public void apply(UiDecorator
.UiDecoration decoration
) {
183 if (decoration
.getLabelFont() != null) {
184 setFont(decoration
.getLabelFont());
187 Insets insets
= decoration
.getLabelInsets();
188 if (insets
!= null) {
189 Insets current
= JBTabsImpl
.ourDefaultDecorator
.getDecoration().getLabelInsets();
190 setBorder(new EmptyBorder(getValue(current
.top
, insets
.top
), getValue(current
.left
, insets
.left
),
191 getValue(current
.bottom
, insets
.bottom
), getValue(current
.right
, insets
.right
)));
195 private int getValue(int curentValue
, int newValue
) {
196 return newValue
!= -1 ? newValue
: curentValue
;
199 public void setTabActions(ActionGroup group
) {
200 removeOldActionPanel();
202 if (group
== null) return;
204 myActionPanel
= new ActionPanel(myTabs
, myInfo
, new Pass
<MouseEvent
>() {
205 public void pass(final MouseEvent event
) {
206 final MouseEvent me
= SwingUtilities
.convertMouseEvent(event
.getComponent(), event
, TabLabel
.this);
207 processMouseEvent(me
);
211 toggleShowActions(false);
213 add(myActionPanel
, BorderLayout
.EAST
);
215 myTabs
.revalidateAndRepaint(false);
219 protected void processMouseEvent(final MouseEvent e
) {
220 super.processMouseEvent(e
);
223 private void removeOldActionPanel() {
224 if (myActionPanel
!= null) {
225 myActionPanel
.getParent().remove(myActionPanel
);
226 myActionPanel
= null;
230 public boolean updateTabActions() {
231 return myActionPanel
!= null && myActionPanel
.update();
235 private void setAttractionIcon(Icon icon
) {
236 if (myIcon
.getIcon(0) == null) {
237 getLayeredIcon().setIcon(null, 1);
238 myOverlayedIcon
= icon
;
240 getLayeredIcon().setIcon(icon
, 1);
241 myOverlayedIcon
= null;
245 public boolean repaintAttraction() {
246 if (!myTabs
.myAttractions
.contains(myInfo
)) {
247 if (getLayeredIcon().isLayerEnabled(1)) {
248 getLayeredIcon().setLayerEnabled(1, false);
249 setAttractionIcon(null);
250 invalidateIfNeeded();
256 boolean needsUpdate
= false;
258 if (getLayeredIcon().getIcon(1) != myInfo
.getAlertIcon()) {
259 setAttractionIcon(myInfo
.getAlertIcon());
263 int maxInitialBlinkCount
= 5;
264 int maxRefireBlinkCount
= maxInitialBlinkCount
+ 2;
265 if (myInfo
.getBlinkCount() < maxInitialBlinkCount
&& myInfo
.isAlertRequested()) {
266 getLayeredIcon().setLayerEnabled(1, !getLayeredIcon().isLayerEnabled(1));
267 if (myInfo
.getBlinkCount() == 0) {
270 myInfo
.setBlinkCount(myInfo
.getBlinkCount() + 1);
272 if (myInfo
.getBlinkCount() == maxInitialBlinkCount
) {
273 myInfo
.resetAlertRequest();
279 if (myInfo
.getBlinkCount() < maxRefireBlinkCount
&& myInfo
.isAlertRequested()) {
280 getLayeredIcon().setLayerEnabled(1, !getLayeredIcon().isLayerEnabled(1));
281 myInfo
.setBlinkCount(myInfo
.getBlinkCount() + 1);
283 if (myInfo
.getBlinkCount() == maxRefireBlinkCount
) {
284 myInfo
.setBlinkCount(maxInitialBlinkCount
);
285 myInfo
.resetAlertRequest();
291 needsUpdate
= !getLayeredIcon().isLayerEnabled(1);
292 getLayeredIcon().setLayerEnabled(1, true);
296 invalidateIfNeeded();
301 protected void paintChildren(final Graphics g
) {
302 super.paintChildren(g
);
304 if (myOverlayedIcon
== null || myLabel
.getParent() == null) return;
306 final Rectangle textBounds
= SwingUtilities
.convertRectangle(myLabel
.getParent(), myLabel
.getBounds(), this);
307 if (getLayeredIcon().isLayerEnabled(1)) {
309 final int top
= (getSize().height
- myOverlayedIcon
.getIconHeight()) / 2;
311 myOverlayedIcon
.paintIcon(this, g
, textBounds
.x
- myOverlayedIcon
.getIconWidth() / 2, top
);
316 public void setTabActionsAutoHide(final boolean autoHide
) {
317 if (myActionPanel
== null || myActionPanel
.isAutoHide() == autoHide
) {
321 myActionPanel
.setAutoHide(autoHide
);
324 public void toggleShowActions(boolean show
) {
325 if (myActionPanel
!= null) {
326 myActionPanel
.toggleShowActtions(show
);