This Bugzilla instance is a read-only archive of historic NetBeans bug reports. To report a bug in NetBeans please follow the project's instructions for reporting issues.

View | Details | Raw Unified | Return to bug 208026
Collapse All | Expand All

(-)a/core.windows/manifest.mf (-1 / +1 lines)
Lines 6-10 Link Here
6
OpenIDE-Module-Recommends: org.netbeans.core.windows.nativeaccess.NativeWindowSystem
6
OpenIDE-Module-Recommends: org.netbeans.core.windows.nativeaccess.NativeWindowSystem
7
AutoUpdate-Show-In-Client: false
7
AutoUpdate-Show-In-Client: false
8
AutoUpdate-Essential-Module: true
8
AutoUpdate-Essential-Module: true
9
OpenIDE-Module-Specification-Version: 2.44
9
OpenIDE-Module-Specification-Version: 2.45
10
10
(-)a/core.windows/nbproject/project.xml (-1 / +1 lines)
Lines 85-91 Link Here
85
                    <build-prerequisite/>
85
                    <build-prerequisite/>
86
                    <compile-dependency/>
86
                    <compile-dependency/>
87
                    <run-dependency>
87
                    <run-dependency>
88
                        <specification-version>1.33</specification-version>
88
                        <specification-version>1.34</specification-version>
89
                    </run-dependency>
89
                    </run-dependency>
90
                </dependency>
90
                </dependency>
91
                <dependency>
91
                <dependency>
(-)a/core.windows/src/org/netbeans/core/windows/Central.java (+13 lines)
Lines 1664-1669 Link Here
1664
                mode, View.CHANGE_TOPCOMPONENT_ICON_CHANGED, null, tc));
1664
                mode, View.CHANGE_TOPCOMPONENT_ICON_CHANGED, null, tc));
1665
        }
1665
        }
1666
    }
1666
    }
1667
1668
    /**
1669
     * 
1670
     * @param mode
1671
     * @param tc
1672
     * @param busy 
1673
     * @since 2.45
1674
     */
1675
    public void topComponentMakeBusy( ModeImpl mode, TopComponent tc, boolean busy ) {
1676
        String modeName = getModeName(mode);
1677
        viewRequestor.scheduleRequest (
1678
            new ViewRequest(modeName, busy ? View.TOPCOMPONENT_SHOW_BUSY : View.TOPCOMPONENT_HIDE_BUSY, tc, tc));
1679
    }
1667
    
1680
    
1668
    public void resetModel() {
1681
    public void resetModel() {
1669
        model.reset();
1682
        model.reset();
(-)a/core.windows/src/org/netbeans/core/windows/WindowManagerImpl.java (+25 lines)
Lines 1919-1924 Link Here
1919
    public void userStartedKeyboardDragAndDrop( TopComponentDraggable draggable ) {
1919
    public void userStartedKeyboardDragAndDrop( TopComponentDraggable draggable ) {
1920
        central.userStartedKeyboardDragAndDrop( draggable );
1920
        central.userStartedKeyboardDragAndDrop( draggable );
1921
    }
1921
    }
1922
1923
    private static final Object BUSY_FLAG = new Object();
1924
    private static final String BUSY_PROP_NAME = "nbwinsys.tc.isbusy"; //NOI18N
1925
1926
    @Override
1927
    protected void topComponentMakeBusy( TopComponent tc, boolean busy ) {
1928
        boolean wasBusy = isTopComponentBusy( tc );
1929
        tc.putClientProperty( BUSY_PROP_NAME, busy ? BUSY_FLAG : null );
1930
        if( busy != wasBusy ) {
1931
            //update winsys
1932
            ModeImpl mode = (ModeImpl) findMode(tc);
1933
            if( null != mode )
1934
                central.topComponentMakeBusy(mode, tc, busy);
1935
        }
1936
    }
1937
1938
    /**
1939
     * Check if the given TopComponent is 'busy'
1940
     * @param tc
1941
     * @return
1942
     * @since 2.45
1943
     */
1944
    public boolean isTopComponentBusy( TopComponent tc ) {
1945
        return tc.getClientProperty( BUSY_PROP_NAME ) == BUSY_FLAG;
1946
    }
1922
    
1947
    
1923
    void fireEvent( WindowSystemEventType type ) {
1948
    void fireEvent( WindowSystemEventType type ) {
1924
        assertEventDispatchThread();
1949
        assertEventDispatchThread();
(-)a/core.windows/src/org/netbeans/core/windows/view/DefaultView.java (+18 lines)
Lines 482-487 Link Here
482
                    Logger.getLogger(DefaultView.class.getName()).fine(
482
                    Logger.getLogger(DefaultView.class.getName()).fine(
483
                        "Could not find mode " + viewEvent.getSource());
483
                        "Could not find mode " + viewEvent.getSource());
484
                }
484
                }
485
            } else if (changeType == View.TOPCOMPONENT_SHOW_BUSY || changeType == View.TOPCOMPONENT_HIDE_BUSY ) {
486
                if (DEBUG) {
487
                    debugLog("Top component show/hide busy"); //NOI18N
488
                }
489
                ModeView modeView = hierarchy.getModeViewForAccessor(wsa.findModeAccessor((String)viewEvent.getSource())); // XXX
490
                if (modeView != null) {
491
                    TopComponent tc = (TopComponent) viewEvent.getNewValue();
492
                    if (tc == null) {
493
                        throw new NullPointerException ("Top component is null for make busy request"); //NOI18N
494
                    }
495
                    //make sure the TC is still opened in the given mode container
496
                    if( modeView.getTopComponents().contains( tc ) ) {
497
                        modeView.makeBusy(tc, changeType == View.TOPCOMPONENT_SHOW_BUSY);
498
                    }
499
                } else {
500
                    Logger.getLogger(DefaultView.class.getName()).fine(
501
                        "Could not find mode " + viewEvent.getSource());
502
                }
485
            } else if (changeType == View.CHANGE_MAXIMIZE_TOPCOMPONENT_SLIDE_IN) {
503
            } else if (changeType == View.CHANGE_MAXIMIZE_TOPCOMPONENT_SLIDE_IN) {
486
                if (DEBUG) {
504
                if (DEBUG) {
487
                    debugLog("Slided-in top component toggle maximize"); //NOI18N
505
                    debugLog("Slided-in top component toggle maximize"); //NOI18N
(-)a/core.windows/src/org/netbeans/core/windows/view/ModeContainer.java (+2 lines)
Lines 89-93 Link Here
89
    public void requestAttention(TopComponent tc);
89
    public void requestAttention(TopComponent tc);
90
90
91
    public void cancelRequestAttention(TopComponent tc);
91
    public void cancelRequestAttention(TopComponent tc);
92
93
    public void makeBusy(TopComponent tc, boolean busy);
92
}
94
}
93
95
(-)a/core.windows/src/org/netbeans/core/windows/view/ModeView.java (+4 lines)
Lines 188-193 Link Here
188
        container.cancelRequestAttention(tc);
188
        container.cancelRequestAttention(tc);
189
    }
189
    }
190
190
191
    public void makeBusy(TopComponent tc, boolean busy) {
192
        container.makeBusy(tc, busy);
193
    }
194
191
    // XXX
195
    // XXX
192
    public void updateFrameState() {
196
    public void updateFrameState() {
193
        Component comp = container.getComponent();
197
        Component comp = container.getComponent();
(-)a/core.windows/src/org/netbeans/core/windows/view/View.java (+4 lines)
Lines 108-113 Link Here
108
    public int TOPCOMPONENT_REQUEST_ATTENTION = 63;
108
    public int TOPCOMPONENT_REQUEST_ATTENTION = 63;
109
    public int TOPCOMPONENT_CANCEL_REQUEST_ATTENTION = 64;
109
    public int TOPCOMPONENT_CANCEL_REQUEST_ATTENTION = 64;
110
    public int CHANGE_MAXIMIZE_TOPCOMPONENT_SLIDE_IN = 65;
110
    public int CHANGE_MAXIMIZE_TOPCOMPONENT_SLIDE_IN = 65;
111
112
    //toggle TopComponent busy
113
    public int TOPCOMPONENT_SHOW_BUSY = 70;
114
    public int TOPCOMPONENT_HIDE_BUSY = 71;
111
    
115
    
112
    /** Provides GUI changes to manifest model changes to user. */
116
    /** Provides GUI changes to manifest model changes to user. */
113
    public void changeGUI(ViewEvent[] viewEvents, WindowSystemSnapshot snapshot);
117
    public void changeGUI(ViewEvent[] viewEvents, WindowSystemSnapshot snapshot);
(-)a/core.windows/src/org/netbeans/core/windows/view/ViewEvent.java (+2 lines)
Lines 129-134 Link Here
129
            case View.CHANGE_VISIBILITY_CHANGED : typeStr = "CHANGE_VISIBILITY_CHANGED"; break; //NOI18N
129
            case View.CHANGE_VISIBILITY_CHANGED : typeStr = "CHANGE_VISIBILITY_CHANGED"; break; //NOI18N
130
            case View.TOPCOMPONENT_REQUEST_ATTENTION : typeStr = "TOPCOMPONENT_REQUEST_ATTENTION"; break; //NOI18N
130
            case View.TOPCOMPONENT_REQUEST_ATTENTION : typeStr = "TOPCOMPONENT_REQUEST_ATTENTION"; break; //NOI18N
131
            case View.TOPCOMPONENT_CANCEL_REQUEST_ATTENTION : typeStr = "TOPCOMPONENT_CANCEL_REQUEST_ATTENTION"; break; //NOI18N
131
            case View.TOPCOMPONENT_CANCEL_REQUEST_ATTENTION : typeStr = "TOPCOMPONENT_CANCEL_REQUEST_ATTENTION"; break; //NOI18N
132
            case View.TOPCOMPONENT_SHOW_BUSY : typeStr = "TOPCOMPONENT_SHOW_BUSY"; break; //NOI18N
133
            case View.TOPCOMPONENT_HIDE_BUSY : typeStr = "TOPCOMPONENT_HIDE_BUSY"; break; //NOI18N
132
        }
134
        }
133
        buf.append(typeStr);
135
        buf.append(typeStr);
134
        buf.append("\nnewValue="); //NOI18N
136
        buf.append("\nnewValue="); //NOI18N
(-)a/core.windows/src/org/netbeans/core/windows/view/ui/DefaultSeparateContainer.java (+5 lines)
Lines 114-119 Link Here
114
        //not implemented
114
        //not implemented
115
    }
115
    }
116
116
117
    @Override
118
    public void makeBusy(TopComponent tc, boolean busy) {
119
        tabbedHandler.makeBusy( tc, busy );
120
    }
121
117
    /** */
122
    /** */
118
    @Override
123
    @Override
119
    protected Component getModeComponent() {
124
    protected Component getModeComponent() {
(-)a/core.windows/src/org/netbeans/core/windows/view/ui/DefaultSplitContainer.java (+5 lines)
Lines 95-100 Link Here
95
        tabbedHandler.cancelRequestAttention(tc);
95
        tabbedHandler.cancelRequestAttention(tc);
96
    }
96
    }
97
97
98
    @Override
99
    public void makeBusy(TopComponent tc, boolean busy) {
100
        tabbedHandler.makeBusy( tc, busy );
101
    }
102
98
    /** */
103
    /** */
99
    protected Component getModeComponent() {
104
    protected Component getModeComponent() {
100
        return panel;
105
        return panel;
(-)a/core.windows/src/org/netbeans/core/windows/view/ui/TabbedHandler.java (+4 lines)
Lines 143-148 Link Here
143
    public void cancelRequestAttention (TopComponent tc) {
143
    public void cancelRequestAttention (TopComponent tc) {
144
        tabbed.cancelRequestAttention(tc);
144
        tabbed.cancelRequestAttention(tc);
145
    }
145
    }
146
147
    public void makeBusy( TopComponent tc, boolean busy ) {
148
        tabbed.makeBusy( tc, busy );
149
    }
146
    
150
    
147
    public Component getComponent() {
151
    public Component getComponent() {
148
        return tabbed.getComponent();
152
        return tabbed.getComponent();
(-)a/core.windows/src/org/netbeans/core/windows/view/ui/slides/SlideBar.java (-1 / +28 lines)
Lines 65-70 Link Here
65
import org.netbeans.swing.tabcontrol.event.ComplexListDataEvent;
65
import org.netbeans.swing.tabcontrol.event.ComplexListDataEvent;
66
import org.netbeans.swing.tabcontrol.event.ComplexListDataListener;
66
import org.netbeans.swing.tabcontrol.event.ComplexListDataListener;
67
import org.netbeans.swing.tabcontrol.event.TabActionEvent;
67
import org.netbeans.swing.tabcontrol.event.TabActionEvent;
68
import org.netbeans.swing.tabcontrol.plaf.BusyTabsSupport;
68
import org.netbeans.swing.tabcontrol.plaf.TabControlButton;
69
import org.netbeans.swing.tabcontrol.plaf.TabControlButton;
69
import org.netbeans.swing.tabcontrol.plaf.TabControlButtonFactory;
70
import org.netbeans.swing.tabcontrol.plaf.TabControlButtonFactory;
70
import org.openide.windows.Mode;
71
import org.openide.windows.Mode;
Lines 465-471 Link Here
465
        if( gap > 0 )
466
        if( gap > 0 )
466
            addStrut(gap);
467
            addStrut(gap);
467
    }
468
    }
468
    
469
470
    void makeBusy( TopComponent tc, boolean busy ) {
471
        BusyTabsSupport.getDefault().makeTabBusy( tabbed, 0, busy );
472
        syncWithModel();
473
    }
474
475
    @Override
476
    public void addNotify() {
477
        super.addNotify();
478
        BusyTabsSupport.getDefault().install( getTabbed(), dataModel );
479
    }
480
481
    @Override
482
    public void removeNotify() {
483
        super.removeNotify();
484
        BusyTabsSupport.getDefault().uninstall( getTabbed(), dataModel );
485
    }
486
469
    private class SlidedWinsysInfoForTabbedContainer extends WinsysInfoForTabbedContainer {
487
    private class SlidedWinsysInfoForTabbedContainer extends WinsysInfoForTabbedContainer {
470
        @Override
488
        @Override
471
        public Object getOrientation(Component comp) {
489
        public Object getOrientation(Component comp) {
Lines 519-524 Link Here
519
        public boolean isSlidedOutContainer() {
537
        public boolean isSlidedOutContainer() {
520
            return true;
538
            return true;
521
        }
539
        }
540
541
        @Override
542
        public boolean isTopComponentBusy( TopComponent tc ) {
543
            return WindowManagerImpl.getInstance().isTopComponentBusy( tc );
544
        }
522
    }
545
    }
523
    
546
    
524
    /*************** non public stuff **************************/
547
    /*************** non public stuff **************************/
Lines 603-608 Link Here
603
            if (blinks != null && blinks.contains(td)) {
626
            if (blinks != null && blinks.contains(td)) {
604
                curButton.setBlinking(true);
627
                curButton.setBlinking(true);
605
            }
628
            }
629
            TopComponent tc = ( TopComponent ) td.getComponent();
630
            if( tabbed.isBusy( tc ) ) {
631
                curButton.setIcon( BusyTabsSupport.getDefault().getBusyIcon(false) );
632
            }
606
            String modeName = getRestoreModeNameForTab( td );
633
            String modeName = getRestoreModeNameForTab( td );
607
            gestureRecognizer.attachButton(curButton);
634
            gestureRecognizer.attachButton(curButton);
608
            buttons.add(curButton);
635
            buttons.add(curButton);
(-)a/core.windows/src/org/netbeans/core/windows/view/ui/slides/SlideBarContainer.java (-1 / +6 lines)
Lines 105-111 Link Here
105
    @Override
105
    @Override
106
    public void cancelRequestAttention (TopComponent tc) {
106
    public void cancelRequestAttention (TopComponent tc) {
107
        tabbedHandler.cancelRequestAttention (tc);
107
        tabbedHandler.cancelRequestAttention (tc);
108
    }    
108
    }
109
110
    @Override
111
    public void makeBusy(TopComponent tc, boolean busy) {
112
        tabbedHandler.makeBusy( tc, busy );
113
    }
109
    
114
    
110
    @Override
115
    @Override
111
    public void setTopComponents(TopComponent[] tcs, TopComponent selected) {
116
    public void setTopComponents(TopComponent[] tcs, TopComponent selected) {
(-)a/core.windows/src/org/netbeans/core/windows/view/ui/slides/TabbedSlideAdapter.java (-1 / +10 lines)
Lines 114-121 Link Here
114
    public void cancelRequestAttention (TopComponent tc) {
114
    public void cancelRequestAttention (TopComponent tc) {
115
        slideBar.setBlinking(tc, false);
115
        slideBar.setBlinking(tc, false);
116
    }
116
    }
117
118
    @Override
119
    public void makeBusy( TopComponent tc, boolean busy ) {
120
        slideBar.makeBusy( tc, busy );
121
    }
122
123
    @Override
124
    public boolean isBusy( TopComponent tc ) {
125
        return WindowManagerImpl.getInstance().isTopComponentBusy( tc );
126
    }
117
    
127
    
118
119
    private void setSide (String side) {
128
    private void setSide (String side) {
120
        int orientation = SlideBarDataModel.WEST;
129
        int orientation = SlideBarDataModel.WEST;
121
        if (Constants.LEFT.equals(side)) {
130
        if (Constants.LEFT.equals(side)) {
(-)a/core.windows/src/org/netbeans/core/windows/view/ui/tabcontrol/AbstractTabbedImpl.java (-4 / +6 lines)
Lines 49-58 Link Here
49
import java.util.logging.Logger;
49
import java.util.logging.Logger;
50
import javax.swing.*;
50
import javax.swing.*;
51
import javax.swing.event.ChangeListener;
51
import javax.swing.event.ChangeListener;
52
import org.netbeans.core.windows.Constants;
52
import org.netbeans.core.windows.*;
53
import org.netbeans.core.windows.Debug;
54
import org.netbeans.core.windows.ModeImpl;
55
import org.netbeans.core.windows.WindowManagerImpl;
56
import org.netbeans.core.windows.actions.ActionUtils;
53
import org.netbeans.core.windows.actions.ActionUtils;
57
import org.netbeans.swing.tabcontrol.ComponentConverter;
54
import org.netbeans.swing.tabcontrol.ComponentConverter;
58
import org.netbeans.swing.tabcontrol.TabData;
55
import org.netbeans.swing.tabcontrol.TabData;
Lines 421-426 Link Here
421
        cs.removeChangeListener( listener );
418
        cs.removeChangeListener( listener );
422
    }
419
    }
423
420
421
    @Override
422
    public boolean isBusy( TopComponent tc ) {
423
        return WindowManagerImpl.getInstance().isTopComponentBusy( tc );
424
    }
425
424
    protected abstract ComponentConverter getComponentConverter();
426
    protected abstract ComponentConverter getComponentConverter();
425
427
426
    /** Returns instance of weak property change listener used to listen to
428
    /** Returns instance of weak property change listener used to listen to
(-)a/core.windows/src/org/netbeans/core/windows/view/ui/tabcontrol/TabbedAdapter.java (+24 lines)
Lines 60-65 Link Here
60
import org.netbeans.core.windows.Switches;
60
import org.netbeans.core.windows.Switches;
61
import org.netbeans.swing.tabcontrol.*;
61
import org.netbeans.swing.tabcontrol.*;
62
import org.netbeans.swing.tabcontrol.event.TabActionEvent;
62
import org.netbeans.swing.tabcontrol.event.TabActionEvent;
63
import org.netbeans.swing.tabcontrol.plaf.BusyTabsSupport;
63
64
64
/** Adapter class that implements a pseudo JTabbedPane API on top
65
/** Adapter class that implements a pseudo JTabbedPane API on top
65
 * of the new tab control.  This class should eventually be eliminated
66
 * of the new tab control.  This class should eventually be eliminated
Lines 192-197 Link Here
192
        public boolean isModeSlidingEnabled() {
193
        public boolean isModeSlidingEnabled() {
193
            return Switches.isModeSlidingEnabled();
194
            return Switches.isModeSlidingEnabled();
194
        }
195
        }
196
197
        @Override
198
        public boolean isTopComponentBusy( TopComponent tc ) {
199
            return WindowManagerImpl.getInstance().isTopComponentBusy( tc );
200
        }
195
    } // end of LocInfo
201
    } // end of LocInfo
196
    
202
    
197
    private final AbstractTabbedImpl tabbedImpl = new AbstractTabbedImpl() {
203
    private final AbstractTabbedImpl tabbedImpl = new AbstractTabbedImpl() {
Lines 306-310 Link Here
306
        protected Shape getDropIndication( TopComponent draggedTC, Point location ) {
312
        protected Shape getDropIndication( TopComponent draggedTC, Point location ) {
307
            return TabbedAdapter.this.getDropIndication( draggedTC, location );
313
            return TabbedAdapter.this.getDropIndication( draggedTC, location );
308
        }
314
        }
315
316
        @Override
317
        public void makeBusy( TopComponent tc, boolean busy ) {
318
            int tabIndex = indexOf( tc );
319
            BusyTabsSupport.getDefault().makeTabBusy( this, tabIndex, busy );
320
        }
309
    };
321
    };
322
323
    @Override
324
    public void addNotify() {
325
        super.addNotify();
326
        BusyTabsSupport.getDefault().install( getTabbed(), getModel() );
327
    }
328
329
    @Override
330
    public void removeNotify() {
331
        super.removeNotify();
332
        BusyTabsSupport.getDefault().uninstall( getTabbed(), getModel() );
333
    }
310
}
334
}
(-)a/o.n.swing.tabcontrol/apichanges.xml (+21 lines)
Lines 108-113 Link Here
108
108
109
<changes>
109
<changes>
110
110
111
    <change id="busy_tabs">
112
      <api name="tabcontrol"/>
113
      <summary>Display notification that a tab is 'busy'.</summary>
114
      <version major="1" minor="34"/>
115
      <date day="13" month="2" year="2012"/>
116
      <author login="saubrecht"/>
117
      <compatibility addition="yes" binary="compatible" deprecation="no"/>
118
      <description>
119
        The look and feel for tabbed containers has been extended to support
120
        notifications that a tab is 'busy', i.e. some lengthy process is being
121
        run in it.<br/>
122
        All supported look and feel implementations use an animated icon to indicate
123
        the busy state.
124
      </description>
125
      <class package="org.netbeans.swing.tabcontrol.plaf" name="BusyTabsSupport"/>
126
      <class package="org.netbeans.swing.tabcontrol" name="WinsysInfoForTabbedContainer"/>
127
      <class package="org.netbeans.swing.tabcontrol" name="TabDisplayerUI"/>
128
      <class package="org.netbeans.swing.tabcontrol.customtabs" name="Tabbed"/>
129
      <issue number="208026"/>
130
    </change>
131
111
    <change id="tabcontrol_factory">
132
    <change id="tabcontrol_factory">
112
      <api name="tabcontrol"/>
133
      <api name="tabcontrol"/>
113
      <summary>Allow custom implementation of tab control.</summary>
134
      <summary>Allow custom implementation of tab control.</summary>
(-)a/o.n.swing.tabcontrol/manifest.mf (-1 / +1 lines)
Lines 1-6 Link Here
1
Manifest-Version: 1.0
1
Manifest-Version: 1.0
2
OpenIDE-Module-Localizing-Bundle: org/netbeans/swing/tabcontrol/Bundle.properties
2
OpenIDE-Module-Localizing-Bundle: org/netbeans/swing/tabcontrol/Bundle.properties
3
OpenIDE-Module: org.netbeans.swing.tabcontrol
3
OpenIDE-Module: org.netbeans.swing.tabcontrol
4
OpenIDE-Module-Specification-Version: 1.33
4
OpenIDE-Module-Specification-Version: 1.34
5
AutoUpdate-Essential-Module: true
5
AutoUpdate-Essential-Module: true
6
6
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/TabDisplayerUI.java (-6 / +29 lines)
Lines 49-64 Link Here
49
49
50
package org.netbeans.swing.tabcontrol;
50
package org.netbeans.swing.tabcontrol;
51
51
52
import org.netbeans.swing.tabcontrol.event.TabActionEvent;
53
54
import javax.swing.*;
55
import javax.swing.plaf.ComponentUI;
56
import java.awt.*;
52
import java.awt.*;
57
import java.awt.event.MouseEvent;
53
import java.awt.event.MouseEvent;
58
import java.util.HashMap;
54
import java.util.HashMap;
59
import java.util.Map;
55
import java.util.Map;
56
import javax.swing.Icon;
57
import javax.swing.JComponent;
58
import javax.swing.SingleSelectionModel;
59
import javax.swing.UIManager;
60
import javax.swing.plaf.ComponentUI;
61
import org.netbeans.swing.tabcontrol.event.TabActionEvent;
60
import org.netbeans.swing.tabcontrol.plaf.TabControlButton;
62
import org.netbeans.swing.tabcontrol.plaf.TabControlButton;
61
import org.netbeans.swing.tabcontrol.plaf.TabControlButtonFactory;
63
import org.netbeans.swing.tabcontrol.plaf.TabControlButtonFactory;
64
import org.openide.windows.TopComponent;
62
65
63
/**
66
/**
64
 * The basic UI of a tab displayer component.  Defines the API of the UI for
67
 * The basic UI of a tab displayer component.  Defines the API of the UI for
Lines 225-230 Link Here
225
    }
228
    }
226
229
227
    /**
230
    /**
231
     * Check if the given tab is busy and should be painted in a special way.
232
     * @param tabIndex
233
     * @return True if given tab is 'busy', false otherwise.
234
     * @since 1.34
235
     */
236
    public final boolean isTabBusy( int tabIndex ) {
237
        WinsysInfoForTabbedContainer winsysInfo = displayer.getContainerWinsysInfo();
238
        if( null == winsysInfo )
239
            return false;
240
        TabDataModel model = displayer.getModel();
241
        if( tabIndex < 0 || tabIndex >= model.size() )
242
            return false;
243
        TabData td = model.getTab( tabIndex );
244
        if( td.getComponent() instanceof TopComponent ) {
245
            return winsysInfo.isTopComponentBusy( (TopComponent)td.getComponent() );
246
        }
247
        return false;
248
    }
249
250
    /**
228
     * Installs the selection model into the tab control via a package private
251
     * Installs the selection model into the tab control via a package private
229
     * method.
252
     * method.
230
     */
253
     */
Lines 247-254 Link Here
247
    
270
    
248
    protected abstract void requestAttention (int tab);
271
    protected abstract void requestAttention (int tab);
249
    
272
    
250
    protected abstract void cancelRequestAttention (int tab);   
273
    protected abstract void cancelRequestAttention (int tab);
251
    
274
252
    /**
275
    /**
253
     * @since 1.9
276
     * @since 1.9
254
     * @return An icon for various buttons displayed in tab control (close/pin/scroll left/right etc), see TabControlButton class.
277
     * @return An icon for various buttons displayed in tab control (close/pin/scroll left/right etc), see TabControlButton class.
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/WinsysInfoForTabbedContainer.java (-1 / +12 lines)
Lines 132-141 Link Here
132
        return false;
132
        return false;
133
    }
133
    }
134
134
135
    /**
136
     * Check if the header of given TopComponent should be painted in a special
137
     * way to indicate that some process is running in that TopComponent.
138
     * @param tc
139
     * @return True to indicate process being run in the TopComponent, false otherwise.
140
     * @since 1.34
141
     */
142
    public boolean isTopComponentBusy( TopComponent tc ) {
143
        return false;
144
    }
145
135
    public static WinsysInfoForTabbedContainer getDefault( WinsysInfoForTabbed winsysInfo ) {
146
    public static WinsysInfoForTabbedContainer getDefault( WinsysInfoForTabbed winsysInfo ) {
136
        return new DefaultWinsysInfoForTabbedContainer( winsysInfo );
147
        return new DefaultWinsysInfoForTabbedContainer( winsysInfo );
137
    }
148
    }
138
    
149
139
    private static class DefaultWinsysInfoForTabbedContainer extends WinsysInfoForTabbedContainer {
150
    private static class DefaultWinsysInfoForTabbedContainer extends WinsysInfoForTabbedContainer {
140
        
151
        
141
        private WinsysInfoForTabbed delegate;
152
        private WinsysInfoForTabbed delegate;
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/customtabs/Tabbed.java (+21 lines)
Lines 141-146 Link Here
141
    public abstract boolean isTransparent();
141
    public abstract boolean isTransparent();
142
    
142
    
143
    public abstract void setTransparent( boolean transparent );
143
    public abstract void setTransparent( boolean transparent );
144
145
    /**
146
     * Notify user that given TopComponent is 'busy' (some lengthy process is
147
     * running in it).
148
     * @param tc
149
     * @param busy True to make the TopComponent busy, false to cancel the notification.
150
     * @since 1.34
151
     */
152
    public void makeBusy( TopComponent tc, boolean busy ) {
153
    }
154
155
    /**
156
     * Check if given TopComponent is busy
157
     * @param tc
158
     * @return True if the TopComponent is busy and its header should be painted
159
     * in a special way, false otherwise.
160
     * @since 1.34
161
     */
162
    public boolean isBusy( TopComponent tc ) {
163
        return false;
164
    }
144
    
165
    
145
    /**
166
    /**
146
     * Visual containers that hold the tabbed components must implement this interface
167
     * Visual containers that hold the tabbed components must implement this interface
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/AbstractTabCellRenderer.java (+7 lines)
Lines 268-273 Link Here
268
        return (state & TabState.AFTER_SELECTED) != 0;
268
        return (state & TabState.AFTER_SELECTED) != 0;
269
    }
269
    }
270
270
271
    /**
272
     * @return True if the tab is busy.
273
     */
274
    protected final boolean isBusy() {
275
        return (state & TabState.BUSY) != 0;
276
    }
277
    
271
    public Dimension getPadding() {
278
    public Dimension getPadding() {
272
        return new Dimension(padding);
279
        return new Dimension(padding);
273
    }
280
    }
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/AquaEditorTabCellRenderer.java (+3 lines)
Lines 92-97 Link Here
92
92
93
    @Override
93
    @Override
94
    protected void paintIconAndText(Graphics g) {
94
    protected void paintIconAndText(Graphics g) {
95
        if( isBusy() ) {
96
            setIcon( BusyTabsSupport.getDefault().getBusyIcon( isSelected() ) );
97
        }
95
        super.paintIconAndText(g);
98
        super.paintIconAndText(g);
96
    }
99
    }
97
100
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/AquaViewTabDisplayerUI.java (+12 lines)
Lines 64-69 Link Here
64
import javax.swing.Icon;
64
import javax.swing.Icon;
65
import javax.swing.JComponent;
65
import javax.swing.JComponent;
66
import javax.swing.UIManager;
66
import javax.swing.UIManager;
67
import org.netbeans.swing.tabcontrol.WinsysInfoForTabbedContainer;
67
68
68
/**
69
/**
69
 * A view tabs ui for OS-X adapted from the view tabs UI for Metal.
70
 * A view tabs ui for OS-X adapted from the view tabs UI for Metal.
Lines 165-170 Link Here
165
            textY = (height / 2) - (textHeight / 2) + fm.getAscent();
166
            textY = (height / 2) - (textHeight / 2) + fm.getAscent();
166
        }
167
        }
167
168
169
        boolean slidedOut = false;
170
        WinsysInfoForTabbedContainer winsysInfo = displayer.getContainerWinsysInfo();
171
        if( null != winsysInfo && winsysInfo.isSlidedOutContainer() )
172
            slidedOut = false;
173
        if( isTabBusy( index ) && !slidedOut ) {
174
            Icon busyIcon = BusyTabsSupport.getDefault().getBusyIcon( isSelected( index ) );
175
            textW -= busyIcon.getIconWidth() - 3 - TXT_X_PAD;
176
            busyIcon.paintIcon( displayer, g, textX, y+(height-busyIcon.getIconHeight())/2);
177
            textX += busyIcon.getIconWidth() + 3;
178
        }
179
168
        int realTextWidth = (int)HtmlRenderer.renderString(text, g, textX, textY, textW, height, getTxtFont(),
180
        int realTextWidth = (int)HtmlRenderer.renderString(text, g, textX, textY, textW, height, getTxtFont(),
169
                          UIManager.getColor("textText"), //NOI18N
181
                          UIManager.getColor("textText"), //NOI18N
170
                          HtmlRenderer.STYLE_TRUNCATE, false);
182
                          HtmlRenderer.STYLE_TRUNCATE, false);
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/BasicTabDisplayerUI.java (+5 lines)
Lines 70-75 Link Here
70
import javax.swing.event.ListDataEvent;
70
import javax.swing.event.ListDataEvent;
71
import org.netbeans.swing.tabcontrol.TabData;
71
import org.netbeans.swing.tabcontrol.TabData;
72
import org.netbeans.swing.tabcontrol.TabDisplayer;
72
import org.netbeans.swing.tabcontrol.TabDisplayer;
73
import org.netbeans.swing.tabcontrol.WinsysInfoForTabbedContainer;
73
import org.netbeans.swing.tabcontrol.event.ComplexListDataEvent;
74
import org.netbeans.swing.tabcontrol.event.ComplexListDataEvent;
74
import org.openide.windows.TopComponent;
75
import org.openide.windows.TopComponent;
75
76
Lines 427-432 Link Here
427
                            TabCellRenderer ren = getTabCellRenderer(i);
428
                            TabCellRenderer ren = getTabCellRenderer(i);
428
                            
429
                            
429
                            TabData data = displayer.getModel().getTab(i);
430
                            TabData data = displayer.getModel().getTab(i);
431
432
                            if( isTabBusy( i ) ) {
433
                                state |= TabState.BUSY;
434
                            }
430
                            
435
                            
431
                            JComponent renderer = ren.getRendererComponent(
436
                            JComponent renderer = ren.getRendererComponent(
432
                                    data, scratch, state);
437
                                    data, scratch, state);
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/BusyIcon.java (+210 lines)
Line 0 Link Here
1
/*
2
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
3
 *
4
 * Copyright 2012 Oracle and/or its affiliates. All rights reserved.
5
 *
6
 * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
7
 * Other names may be trademarks of their respective owners.
8
 *
9
 * The contents of this file are subject to the terms of either the GNU
10
 * General Public License Version 2 only ("GPL") or the Common
11
 * Development and Distribution License("CDDL") (collectively, the
12
 * "License"). You may not use this file except in compliance with the
13
 * License. You can obtain a copy of the License at
14
 * http://www.netbeans.org/cddl-gplv2.html
15
 * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
16
 * specific language governing permissions and limitations under the
17
 * License.  When distributing the software, include this License Header
18
 * Notice in each file and include the License file at
19
 * nbbuild/licenses/CDDL-GPL-2-CP.  Oracle designates this
20
 * particular file as subject to the "Classpath" exception as provided
21
 * by Oracle in the GPL Version 2 section of the License file that
22
 * accompanied this code. If applicable, add the following below the
23
 * License Header, with the fields enclosed by brackets [] replaced by
24
 * your own identifying information:
25
 * "Portions Copyrighted [year] [name of copyright owner]"
26
 *
27
 * If you wish your version of this file to be governed by only the CDDL
28
 * or only the GPL Version 2, indicate your decision by adding
29
 * "[Contributor] elects to include this software in this distribution
30
 * under the [CDDL or GPL Version 2] license." If you do not indicate a
31
 * single choice of license, a recipient has the option to distribute
32
 * your version of this file under either the CDDL, the GPL Version 2 or
33
 * to extend the choice of license to its licensees as provided above.
34
 * However, if you add GPL Version 2 code and therefore, elected the GPL
35
 * Version 2 license, then the option applies only if the new code is
36
 * made subject to such option by the copyright holder.
37
 *
38
 * Contributor(s):
39
 *
40
 * Portions Copyrighted 2012 Sun Microsystems, Inc.
41
 */
42
package org.netbeans.swing.tabcontrol.plaf;
43
44
import java.awt.Component;
45
import java.awt.Graphics;
46
import java.awt.Graphics2D;
47
import java.awt.Image;
48
import java.awt.geom.AffineTransform;
49
import java.lang.reflect.Constructor;
50
import java.lang.reflect.Method;
51
import java.util.logging.Level;
52
import java.util.logging.Logger;
53
import javax.swing.Icon;
54
import javax.swing.UIManager;
55
import org.openide.util.ImageUtilities;
56
import org.openide.util.Lookup;
57
58
/**
59
 * An animated icon to indicate that a tab is 'busy'.
60
 * @see BusyTabsSupport
61
 * @author S. Aubrecht
62
 * @since 1.34
63
 */
64
abstract class BusyIcon implements Icon {
65
66
    protected final int width;
67
    protected final int height;
68
69
    protected BusyIcon( int width, int height ) {
70
        this.width = width;
71
        this.height = height;
72
    }
73
    
74
    /**
75
     * <p>Creates a new instance.</p>
76
     * <p>
77
     * The implementation first checks <code>UIManager</code> defaults and looks for <code>Icon</code>
78
     * under keys <code>"nb.tabcontrol.busy.icon.selected"</code> and <code>"nb.tabcontrol.busy.icon.normal"</code>.
79
     * If there is an Icon under those keys then the created instance will rotate
80
     * that Icon to animate it.
81
     * </p><p>
82
     * If there are no Icons in UIManager then there will be an attempt to create
83
     * animated Icon based <code>BusyPainter</code> in SwingX library. If swingx.jar
84
     * is available on classpath then reflection is used to create BusyPainter
85
     * instance and paint icon animations with it.
86
     * </p><p>
87
     * If SwingX library isn't available then the default image 
88
     * <code>"org/netbeans/swing/tabcontrol/resources/busy_icon.png"</code>
89
     * will be rotated.
90
     * </p>
91
     * 
92
     * @param selectedTab Boolean to create icon for selected tab state, false
93
     * to create icon for normal tab state.
94
     * @return Animated icon.
95
     */
96
    public static BusyIcon create( boolean selectedTab ) {
97
        BusyIcon res = null;
98
        Icon img = UIManager.getIcon( "nb.tabcontrol.busy.icon." + (selectedTab ? ".selected" : ".normal") ); //NOI18N
99
        if( null != img ) {
100
            res = new ImageBusyIcon( ImageUtilities.icon2Image( img ) );
101
        } else {
102
            res = SwingXBusyIcon.create();
103
        }
104
        if( null == res )
105
            res = new ImageBusyIcon( ImageUtilities.loadImage( "org/netbeans/swing/tabcontrol/resources/busy_icon.png") ); //NOI18N
106
        return res;
107
    }
108
109
    abstract void tick();
110
111
    @Override
112
    public final int getIconWidth() {
113
        return width;
114
    }
115
116
    @Override
117
    public final int getIconHeight() {
118
        return height;
119
    }
120
121
    private static class ImageBusyIcon extends BusyIcon {
122
123
        private final Image img;
124
        private int state = 0;
125
        private AffineTransform at;
126
        private static final int STEP = 15;
127
128
        public ImageBusyIcon( Image img ) {
129
            super( img.getWidth( null ), img.getHeight( null ) );
130
            this.img = img;
131
        }
132
133
        @Override
134
        void tick() {
135
            state += STEP;
136
            if( state >= 360 )
137
                state = 0;
138
            at = new AffineTransform();
139
            at.rotate( state * Math.PI / 180.0, width/2, height/2 );
140
        }
141
142
        @Override
143
        public void paintIcon( Component c, Graphics g, int x, int y ) {
144
            if( g instanceof Graphics2D ) {
145
                Graphics2D g2d = ( Graphics2D ) g;
146
                g2d.translate( x, y );
147
                g2d.drawImage( img, at, null );
148
                g2d.translate( -x, -y );
149
            }
150
        }
151
    }
152
153
    private static class SwingXBusyIcon extends BusyIcon {
154
155
        private final Object painter;
156
        private final Method setFrameMethod;
157
        private final Method paintMethod;
158
        private int currentFrame = 0;
159
        private static final int POINTS = 8;
160
        private static final int HEIGHT = 14;
161
162
        private SwingXBusyIcon( Object painter, Method paint, Method setFrame ) {
163
            super( HEIGHT, HEIGHT );
164
            this.painter = painter;
165
            this.setFrameMethod = setFrame;
166
            this.paintMethod = paint;
167
        }
168
169
        public static BusyIcon create() {
170
            Object painter = null;
171
            ClassLoader cl = Lookup.getDefault().lookup( ClassLoader.class );
172
            try {
173
                Class painterClass = cl.loadClass( "org.jdesktop.swingx.painter.BusyPainter" ); //NOI18N
174
                Constructor ctor = painterClass.getConstructor( int.class );
175
                painter = ctor.newInstance( HEIGHT );
176
                Method setFrame = painterClass.getMethod( "setFrame", int.class ); //NOI18N
177
                Method paint = painterClass.getMethod( "paint", Graphics2D.class, Object.class, int.class, int.class ); //NOI18N
178
                Method m = painterClass.getMethod( "setPoints", int.class ); //NOI18N
179
                m.invoke( painter, POINTS );
180
                return new SwingXBusyIcon( painter, paint, setFrame );
181
            } catch( Exception ex ) {
182
                Logger.getLogger( BusyIcon.class.getName() ).log( Level.FINE, null, ex );
183
            }
184
            return null;
185
        }
186
187
        @Override
188
        public void tick() {
189
            currentFrame = (currentFrame + 1) % POINTS;
190
            try {
191
                setFrameMethod.invoke( painter, currentFrame );
192
            } catch( Exception ex ) {
193
            }
194
        }
195
196
        @Override
197
        public void paintIcon( Component c, Graphics g, int x, int y ) {
198
            if( g instanceof Graphics2D ) {
199
                Graphics2D g2d = ( Graphics2D ) g;
200
                try {
201
                    g2d.translate( x, y );
202
                    paintMethod.invoke( painter, g, c, x, y );
203
                } catch( Exception ex ) {
204
                    Logger.getLogger( BusyIcon.class.getName() ).log( Level.FINE, null, ex );
205
                }
206
                g2d.translate( -x, -y );
207
            }
208
        }
209
    }
210
}
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/BusyTabsSupport.java (+277 lines)
Line 0 Link Here
1
/*
2
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
3
 *
4
 * Copyright 2012 Oracle and/or its affiliates. All rights reserved.
5
 *
6
 * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
7
 * Other names may be trademarks of their respective owners.
8
 *
9
 * The contents of this file are subject to the terms of either the GNU
10
 * General Public License Version 2 only ("GPL") or the Common
11
 * Development and Distribution License("CDDL") (collectively, the
12
 * "License"). You may not use this file except in compliance with the
13
 * License. You can obtain a copy of the License at
14
 * http://www.netbeans.org/cddl-gplv2.html
15
 * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
16
 * specific language governing permissions and limitations under the
17
 * License.  When distributing the software, include this License Header
18
 * Notice in each file and include the License file at
19
 * nbbuild/licenses/CDDL-GPL-2-CP.  Oracle designates this
20
 * particular file as subject to the "Classpath" exception as provided
21
 * by Oracle in the GPL Version 2 section of the License file that
22
 * accompanied this code. If applicable, add the following below the
23
 * License Header, with the fields enclosed by brackets [] replaced by
24
 * your own identifying information:
25
 * "Portions Copyrighted [year] [name of copyright owner]"
26
 *
27
 * If you wish your version of this file to be governed by only the CDDL
28
 * or only the GPL Version 2, indicate your decision by adding
29
 * "[Contributor] elects to include this software in this distribution
30
 * under the [CDDL or GPL Version 2] license." If you do not indicate a
31
 * single choice of license, a recipient has the option to distribute
32
 * your version of this file under either the CDDL, the GPL Version 2 or
33
 * to extend the choice of license to its licensees as provided above.
34
 * However, if you add GPL Version 2 code and therefore, elected the GPL
35
 * Version 2 license, then the option applies only if the new code is
36
 * made subject to such option by the copyright holder.
37
 *
38
 * Contributor(s):
39
 *
40
 * Portions Copyrighted 2012 Sun Microsystems, Inc.
41
 */
42
package org.netbeans.swing.tabcontrol.plaf;
43
44
import java.awt.Rectangle;
45
import java.awt.event.ActionEvent;
46
import java.awt.event.ActionListener;
47
import java.util.Set;
48
import javax.swing.Icon;
49
import javax.swing.Timer;
50
import javax.swing.event.ChangeEvent;
51
import javax.swing.event.ChangeListener;
52
import org.netbeans.swing.tabcontrol.TabDataModel;
53
import org.netbeans.swing.tabcontrol.customtabs.Tabbed;
54
import org.openide.util.Lookup;
55
import org.openide.util.WeakSet;
56
import org.openide.util.lookup.ServiceProvider;
57
import org.openide.windows.TopComponent;
58
59
/**
60
 * Support class to implement animation in tab headers to indicate some sort of
61
 * 'busy' state.<br
62
 * The default implementation tracks changes in registered tab containers
63
 * (<code>install(Tabbed, TabDataModel)</code>) and if any tab is marked as 'busy'
64
 * (<code>TopComponent.makeBusy(boolean)</code>) it forces repeated repaints of
65
 * that tab to allow animation effects. The UI of the tab container then can use
66
 * an icon this class provides (<code>getBusyIcon(boolean)</code>)to indicate
67
 * the busy state. The default implementation of this class ensures that the
68
 * icon is properly animated in each repaint.
69
 *
70
 * @see TopComponent#makeBusy(boolean)
71
 *
72
 * @author S. Aubrecht
73
 */
74
public abstract class BusyTabsSupport {
75
76
    private Timer animationTimer;
77
78
    private final ChangeListener modelListener = new ChangeListener() {
79
80
        @Override
81
        public void stateChanged( ChangeEvent e ) {
82
            checkBusyTabs();
83
        }
84
    };
85
86
    private final Set<Tabbed> containers = new WeakSet<Tabbed>(10);
87
    private final Set<Tabbed> busyContainers = new WeakSet<Tabbed>(10);
88
89
    /**
90
     * @return The default implementation registered in global Lookup.
91
     * @see DefaultBusyTabsSupport
92
     */
93
    public static BusyTabsSupport getDefault() {
94
        return Lookup.getDefault().lookup( BusyTabsSupport.class );
95
    }
96
97
    /**
98
     * Track changes in given tab container to have busy tab headers repainted.
99
     * @param tabContainer Tab container. This method should be typically called
100
     * from container's <code>addNotify()</code>.
101
     * @param tabModel Container data model.
102
     */
103
    public final void install( Tabbed tabContainer, TabDataModel tabModel ) {
104
        if( containers.contains( tabContainer ) )
105
            return;
106
        tabModel.addChangeListener( modelListener );
107
        containers.add( tabContainer );
108
        checkBusyTabs();
109
    }
110
111
    /**
112
     * Unregister the given tab container. This method should be typically called
113
     * from container's <code>removeNotify()</code>.
114
     * 
115
     * @param tabContainer
116
     * @param tabModel 
117
     */
118
    public final void uninstall( Tabbed tabContainer, TabDataModel tabModel ) {
119
        if( busyContainers.remove( tabContainer ) )
120
            repaintAll( tabContainer );
121
        tabModel.removeChangeListener( modelListener );
122
        containers.remove( tabContainer );
123
        checkBusyTabs();
124
    }
125
126
    /**
127
     * An icon that can be shown in busy tab's header to indicate some lengthy
128
     * process is being run in it. The default implementation ensures the icon
129
     * is properly animated.
130
     * @param isTabSelected True to get icon for a selected tab, false to get
131
     * icon for regular tab state.
132
     * @return Busy-like icon.
133
     */
134
    public abstract Icon getBusyIcon( boolean isTabSelected );
135
136
    /**
137
     * Notification that busy state has changed for a given tab.
138
     * @param tabContainer Tab container.
139
     * @param tabIndex Index of the tab.
140
     * @param busy 
141
     */
142
    public final void makeTabBusy( Tabbed tabContainer, int tabIndex, boolean busy ) {
143
        if( !busy ) {
144
            Rectangle tabRect = tabContainer.getTabBounds( tabIndex );
145
            tabContainer.getComponent().repaint( tabRect.x, tabRect.y, tabRect.width, tabRect.height );
146
        }
147
        checkBusyTabs();
148
    }
149
150
    /**
151
     * 
152
     * @return The time in milliseconds between repaints of busy tabs. Value of
153
     * zero means there are no repeated repaints.
154
     */
155
    protected abstract int getRepaintTimerIntervalMillis();
156
157
    /**
158
     * Invoked between each repaint events. The default implementation animates
159
     * the busy icon in this method.
160
     */
161
    protected abstract void tick();
162
    
163
    private void startAnimationTimer() {
164
        if( null != animationTimer ) {
165
            return;
166
        }
167
        int interval = getRepaintTimerIntervalMillis();
168
        if( interval <= 0 )
169
            return;
170
        animationTimer = new Timer( interval, new ActionListener() {
171
            @Override
172
            public void actionPerformed( ActionEvent e ) {
173
                checkBusyTabs();
174
                repaintBusyTabs();
175
                tick();
176
            }
177
        });
178
        animationTimer.setRepeats( true );
179
        animationTimer.start();
180
    }
181
182
    private void stopAnimationTimer() {
183
        if( null == animationTimer ) {
184
            return;
185
        }
186
        animationTimer.stop();
187
        animationTimer = null;
188
        repaintBusyTabs();
189
    }
190
191
    private void checkBusyTabs() {
192
        busyContainers.clear();
193
194
        for( Tabbed tc : containers ) {
195
            if( hasBusyTabs( tc ) )
196
                busyContainers.add( tc );
197
        }
198
199
        if( busyContainers.isEmpty() ) {
200
            stopAnimationTimer();
201
        } else {
202
            startAnimationTimer();
203
        }
204
    }
205
206
    private void repaintBusyTabs() {
207
        for( Tabbed tc : busyContainers ) {
208
            repaintBusy( tc );
209
        }
210
    }
211
212
    private void repaintBusy( Tabbed tabbed ) {
213
        for( int i=0; i<tabbed.getTabCount(); i++ ) {
214
            TopComponent tc = tabbed.getTopComponentAt( i );
215
            if( tabbed.isBusy( tc ) ) {
216
                Rectangle rect = tabbed.getTabBounds( i );
217
                tabbed.getComponent().repaint( rect.x, rect.y, rect.width, rect.height );
218
            }
219
        }
220
    }
221
222
    private void repaintAll( Tabbed tc ) {
223
        Rectangle rect = tc.getTabsArea();
224
        tc.getComponent().repaint( rect.x, rect.y, rect.width, rect.height );
225
    }
226
227
    private boolean hasBusyTabs( Tabbed tabbedContainer ) {
228
        boolean res = false;
229
        for( int tabIndex = 0; tabIndex<tabbedContainer.getTabCount(); tabIndex++ ) {
230
            if( tabbedContainer.isBusy( tabbedContainer.getTopComponentAt( tabIndex ) ) ) {
231
                res = true;
232
                break;
233
            }
234
        }
235
        return res;
236
    }
237
238
    /**
239
     * The default implementation of busy tabs.
240
     * @see BusyIcon
241
     */
242
    @ServiceProvider(service=BusyTabsSupport.class)
243
    public static final class DefaultBusyTabsSupport extends BusyTabsSupport {
244
245
        private BusyIcon busyIconSelected;
246
        private BusyIcon busyIconDefault;
247
248
        @Override
249
        public Icon getBusyIcon( boolean isTabSelected ) {
250
            if( isTabSelected ) {
251
                if( null == busyIconSelected ) {
252
                    busyIconSelected = BusyIcon.create( isTabSelected );
253
                }
254
                return busyIconSelected;
255
            } else {
256
                if( null == busyIconDefault ) {
257
                    busyIconDefault = BusyIcon.create( isTabSelected );
258
                }
259
                return busyIconDefault;
260
            }
261
        }
262
263
        @Override
264
        protected void tick() {
265
            if( null != busyIconSelected )
266
                busyIconSelected.tick();
267
268
            if( null != busyIconDefault )
269
                busyIconDefault.tick();
270
        }
271
272
        @Override
273
        protected int getRepaintTimerIntervalMillis() {
274
            return 150;
275
        }
276
    }
277
}
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/GtkEditorTabCellRenderer.java (+8 lines)
Lines 90-95 Link Here
90
    public Color getForeground() {
90
    public Color getForeground() {
91
        return getSelectedForeground();
91
        return getSelectedForeground();
92
    }
92
    }
93
94
    @Override
95
    protected void paintIconAndText( Graphics g ) {
96
        if( isBusy() ) {
97
            setIcon( BusyTabsSupport.getDefault().getBusyIcon( isSelected() ) );
98
        }
99
        super.paintIconAndText( g );
100
    }
93
    
101
    
94
    /**
102
    /**
95
     * #56245 - need more space between icon and edge on classic for the case
103
     * #56245 - need more space between icon and edge on classic for the case
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/GtkViewTabDisplayerUI.java (+11 lines)
Lines 72-77 Link Here
72
import javax.swing.plaf.synth.SynthPainter;
72
import javax.swing.plaf.synth.SynthPainter;
73
import javax.swing.plaf.synth.SynthStyle;
73
import javax.swing.plaf.synth.SynthStyle;
74
import javax.swing.plaf.synth.SynthStyleFactory;
74
import javax.swing.plaf.synth.SynthStyleFactory;
75
import org.netbeans.swing.tabcontrol.WinsysInfoForTabbedContainer;
75
import org.openide.awt.HtmlRenderer;
76
import org.openide.awt.HtmlRenderer;
76
77
77
/**
78
/**
Lines 190-195 Link Here
190
        // draw bump (dragger)
191
        // draw bump (dragger)
191
        drawBump(g, index, x + 4, y + 6, BUMP_WIDTH, height - 8);
192
        drawBump(g, index, x + 4, y + 6, BUMP_WIDTH, height - 8);
192
        
193
        
194
        boolean slidedOut = false;
195
        WinsysInfoForTabbedContainer winsysInfo = displayer.getContainerWinsysInfo();
196
        if( null != winsysInfo && winsysInfo.isSlidedOutContainer() )
197
            slidedOut = false;
198
        if( isTabBusy( index ) && !slidedOut ) {
199
            Icon busyIcon = BusyTabsSupport.getDefault().getBusyIcon( isSelected( index ) );
200
            txtWidth -= busyIcon.getIconWidth() - 3 - TXT_X_PAD;
201
            busyIcon.paintIcon( displayer, g, x+TXT_X_PAD, y+(height-busyIcon.getIconHeight())/2);
202
            x += busyIcon.getIconWidth() + 3;
203
        }
193
        // draw text in right color
204
        // draw text in right color
194
        Color txtC = UIManager.getColor("textText"); //NOI18N
205
        Color txtC = UIManager.getColor("textText"); //NOI18N
195
        HtmlRenderer.renderString(text, g, x + TXT_X_PAD, y + fm.getAscent()
206
        HtmlRenderer.renderString(text, g, x + TXT_X_PAD, y + fm.getAscent()
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/MetalEditorTabCellRenderer.java (+8 lines)
Lines 81-86 Link Here
81
        return d;
81
        return d;
82
    }
82
    }
83
83
84
    @Override
85
    protected void paintIconAndText( Graphics g ) {
86
        if( isBusy() ) {
87
            setIcon( BusyTabsSupport.getDefault().getBusyIcon( isSelected() ) );
88
        }
89
        super.paintIconAndText( g );
90
    }
91
84
    private static class MetalTabPainter implements TabPainter {
92
    private static class MetalTabPainter implements TabPainter {
85
        public Insets getBorderInsets(Component c) {
93
        public Insets getBorderInsets(Component c) {
86
            MetalEditorTabCellRenderer mtr = (MetalEditorTabCellRenderer) c;
94
            MetalEditorTabCellRenderer mtr = (MetalEditorTabCellRenderer) c;
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/MetalViewTabDisplayerUI.java (-1 / +21 lines)
Lines 59-64 Link Here
59
import org.netbeans.swing.tabcontrol.TabDisplayer;
59
import org.netbeans.swing.tabcontrol.TabDisplayer;
60
60
61
import javax.swing.plaf.ComponentUI;
61
import javax.swing.plaf.ComponentUI;
62
import org.netbeans.swing.tabcontrol.WinsysInfoForTabbedContainer;
62
63
63
64
64
import org.openide.awt.HtmlRenderer;
65
import org.openide.awt.HtmlRenderer;
Lines 149-154 Link Here
149
    @Override
150
    @Override
150
    protected void paintTabContent(Graphics g, int index, String text, int x,
151
    protected void paintTabContent(Graphics g, int index, String text, int x,
151
                                   int y, int width, int height) {
152
                                   int y, int width, int height) {
153
        boolean slidedOut = false;
154
        WinsysInfoForTabbedContainer winsysInfo = displayer.getContainerWinsysInfo();
155
        if( null != winsysInfo && winsysInfo.isSlidedOutContainer() )
156
            slidedOut = false;
157
152
        FontMetrics fm = getTxtFontMetrics();
158
        FontMetrics fm = getTxtFontMetrics();
153
        // setting font already here to compute string width correctly
159
        // setting font already here to compute string width correctly
154
        g.setFont(getTxtFont());
160
        g.setFont(getTxtFont());
Lines 168-174 Link Here
168
                }
174
                }
169
            }
175
            }
170
            
176
            
171
            txtWidth = (int)HtmlRenderer.renderString(text, g, x + TXT_X_PAD, height - 
177
            if( isTabBusy( index ) && !slidedOut ) {
178
                Icon busyIcon = BusyTabsSupport.getDefault().getBusyIcon( isSelected( index ) );
179
                txtWidth -= busyIcon.getIconWidth() - 3 - TXT_X_PAD;
180
                busyIcon.paintIcon( displayer, g, x+TXT_X_PAD, y+(height-busyIcon.getIconHeight())/2);
181
                x += busyIcon.getIconWidth() + 3;
182
            }
183
184
            txtWidth = (int)HtmlRenderer.renderString(text, g, x + TXT_X_PAD, height -
172
                    fm.getDescent() - 4, txtWidth, height, getTxtFont(),
185
                    fm.getDescent() - 4, txtWidth, height, getTxtFont(),
173
                    UIManager.getColor("textText"),
186
                    UIManager.getColor("textText"),
174
                    HtmlRenderer.STYLE_TRUNCATE, true);
187
                    HtmlRenderer.STYLE_TRUNCATE, true);
Lines 179-184 Link Here
179
                          y + BUMP_Y_PAD, bumpWidth, height - 2 * BUMP_Y_PAD);
192
                          y + BUMP_Y_PAD, bumpWidth, height - 2 * BUMP_Y_PAD);
180
            }
193
            }
181
        } else {
194
        } else {
195
            if( isTabBusy( index ) && !slidedOut ) {
196
                Icon busyIcon = BusyTabsSupport.getDefault().getBusyIcon( isSelected( index ) );
197
                txtWidth -= busyIcon.getIconWidth() - 3 - TXT_X_PAD;
198
                busyIcon.paintIcon( displayer, g, x+TXT_X_PAD, y+(height-busyIcon.getIconHeight())/2);
199
                x += busyIcon.getIconWidth() + 3;
200
            }
201
182
            txtWidth = width - 2 * TXT_X_PAD;
202
            txtWidth = width - 2 * TXT_X_PAD;
183
            HtmlRenderer.renderString(text, g, x + TXT_X_PAD, height - 
203
            HtmlRenderer.renderString(text, g, x + TXT_X_PAD, height - 
184
                fm.getDescent() - 4, txtWidth, height, getTxtFont(),
204
                fm.getDescent() - 4, txtWidth, height, getTxtFont(),
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/NimbusEditorTabCellRenderer.java (+8 lines)
Lines 105-110 Link Here
105
        d.width = isShowCloseButton() && !Boolean.getBoolean("nb.tabs.suppressCloseButton") ? 28 : 14;
105
        d.width = isShowCloseButton() && !Boolean.getBoolean("nb.tabs.suppressCloseButton") ? 28 : 14;
106
        return d;
106
        return d;
107
    }
107
    }
108
109
    @Override
110
    protected void paintIconAndText( Graphics g ) {
111
        if( isBusy() ) {
112
            setIcon( BusyTabsSupport.getDefault().getBusyIcon( isSelected() ) );
113
        }
114
        super.paintIconAndText( g );
115
    }
108
    
116
    
109
    private static final Insets INSETS = new Insets(0, 2, 0, 10);
117
    private static final Insets INSETS = new Insets(0, 2, 0, 10);
110
    
118
    
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/NimbusViewTabDisplayerUI.java (+12 lines)
Lines 62-67 Link Here
62
import javax.swing.Icon;
62
import javax.swing.Icon;
63
import javax.swing.JComponent;
63
import javax.swing.JComponent;
64
import javax.swing.UIManager;
64
import javax.swing.UIManager;
65
import org.netbeans.swing.tabcontrol.WinsysInfoForTabbedContainer;
65
import org.openide.awt.HtmlRenderer;
66
import org.openide.awt.HtmlRenderer;
66
67
67
/**
68
/**
Lines 183-188 Link Here
183
        // draw bump (dragger)
184
        // draw bump (dragger)
184
        drawBump(g, index, x + 4, y + 6, BUMP_WIDTH, height - 8);
185
        drawBump(g, index, x + 4, y + 6, BUMP_WIDTH, height - 8);
185
        
186
        
187
        boolean slidedOut = false;
188
        WinsysInfoForTabbedContainer winsysInfo = displayer.getContainerWinsysInfo();
189
        if( null != winsysInfo && winsysInfo.isSlidedOutContainer() )
190
            slidedOut = false;
191
        if( isTabBusy( index ) && !slidedOut ) {
192
            Icon busyIcon = BusyTabsSupport.getDefault().getBusyIcon( isSelected( index ) );
193
            txtWidth -= busyIcon.getIconWidth() - 3 - TXT_X_PAD;
194
            busyIcon.paintIcon( displayer, g, x+TXT_X_PAD, y+(height-busyIcon.getIconHeight())/2);
195
            x += busyIcon.getIconWidth() + 3;
196
        }
197
186
        // draw text in right color
198
        // draw text in right color
187
        Color txtC = UIManager.getColor("TabbedPane.foreground"); //NOI18N
199
        Color txtC = UIManager.getColor("TabbedPane.foreground"); //NOI18N
188
        
200
        
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/TabState.java (-2 / +8 lines)
Lines 203-214 Link Here
203
     * less one
203
     * less one
204
     */
204
     */
205
    public static final int BEFORE_ARMED = 32768;
205
    public static final int BEFORE_ARMED = 32768;
206
    
206
207
    /**
208
     * Indicates the given tab is 'busy', i.e. the editor is still loading its data
209
     * or there's some lengthy process running in that tab.
210
     * @since 1.34
211
     */
212
    public static final int BUSY = 2*32768;
207
    /**
213
    /**
208
     * Indicates the last constant defined - renderers that wish to add their
214
     * Indicates the last constant defined - renderers that wish to add their
209
     * own bitmasks should use multiples of this number
215
     * own bitmasks should use multiples of this number
210
     */
216
     */
211
    public static int STATE_LAST = MOUSE_PRESSED_IN_CLOSE_BUTTON;
217
    public static int STATE_LAST = BUSY;
212
218
213
219
214
    private int pressedIndex = -1;
220
    private int pressedIndex = -1;
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/WinClassicEditorTabCellRenderer.java (+8 lines)
Lines 98-103 Link Here
98
        return d;
98
        return d;
99
    }
99
    }
100
    
100
    
101
    @Override
102
    protected void paintIconAndText( Graphics g ) {
103
        if( isBusy() ) {
104
            setIcon( BusyTabsSupport.getDefault().getBusyIcon( isSelected() ) );
105
        }
106
        super.paintIconAndText( g );
107
    }
108
101
    private static final Insets INSETS = new Insets(0, 2, 0, 10);
109
    private static final Insets INSETS = new Insets(0, 2, 0, 10);
102
110
103
    private static class WinClassicPainter implements TabPainter {
111
    private static class WinClassicPainter implements TabPainter {
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/WinClassicViewTabDisplayerUI.java (+12 lines)
Lines 62-67 Link Here
62
import javax.swing.Icon;
62
import javax.swing.Icon;
63
import javax.swing.JComponent;
63
import javax.swing.JComponent;
64
import javax.swing.UIManager;
64
import javax.swing.UIManager;
65
import org.netbeans.swing.tabcontrol.WinsysInfoForTabbedContainer;
65
import org.openide.awt.HtmlRenderer;
66
import org.openide.awt.HtmlRenderer;
66
67
67
/**
68
/**
Lines 194-199 Link Here
194
            // draw bump (dragger)
195
            // draw bump (dragger)
195
            drawBump(g, index, x + 4, y + 6, BUMP_WIDTH, height - 8);
196
            drawBump(g, index, x + 4, y + 6, BUMP_WIDTH, height - 8);
196
        }
197
        }
198
199
        boolean slidedOut = false;
200
        WinsysInfoForTabbedContainer winsysInfo = displayer.getContainerWinsysInfo();
201
        if( null != winsysInfo && winsysInfo.isSlidedOutContainer() )
202
            slidedOut = false;
203
        if( isTabBusy( index ) && !slidedOut ) {
204
            Icon busyIcon = BusyTabsSupport.getDefault().getBusyIcon( isSelected( index ) );
205
            txtWidth -= busyIcon.getIconWidth() - 3 - TXT_X_PAD;
206
            busyIcon.paintIcon( displayer, g, x+TXT_X_PAD, y+(height-busyIcon.getIconHeight())/2);
207
            x += busyIcon.getIconWidth() + 3;
208
        }
197
        
209
        
198
        // draw text in right color
210
        // draw text in right color
199
        Color txtC = UIManager.getColor("TabbedPane.foreground"); //NOI18N
211
        Color txtC = UIManager.getColor("TabbedPane.foreground"); //NOI18N
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/WinVistaEditorTabCellRenderer.java (+8 lines)
Lines 273-278 Link Here
273
    protected int getIconYAdjustment() {
273
    protected int getIconYAdjustment() {
274
        return -2;
274
        return -2;
275
    }
275
    }
276
277
    @Override
278
    protected void paintIconAndText( Graphics g ) {
279
        if( isBusy() ) {
280
            setIcon( BusyTabsSupport.getDefault().getBusyIcon( isSelected() ) );
281
        }
282
        super.paintIconAndText( g );
283
    }
276
    
284
    
277
    private static class WinVistaPainter implements TabPainter {
285
    private static class WinVistaPainter implements TabPainter {
278
286
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/WinVistaViewTabDisplayerUI.java (+13 lines)
Lines 64-69 Link Here
64
import javax.swing.Icon;
64
import javax.swing.Icon;
65
import javax.swing.JComponent;
65
import javax.swing.JComponent;
66
import javax.swing.UIManager;
66
import javax.swing.UIManager;
67
import org.netbeans.swing.tabcontrol.WinsysInfoForTabbedContainer;
67
import org.netbeans.swing.tabcontrol.event.TabActionEvent;
68
import org.netbeans.swing.tabcontrol.event.TabActionEvent;
68
69
69
70
Lines 195-200 Link Here
195
                     + BUMP_Y_PAD_UPPER, height - (BUMP_Y_PAD_UPPER
196
                     + BUMP_Y_PAD_UPPER, height - (BUMP_Y_PAD_UPPER
196
                     + BUMP_Y_PAD_BOTTOM));
197
                     + BUMP_Y_PAD_BOTTOM));
197
        }
198
        }
199
200
        boolean slidedOut = false;
201
        WinsysInfoForTabbedContainer winsysInfo = displayer.getContainerWinsysInfo();
202
        if( null != winsysInfo && winsysInfo.isSlidedOutContainer() )
203
            slidedOut = false;
204
        if( isTabBusy( index ) && !slidedOut ) {
205
            Icon busyIcon = BusyTabsSupport.getDefault().getBusyIcon( isSelected( index ) );
206
            txtWidth -= busyIcon.getIconWidth() - 3 - TXT_X_PAD;
207
            busyIcon.paintIcon( displayer, g, x+TXT_X_PAD, y+(height-busyIcon.getIconHeight())/2);
208
            x += busyIcon.getIconWidth() + 3;
209
        }
210
198
        HtmlRenderer.renderString(text, g, x + TXT_X_PAD, y + fm.getAscent()
211
        HtmlRenderer.renderString(text, g, x + TXT_X_PAD, y + fm.getAscent()
199
                + TXT_Y_PAD, txtWidth, height, getTxtFont(),
212
                + TXT_Y_PAD, txtWidth, height, getTxtFont(),
200
                txtC,
213
                txtC,
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/WinXPEditorTabCellRenderer.java (+8 lines)
Lines 210-215 Link Here
210
        return result;
210
        return result;
211
    }
211
    }
212
212
213
    @Override
214
    protected void paintIconAndText( Graphics g ) {
215
        if( isBusy() ) {
216
            setIcon( BusyTabsSupport.getDefault().getBusyIcon( isSelected() ) );
217
        }
218
        super.paintIconAndText( g );
219
    }
220
213
    private static final Color getRightEdgeSelectedShadow() {
221
    private static final Color getRightEdgeSelectedShadow() {
214
        Color result = UIManager.getColor("close_button_border_focus"); //NOI18N
222
        Color result = UIManager.getColor("close_button_border_focus"); //NOI18N
215
        if (result == null) {
223
        if (result == null) {
(-)a/o.n.swing.tabcontrol/src/org/netbeans/swing/tabcontrol/plaf/WinXPViewTabDisplayerUI.java (+13 lines)
Lines 53-58 Link Here
53
53
54
import java.util.HashMap;
54
import java.util.HashMap;
55
import java.util.Map;
55
import java.util.Map;
56
import org.netbeans.swing.tabcontrol.WinsysInfoForTabbedContainer;
56
import org.netbeans.swing.tabcontrol.event.TabActionEvent;
57
import org.netbeans.swing.tabcontrol.event.TabActionEvent;
57
58
58
59
Lines 192-197 Link Here
192
                     + BUMP_Y_PAD_UPPER, height - (BUMP_Y_PAD_UPPER
193
                     + BUMP_Y_PAD_UPPER, height - (BUMP_Y_PAD_UPPER
193
                     + BUMP_Y_PAD_BOTTOM)+highlightedRaiseCompensation);
194
                     + BUMP_Y_PAD_BOTTOM)+highlightedRaiseCompensation);
194
        }
195
        }
196
197
        boolean slidedOut = false;
198
        WinsysInfoForTabbedContainer winsysInfo = displayer.getContainerWinsysInfo();
199
        if( null != winsysInfo && winsysInfo.isSlidedOutContainer() )
200
            slidedOut = false;
201
        if( isTabBusy( index ) && !slidedOut ) {
202
            Icon busyIcon = BusyTabsSupport.getDefault().getBusyIcon( isSelected( index ) );
203
            txtWidth -= busyIcon.getIconWidth() - 3 - TXT_X_PAD;
204
            busyIcon.paintIcon( displayer, g, x+TXT_X_PAD, y+(height-busyIcon.getIconHeight())/2);
205
            x += busyIcon.getIconWidth() + 3;
206
        }
207
195
        HtmlRenderer.renderString(text, g, x + TXT_X_PAD, y + fm.getAscent()
208
        HtmlRenderer.renderString(text, g, x + TXT_X_PAD, y + fm.getAscent()
196
                + TXT_Y_PAD, txtWidth, height, getTxtFont(),
209
                + TXT_Y_PAD, txtWidth, height, getTxtFont(),
197
                txtC,
210
                txtC,
(-)a/openide.windows/apichanges.xml (+15 lines)
Lines 50-55 Link Here
50
<apidef name="winsys">Window System API</apidef>
50
<apidef name="winsys">Window System API</apidef>
51
</apidefs>
51
</apidefs>
52
<changes>
52
<changes>
53
<change id="topcomponent.busy">
54
    <api name="winsys"/>
55
    <summary>Added method TopComponent.makeBusy(boolean).</summary>
56
    <version major="6" minor="51"/>
57
    <date day="8" month="2" year="2012"/>
58
    <author login="saubrecht"/>
59
    <compatibility addition="yes" source="compatible" semantic="compatible" deprecation="no" deletion="no" modification="no"/>
60
    <description>
61
        <p>The new method can be used to inform user that some (possibly lengthy)
62
        process is being run in given <code>TopComponent.</code></p>
63
    </description>
64
    <class package="org.openide.windows" name="WindowManager"/>
65
    <class package="org.openide.windows" name="TopComponent"/>
66
    <issue number="208026"/>
67
</change>
53
<change id="jtabbedpane.replacement.for.tabbedcontainer">
68
<change id="jtabbedpane.replacement.for.tabbedcontainer">
54
    <api name="winsys"/>
69
    <api name="winsys"/>
55
    <summary>Added branding options to replace the custom TabbedContainer with
70
    <summary>Added branding options to replace the custom TabbedContainer with
(-)a/openide.windows/manifest.mf (-1 / +1 lines)
Lines 1-6 Link Here
1
Manifest-Version: 1.0
1
Manifest-Version: 1.0
2
OpenIDE-Module: org.openide.windows
2
OpenIDE-Module: org.openide.windows
3
OpenIDE-Module-Specification-Version: 6.50
3
OpenIDE-Module-Specification-Version: 6.51
4
OpenIDE-Module-Localizing-Bundle: org/openide/windows/Bundle.properties
4
OpenIDE-Module-Localizing-Bundle: org/openide/windows/Bundle.properties
5
AutoUpdate-Essential-Module: true
5
AutoUpdate-Essential-Module: true
6
6
(-)a/openide.windows/src/org/openide/windows/TopComponent.java (-9 / +20 lines)
Lines 95-109 Link Here
95
import org.openide.nodes.Node;
95
import org.openide.nodes.Node;
96
import org.openide.nodes.NodeAdapter;
96
import org.openide.nodes.NodeAdapter;
97
import org.openide.nodes.NodeListener;
97
import org.openide.nodes.NodeListener;
98
import org.openide.util.ContextAwareAction;
98
import org.openide.util.*;
99
import org.openide.util.HelpCtx;
100
import org.openide.util.ImageUtilities;
101
import org.openide.util.Lookup;
102
import org.openide.util.NbBundle;
103
import org.openide.util.NbPreferences;
104
import org.openide.util.Utilities;
105
import org.openide.util.WeakListeners;
106
import org.openide.util.WeakSet;
107
import org.openide.util.actions.NodeAction;
99
import org.openide.util.actions.NodeAction;
108
import org.openide.util.actions.SystemAction;
100
import org.openide.util.actions.SystemAction;
109
101
Lines 922-927 Link Here
922
    }
914
    }
923
915
924
    /**
916
    /**
917
     * Notify the user that some (possibly lengthy) process is being run in this
918
     * window.
919
     * It is safe to call this method outside EDT.
920
     *
921
     * @param True to start 'busy' notification, 'false' to stop it.
922
     *
923
     * @see WindowManager#topComponentMakeBusy(org.openide.windows.TopComponent, boolean)
924
     * @since 6.51
925
     */
926
    public final void makeBusy( final boolean busy ) {
927
        Mutex.EVENT.readAccess( new Runnable() {
928
            @Override
929
            public void run() {
930
                WindowManager.getDefault().topComponentMakeBusy( TopComponent.this, busy );
931
            }
932
        });
933
    }
934
935
    /**
925
     * Cause this TopComponent's tab to stop flashing if it was flashing.
936
     * Cause this TopComponent's tab to stop flashing if it was flashing.
926
     * @since 5.1
937
     * @since 5.1
927
     */
938
     */
(-)a/openide.windows/src/org/openide/windows/WindowManager.java (+13 lines)
Lines 488-493 Link Here
488
    }
488
    }
489
489
490
    /**
490
    /**
491
     * Notifies the user that some process is running in the given TopComponent,
492
     * for example by drawing an animated "wait" icon in TopComponent's header.<br>
493
     * The default implementation does nothing.
494
     *
495
     * @param tc
496
     * @param busy True to start 'busy' notification, false to stop it.
497
     *
498
     * @since 6.51
499
     */
500
    protected void topComponentMakeBusy( TopComponent tc, boolean busy ) {
501
    }
502
503
    /**
491
     * Attempts to bring the parent <code>Window</code> of the given <code>TopComponent</code>
504
     * Attempts to bring the parent <code>Window</code> of the given <code>TopComponent</code>
492
     * to front of other windows.
505
     * to front of other windows.
493
     * @see java.awt.Window#toFront()
506
     * @see java.awt.Window#toFront()

Return to bug 208026