Logo Search packages:      
Sourcecode: eclipse version File versions  Download package

WorkbenchWindow.java

/*******************************************************************************
 * Copyright (c) 2000, 2005 IBM Corporation and others.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 *
 * Contributors:
 *     IBM Corporation - initial API and implementation
 *******************************************************************************/

package org.eclipse.ui.internal;

import java.lang.reflect.InvocationTargetException;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

import org.eclipse.core.commands.IHandler;
import org.eclipse.core.expressions.Expression;
import org.eclipse.core.runtime.IAdaptable;
import org.eclipse.core.runtime.IExtension;
import org.eclipse.core.runtime.IExtensionPoint;
import org.eclipse.core.runtime.IStatus;
import org.eclipse.core.runtime.MultiStatus;
import org.eclipse.core.runtime.Platform;
import org.eclipse.core.runtime.Status;
import org.eclipse.core.runtime.dynamichelpers.ExtensionTracker;
import org.eclipse.core.runtime.dynamichelpers.IExtensionChangeHandler;
import org.eclipse.core.runtime.dynamichelpers.IExtensionTracker;
import org.eclipse.jface.action.CoolBarManager;
import org.eclipse.jface.action.GroupMarker;
import org.eclipse.jface.action.IAction;
import org.eclipse.jface.action.IContributionItem;
import org.eclipse.jface.action.IContributionManager;
import org.eclipse.jface.action.IMenuManager;
import org.eclipse.jface.action.MenuManager;
import org.eclipse.jface.action.Separator;
import org.eclipse.jface.action.StatusLineManager;
import org.eclipse.jface.action.ToolBarContributionItem;
import org.eclipse.jface.action.ToolBarManager;
import org.eclipse.jface.commands.ActionHandler;
import org.eclipse.jface.operation.IRunnableWithProgress;
import org.eclipse.jface.window.ApplicationWindow;
import org.eclipse.jface.window.Window;
import org.eclipse.osgi.util.NLS;
import org.eclipse.swt.SWT;
import org.eclipse.swt.custom.BusyIndicator;
import org.eclipse.swt.custom.CBanner;
import org.eclipse.swt.custom.StackLayout;
import org.eclipse.swt.events.ControlAdapter;
import org.eclipse.swt.events.ControlEvent;
import org.eclipse.swt.events.ShellAdapter;
import org.eclipse.swt.events.ShellEvent;
import org.eclipse.swt.graphics.Point;
import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Control;
import org.eclipse.swt.widgets.CoolBar;
import org.eclipse.swt.widgets.Display;
import org.eclipse.swt.widgets.Event;
import org.eclipse.swt.widgets.Layout;
import org.eclipse.swt.widgets.Listener;
import org.eclipse.swt.widgets.Menu;
import org.eclipse.swt.widgets.Shell;
import org.eclipse.ui.ActiveShellExpression;
import org.eclipse.ui.IEditorPart;
import org.eclipse.ui.IElementFactory;
import org.eclipse.ui.IMemento;
import org.eclipse.ui.IPageListener;
import org.eclipse.ui.IPartService;
import org.eclipse.ui.IPersistable;
import org.eclipse.ui.IPersistableElement;
import org.eclipse.ui.IPerspectiveDescriptor;
import org.eclipse.ui.ISelectionService;
import org.eclipse.ui.ISources;
import org.eclipse.ui.IViewReference;
import org.eclipse.ui.IWorkbench;
import org.eclipse.ui.IWorkbenchActionConstants;
import org.eclipse.ui.IWorkbenchPage;
import org.eclipse.ui.IWorkbenchPart;
import org.eclipse.ui.IWorkbenchPartReference;
import org.eclipse.ui.IWorkbenchPreferenceConstants;
import org.eclipse.ui.IWorkbenchWindow;
import org.eclipse.ui.PlatformUI;
import org.eclipse.ui.WorkbenchException;
import org.eclipse.ui.application.ActionBarAdvisor;
import org.eclipse.ui.application.IActionBarConfigurer;
import org.eclipse.ui.application.WorkbenchAdvisor;
import org.eclipse.ui.application.WorkbenchWindowAdvisor;
import org.eclipse.ui.contexts.IContextService;
import org.eclipse.ui.contexts.IWorkbenchContextSupport;
import org.eclipse.ui.handlers.IHandlerActivation;
import org.eclipse.ui.handlers.IHandlerService;
import org.eclipse.ui.internal.dialogs.CustomizePerspectiveDialog;
import org.eclipse.ui.internal.dnd.DragUtil;
import org.eclipse.ui.internal.dnd.SwtUtil;
import org.eclipse.ui.internal.intro.IIntroConstants;
import org.eclipse.ui.internal.layout.CacheWrapper;
import org.eclipse.ui.internal.layout.LayoutUtil;
import org.eclipse.ui.internal.layout.TrimLayout;
import org.eclipse.ui.internal.layout.TrimLayoutData;
import org.eclipse.ui.internal.misc.Assert;
import org.eclipse.ui.internal.misc.Policy;
import org.eclipse.ui.internal.misc.UIListenerLogging;
import org.eclipse.ui.internal.misc.UIStats;
import org.eclipse.ui.internal.progress.ProgressRegion;
import org.eclipse.ui.internal.registry.ActionSetRegistry;
import org.eclipse.ui.internal.registry.IActionSet;
import org.eclipse.ui.internal.registry.IActionSetDescriptor;
import org.eclipse.ui.internal.registry.UIExtensionTracker;
import org.eclipse.ui.internal.util.PrefUtil;

/**
 * A window within the workbench.
 */
00120 public class WorkbenchWindow extends ApplicationWindow implements
        IWorkbenchWindow {

    private WorkbenchWindowAdvisor windowAdvisor;
    
    private ActionBarAdvisor actionBarAdvisor;
    
    private int number;

    private PageList pageList = new PageList();

    private PageListenerList pageListeners = new PageListenerList();

    private PerspectiveListenerList perspectiveListeners = new PerspectiveListenerList();

    private WWinPartService partService = new WWinPartService(this);

    private ActionPresentation actionPresentation;

    private WWinActionBars actionBars;

    private boolean updateDisabled = true;

    private boolean closing = false;

    private boolean shellActivated = false;

    private FastViewBar fastViewBar;

    private PerspectiveSwitcher perspectiveSwitcher;

    private TrimLayout defaultLayout;

    ProgressRegion progressRegion;

      private HeapStatus heapStatus;


      private boolean emptyWindowContentsCreated = false;

      private Control emptyWindowContents;

    private Rectangle normalBounds;

    private boolean asMaximizedState = false;

    private CBanner topBar;

    // Previous shell size. Used to prevent the CBanner from triggering redundant layouts
    private Point lastShellSize = new Point(0, 0);

    /**
     * The composite under which workbench pages create their controls.
     * 
     * @since 3.0
     */
00176     private Composite pageComposite;

    /**
     * Bit flags indication which submenus (New, Show Views, ...) this
     * window contains. Initially none.
     * 
     * @since 3.0
     */
00184     private int submenus = 0x00;

    /**
     * Object for configuring this workbench window. Lazily initialized to
     * an instance unique to this window.
     *  
     * @since 3.0
     */
00192     private WorkbenchWindowConfigurer windowConfigurer = null;

    private ShellPool detachedWindowShells;
    
    // constants for shortcut bar group ids 
    static final String GRP_PAGES = "pages"; //$NON-NLS-1$

    static final String GRP_PERSPECTIVES = "perspectives"; //$NON-NLS-1$

    static final String GRP_FAST_VIEWS = "fastViews"; //$NON-NLS-1$

    // static fields for inner classes.
    static final int VGAP = 0;

    static final int CLIENT_INSET = 3;

    static final int BAR_SIZE = 23;

    /**
     * Constant (bit mask) indicating which the Show View submenu is
     * probably present somewhere in this window.
     * 
     * @see #addSubmenu
     * @since 3.0
     */
00217     public static final int SHOW_VIEW_SUBMENU = 0x01;

    /**
     * Constant (bit mask) indicating which the Open Perspective submenu is
     * probably present somewhere in this window.
     *
     * @see #addSubmenu
     * @since 3.0
     */
00226     public static final int OPEN_PERSPECTIVE_SUBMENU = 0x02;

    /**
     * Constant (bit mask) indicating which the New Wizard submenu is
     * probably present somewhere in this window.
     * 
     * @see #addSubmenu
     * @since 3.0
     */
00235     public static final int NEW_WIZARD_SUBMENU = 0x04;

    /**
     * Remembers that this window contains the given submenu.
     * 
     * @param type the type of submenu, one of: 
     * {@link #NEW_WIZARD_SUBMENU NEW_WIZARD_SUBMENU},
     * {@link #OPEN_PERSPECTIVE_SUBMENU OPEN_PERSPECTIVE_SUBMENU},
     * {@link #SHOW_VIEW_SUBMENU SHOW_VIEW_SUBMENU}
     * @see #containsSubmenu
     * @since 3.0
     */
00247     public void addSubmenu(int type) {
        submenus |= type;
    }

    /**
     * Checks to see if this window contains the given type of submenu.
     * 
     * @param type the type of submenu, one of: 
     * {@link #NEW_WIZARD_SUBMENU NEW_WIZARD_SUBMENU},
     * {@link #OPEN_PERSPECTIVE_SUBMENU OPEN_PERSPECTIVE_SUBMENU},
     * {@link #SHOW_VIEW_SUBMENU SHOW_VIEW_SUBMENU}
     * @return <code>true</code> if window contains submenu,
     * <code>false</code> otherwise
     * @see #addSubmenu
     * @since 3.0
     */
00263     public boolean containsSubmenu(int type) {
        return ((submenus & type) != 0);
    }

    /**
     * Constant indicating that all the actions bars should be
     * filled.
     * 
     * @since 3.0
     */
00273     private static final int FILL_ALL_ACTION_BARS = ActionBarAdvisor.FILL_MENU_BAR
            | ActionBarAdvisor.FILL_COOL_BAR
            | ActionBarAdvisor.FILL_STATUS_LINE;

    /**
     * Creates and initializes a new workbench window.
     * 
     * @param number the number for the window
     */
00282     public WorkbenchWindow(int number) {
        super(null);
        this.number = number;

        // Make sure there is a workbench. This call will throw
        // an exception if workbench not created yet. 
        PlatformUI.getWorkbench();

        // Add contribution managers that are exposed to other plugins.
        addMenuBar();
        addCoolBar(SWT.FLAT);
        addStatusLine();

        actionPresentation = new ActionPresentation(this);
        
        // register with the tracker
        getExtensionTracker()
                .registerHandler(
                        actionSetHandler,
                        ExtensionTracker
                                .createExtensionPointFilter(getActionSetExtensionPoint()));

        fireWindowOpening();

        // set the shell style
        setShellStyle(getWindowConfigurer().getShellStyle());

        // Fill the action bars
        fillActionBars(FILL_ALL_ACTION_BARS);
    }
    
    /**
     * Return the action set extension point.
     * 
     * @return the action set extension point
     * @since 3.1
     */
00319     private IExtensionPoint getActionSetExtensionPoint() {
        return Platform.getExtensionRegistry().getExtensionPoint(
                PlatformUI.PLUGIN_ID, IWorkbenchConstants.PL_ACTION_SETS);
    }

    /**
     * Return the style bits for the shortcut bar.
     * @return int
     */
00328     protected int perspectiveBarStyle() {
        return SWT.FLAT | SWT.WRAP | SWT.RIGHT | SWT.HORIZONTAL;
    }

    private TrimDropTarget trimDropTarget;

    private boolean coolBarVisible = true;

    private boolean perspectiveBarVisible = true;

    private boolean statusLineVisible = true;

    /**
     * The handlers for action set actions that were last submitted to the
     * workbench command support. This is a map of command identifiers to
     * <code>ActionHandler</code>. This map is never <code>null</code>,
     * and is never empty as long as at least one action set has been
     * registered. The items in this map may not all be submitted, as global
     * actions take priority.
     */
00348     private Map actionSetHandlersByCommandId = new HashMap();

    /**
     * The handlers for global actions that were last submitted to the workbench
     * command support. This is a map of command identifiers to
     * <code>ActionHandler</code>. This map is never <code>null</code>,
     * and is never empty as long as at least one global action has been
     * registered.
     */
00357     private Map globalActionHandlersByCommandId = new HashMap();

    /**
     * The list of handler submissions submitted to the workbench command
     * support. This list may be empty, but it is never <code>null</code>.
     */
00363     private List handlerActivations = new ArrayList();
    
    /**
     * The number of large updates that are currently going on. If this is
     * number is greater than zero, then UI updateActionBars is a no-op.
     * 
     * @since 3.1
     */
00371     private int largeUpdates = 0;

      private IExtensionTracker tracker;
    
    private IExtensionChangeHandler actionSetHandler = new IExtensionChangeHandler() {

        /* (non-Javadoc)
         * @see org.eclipse.core.runtime.dynamichelpers.IExtensionChangeHandler#addExtension(org.eclipse.core.runtime.dynamichelpers.IExtensionTracker, org.eclipse.core.runtime.IExtension)
         */
        public void addExtension(IExtensionTracker tracker, IExtension extension) {
            // this assumes that the workbench-level tracker will have already
            // updated the registry

            ArrayList setsToActivate = new ArrayList();
            // look for all new sets that are on by default. Examine the tracker
            // at the workbench level to see what descriptors are registered
            // against this extension
            Object[] registeredObjects = getWorkbench().getExtensionTracker()
                    .getObjects(extension);
            for (int i = 0; i < registeredObjects.length; i++) {
                if (registeredObjects[i] instanceof IActionSetDescriptor) {
                    IActionSetDescriptor desc = (IActionSetDescriptor) registeredObjects[i];
                    if (desc.isInitiallyVisible()) {
                        setsToActivate.add(desc);
                    }
                }
            }
            
            // if none of the new sets are marked as initially visible, abort.
            if (setsToActivate.isEmpty())
                return;
            
            IActionSetDescriptor[] descriptors = (IActionSetDescriptor[]) setsToActivate
                .toArray(new IActionSetDescriptor[setsToActivate.size()]);

            WorkbenchPage page = getActiveWorkbenchPage();
            if (page != null) {
                  Perspective[] perspectives = page.getOpenInternalPerspectives();
      
                  for (int i = 0; i < perspectives.length; i++) {
                    perspectives[i].turnOnActionSets(descriptors);
                  }
            }

            updateActionSets();
        }

        /* (non-Javadoc)
         * @see org.eclipse.core.runtime.dynamichelpers.IExtensionChangeHandler#removeExtension(org.eclipse.core.runtime.IExtension, java.lang.Object[])
         */
        public void removeExtension(IExtension extension, Object[] objects) {
            // remove the contributions from the window bars and dispose of the
            // actions
            for (int i = 0; i < objects.length; i++) {
                if (objects[i] instanceof PluginActionSetBuilder.Binding) {
                    PluginActionSetBuilder.Binding binding = (PluginActionSetBuilder.Binding) objects[i];
                    binding.builder.removeActionExtensions(binding.set, binding.window);
                    binding.set.dispose();
                }
            }

            // update all opened perspectives
            Perspective[] perspectives = getActiveWorkbenchPage()
                    .getOpenInternalPerspectives();
            boolean updateNeeded = true;
            for (int i = 0; i < perspectives.length; i++) {
                
                for (int j = 0; j < objects.length; j++) {
                    if (objects[j] instanceof IActionSetDescriptor) {
                        perspectives[i].removeActionSet((IActionSetDescriptor)objects[j]);
                    }
                }
            }

            if (updateNeeded) {
                // refresh the window
                updateActionSets();
            }
        }
    };
    

    void registerActionSets(IActionSet[] actionSets) {
        
        HashMap newActionSetHandlersByCommandId = new HashMap();
        
        /*
         * For each action in each action, create a new action handler. If there
         * are duplicates, then dispose of the earlier handler before clobbering
         * it. This avoids memory leaks.
         */
        for (int i = 0; i < actionSets.length; i++) {
            if (actionSets[i] instanceof PluginActionSet) {
                PluginActionSet pluginActionSet = (PluginActionSet) actionSets[i];
                IAction[] pluginActions = pluginActionSet.getPluginActions();

                for (int j = 0; j < pluginActions.length; j++) {
                    IAction pluginAction = pluginActions[j];
                    String commandId = pluginAction.getActionDefinitionId();

                    if (commandId != null) {
                        ActionHandler value = (ActionHandler)actionSetHandlersByCommandId
                                .get(commandId);
                        
                        // If we don't have a compatible handler already, create a new one
                        if (value == null || value.getAction() != pluginAction) {
                            value = new ActionHandler(pluginAction);
                        }

                        // In the bizarre event that we were given two IActions with the same
                        // command ID, dispose the old one before we clobber it 
                        ActionHandler clobberedHandler = (ActionHandler)newActionSetHandlersByCommandId.get(commandId);
                        if (clobberedHandler != null && clobberedHandler != value) {
                            clobberedHandler.dispose();
                        }
                        
                        // We either had a suitable handler already or we created a new one
                        // for the action. Add it to the new map.
                        
                        newActionSetHandlersByCommandId.put(commandId, value);                        
                    }
                }
            }
        }
        
        // Dispose any unused entries
        Collection entrySet = actionSetHandlersByCommandId.entrySet();
        
        Iterator iter = actionSetHandlersByCommandId.entrySet().iterator();
        
        while (iter.hasNext()) {
            Map.Entry entry = (Map.Entry)iter.next();
            
            Object key = entry.getKey();
            
            // If the old handler isn't being reused, dispose it.
            ActionHandler oldHandler = (ActionHandler)entry.getValue();
            ActionHandler newHandler = (ActionHandler)newActionSetHandlersByCommandId.get(key);
            if (oldHandler != newHandler) {
                oldHandler.dispose();
            }
        }
        
        actionSetHandlersByCommandId = newActionSetHandlersByCommandId;

        /* Submit the new amalgamated list of action set handlers and global
         * handlers.
         */
        submitActionSetAndGlobalHandlers();
    }

    void registerGlobalAction(IAction globalAction) {
        String commandId = globalAction.getActionDefinitionId();

        if (commandId != null) {
            final Object value = globalActionHandlersByCommandId.get(commandId);
            if (value instanceof ActionHandler) {
                // This handler is about to get clobbered, so dispose it.
                final ActionHandler handler = (ActionHandler) value;
                handler.dispose();
            }

            globalActionHandlersByCommandId.put(commandId, new ActionHandler(
                    globalAction));
        }

        submitActionSetAndGlobalHandlers();
    }

    /**
     * <p>
     * Submits the action handlers for action set actions and global actions.
     * Global actions are given priority, so that if a global action and an
     * action set action both handle the same command, the global action is
     * given priority.
     * </p>
     * <p>
     * These submissions are submitted as <code>Priority.LEGACY</code>, which
     * means that they are the lowest priority. This means that if a higher
     * priority submission handles the same command under the same conditions,
     * that that submission will become the handler.
     * </p>
     */
00554     void submitActionSetAndGlobalHandlers() {
            final IHandlerService handlerService = (IHandlerService) PlatformUI
                        .getWorkbench().getAdapter(IHandlerService.class);
            
        /* Mash the action sets and global actions together, with global actions
         * taking priority.
         */
        Map handlersByCommandId = new HashMap();
        handlersByCommandId.putAll(actionSetHandlersByCommandId);
        handlersByCommandId.putAll(globalActionHandlersByCommandId);
        
        List newHandlers = new ArrayList(handlersByCommandId.size());
        
        Iterator existingIter = handlerActivations.iterator();
        while (existingIter.hasNext()) {
            IHandlerActivation next = (IHandlerActivation) existingIter.next();
            
            String cmdId = next.getCommandId();
            
            Object handler = handlersByCommandId.get(cmdId);
            if (handler == next.getHandler()) {
                handlersByCommandId.remove(cmdId);
                newHandlers.add(next);
            } else {
                handlerService.deactivateHandler(next);
            }
        }
        
        final Shell shell = getShell();
        if (shell != null) {
                  final Expression expression = new ActiveShellExpression(shell);
            for (Iterator iterator = handlersByCommandId.entrySet().iterator(); iterator
                    .hasNext();) {
                Map.Entry entry = (Map.Entry) iterator.next();
                String commandId = (String) entry.getKey();
                IHandler handler = (IHandler) entry.getValue();
                        newHandlers.add(handlerService.activateHandler(commandId,
                        handler, expression, ActiveShellExpression.SOURCES
                                | ISources.LEGACY_LEGACY));
            }
        }
        
        handlerActivations = newHandlers;
    }

    /*
     * Adds an listener to the part service.
     */
00602     public void addPageListener(IPageListener l) {
        pageListeners.addPageListener(l);
    }

    /**
     * @see org.eclipse.ui.IPageService
     */
00609     public void addPerspectiveListener(org.eclipse.ui.IPerspectiveListener l) {
        perspectiveListeners.addPerspectiveListener(l);
    }

    /**
     * Configures this window to have a perspecive bar.
     * Does nothing if it already has one.
     */
00617     protected void addPerspectiveBar(int style) {
        Assert.isTrue(perspectiveSwitcher == null);
        perspectiveSwitcher = new PerspectiveSwitcher(this, topBar, style);
    }

    /**
     * Close the window.
     * 
     * Assumes that busy cursor is active.
     */
00627     private boolean busyClose() {
        // Whether the window was actually closed or not
        boolean windowClosed = false;

        // Setup internal flags to indicate window is in
        // progress of closing and no update should be done.
        closing = true;
        updateDisabled = true;

        try {
            // Only do the check if it is OK to close if we are not closing
            // via the workbench as the workbench will check this itself.
            Workbench workbench = getWorkbenchImpl();
            int count = workbench.getWorkbenchWindowCount();
            //also check for starting - if the first window dies on startup then we'll need to open a default window.
            if (!workbench.isStarting() && !workbench.isClosing() && count <= 1 && workbench.getWorkbenchConfigurer().getExitOnLastWindowClose()) {
                windowClosed = workbench.close();
            } else {
                if (okToClose()) {
                    windowClosed = hardClose();
                }
            }
        } finally {
            if (!windowClosed) {
                // Reset the internal flags if window was not closed.
                closing = false;
                updateDisabled = false;
            }
        }

        if (windowClosed && tracker != null)
            tracker.close();
        
        return windowClosed;
    }

    /**
     * Opens a new page. Assumes that busy cursor is active.
     * <p>
     * <b>Note:</b> Since release 2.0, a window is limited to contain at most
     * one page. If a page exist in the window when this method is used, then
     * another window is created for the new page.  Callers are strongly
     * recommended to use the <code>IWorkbench.openPerspective</code> APIs to
     * programmatically show a perspective.
     * </p>
     */
00673     protected IWorkbenchPage busyOpenPage(String perspID, IAdaptable input)
            throws WorkbenchException {
        IWorkbenchPage newPage = null;

        if (pageList.isEmpty()) {
            newPage = new WorkbenchPage(this, perspID, input);
            pageList.add(newPage);
            firePageOpened(newPage);
            setActivePage(newPage);
        } else {
            IWorkbenchWindow window = getWorkbench().openWorkbenchWindow(
                    perspID, input);
            newPage = window.getActivePage();
        }

        return newPage;
    }

    /**
     * @see Window
     */
00694     public int open() {
      if (getPages().length == 0) {
            showEmptyWindowContents();
      }
        fireWindowCreated();
        getWindowAdvisor().openIntro();
        int result = super.open();
        fireWindowOpened();
        if (perspectiveSwitcher != null) {
            perspectiveSwitcher.updatePerspectiveBar();
            perspectiveSwitcher.updateBarParent();
        }
        return result;
    }

    /* (non-Javadoc)
     * Method declared on Window.
     */
00712     protected boolean canHandleShellCloseEvent() {
        if (!super.canHandleShellCloseEvent()) {
            return false;
        }
        // let the advisor or other interested parties
        // veto the user's explicit request to close the window
        return fireWindowShellClosing();
    }

    /**
     * @see IWorkbenchWindow
     */
00724     public boolean close() {
        final boolean[] ret = new boolean[1];
        BusyIndicator.showWhile(null, new Runnable() {
            public void run() {
                ret[0] = busyClose();
            }
        });
        return ret[0];
    }

    protected boolean isClosing() {
        return closing || getWorkbenchImpl().isClosing();
    }

    /**
     * Return whether or not the coolbar layout is locked.
     */
00741     protected boolean isCoolBarLocked() {
        CoolBarManager cbm = getCoolBarManager(); 
        return cbm != null && cbm.getLockLayout();
    }

    /**
     * Close all of the pages.
     */
00749     private void closeAllPages() {
        // Deactivate active page.
        setActivePage(null);

        // Clone and deref all so that calls to getPages() returns
        // empty list (if call by pageClosed event handlers)
        PageList oldList = pageList;
        pageList = new PageList();

        // Close all.
        Iterator itr = oldList.iterator();
        while (itr.hasNext()) {
            WorkbenchPage page = (WorkbenchPage) itr.next();
            firePageClosed(page);
            page.dispose();
        }
        if (!closing)
            showEmptyWindowContents();
    }

    /**
     * Save and close all of the pages.
     */
00772     public void closeAllPages(boolean save) {
        if (save) {
            boolean ret = saveAllPages(true);
            if (!ret)
                return;
        }
        closeAllPages();
    }

    /**
     * closePerspective method comment.
     */
00784     protected boolean closePage(IWorkbenchPage in, boolean save) {
        // Validate the input.
        if (!pageList.contains(in))
            return false;
        WorkbenchPage oldPage = (WorkbenchPage) in;

        // Save old perspective.
        if (save && oldPage.isSaveNeeded()) {
            if (!oldPage.saveAllEditors(true))
                return false;
        }

        // If old page is activate deactivate.
        boolean oldIsActive = (oldPage == getActiveWorkbenchPage());
        if (oldIsActive)
            setActivePage(null);

        // Close old page. 
        pageList.remove(oldPage);
        firePageClosed(oldPage);
        oldPage.dispose();

        // Activate new page.
        if (oldIsActive) {
            IWorkbenchPage newPage = pageList.getNextActive();
            if (newPage != null)
                setActivePage(newPage);
        }
        if (!closing && pageList.isEmpty())
            showEmptyWindowContents();
        return true;
    }

    private void showEmptyWindowContents() {
        if (!emptyWindowContentsCreated) {
            Composite parent = getPageComposite();
              emptyWindowContents = getWindowAdvisor().createEmptyWindowContents(parent);
              emptyWindowContentsCreated = true;
            // force the empty window composite to be layed out
              ((StackLayout) parent.getLayout()).topControl = emptyWindowContents;
            parent.layout();
        }
    }
    
    private void hideEmptyWindowContents() {
        if (emptyWindowContentsCreated) {
            if (emptyWindowContents != null) {
                emptyWindowContents.dispose();
                emptyWindowContents = null;
                getPageComposite().layout();
            }
            emptyWindowContentsCreated = false;
        }
    }

    /* (non-Javadoc)
     * @see org.eclipse.jface.window.Window#configureShell(org.eclipse.swt.widgets.Shell)
     */
00842     protected void configureShell(Shell shell) {
        super.configureShell(shell);

        detachedWindowShells = new ShellPool(shell, SWT.TOOL | SWT.TITLE | SWT.MAX | SWT.RESIZE | getDefaultOrientation());
        
        String title = getWindowConfigurer().basicGetTitle();
        if (title != null) {
            shell.setText(title);
        }

            final IWorkbench workbench = getWorkbench();
            workbench.getHelpSystem().setHelp(shell,
                        IWorkbenchHelpContextIds.WORKBENCH_WINDOW);
            final IContextService contextService = (IContextService) workbench
                        .getAdapter(IContextService.class);
            contextService.registerShell(shell, IContextService.TYPE_WINDOW);

        trackShellActivation(shell);
        trackShellResize(shell);
    }
    
    /* package */ ShellPool getDetachedWindowPool() {
        return detachedWindowShells;
    }

    /* (non-Javadoc)
     * @see org.eclipse.jface.window.ApplicationWindow#createTrimWidgets(org.eclipse.swt.widgets.Shell)
     */
00870     protected void createTrimWidgets(Shell shell) {
        // do nothing -- trim widgets are created in createDefaultContents
    }

    /**
     * Creates and remembers the client composite, under which workbench
     * pages create their controls.
     * 
     * @since 3.0
     */
00880     protected Composite createPageComposite(Composite parent) {
        pageComposite = new Composite(parent, SWT.NONE);
        // use a StackLayout instead of a FillLayout (see bug 81460 [Workbench] (regression) Close all perspectives, open Java perspective, layout wrong)
        pageComposite.setLayout(new StackLayout());        
        return pageComposite;
    }

    /**
     * Creates the contents of the workbench window, including
     * trim controls and the client composite.
     * This MUST create the client composite via a call to
     * <code>createClientComposite</code>.
     * 
     * @since 3.0
     */
00895     protected Control createContents(Composite parent) {
        // we know from Window.create that the parent is a Shell.
        getWindowAdvisor().createWindowContents((Shell) parent);
        // the page composite must be set by createWindowContents
        Assert
                .isNotNull(pageComposite,
                        "createWindowContents must call configurer.createPageComposite"); //$NON-NLS-1$
        return pageComposite;
    }

    /**
     * If the perspective bar is drawn on the top right corner of the window,
     * then this method changes its appearance from curved to square. This
     * should have its own preference, but for now it piggy-backs on the
     * SHOW_TRADITIONAL_STYLE_TABS preference.
     * 
     * @param square
     *            true for a square banner and false otherwise
     */
00914     public void setBannerCurve(boolean square) {
        if (topBar != null)
            topBar.setSimple(square);
    }

    /**
     * Creates the default contents and layout of the shell. 
     * 
     * @param shell the shell
     */
00924     protected void createDefaultContents(final Shell shell) {
        defaultLayout = new TrimLayout();
        defaultLayout.setSpacing(5, 5, 2, 2);
        shell.setLayout(defaultLayout);

        Menu menuBar = getMenuBarManager().createMenuBar(shell);
        if (getWindowConfigurer().getShowMenuBar()) {
            shell.setMenuBar(menuBar);
        }

        // Create the CBanner widget which parents both the Coolbar
        // and the perspective switcher, and supports some configurations
        // on the left right and bottom
        topBar = new CBanner(shell, SWT.NONE);

        // the banner gets a curve along with the new tab style
        // TODO create a dedicated preference for this
        setBannerCurve(PrefUtil.getAPIPreferenceStore().getBoolean(
                IWorkbenchPreferenceConstants.SHOW_TRADITIONAL_STYLE_TABS));

        CacheWrapper coolbarCacheWrapper = new CacheWrapper(topBar);

        final Control coolBar = createCoolBarControl(coolbarCacheWrapper
                .getControl());
        // need to resize the shell, not just the coolbar's immediate
        // parent, if the coolbar wants to grow or shrink

        coolBar.addListener(SWT.Resize, new Listener() {
            public void handleEvent(Event event) {
                // If the user is dragging the sash then we will need to force
                // a resize. However, if the coolbar was resized programatically
                // then everything is already layed out correctly. There is no
                // direct way to tell the difference between these cases, however
                // we take advantage of the fact that dragging the sash does not
                // change the size of the shell, and only force another layout
                // if the shell size is unchanged.
                Rectangle clientArea = shell.getClientArea();

                if (lastShellSize.x == clientArea.width
                        && lastShellSize.y == clientArea.height) {
                    LayoutUtil.resize(coolBar);
                }

                lastShellSize.x = clientArea.width;
                lastShellSize.y = clientArea.height;
            }
        });

        if (getWindowConfigurer().getShowCoolBar()) {
            topBar.setLeft(coolbarCacheWrapper.getControl());
        }

        createStatusLine(shell);

        fastViewBar = new FastViewBar(this);
        fastViewBar.createControl(shell);

        if (getWindowConfigurer().getShowPerspectiveBar()) {
            addPerspectiveBar(perspectiveBarStyle());
            perspectiveSwitcher.createControl(shell);
        }

        createProgressIndicator(shell);

            if (getShowHeapStatus()) {
                  createHeapStatus(shell);
            }
        trimDropTarget = new TrimDropTarget(shell, this);
        DragUtil.addDragTarget(shell, trimDropTarget);

        // Create the client composite area (where page content goes).
        createPageComposite(shell);

        setLayoutDataForContents();
    }

      /**
       * Returns whether the heap status indicator should be shown.
       * 
       * @return <code>true</code> to show the heap status indicator, <code>false</code> otherwise
       */
01005       private boolean getShowHeapStatus() {
            return Boolean.valueOf(
                        Platform.getDebugOption(PlatformUI.PLUGIN_ID
                                    + "/perf/showHeapStatus")).booleanValue(); //$NON-NLS-1$
      }

      /**
       * Creates the controls for the heap status indicator.
       * 
       * @param parent the parent composite
       */
01016       private void createHeapStatus(Composite parent) {
            heapStatus = new HeapStatus(parent, PrefUtil.getInternalPreferenceStore());
      }
      
    /**
     * Set the perspective bar location
     * 
     * @param location the location to place the bar
     */
01025     public void setPerspectiveBarLocation(String location) {
        if (perspectiveSwitcher != null)
            perspectiveSwitcher.setPerspectiveBarLocation(location);
    }

    /**
     * Notifies interested parties (namely the advisor)
     * that the window is about to be opened.
     * 
     * @since 3.1
     */
01036     private void fireWindowOpening() {
        // let the application do further configuration
        getWindowAdvisor().preWindowOpen();
    }

    /**
     * Notifies interested parties (namely the advisor) that the
     * window has been restored from a previously saved state.
     * 
     * @throws WorkbenchException passed through from the advisor
     * @since 3.1
     */
01048     void fireWindowRestored() throws WorkbenchException {
        getWindowAdvisor().postWindowRestore();
    }

    /**
     * Notifies interested parties (namely the advisor)
     * that the window has been created.
     * 
     * @since 3.1
     */
01058     private void fireWindowCreated() {
        getWindowAdvisor().postWindowCreate();
    }

    /**
     * Notifies interested parties (namely the advisor and the
     * window listeners) that the window has been opened.
     * 
     * @since 3.1
     */
01068     private void fireWindowOpened() {
        getWorkbenchImpl().fireWindowOpened(this);
        getWindowAdvisor().postWindowOpen();
    }

    /**
     * Notifies interested parties (namely the advisor)
     * that the window's shell is closing.  Allows
     * the close to be vetoed.
     * 
     * @return <code>true</code> if the close should proceed,
     *   <code>false</code> if it should be canceled
     * @since 3.1
     */
01082     private boolean fireWindowShellClosing() {
        return getWindowAdvisor().preWindowShellClose();
    }

    /**
     * Notifies interested parties (namely the advisor and the
     * window listeners) that the window has been closed.
     * 
     * @since 3.1
     */
01092     private void fireWindowClosed() {
        // let the application do further deconfiguration
        getWindowAdvisor().postWindowClose();
        getWorkbenchImpl().fireWindowClosed(this);
    }

    /**
     * Fires page activated
     */
01101     private void firePageActivated(IWorkbenchPage page) {
        String label = null; // debugging only
        if (UIStats.isDebugging(UIStats.NOTIFY_PAGE_LISTENERS)) {
            label = "activated " + page.getLabel(); //$NON-NLS-1$
        }
        try {
              UIStats.start(UIStats.NOTIFY_PAGE_LISTENERS, label);
            UIListenerLogging.logPageEvent(this, page, UIListenerLogging.WPE_PAGE_ACTIVATED);
              pageListeners.firePageActivated(page);
              partService.pageActivated(page);
        } finally {
            UIStats.end(UIStats.NOTIFY_PAGE_LISTENERS, page.getLabel(), label);
        }
    }

    /**
     * Fires page closed
     */
01119     private void firePageClosed(IWorkbenchPage page) {
        String label = null; // debugging only
        if (UIStats.isDebugging(UIStats.NOTIFY_PAGE_LISTENERS)) {
            label = "closed " + page.getLabel(); //$NON-NLS-1$
        }
        try {
              UIStats.start(UIStats.NOTIFY_PAGE_LISTENERS, label);
            UIListenerLogging.logPageEvent(this, page, UIListenerLogging.WPE_PAGE_CLOSED);
              pageListeners.firePageClosed(page);
              partService.pageClosed(page);
        } finally {
            UIStats.end(UIStats.NOTIFY_PAGE_LISTENERS, page.getLabel(), label);
        }

    }

    /**
     * Fires page opened
     */
01138     private void firePageOpened(IWorkbenchPage page) {
        String label = null; // debugging only
        if (UIStats.isDebugging(UIStats.NOTIFY_PAGE_LISTENERS)) {
            label = "opened " + page.getLabel(); //$NON-NLS-1$
        }
        try {             
            UIStats.start(UIStats.NOTIFY_PAGE_LISTENERS, label);
            UIListenerLogging.logPageEvent(this, page, UIListenerLogging.WPE_PAGE_OPENED);
            pageListeners.firePageOpened(page);
            partService.pageOpened(page);
        } finally {
            UIStats.end(UIStats.NOTIFY_PAGE_LISTENERS, page.getLabel(), label);
        }
    }

    /**
     * Fires perspective activated
     */
01156     void firePerspectiveActivated(IWorkbenchPage page,
            IPerspectiveDescriptor perspective) {
        UIListenerLogging.logPerspectiveEvent(this, page, perspective, UIListenerLogging.PLE_PERSP_ACTIVATED);
        perspectiveListeners.firePerspectiveActivated(page, perspective);
    }

    /**
     * Fires perspective deactivated.
     * 
     * @since 3.1
     */
01167     void firePerspectiveDeactivated(IWorkbenchPage page,
            IPerspectiveDescriptor perspective) {
        UIListenerLogging.logPerspectiveEvent(this, page, perspective, UIListenerLogging.PLE_PERSP_DEACTIVATED);
      perspectiveListeners.firePerspectiveDeactivated(page, perspective);
    }
    
    /**
     * Fires perspective changed
     */
01176     void firePerspectiveChanged(IWorkbenchPage page,
            IPerspectiveDescriptor perspective, String changeId) {
        // Some callers call this even when there is no active perspective.
        // Just ignore this case.
        if (perspective != null) {
            UIListenerLogging.logPerspectiveChangedEvent(this, page, perspective, null, changeId);
            perspectiveListeners.firePerspectiveChanged(page, perspective,
                    changeId);
        }
    }

    /**
     * Fires perspective changed for an affected part
     */
01190     void firePerspectiveChanged(IWorkbenchPage page,
            IPerspectiveDescriptor perspective,
            IWorkbenchPartReference partRef, String changeId) {
        // Some callers call this even when there is no active perspective.
        // Just ignore this case.
        if (perspective != null) {
            UIListenerLogging.logPerspectiveChangedEvent(this, page, perspective, partRef, changeId);
            perspectiveListeners.firePerspectiveChanged(page, perspective,
                    partRef, changeId);
        }
    }

    /**
     * Fires perspective closed
     */
01205     void firePerspectiveClosed(IWorkbenchPage page,
            IPerspectiveDescriptor perspective) {
        UIListenerLogging.logPerspectiveEvent(this, page, perspective, UIListenerLogging.PLE_PERSP_CLOSED);
      perspectiveListeners.firePerspectiveClosed(page, perspective);
    }

    /**
     * Fires perspective opened
     */
01214     void firePerspectiveOpened(IWorkbenchPage page,
            IPerspectiveDescriptor perspective) {
        UIListenerLogging.logPerspectiveEvent(this, page, perspective, UIListenerLogging.PLE_PERSP_OPENED);
      perspectiveListeners.firePerspectiveOpened(page, perspective);
    }

    /**
     * Fires perspective saved as.
     * 
     * @since 3.1
     */
01225     void firePerspectiveSavedAs(IWorkbenchPage page,
            IPerspectiveDescriptor oldPerspective, IPerspectiveDescriptor newPerspective) {
        UIListenerLogging.logPerspectiveSavedAs(this, page, oldPerspective, newPerspective);
      perspectiveListeners.firePerspectiveSavedAs(page, oldPerspective, newPerspective);
    }

    /**
     * Returns the action bars for this window.
     */
01234     public WWinActionBars getActionBars() {
        if (actionBars == null) {
            actionBars = new WWinActionBars(this);
        }
        return actionBars;
    }

    /**
     * Returns the active page.
     *
     * @return the active page
     */
01246     public IWorkbenchPage getActivePage() {
        return pageList.getActive();
    }

    /**
     * Returns the active workbench page.
     *
     * @return the active workbench page
     */
    /* package */
01256     WorkbenchPage getActiveWorkbenchPage() {
        return pageList.getActive();
    }

    /**
     * Returns the page composite, under which the window's pages create
     * their controls.
     */
01264     protected Composite getPageComposite() {
        return pageComposite;
    }

    /**
     * Answer the menu manager for this window.
     */
01271     public MenuManager getMenuManager() {
        return getMenuBarManager();
    }

    /**
     * Returns the number.  This corresponds to a page number in a window or a
     * window number in the workbench.
     */
01279     public int getNumber() {
        return number;
    }

    /**
     * Returns an array of the pages in the workbench window.
     *
     * @return an array of pages
     */
01288     public IWorkbenchPage[] getPages() {
        return pageList.getPages();
    }

    /**
     * @see IWorkbenchWindow
     */
01295     public IPartService getPartService() {
        return partService;
    }

    /**
     * Returns the layout for the shell.
     * 
     * @return the layout for the shell
     */
01304     protected Layout getLayout() {
        return null;
    }

    /**
     * @see IWorkbenchWindow
     */
01311     public ISelectionService getSelectionService() {
        return partService.getSelectionService();
    }

    /**
     * Returns <code>true</code> when the window's shell
     * is activated, <code>false</code> when it's shell is
     * deactivated
     * 
     * @return boolean <code>true</code> when shell activated,
     *            <code>false</code> when shell deactivated
     */
01323     public boolean getShellActivated() {
        return shellActivated;
    }

    /**
     * Returns the status line manager for this window (if it has one).
     *
     * @return the status line manager, or <code>null</code> if
     *   this window does not have a status line
     * @see #addStatusLine
     */
01334     public StatusLineManager getStatusLineManager() {
        return super.getStatusLineManager();
    }

    /**
     * @see IWorkbenchWindow
     */
01341     public IWorkbench getWorkbench() {
        return PlatformUI.getWorkbench();
    }

    public String getToolbarLabel(String actionSetId) {
        ActionSetRegistry registry = WorkbenchPlugin.getDefault()
                .getActionSetRegistry();
        IActionSetDescriptor actionSet = registry.findActionSet(actionSetId);
        if (actionSet != null) {
            return actionSet.getLabel();
        } else {
            if (IWorkbenchActionConstants.TOOLBAR_FILE
                    .equalsIgnoreCase(actionSetId))
                return WorkbenchMessages.WorkbenchWindow_FileToolbar;
            if (IWorkbenchActionConstants.TOOLBAR_NAVIGATE
                    .equalsIgnoreCase(actionSetId))
                return WorkbenchMessages.WorkbenchWindow_NavigateToolbar;
        }
        return null;
    }

    /**
     * Unconditionally close this window. Assumes the proper
     * flags have been set correctly (e.i. closing and updateDisabled)
     */
01366     private boolean hardClose() {
        boolean result;
        try {
            // Clear the action sets, fix for bug 27416.
            actionPresentation.clearActionSets();

            // Remove the handler submissions. Bug 64024.
            final IWorkbench workbench = getWorkbench();
                  final IHandlerService handlerService = (IHandlerService) workbench
                              .getAdapter(IHandlerService.class);
                  handlerService.deactivateHandlers(handlerActivations);
                  final Iterator activationItr = handlerActivations.iterator();
                  while (activationItr.hasNext()) {
                        final IHandlerActivation activation = (IHandlerActivation) activationItr
                                    .next();
                        activation.getHandler().dispose();
                  }
            handlerActivations.clear();
            actionSetHandlersByCommandId.clear();
            globalActionHandlersByCommandId.clear();

            // Remove the enabled submissions. Bug 64024.
                  final IContextService contextService = (IContextService) workbench
                              .getAdapter(IContextService.class);
            contextService.unregisterShell(getShell());

            closeAllPages();
            
            fireWindowClosed();

            getActionBarAdvisor().dispose();
            getWindowAdvisor().dispose();
            detachedWindowShells.dispose();
            
            // Null out the progress region.  Bug 64024.
            progressRegion = null;
        } finally {
            result = super.close();
        }
        return result;
    }

    /**
     * @see IWorkbenchWindow
     */
01411     public boolean isApplicationMenu(String menuID) {
        // delegate this question to the action bar advisor
        return getActionBarAdvisor().isApplicationMenu(menuID);
    }

    /**
     * Return whether or not the given id matches the id of the coolitems that
     * the application creates.
     */
    /* package */
01421     boolean isWorkbenchCoolItemId(String id) {
        return windowConfigurer.containsCoolItem(id);
    }

    /**
     * Locks/unlocks the CoolBar for the workbench.
     * 
     * @param lock whether the CoolBar should be locked or unlocked
     */
    /* package */
01431     void lockCoolBar(boolean lock) {
        getCoolBarManager().setLockLayout(lock);
    }

    /**
     * Makes the window visible and frontmost.
     */
01438     void makeVisible() {
      Shell shell = getShell();
      if (shell != null && !shell.isDisposed()) {
            // see bug 96700 and bug 4414 for a discussion on the use of open() here
            shell.open();
      }
    }
    
    /**
     * Called when this window is about to be closed.
     *
     * Subclasses may overide to add code that returns <code>false</code> 
     * to prevent closing under certain conditions.
     */
01452     public boolean okToClose() {
        // Save all of the editors.
        if (!getWorkbenchImpl().isClosing())
            if (!saveAllPages(true))
                return false;
        return true;
    }

    /**
     * Opens a new page.
     * <p>
     * <b>Note:</b> Since release 2.0, a window is limited to contain at most
     * one page. If a page exist in the window when this method is used, then
     * another window is created for the new page.  Callers are strongly
     * recommended to use the <code>IWorkbench.openPerspective</code> APIs to
     * programmatically show a perspective.
     * </p>
     */
01470     public IWorkbenchPage openPage(final String perspId, final IAdaptable input)
            throws WorkbenchException {
        Assert.isNotNull(perspId);

        // Run op in busy cursor.
        final Object[] result = new Object[1];
        BusyIndicator.showWhile(null, new Runnable() {
            public void run() {
                try {
                    result[0] = busyOpenPage(perspId, input);
                } catch (WorkbenchException e) {
                    result[0] = e;
                }
            }
        });

        if (result[0] instanceof IWorkbenchPage)
            return (IWorkbenchPage) result[0];
        else if (result[0] instanceof WorkbenchException)
            throw (WorkbenchException) result[0];
        else
            throw new WorkbenchException(WorkbenchMessages.WorkbenchWindow_exceptionMessage);
    }

    /**
     * Opens a new page. 
     * <p>
     * <b>Note:</b> Since release 2.0, a window is limited to contain at most
     * one page. If a page exist in the window when this method is used, then
     * another window is created for the new page.  Callers are strongly
     * recommended to use the <code>IWorkbench.openPerspective</code> APIs to
     * programmatically show a perspective.
     * </p>
     */
01504     public IWorkbenchPage openPage(IAdaptable input) throws WorkbenchException {
        String perspId = getWorkbenchImpl().getPerspectiveRegistry()
                .getDefaultPerspective();
        return openPage(perspId, input);
    }

    /*
     * Removes an listener from the part service.
     */
01513     public void removePageListener(IPageListener l) {
        pageListeners.removePageListener(l);
    }

    /**
     * @see org.eclipse.ui.IPageService
     */
01520     public void removePerspectiveListener(org.eclipse.ui.IPerspectiveListener l) {
        perspectiveListeners.removePerspectiveListener(l);
    }

    private IStatus unableToRestorePage(IMemento pageMem) {
        String pageName = pageMem.getString(IWorkbenchConstants.TAG_LABEL);
        if (pageName == null)
            pageName = ""; //$NON-NLS-1$
        return new Status(
                IStatus.ERROR,
                PlatformUI.PLUGIN_ID,
                0,
                NLS.bind(WorkbenchMessages.WorkbenchWindow_unableToRestorePerspective, pageName),
                null);
    }

    /**
     * @see IPersistable.
     */
01539     public IStatus restoreState(IMemento memento,
            IPerspectiveDescriptor activeDescriptor) {
        Assert.isNotNull(getShell());

        MultiStatus result = new MultiStatus(
                PlatformUI.PLUGIN_ID,
                IStatus.OK,
                WorkbenchMessages.WorkbenchWindow_problemsRestoringWindow, null); 
            
            // Restore the window advisor state.
            IMemento windowAdvisorState = memento.getChild(
                        IWorkbenchConstants.TAG_WORKBENCH_WINDOW_ADVISOR);
            if (windowAdvisorState != null)
                  result.add(getWindowAdvisor().restoreState(windowAdvisorState));
            
            // Restore actionbar advisor state.
            IMemento actionBarAdvisorState = memento
                        .getChild(IWorkbenchConstants.TAG_ACTION_BAR_ADVISOR);
            if (actionBarAdvisorState != null)
                  result.add(getActionBarAdvisor().restoreState(actionBarAdvisorState));

        // Read window's bounds and state.
        Rectangle displayBounds = getShell().getDisplay().getBounds();
        Rectangle shellBounds = new Rectangle(0, 0, 0, 0);

        IMemento fastViewMem = memento
                .getChild(IWorkbenchConstants.TAG_FAST_VIEW_DATA);
        if (fastViewMem != null) {
            if (fastViewBar != null) {
                fastViewBar.restoreState(fastViewMem);
            }
        }
        Integer bigInt = memento.getInteger(IWorkbenchConstants.TAG_X);
        shellBounds.x = bigInt == null ? 0 : bigInt.intValue();
        bigInt = memento.getInteger(IWorkbenchConstants.TAG_Y);
        shellBounds.y = bigInt == null ? 0 : bigInt.intValue();
        bigInt = memento.getInteger(IWorkbenchConstants.TAG_WIDTH);
        shellBounds.width = bigInt == null ? 0 : bigInt.intValue();
        bigInt = memento.getInteger(IWorkbenchConstants.TAG_HEIGHT);
        shellBounds.height = bigInt == null ? 0 : bigInt.intValue();
        if (!shellBounds.isEmpty()) {
            if (!shellBounds.intersects(displayBounds)) {
                Rectangle clientArea = getShell().getDisplay().getClientArea();
                shellBounds.x = clientArea.x;
                shellBounds.y = clientArea.y;
            }
            getShell().setBounds(shellBounds);
        }
        if ("true".equals(memento.getString(IWorkbenchConstants.TAG_MAXIMIZED))) { //$NON-NLS-1$
            getShell().setMaximized(true);
        }
        if ("true".equals(memento.getString(IWorkbenchConstants.TAG_MINIMIZED))) { //$NON-NLS-1$
            //          getShell().setMinimized(true);
        }

        // restore the width of the perspective bar
        if (perspectiveSwitcher != null)
            perspectiveSwitcher.restoreState(memento);

        // Restore the cool bar order by creating all the tool bar contribution items
        // This needs to be done before pages are created to ensure proper canonical creation
        // of cool items
        if (getCoolBarManager() != null) {
            CoolBarManager coolBarMgr = getCoolBarManager();
            IMemento coolBarMem = memento
                    .getChild(IWorkbenchConstants.TAG_COOLBAR_LAYOUT);
            if (coolBarMem != null) {
                // Check if the layout is locked
                Integer lockedInt = coolBarMem
                        .getInteger(IWorkbenchConstants.TAG_LOCKED);
                if ((lockedInt != null) && (lockedInt.intValue() == 1)) {
                    coolBarMgr.setLockLayout(true);
                } else {
                    coolBarMgr.setLockLayout(false);
                }
                // The new layout of the cool bar manager
                ArrayList coolBarLayout = new ArrayList();
                // Traverse through all the cool item in the memento
                IMemento contributionMems[] = coolBarMem
                        .getChildren(IWorkbenchConstants.TAG_COOLITEM);
                for (int i = 0; i < contributionMems.length; i++) {
                    IMemento contributionMem = contributionMems[i];
                    String type = contributionMem
                            .getString(IWorkbenchConstants.TAG_ITEM_TYPE);
                    if (type == null) {
                        // Do not recognize that type
                        continue;
                    }
                    String id = contributionMem
                            .getString(IWorkbenchConstants.TAG_ID);

                    // Prevent duplicate items from being read back in.
                    IContributionItem existingItem = coolBarMgr.find(id);
                    if ((id != null) && (existingItem != null)) {
                        if (Policy.DEBUG_TOOLBAR_DISPOSAL) {
                            System.out
                                    .println("Not loading duplicate cool bar item: " + id); //$NON-NLS-1$
                        }
                        coolBarLayout.add(existingItem);
                        continue;
                    }
                    IContributionItem newItem = null;
                    if (type.equals(IWorkbenchConstants.TAG_TYPE_SEPARATOR)) {
                        if (id != null) {
                            newItem = new Separator(id);
                        } else {
                            newItem = new Separator();
                        }
                    } else if (id != null) {
                        if (type
                                .equals(IWorkbenchConstants.TAG_TYPE_GROUPMARKER)) {
                            newItem = new GroupMarker(id);

                        } else if (type
                                .equals(IWorkbenchConstants.TAG_TYPE_TOOLBARCONTRIBUTION)
                                || type
                                        .equals(IWorkbenchConstants.TAG_TYPE_PLACEHOLDER)) {

                            // Get Width and height
                            Integer width = contributionMem
                                    .getInteger(IWorkbenchConstants.TAG_ITEM_X);
                            Integer height = contributionMem
                                    .getInteger(IWorkbenchConstants.TAG_ITEM_Y);
                            // Look for the object in the current cool bar manager
                            IContributionItem oldItem = coolBarMgr.find(id);
                            // If a tool bar contribution item already exists for this id then use the old object
                            if (oldItem != null) {
                                newItem = oldItem;
                            } else {
                                newItem = new ToolBarContributionItem(
                                        new ToolBarManager(coolBarMgr
                                                .getStyle()), id);
                                if (type
                                        .equals(IWorkbenchConstants.TAG_TYPE_PLACEHOLDER)) {
                                    ToolBarContributionItem newToolBarItem = (ToolBarContributionItem) newItem;
                                    if (height != null) {
                                        newToolBarItem.setCurrentHeight(height
                                                .intValue());
                                    }
                                    if (width != null) {
                                        newToolBarItem.setCurrentWidth(width
                                                .intValue());
                                    }
                                    newItem = new PlaceholderContributionItem(
                                            newToolBarItem);
                                }
                                // make it invisible by default
                                newItem.setVisible(false);
                                // Need to add the item to the cool bar manager so that its canonical order can be preserved
                                IContributionItem refItem = findAlphabeticalOrder(
                                        IWorkbenchActionConstants.MB_ADDITIONS,
                                        id, coolBarMgr);
                                if (refItem != null) {
                                    coolBarMgr.insertAfter(refItem.getId(),
                                            newItem);
                                } else {
                                    coolBarMgr.add(newItem);
                                }
                            }
                            // Set the current height and width
                            if ((width != null)
                                    && (newItem instanceof ToolBarContributionItem)) {
                                ((ToolBarContributionItem) newItem)
                                        .setCurrentWidth(width.intValue());
                            }
                            if ((height != null)
                                    && (newItem instanceof ToolBarContributionItem)) {
                                ((ToolBarContributionItem) newItem)
                                        .setCurrentHeight(height.intValue());
                            }
                        }
                    }
                    // Add new item into cool bar manager
                    if (newItem != null) {
                        coolBarLayout.add(newItem);
                        newItem.setParent(coolBarMgr);
                        coolBarMgr.markDirty();
                    }
                }

                // We need to check if we have everything we need in the layout.
                final ArrayList finalLayout = new ArrayList();
                IContributionItem[] existingItems = coolBarMgr.getItems();
                for (int i = 0; i < existingItems.length; i++) {
                    IContributionItem existingItem = existingItems[i];

                    /* This line shouldn't be necessary, but is here for
                     * robustness.
                     */
                    if (existingItem == null) {
                        continue;
                    }

                    boolean found = false;
                    Iterator layoutItemItr = coolBarLayout.iterator();
                    while (layoutItemItr.hasNext()) {
                        IContributionItem layoutItem = (IContributionItem) layoutItemItr
                                .next();
                        if ((layoutItem != null)
                                && (layoutItem.equals(existingItem))) {
                            found = true;
                            break;
                        }
                    }

                    if (!found) {
                        if (existingItem != null) {
                            finalLayout.add(existingItem);
                        }
                    }
                }

                // Set the cool bar layout to the given layout.
                finalLayout.addAll(coolBarLayout);
                IContributionItem[] itemsToSet = new IContributionItem[finalLayout
                        .size()];
                finalLayout.toArray(itemsToSet);
                coolBarMgr.setItems(itemsToSet);
            } else {
                // For older workbenchs
                coolBarMem = memento
                        .getChild(IWorkbenchConstants.TAG_TOOLBAR_LAYOUT);
                if (coolBarMem != null) {
                    // Restore an older layout
                    restoreOldCoolBar(coolBarMem);
                }
            }
        }

        // Recreate each page in the window. 
        IWorkbenchPage newActivePage = null;
        IMemento[] pageArray = memento
                .getChildren(IWorkbenchConstants.TAG_PAGE);
        for (int i = 0; i < pageArray.length; i++) {
            IMemento pageMem = pageArray[i];
            String strFocus = pageMem.getString(IWorkbenchConstants.TAG_FOCUS);
            if (strFocus == null || strFocus.length() == 0)
                continue;

            // Get the input factory.
            IAdaptable input = null;
            IMemento inputMem = pageMem.getChild(IWorkbenchConstants.TAG_INPUT);
            if (inputMem != null) {
                String factoryID = inputMem
                        .getString(IWorkbenchConstants.TAG_FACTORY_ID);
                if (factoryID == null) {
                    WorkbenchPlugin
                            .log("Unable to restore page - no input factory ID."); //$NON-NLS-1$
                    result.add(unableToRestorePage(pageMem));
                    continue;
                }
                try {
                    UIStats.start(UIStats.RESTORE_WORKBENCH,
                            "WorkbenchPageFactory"); //$NON-NLS-1$
                    IElementFactory factory = PlatformUI.getWorkbench()
                            .getElementFactory(factoryID);
                    if (factory == null) {
                        WorkbenchPlugin
                                .log("Unable to restore page - cannot instantiate input factory: " + factoryID); //$NON-NLS-1$
                        result.add(unableToRestorePage(pageMem));
                        continue;
                    }

                    // Get the input element.
                    input = factory.createElement(inputMem);
                    if (input == null) {
                        WorkbenchPlugin
                                .log("Unable to restore page - cannot instantiate input element: " + factoryID); //$NON-NLS-1$
                        result.add(unableToRestorePage(pageMem));
                        continue;
                    }
                } finally {
                    UIStats.end(UIStats.RESTORE_WORKBENCH, factoryID,
                            "WorkbenchPageFactory"); //$NON-NLS-1$
                }
            }
            // Open the perspective.
            WorkbenchPage newPage = null;
            try {
                newPage = new WorkbenchPage(this, input);
                result.add(newPage.restoreState(pageMem, activeDescriptor));
                pageList.add(newPage);
                firePageOpened(newPage);
            } catch (WorkbenchException e) {
                WorkbenchPlugin
                        .log("Unable to restore perspective - constructor failed.", e); //$NON-NLS-1$
                result.add(e.getStatus());
                continue;
            }

            if (strFocus != null && strFocus.length() > 0)
                newActivePage = newPage;
        }

        // If there are no pages create a default.
        if (pageList.isEmpty()) {
            try {
                String defPerspID = getWorkbenchImpl().getPerspectiveRegistry()
                        .getDefaultPerspective();
                if (defPerspID != null) {
                      WorkbenchPage newPage = new WorkbenchPage(this, defPerspID,
                              getDefaultPageInput());
                      pageList.add(newPage);
                      firePageOpened(newPage);
                }
            } catch (WorkbenchException e) {
                WorkbenchPlugin
                        .log("Unable to create default perspective - constructor failed.", e); //$NON-NLS-1$
                result.add(e.getStatus());
                String productName = WorkbenchPlugin.getDefault()
                        .getProductName();
                if (productName == null) {
                    productName = ""; //$NON-NLS-1$
                }
                getShell().setText(productName);
            }
        }

        // Set active page.
        if (newActivePage == null)
            newActivePage = pageList.getNextActive();

        setActivePage(newActivePage);

        IMemento introMem = memento.getChild(IWorkbenchConstants.TAG_INTRO);
        if (introMem != null) {
            getWorkbench()
                    .getIntroManager()
                    .showIntro(
                            this,
                            Boolean
                                    .valueOf(
                                            introMem
                                                    .getString(IWorkbenchConstants.TAG_STANDBY))
                                    .booleanValue());
        }
        return result;
    }

    /**
     * Restores cool item order from an old workbench.
     */
01881     private boolean restoreOldCoolBar(IMemento coolbarMem) {
        // Make sure the tag exist
        if (coolbarMem == null) {
            return false;
        }
        CoolBarManager coolBarMgr = getCoolBarManager();
        // Check to see if layout is locked
        Integer locked = coolbarMem.getInteger(IWorkbenchConstants.TAG_LOCKED);
        boolean state = (locked != null) && (locked.intValue() == 1);
        coolBarMgr.setLockLayout(state);

        // Get the visual layout
        IMemento visibleLayout = coolbarMem
                .getChild(IWorkbenchConstants.TAG_TOOLBAR_LAYOUT);
        ArrayList visibleWrapIndicies = new ArrayList();
        ArrayList visibleItems = new ArrayList();
        if (visibleLayout != null) {
            if (readLayout(visibleLayout, visibleItems, visibleWrapIndicies) == false) {
                return false;
            }
        }
        // Get the remembered layout
        IMemento rememberedLayout = coolbarMem
                .getChild(IWorkbenchConstants.TAG_LAYOUT);
        ArrayList rememberedWrapIndicies = new ArrayList();
        ArrayList rememberedItems = new ArrayList();
        if (rememberedLayout != null) {
            if (readLayout(rememberedLayout, rememberedItems,
                    rememberedWrapIndicies) == false) {
                return false;
            }
        }

        // Create the objects
        if (visibleItems != null) {
            // Merge remembered layout into visible layout
            if (rememberedItems != null) {
                // Traverse through all the remembered items
                int currentIndex = 0;
                for (Iterator i = rememberedItems.iterator(); i.hasNext(); currentIndex++) {
                    String id = (String) i.next();
                    int index = -1;
                    for (Iterator iter = visibleItems.iterator(); iter
                            .hasNext();) {
                        String visibleId = (String) iter.next();
                        if (visibleId.equals(id)) {
                            index = visibleItems.indexOf(visibleId);
                            break;
                        }
                    }
                    // The item is not in the visible list
                    if (index == -1) {
                        int insertAt = Math.max(0, Math.min(currentIndex,
                                visibleItems.size()));
                        boolean separateLine = false;
                        // Check whether this item is on a separate line
                        for (Iterator iter = rememberedWrapIndicies.iterator(); iter
                                .hasNext();) {
                            Integer wrapIndex = (Integer) iter.next();
                            if (wrapIndex.intValue() <= insertAt) {
                                insertAt = visibleItems.size();
                                // Add new wrap index for this Item
                                visibleWrapIndicies.add(new Integer(insertAt));
                                separateLine = true;
                            }
                        }
                        // Add item to array list
                        visibleItems.add(insertAt, id);
                        // If the item was not on a separate line then adjust the visible wrap indicies
                        if (!separateLine) {
                            // Adjust visible wrap indicies
                            for (int j = 0; j < visibleWrapIndicies.size(); j++) {
                                Integer index2 = (Integer) visibleWrapIndicies
                                        .get(j);
                                if (index2.intValue() >= insertAt) {
                                    visibleWrapIndicies.set(j, new Integer(
                                            index2.intValue() + 1));
                                }
                            }
                        }
                    }
                }
            }
            // The new layout of the cool bar manager
            ArrayList coolBarLayout = new ArrayList(visibleItems.size());
            // Add all visible items to the layout object
            for (Iterator i = visibleItems.iterator(); i.hasNext();) {
                String id = (String) i.next();
                // Look for the object in the current cool bar manager
                IContributionItem oldItem = null;
                IContributionItem newItem = null;
                if (id != null) {
                    oldItem = coolBarMgr.find(id);
                }
                // If a tool bar contribution item already exists for this id then use the old object
                if (oldItem instanceof ToolBarContributionItem) {
                    newItem = (ToolBarContributionItem) oldItem;
                } else {
                    newItem = new ToolBarContributionItem(new ToolBarManager(
                            coolBarMgr.getStyle()), id);
                    // make it invisible by default
                    newItem.setVisible(false);
                    // Need to add the item to the cool bar manager so that its canonical order can be preserved
                    IContributionItem refItem = findAlphabeticalOrder(
                            IWorkbenchActionConstants.MB_ADDITIONS, id,
                            coolBarMgr);
                    if (refItem != null) {
                        coolBarMgr.insertAfter(refItem.getId(), newItem);
                    } else {
                        coolBarMgr.add(newItem);
                    }
                }
                // Add new item into cool bar manager
                if (newItem != null) {
                    coolBarLayout.add(newItem);
                    newItem.setParent(coolBarMgr);
                    coolBarMgr.markDirty();
                }
            }

            // Add separators to the displayed Items data structure
            int offset = 0;
            for (int i = 1; i < visibleWrapIndicies.size(); i++) {
                int insertAt = ((Integer) visibleWrapIndicies.get(i))
                        .intValue()
                        + offset;
                coolBarLayout.add(insertAt, new Separator(
                        CoolBarManager.USER_SEPARATOR));
                offset++;
            }

            // Add any group markers in their appropriate places
            IContributionItem[] items = coolBarMgr.getItems();
            for (int i = 0; i < items.length; i++) {
                IContributionItem item = items[i];
                if (item.isGroupMarker()) {
                    coolBarLayout.add(Math.max(Math
                            .min(i, coolBarLayout.size()), 0), item);
                }
            }
            IContributionItem[] itemsToSet = new IContributionItem[coolBarLayout
                    .size()];
            coolBarLayout.toArray(itemsToSet);
            coolBarMgr.setItems(itemsToSet);
        }
        return true;
    }

    /**
     * Helper method used for restoring an old cool bar layout. This method reads the memento
     * and populatates the item id's and wrap indicies.
     */
02033     private boolean readLayout(IMemento memento, ArrayList itemIds,
            ArrayList wrapIndicies) {
        // Get the Wrap indicies
        IMemento[] wraps = memento
                .getChildren(IWorkbenchConstants.TAG_ITEM_WRAP_INDEX);
        if (wraps == null)
            return false;
        for (int i = 0; i < wraps.length; i++) {
            IMemento wrapMem = wraps[i];
            Integer index = wrapMem.getInteger(IWorkbenchConstants.TAG_INDEX);
            if (index == null)
                return false;
            wrapIndicies.add(index);
        }
        // Get the Item ids
        IMemento[] savedItems = memento
                .getChildren(IWorkbenchConstants.TAG_ITEM);
        if (savedItems == null)
            return false;
        for (int i = 0; i < savedItems.length; i++) {
            IMemento savedMem = savedItems[i];
            String id = savedMem.getString(IWorkbenchConstants.TAG_ID);
            if (id == null)
                return false;
            itemIds.add(id);
        }
        return true;
    }

    /**
     * Returns the contribution item that the given contribution item should be inserted after.
     * 
     * @param startId the location to start looking alphabetically.
     * @param itemId the target item id.
     * @param mgr the contribution manager.
     * @return the contribution item that the given items should be returned after.
     */
02070     private IContributionItem findAlphabeticalOrder(String startId,
            String itemId, IContributionManager mgr) {
        IContributionItem[] items = mgr.getItems();
        int insertIndex = 0;

        // look for starting point
        while (insertIndex < items.length) {
            IContributionItem item = items[insertIndex];
            if (item.getId() != null && item.getId().equals(startId))
                break;
            ++insertIndex;
        }

        // Find the index that this item should be inserted in
        for (int i = insertIndex + 1; i < items.length; i++) {
            IContributionItem item = items[i];
            String testId = item.getId();

            if (item.isGroupMarker())
                break;

            if (itemId != null && testId != null) {
                if (itemId.compareTo(testId) < 1)
                    break;
            }
            insertIndex = i;
        }
        if (insertIndex >= items.length) {
            return null;
        }
        return items[insertIndex];
    }

    /* (non-Javadoc)
     * Method declared on IRunnableContext.
     */
02106     public void run(boolean fork, boolean cancelable,
            IRunnableWithProgress runnable) throws InvocationTargetException,
            InterruptedException {
        IWorkbenchContextSupport contextSupport = getWorkbench()
                .getContextSupport();
        final boolean keyFilterEnabled = contextSupport.isKeyFilterEnabled();

        Control fastViewBarControl = getFastViewBar() == null ? null
                : getFastViewBar().getControl();
        boolean fastViewBarWasEnabled = fastViewBarControl == null ? false
                : fastViewBarControl.getEnabled();

        Control perspectiveBarControl = getPerspectiveBar() == null ? null
                : getPerspectiveBar().getControl();
        boolean perspectiveBarWasEnabled = perspectiveBarControl == null ? false
                : perspectiveBarControl.getEnabled();

        try {
            if (fastViewBarControl != null && !fastViewBarControl.isDisposed())
                fastViewBarControl.setEnabled(false);

            if (perspectiveBarControl != null
                    && !perspectiveBarControl.isDisposed())
                perspectiveBarControl.setEnabled(false);

            if (keyFilterEnabled)
                contextSupport.setKeyFilterEnabled(false);

            super.run(fork, cancelable, runnable);
        } finally {
            if (fastViewBarControl != null && !fastViewBarControl.isDisposed())
                fastViewBarControl.setEnabled(fastViewBarWasEnabled);

            if (perspectiveBarControl != null
                    && !perspectiveBarControl.isDisposed())
                perspectiveBarControl.setEnabled(perspectiveBarWasEnabled);

            if (keyFilterEnabled)
                contextSupport.setKeyFilterEnabled(true);
        }
    }

    /**
     * Save all of the pages.  Returns true if the operation succeeded.
     */
02151     private boolean saveAllPages(boolean bConfirm) {
        boolean bRet = true;
        Iterator itr = pageList.iterator();
        while (bRet && itr.hasNext()) {
            WorkbenchPage page = (WorkbenchPage) itr.next();
            bRet = page.saveAllEditors(bConfirm);
        }
        return bRet;
    }

    /**
     * @see IPersistable
     */
02164     public IStatus saveState(IMemento memento) {

        MultiStatus result = new MultiStatus(
                PlatformUI.PLUGIN_ID,
                IStatus.OK,
                WorkbenchMessages.WorkbenchWindow_problemsSavingWindow, null); 

        // Save the window's state and bounds.
        if (getShell().getMaximized() || asMaximizedState) {
            memento.putString(IWorkbenchConstants.TAG_MAXIMIZED, "true"); //$NON-NLS-1$
        }
        if (getShell().getMinimized()) {
            memento.putString(IWorkbenchConstants.TAG_MINIMIZED, "true"); //$NON-NLS-1$
        }
        if (normalBounds == null) {
            normalBounds = getShell().getBounds();
        }
        IMemento fastViewBarMem = memento
                .createChild(IWorkbenchConstants.TAG_FAST_VIEW_DATA);
        if (fastViewBar != null) {
            fastViewBar.saveState(fastViewBarMem);
        }

        memento.putInteger(IWorkbenchConstants.TAG_X, normalBounds.x);
        memento.putInteger(IWorkbenchConstants.TAG_Y, normalBounds.y);
        memento.putInteger(IWorkbenchConstants.TAG_WIDTH, normalBounds.width);
        memento.putInteger(IWorkbenchConstants.TAG_HEIGHT, normalBounds.height);

        IWorkbenchPage activePage = getActivePage();
        if (activePage != null
                && activePage.findView(IIntroConstants.INTRO_VIEW_ID) != null) {
            IMemento introMem = memento
                    .createChild(IWorkbenchConstants.TAG_INTRO);
            boolean isStandby = getWorkbench()
                              .getIntroManager()
                              .isIntroStandby(getWorkbench().getIntroManager().getIntro());
            introMem.putString(IWorkbenchConstants.TAG_STANDBY, String
                              .valueOf(isStandby));
        }

        // save the width of the perspective bar
        IMemento persBarMem = memento
                .createChild(IWorkbenchConstants.TAG_PERSPECTIVE_BAR);
        if (perspectiveSwitcher != null) {
            perspectiveSwitcher.saveState(persBarMem);
        }

        /// Save the order of the cool bar contribution items
        if (getCoolBarManager() != null) {
            getCoolBarManager().refresh();
            IMemento coolBarMem = memento
                    .createChild(IWorkbenchConstants.TAG_COOLBAR_LAYOUT);
            if (getCoolBarManager().getLockLayout() == true) {
                coolBarMem.putInteger(IWorkbenchConstants.TAG_LOCKED, 1);
            } else {
                coolBarMem.putInteger(IWorkbenchConstants.TAG_LOCKED, 0);
            }
            IContributionItem[] items = getCoolBarManager().getItems();
            for (int i = 0; i < items.length; i++) {
                IMemento coolItemMem = coolBarMem
                        .createChild(IWorkbenchConstants.TAG_COOLITEM);
                IContributionItem item = items[i];
                // The id of the contribution item
                if (item.getId() != null) {
                    coolItemMem.putString(IWorkbenchConstants.TAG_ID, item
                            .getId());
                }
                // Write out type and size if applicable
                if (item.isSeparator()) {
                    coolItemMem.putString(IWorkbenchConstants.TAG_ITEM_TYPE,
                            IWorkbenchConstants.TAG_TYPE_SEPARATOR);
                } else if (item.isGroupMarker() && !item.isSeparator()) {
                    coolItemMem.putString(IWorkbenchConstants.TAG_ITEM_TYPE,
                            IWorkbenchConstants.TAG_TYPE_GROUPMARKER);
                } else {
                    if (item instanceof PlaceholderContributionItem) {
                        coolItemMem.putString(
                                IWorkbenchConstants.TAG_ITEM_TYPE,
                                IWorkbenchConstants.TAG_TYPE_PLACEHOLDER);
                    } else {
                        // Store the identifier.
                        coolItemMem
                                .putString(
                                        IWorkbenchConstants.TAG_ITEM_TYPE,
                                        IWorkbenchConstants.TAG_TYPE_TOOLBARCONTRIBUTION);
                    }

                    /* Retrieve a reasonable approximation of the height and
                     * width, if possible.
                     */
                    final int height;
                    final int width;
                    if (item instanceof ToolBarContributionItem) {
                        ToolBarContributionItem toolBarItem = (ToolBarContributionItem) item;
                        toolBarItem.saveWidgetState();
                        height = toolBarItem.getCurrentHeight();
                        width = toolBarItem.getCurrentWidth();
                    } else if (item instanceof PlaceholderContributionItem) {
                        PlaceholderContributionItem placeholder = (PlaceholderContributionItem) item;
                        height = placeholder.getHeight();
                        width = placeholder.getWidth();
                    } else {
                        height = -1;
                        width = -1;
                    }

                    // Store the height and width.
                    coolItemMem.putInteger(IWorkbenchConstants.TAG_ITEM_X,
                            width);
                    coolItemMem.putInteger(IWorkbenchConstants.TAG_ITEM_Y,
                            height);
                }
            }
        }

        // Save each page.
        Iterator itr = pageList.iterator();
        while (itr.hasNext()) {
            WorkbenchPage page = (WorkbenchPage) itr.next();

            // Save perspective.
            IMemento pageMem = memento
                    .createChild(IWorkbenchConstants.TAG_PAGE);
            pageMem.putString(IWorkbenchConstants.TAG_LABEL, page.getLabel());
            result.add(page.saveState(pageMem));

            if (page == getActiveWorkbenchPage()) {
                pageMem.putString(IWorkbenchConstants.TAG_FOCUS, "true"); //$NON-NLS-1$
            }

            // Get the input.
            IAdaptable input = page.getInput();
            if (input != null) {
                IPersistableElement persistable = (IPersistableElement) input
                        .getAdapter(IPersistableElement.class);
                if (persistable == null) {
                    WorkbenchPlugin
                            .log("Unable to save page input: " //$NON-NLS-1$
                                    + input
                                    + ", because it does not adapt to IPersistableElement"); //$NON-NLS-1$
                } else {
                    // Save input.  
                    IMemento inputMem = pageMem
                            .createChild(IWorkbenchConstants.TAG_INPUT);
                    inputMem.putString(IWorkbenchConstants.TAG_FACTORY_ID,
                            persistable.getFactoryId());
                    persistable.saveState(inputMem);
                }
            }
        }
            
            // Save window advisor state.
            IMemento windowAdvisorState = memento.createChild(
                        IWorkbenchConstants.TAG_WORKBENCH_WINDOW_ADVISOR);
            result.add(getWindowAdvisor().saveState(windowAdvisorState));
            
            // Save actionbar advisor state.
            IMemento actionBarAdvisorState = memento
                        .createChild(IWorkbenchConstants.TAG_ACTION_BAR_ADVISOR);
            result.add(getActionBarAdvisor().saveState(actionBarAdvisorState));
            
        return result;
    }

    /**
     * Sets the active page within the window.
     *
     * @param in identifies the new active page, or <code>null</code> for no active page
     */
02333     public void setActivePage(final IWorkbenchPage in) {
        if (getActiveWorkbenchPage() == in)
            return;

        // 1FVGTNR: ITPUI:WINNT - busy cursor for switching perspectives
        BusyIndicator.showWhile(getShell().getDisplay(), new Runnable() {
            public void run() {
                // Deactivate old persp.
                WorkbenchPage currentPage = getActiveWorkbenchPage();
                if (currentPage != null) {
                    currentPage.onDeactivate();
                }

                // Activate new persp.
                if (in == null || pageList.contains(in))
                    pageList.setActive(in);
                WorkbenchPage newPage = pageList.getActive();
                  Composite parent = getPageComposite();
                  StackLayout layout = (StackLayout) parent.getLayout();
                if (newPage != null) {
                  layout.topControl = newPage.getClientComposite();
                  parent.layout();
                  hideEmptyWindowContents();
                    newPage.onActivate();
                    firePageActivated(newPage);
                    if (newPage.getPerspective() != null)
                        firePerspectiveActivated(newPage, newPage
                                .getPerspective());
                } 
                else {
                  layout.topControl = null;
                  parent.layout();
                }

                updateFastViewBar();
                
                if (isClosing())
                    return;

                updateDisabled = false;

                // Update action bars ( implicitly calls updateActionBars() )
                updateActionSets();

                if (perspectiveSwitcher != null)
                    perspectiveSwitcher.update(false);

                getMenuManager().update(IAction.TEXT);
            }
        });
    }

    /**
     * Returns whether or not children exist for the Window's toolbar control.
     * Overridden for coolbar support.
     * <p>
     * @return boolean true if children exist, false otherwise
     */
02391     protected boolean toolBarChildrenExist() {
        CoolBar coolBarControl = (CoolBar) getCoolBarControl();
        return coolBarControl.getItemCount() > 0;
    }

    /**
     * Hooks a listener to track the activation and
     * deactivation of the window's shell. Notifies
     * the active part and editor of the change
     */
02401     private void trackShellActivation(Shell shell) {
        shell.addShellListener(new ShellAdapter() {
            public void shellActivated(ShellEvent event) {
                shellActivated = true;
                getWorkbenchImpl().setActivatedWindow(WorkbenchWindow.this);
                WorkbenchPage currentPage = getActiveWorkbenchPage();
                if (currentPage != null) {
                    IWorkbenchPart part = currentPage.getActivePart();
                    if (part != null) {
                        PartSite site = (PartSite) part.getSite();
                        site.getPane().shellActivated();
                    }
                    IEditorPart editor = currentPage.getActiveEditor();
                    if (editor != null) {
                        PartSite site = (PartSite) editor.getSite();
                        site.getPane().shellActivated();
                    }
                    getWorkbenchImpl()
                            .fireWindowActivated(WorkbenchWindow.this);
                }
            }

            public void shellDeactivated(ShellEvent event) {
                shellActivated = false;
                WorkbenchPage currentPage = getActiveWorkbenchPage();
                if (currentPage != null) {
                    IWorkbenchPart part = currentPage.getActivePart();
                    if (part != null) {
                        PartSite site = (PartSite) part.getSite();
                        site.getPane().shellDeactivated();
                    }
                    IEditorPart editor = currentPage.getActiveEditor();
                    if (editor != null) {
                        PartSite site = (PartSite) editor.getSite();
                        site.getPane().shellDeactivated();
                    }
                    getWorkbenchImpl().fireWindowDeactivated(
                            WorkbenchWindow.this);
                }
            }
        });
    }

    /**
     * Hooks a listener to track the resize of the window's
     * shell. Stores the new bounds if in normal state - that
     * is, not in minimized or maximized state)
     */
02449     private void trackShellResize(Shell newShell) {
        newShell.addControlListener(new ControlAdapter() {
            public void controlMoved(ControlEvent e) {
                saveBounds();
            }

            public void controlResized(ControlEvent e) {
                saveBounds();
            }

            private void saveBounds() {
                Shell shell = getShell();
                if (shell == null)
                    return;
                if (shell.isDisposed())
                    return;
                if (shell.getMinimized())
                    return;
                if (shell.getMaximized()) {
                    asMaximizedState = true;
                    return;
                }
                asMaximizedState = false;
                normalBounds = shell.getBounds();
            }
        });
    }

    /**
     * update the action bars.
     */
02480     public void updateActionBars() {
        if (updateDisabled || updatesDeferred()) {
            return;
        }
        // updateAll required in order to enable accelerators on pull-down menus
        getMenuBarManager().updateAll(false);
        getCoolBarManager().update(false);
        getStatusLineManager().update(false);
    }

    /**
     * Returns true iff we are currently deferring UI processing due to a large update
     * @return true iff we are deferring UI updates.
     * @since 3.1
     */
02495     private boolean updatesDeferred() {
        return largeUpdates > 0;
    }
    
    /**
     * <p>
     * Indicates the start of a large update within this window. This is used to
     * disable CPU-intensive, change-sensitive services that were temporarily
     * disabled in the midst of large changes. This method should always be
     * called in tandem with <code>largeUpdateEnd</code>, and the event loop
     * should not be allowed to spin before that method is called.
     * </p>
     * <p>
     * Important: always use with <code>largeUpdateEnd</code>!
     * </p>
     * 
     * @since 3.1
     */
02513     public final void largeUpdateStart() {
        largeUpdates++;
    }

    /**
     * <p>
     * Indicates the end of a large update within this window. This is used to
     * re-enable services that were temporarily disabled in the midst of large
     * changes. This method should always be called in tandem with
     * <code>largeUpdateStart</code>, and the event loop should not be
     * allowed to spin before this method is called.
     * </p>
     * <p>
     * Important: always protect this call by using <code>finally</code>!
     * </p>
     * 
     * @since 3.1
     */
02531     public final void largeUpdateEnd() {
        if (--largeUpdates == 0) {
            updateActionBars();
        }
    }

    /**
     * Update the visible action sets. This method is typically called
     * from a page when the user changes the visible action sets
     * within the prespective.  
     */
02542     public void updateActionSets() {
        if (updateDisabled)
            return;

        WorkbenchPage currentPage = getActiveWorkbenchPage();
        if (currentPage == null)
            actionPresentation.clearActionSets();
        else {
            if (getCoolBarManager() != null) {
                getCoolBarManager().refresh();
            }
            actionPresentation.setActionSets(currentPage.getActionSets());
        }
        updateActionBars();

        // hide the launch menu if it is empty
        String path = IWorkbenchActionConstants.M_WINDOW
                + IWorkbenchActionConstants.SEP
                + IWorkbenchActionConstants.M_LAUNCH;
        IMenuManager manager = getMenuBarManager().findMenuUsingPath(path);
        IContributionItem item = getMenuBarManager().findUsingPath(path);

        // TODO remove: updateActiveActions();
        IActionSet actionSets[] = actionPresentation.getActionSets();
        registerActionSets(actionSets);

        if (manager == null || item == null)
            return;
        item.setVisible(manager.getItems().length >= 2);
        // there is a separator for the additions group thus >= 2
    }

    /**
     * Create the progress indicator for the receiver.
     * @param shell     the parent shell
     */
02578     private void createProgressIndicator(Shell shell) {
        if (getWindowConfigurer().getShowProgressIndicator()) {
            progressRegion = new ProgressRegion();
            progressRegion.createContents(shell, this);
        }

    }

    class PageList {
        //List of pages in the order they were created;
        private List pagesInCreationOrder;

        //List of pages where the top is the last activated.
        private List pageInActivationOrder;

        // The page explicitly activated
        private Object active;

        public PageList() {
            pagesInCreationOrder = new ArrayList(4);
            pageInActivationOrder = new ArrayList(4);
        }

        public boolean add(Object object) {
            pagesInCreationOrder.add(object);
            pageInActivationOrder.add(0, object);
            //It will be moved to top only when activated.
            return true;
        }

        public Iterator iterator() {
            return pagesInCreationOrder.iterator();
        }

        public boolean contains(Object object) {
            return pagesInCreationOrder.contains(object);
        }

        public boolean remove(Object object) {
            if (active == object)
                active = null;
            pageInActivationOrder.remove(object);
            return pagesInCreationOrder.remove(object);
        }

        public boolean isEmpty() {
            return pagesInCreationOrder.isEmpty();
        }

        public IWorkbenchPage[] getPages() {
            int nSize = pagesInCreationOrder.size();
            IWorkbenchPage[] retArray = new IWorkbenchPage[nSize];
            pagesInCreationOrder.toArray(retArray);
            return retArray;
        }

        public void setActive(Object page) {
            if (active == page)
                return;

            active = page;

            if (page != null) {
                pageInActivationOrder.remove(page);
                pageInActivationOrder.add(page);
            }
        }

        public WorkbenchPage getActive() {
            return (WorkbenchPage) active;
        }

        public WorkbenchPage getNextActive() {
            if (active == null) {
                if (pageInActivationOrder.isEmpty())
                    return null;
                else
                    return (WorkbenchPage) pageInActivationOrder
                            .get(pageInActivationOrder.size() - 1);
            } else {
                if (pageInActivationOrder.size() < 2)
                    return null;
                else
                    return (WorkbenchPage) pageInActivationOrder
                            .get(pageInActivationOrder.size() - 2);
            }
        }
    }

    /**
     * Returns the unique object that applications use to configure this window.
     * <p>
     * IMPORTANT This method is declared package-private to prevent regular
     * plug-ins from downcasting IWorkbenchWindow to WorkbenchWindow and getting
     * hold of the workbench window configurer that would allow them to tamper
     * with the workbench window. The workbench window configurer is available
     * only to the application.
     * </p>
     */
    /* package - DO NOT CHANGE */
02678     WorkbenchWindowConfigurer getWindowConfigurer() {
        if (windowConfigurer == null) {
            // lazy initialize
            windowConfigurer = new WorkbenchWindowConfigurer(this);
        }
        return windowConfigurer;
    }

    /**
     * Returns the workbench advisor. Assumes the workbench
     * has been created already.
     * <p>
     * IMPORTANT This method is declared private to prevent regular
     * plug-ins from downcasting IWorkbenchWindow to WorkbenchWindow and getting
     * hold of the workbench advisor that would allow them to tamper with the
     * workbench. The workbench advisor is internal to the application.
     * </p>
     */
    private/* private - DO NOT CHANGE */
02697     WorkbenchAdvisor getAdvisor() {
        return getWorkbenchImpl().getAdvisor();
    }

    /**
     * Returns the window advisor, creating a new one for this
     * window if needed.
     * <p>
     * IMPORTANT This method is declared private to prevent regular
     * plug-ins from downcasting IWorkbenchWindow to WorkbenchWindow and getting
     * hold of the window advisor that would allow them to tamper with the
     * window. The window advisor is internal to the application.
     * </p>
     */
    private/* private - DO NOT CHANGE */
02712     WorkbenchWindowAdvisor getWindowAdvisor() {
        if (windowAdvisor == null) {
            windowAdvisor = getAdvisor().createWorkbenchWindowAdvisor(getWindowConfigurer());
            Assert.isNotNull(windowAdvisor);
        }
        return windowAdvisor;
    }

    /**
     * Returns the action bar advisor, creating a new one for this
     * window if needed.
     * <p>
     * IMPORTANT This method is declared private to prevent regular
     * plug-ins from downcasting IWorkbenchWindow to WorkbenchWindow and getting
     * hold of the action bar advisor that would allow them to tamper with the
     * window's action bars. The action bar advisor is internal to the application.
     * </p>
     */
    private/* private - DO NOT CHANGE */
02731     ActionBarAdvisor getActionBarAdvisor() {
        if (actionBarAdvisor == null) {
            actionBarAdvisor = getWindowAdvisor().createActionBarAdvisor(getWindowConfigurer().getActionBarConfigurer());
            Assert.isNotNull(actionBarAdvisor);
        }
        return actionBarAdvisor;
    }

    /*
     * Returns the IWorkbench implementation.
     */
    private Workbench getWorkbenchImpl() {
        return Workbench.getInstance();
    }

    /**
     * Fills the window's real action bars.
     * 
     * @param flags indicate which bars to fill
     */
02751     public void fillActionBars(int flags) {
        Workbench workbench = getWorkbenchImpl();
        workbench.largeUpdateStart();
        try {
            getActionBarAdvisor().fillActionBars(flags);
        } finally {
            workbench.largeUpdateEnd();
        }
    }

    /**
     * Fills the window's proxy action bars.
     * 
     * @param proxyBars the proxy configurer
     * @param flags indicate which bars to fill
     */
02767     public void fillActionBars(IActionBarConfigurer proxyBars, int flags) {
        Assert.isNotNull(proxyBars);
        WorkbenchWindowConfigurer.WindowActionBarConfigurer wab = (WorkbenchWindowConfigurer.WindowActionBarConfigurer) getWindowConfigurer().getActionBarConfigurer();
        wab.setProxy(proxyBars);
        try {
            getActionBarAdvisor().fillActionBars(flags | ActionBarAdvisor.FILL_PROXY);
        } finally {
            wab.setProxy(null);
        }
    }

    /**
     * The <code>WorkbenchWindow</code> implementation of this method has the same
     * logic as <code>Window</code>'s implementation, but without the resize check.
     * We don't want to skip setting the bounds if the shell has been resized since a
     * free resize event occurs on Windows when the menubar is set in configureShell. 
     */
02784     protected void initializeBounds() {
        Point size = getInitialSize();
        Point location = getInitialLocation(size);
        getShell().setBounds(
                getConstrainedShellBounds(new Rectangle(location.x, location.y,
                        size.x, size.y)));
    }
    
    /*
     * Unlike dialogs, the position of the workbench window is set by the user
     * and persisted across sessions. If the user wants to put the window
     * offscreen or spanning multiple monitors, let them (bug 74762)
     */
02797     protected void constrainShellSize() {
        // As long as the shell is visible on some monitor, don't change it.
        Rectangle bounds = getShell().getBounds();
        if (!SwtUtil.intersectsAnyMonitor(Display.getCurrent(), bounds)) {
            super.constrainShellSize();
        }
    }
    
    /*
     * Unlike dialogs, the position of the workbench window is set by the user
     * and persisted across sessions. If the user wants to put the window
     * offscreen or spanning multiple monitors, let them (bug 74762)
     */
02810     protected Point getInitialLocation(Point size) {
        Shell shell = getShell();
        if (shell != null) {
            return shell.getLocation();
        }
        
        return super.getInitialLocation(size);
    }
    
    /**
     * The <code>WorkbenchWindow</code> implementation of this method
     * delegates to the window configurer.
     *  
     * @since 3.0
     */
02825     protected Point getInitialSize() {
        return getWindowConfigurer().getInitialSize();
    }

    /**
     * @param visible whether the cool bar should be shown.  This is only 
     * applicable if the window configurer also wishes either the cool bar to be
     * visible.
     * @since 3.0 
     */
02835     public void setCoolBarVisible(boolean visible) {
        boolean oldValue = coolBarVisible;
        coolBarVisible = visible;
        if (oldValue != coolBarVisible) {
            updateLayoutDataForContents();
        }
    }

    /** 
     * @return whether the cool bar should be shown.  This is only 
     * applicable if the window configurer also wishes either the cool bar to be
     * visible.
     * @since 3.0
     */
02849     public boolean getCoolBarVisible() {
        return coolBarVisible;
    }

    /**
     * @param visible whether the perspective bar should be shown.  This is only 
     * applicable if the window configurer also wishes either the perspective 
     * bar to be visible.
     * @since 3.0 
     */
02859     public void setPerspectiveBarVisible(boolean visible) {
        boolean oldValue = perspectiveBarVisible;
        perspectiveBarVisible = visible;
        if (oldValue != perspectiveBarVisible) {
            updateLayoutDataForContents();
        }
    }

    /** 
     * @return whether the perspective bar should be shown.  This is only 
     * applicable if the window configurer also wishes either the perspective 
     * bar to be visible.
     * @since 3.0
     */
02873     public boolean getPerspectiveBarVisible() {
        return perspectiveBarVisible;
    }

    /**
     * @param visible whether the perspective bar should be shown.  This is only 
     * applicable if the window configurer also wishes either the perspective 
     * bar to be visible.
     * @since 3.0 
     */
02883     public void setStatusLineVisible(boolean visible) {
        boolean oldValue = statusLineVisible;
        statusLineVisible = visible;
        if (oldValue != statusLineVisible) {
            updateLayoutDataForContents();
        }
    }

    /** 
     * @return whether the perspective bar should be shown.  This is only 
     * applicable if the window configurer also wishes either the perspective 
     * bar to be visible.
     * @since 3.0
     */
02897     public boolean getStatusLineVisible() {
        return statusLineVisible;
    }

    /** 
     * Note that this will only have an effect if the default implementation of
     * WorkbenchAdvisor.createWindowContents() has been invoked.
     *  
     * called  IWorkbench
     * @since 3.0
     */
02908     private void updateLayoutDataForContents() {
        if (defaultLayout == null)
            return;

        // @issue this is not ideal; coolbar and perspective shortcuts should be
        //   separately configurable
        if ((getCoolBarVisible() && getWindowConfigurer().getShowCoolBar())
                || (getPerspectiveBarVisible() && getWindowConfigurer()
                        .getShowPerspectiveBar())) {
            defaultLayout.addTrim(topBar, SWT.TOP, null);
            topBar.setVisible(true);
        } else {
            defaultLayout.removeTrim(topBar);
            topBar.setVisible(false);
        }

        if (getStatusLineVisible() && getWindowConfigurer().getShowStatusLine()) {
            defaultLayout.addTrim(getStatusLineManager().getControl(),
                    SWT.BOTTOM, null);
            getStatusLineManager().getControl().setVisible(true);
        } else {
            defaultLayout.removeTrim(getStatusLineManager().getControl());
            getStatusLineManager().getControl().setVisible(false);
        }

            if (getShowHeapStatus()) {
                  if (heapStatus != null) {
                  if (heapStatus.getLayoutData() == null) {
                      TrimLayoutData animationData = new TrimLayoutData(false,
                                          heapStatus.computeSize(SWT.DEFAULT,
                                      SWT.DEFAULT).x, getStatusLineManager()
                                      .getControl().computeSize(SWT.DEFAULT,
                                              SWT.DEFAULT).y);
                              heapStatus.setLayoutData(animationData);
                  }

                  defaultLayout.addTrim(heapStatus, SWT.BOTTOM, null);
                        heapStatus.setVisible(true);
                  }
            }
            else {
                  if (heapStatus != null) {
                  defaultLayout.removeTrim(heapStatus);
                        heapStatus.setVisible(false);
                  }
            }
            
        if (getWindowConfigurer().getShowProgressIndicator()) {
            if (progressRegion.getControl().getLayoutData() == null) {
                TrimLayoutData animationData = new TrimLayoutData(false,
                        progressRegion.getControl().computeSize(SWT.DEFAULT,
                                SWT.DEFAULT).x, getStatusLineManager()
                                .getControl().computeSize(SWT.DEFAULT,
                                        SWT.DEFAULT).y);

                progressRegion.getControl().setLayoutData(animationData);
            }
            defaultLayout
                    .addTrim(progressRegion.getControl(), SWT.BOTTOM, null);
            progressRegion.getControl().setVisible(true);
        } else {
            if (progressRegion != null) {
                defaultLayout.removeTrim(progressRegion.getControl());
                progressRegion.getControl().setVisible(false);
            }
        }
        defaultLayout.setCenterControl(getPageComposite());
    }

    public boolean getShowFastViewBars() {
        return getWindowConfigurer().getShowFastViewBars();
    }

    /**
     * Set the layout data for the contents of the window.
     */
02984     private void setLayoutDataForContents() {
        updateLayoutDataForContents();

        if (getWindowConfigurer().getShowFastViewBars() && fastViewBar != null) {
            fastViewBar.addDockingListener(new IChangeListener() {
                public void update(boolean changed) {
                    Control reference = null;
                    int side = fastViewBar.getSide();

                    fastViewBar.getControl().setLayoutData(
                            new TrimLayoutData(false, SWT.DEFAULT,
                                    SWT.DEFAULT));

                    if (side == SWT.BOTTOM
                            && getWindowConfigurer().getShowStatusLine()) {
                        reference = getStatusLineManager().getControl();
                    }

                    defaultLayout.addTrim(fastViewBar.getControl(), side,
                            reference);
                    WorkbenchPage page = getActiveWorkbenchPage();

                    if (page != null) {
                        Perspective persp = page.getActivePerspective();
                        IViewReference activeFastView = persp
                                .getActiveFastView();
                        if (activeFastView != null) {
                            persp.setActiveFastView(null);
                            persp.setActiveFastView(activeFastView);
                        }
                    }

                    LayoutUtil.resize(fastViewBar.getControl());
                }
            });
        }
    }

    /**
     * Returns the fast view bar.
     */
03025     public FastViewBar getFastViewBar() {
        return fastViewBar;
    }

    /**
     * Returns the perspective bar.
     */
03032     public PerspectiveBarManager getPerspectiveBar() {
        return perspectiveSwitcher == null ? null : perspectiveSwitcher
                .getPerspectiveBar();
    }

    //for dynamic UI
    public ActionPresentation getActionPresentation() {
        return actionPresentation;
    }

    /* (non-Javadoc)
     * @see org.eclipse.jface.window.ApplicationWindow#showTopSeperator()
     */
03045     protected boolean showTopSeperator() {
        return false;
    }

    /**
     * Delegate to the presentation factory.
     * 
     * @see org.eclipse.jface.window.ApplicationWindow#createStatusLineManager
     * @since 3.0
     */
03055     protected StatusLineManager createStatusLineManager() {
        // @issue ApplicationWindow and WorkbenchWindow should allow full IStatusLineManager
        return (StatusLineManager) getWindowConfigurer()
                .getPresentationFactory().createStatusLineManager();
    }

    /**
     * Delegate to the presentation factory.
     * 
     * @see org.eclipse.jface.window.ApplicationWindow#createStatusLine
     * @since 3.0
     */
03067     protected void createStatusLine(Shell shell) {
        getWindowConfigurer().getPresentationFactory().createStatusLineControl(
                getStatusLineManager(), shell);
    }

    /**
     * Updates the fast view bar, if present.
     * TODO: The fast view bar should update itself as necessary.
     * All calls to this should be cleaned up.
     * 
     * @since 3.0
     */
03079     public void updateFastViewBar() {
        if (getFastViewBar() != null) {
            getFastViewBar().update(true);
        }
    }

    /**
     * @return Returns the progressRegion.
     */
03088     public ProgressRegion getProgressRegion() {
        return progressRegion;
    }

    /**
     * Adds the given control to the specified side of this window's trim.
     * 
     * @param control
     *            the perspective bar's control
     * @param side
     *            one of <code>SWT.LEFT</code>,<code>SWT.BOTTOM</code>,
     *            or <code>SWT.RIGHT</code> (only LEFT has been tested)
     * @since 3.0
     */
03102     public void addToTrim(Control control, int side) {
        Control reference = null;

        // the perspective bar should go before the fast view bar they're on the
        // same side and before the status line if on the bottom
        if (side == fastViewBar.getSide())
            reference = fastViewBar.getControl();
        else if (side == SWT.BOTTOM
                && getWindowConfigurer().getShowStatusLine())
            reference = getStatusLineManager().getControl();

        control.setLayoutData(new TrimLayoutData(false, SWT.DEFAULT,
                SWT.DEFAULT));
        defaultLayout.addTrim(control, side, reference);
    }

      /* (non-Javadoc)
       * @see org.eclipse.ui.IWorkbenchWindow#getExtensionTracker()
       */
03121       public IExtensionTracker getExtensionTracker() {
            if (tracker == null) {
                  tracker = new UIExtensionTracker(getWorkbench().getDisplay());
            }
            return tracker ;
      }

    /**
     * Creates the perspective customization dialog.
     * 
     * @param persp perspective to customize 
     * 
     * @return a new perspective customization dialog
     * @since 3.1
     */
03136     public CustomizePerspectiveDialog createCustomizePerspectiveDialog(Perspective persp) {
        return new CustomizePerspectiveDialog(getWindowConfigurer(), persp);
    }

    /**
     * Returns the default page input for workbench pages
     * opened in this window.
     * 
     * @return the default page input or <code>null</code> if none
     * @since 3.1
     */
03147     IAdaptable getDefaultPageInput() {
        return getWorkbenchImpl().getDefaultPageInput();
    }

      /**
       * Add a listener for perspective reordering.
       * @param listener
       */
03155       public void addPerspectiveReorderListener(IReorderListener listener) {
            if (perspectiveSwitcher != null)
                  perspectiveSwitcher.addReorderListener(listener);
      }

}

Generated by  Doxygen 1.6.0   Back to index