My previous entry showed the way to provide visual indication of frames with changed content. Based on the suggestions from the comments, this behaviour has been also added to JTabbedPane.
Application should set SubstanceLookAndFeel.WINDOW_MODIFIED client property on the tabbed pane's Component (if it's JComponent). The value that corresponds to unsaved state is Boolean.TRUE. See 67-second AVI movie (1.2 MB) illustrating the technique.
Pulsating loop on JTabbedPane - red theme (animation start):

Pulsating loop on JTabbedPane - orange theme (midway through animation):

Pulsating loop on JTabbedPane - yellow theme (animation flex point):

In addition, the tabs can now have close buttons (like in NetBeans or SWT). Application should set SubstanceLookAndFeel.TABBED_PANE_CLOSE_BUTTONS_PROPERTY client property on either the tabbed pane's Component (if it's JComponent), JTabbedPane (for all tabs of that pane) or the UIManager (for all tabbed panes). The value that corresponds to tab with close button is Boolean.TRUE. In addition, there's rollover effect on enabled tabs (like on any other control such as buttons or scroll bars). See 45-second AVI movie (810 KB) illustrating the technique.
Close button on active tab in JTabbedPane - mouse not over close button (includes mouse pointer):

Close button on active tab in JTabbedPane - mouse over close button (includes mouse pointer):

Close button on inactive enabled tab in JTabbedPane - mouse not over tab (includes mouse pointer):

Close button on inactive enabled tab in JTabbedPane - mouse over tab but not over close button (includes mouse pointer):

Close button on inactive enabled tab in JTabbedPane - mouse over tab and over close button (includes mouse pointer):

This property can be set in three ways:

- On JTabbedPane tab component itself (if it's JComponent). If the property is specified here and it's either Boolean.TRUE or Boolean.FALSE, its value is taken.
- On JTabbedPane itself. If the property is specified here and it's either Boolean.TRUE or Boolean.FALSE, its value is taken and is relevant for all tabs in this JTabbedPane that weren't found in the previous step.
- As global setting in UIManager. If the property is specified here and it's either Boolean.TRUE or Boolean.FALSE, its value is taken and is relevant for all tabs in all JTabbedPanes that weren't found in the previous two steps.

Note that the default behaviour (if you do not specify this property anywhere) is not to use close buttons at all - in order to not interfere with Java 6.0 tabbed components. For example:

      JTabbedPane pane = new JTabbedPane();
      JPanel component = new JPanel();
      component.putClientProperty(SubstanceLookAndFeel.TABBED_PANE_CLOSE_BUTTONS_PROPERTY,
    	Boolean.TRUE);
      pane.addTab(component);
      JPanel component2 = new JPanel();
      // Will not have close button unless the tabbed pane itself specifies
      // Boolean.TRUE as value for its client property or UIManager.put is
      // called on this property with Boolean.TRUE

      pane.addTab(component2);

Once again - the behaviour is not disruptive. If you don't specify this property anywhere, you will not have close buttons on your tabs. This will allow Java 6.0 applications that set custom tab header components to continue working correctly.
As always, you can run a Web Start demo or download the latest Substance 2.1 development drop from here.