/*******************************************************************************
* Copyright (c) 2005, 2010 QNX Software Systems 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:
* QNX Software Systems - initial API and implementation
* IBM Corporation
*******************************************************************************/
package org.eclipse.cdt.launch.internal.ui;
import java.util.Map;
import org.eclipse.cdt.debug.core.ICDTLaunchConfigurationConstants;
import org.eclipse.cdt.debug.core.ICDebugConfiguration;
import org.eclipse.cdt.debug.ui.CDebugUIPlugin;
import org.eclipse.cdt.debug.ui.ICDebuggerPage;
import org.eclipse.cdt.debug.ui.ICDebuggerPageExtension;
import org.eclipse.cdt.debug.ui.ICDebuggerPageExtension.IContentChangeListener;
import org.eclipse.cdt.launch.ui.CLaunchConfigurationTab;
import org.eclipse.core.runtime.CoreException;
import org.eclipse.debug.core.ILaunchConfiguration;
import org.eclipse.debug.core.ILaunchConfigurationWorkingCopy;
import org.eclipse.debug.ui.ILaunchConfigurationTab;
import org.eclipse.swt.SWT;
import org.eclipse.swt.events.SelectionEvent;
import org.eclipse.swt.events.SelectionListener;
import org.eclipse.swt.graphics.Image;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Combo;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Control;
import org.eclipse.swt.widgets.Group;
import org.eclipse.swt.widgets.Label;
public abstract class AbstractCDebuggerTab extends CLaunchConfigurationTab {
protected ILaunchConfiguration fLaunchConfiguration;
protected ILaunchConfigurationWorkingCopy fWorkingCopy;
protected ICDebugConfiguration fCurrentDebugConfig;
// Dynamic Debugger UI widgets
protected ICDebuggerPage fDynamicTab;
protected Composite fDynamicTabHolder;
private boolean fInitDefaults;
private Combo fDCombo;
private boolean fIsInitializing = false;
private boolean fPageUpdated;
private IContentChangeListener fContentListener = new IContentChangeListener() {
/* (non-Javadoc)
* @see org.eclipse.cdt.debug.ui.ICDebuggerPageExtension.IContentChangeListener#contentChanged()
*/
public void contentChanged() {
contentsChanged();
}
};
protected void setDebugConfig(ICDebugConfiguration config) {
fCurrentDebugConfig = config;
}
protected ICDebugConfiguration getDebugConfig() {
return fCurrentDebugConfig;
}
protected ICDebuggerPage getDynamicTab() {
return fDynamicTab;
}
protected void setDynamicTab(ICDebuggerPage tab) {
if ( fDynamicTab instanceof ICDebuggerPageExtension )
((ICDebuggerPageExtension)fDynamicTab).removeContentChangeListener( fContentListener );
fDynamicTab = tab;
if ( fDynamicTab instanceof ICDebuggerPageExtension )
((ICDebuggerPageExtension)fDynamicTab).addContentChangeListener( fContentListener );
}
protected Composite getDynamicTabHolder() {
return fDynamicTabHolder;
}
protected void setDynamicTabHolder(Composite tabHolder) {
fDynamicTabHolder = tabHolder;
}
protected ILaunchConfigurationWorkingCopy getLaunchConfigurationWorkingCopy() {
return fWorkingCopy;
}
protected void setLaunchConfiguration(ILaunchConfiguration launchConfiguration) {
fLaunchConfiguration = launchConfiguration;
setLaunchConfigurationWorkingCopy(null);
}
protected ILaunchConfiguration getLaunchConfiguration() {
return fLaunchConfiguration;
}
protected void setLaunchConfigurationWorkingCopy(ILaunchConfigurationWorkingCopy workingCopy) {
fWorkingCopy = workingCopy;
}
/**
* Overridden here so that any error message in the dynamic UI gets
* returned.
*
* @see ILaunchConfigurationTab#getErrorMessage()
*/
public String getErrorMessage() {
ICDebuggerPage tab = getDynamicTab();
if ( (super.getErrorMessage() != null) || (tab == null)) {
return super.getErrorMessage();
}
return tab.getErrorMessage();
}
/**
* Notification that the user changed the selection of the Debugger.
*/
protected void handleDebuggerChanged() {
loadDynamicDebugArea();
// always set the newly created area with defaults
ILaunchConfigurationWorkingCopy wc = getLaunchConfigurationWorkingCopy();
if (getDynamicTab() == null) {
// remove any debug specfic args from the config
if (wc == null) {
if (getLaunchConfiguration().isWorkingCopy()) {
wc = (ILaunchConfigurationWorkingCopy)getLaunchConfiguration();
}
}
if (wc != null) {
wc.setAttribute(ICDTLaunchConfigurationConstants.ATTR_DEBUGGER_SPECIFIC_ATTRS_MAP, (Map<String, String>) null);
}
} else {
if (wc == null) {
try {
if (getLaunchConfiguration().isWorkingCopy()) {
setLaunchConfigurationWorkingCopy((ILaunchConfigurationWorkingCopy)getLaunchConfiguration());
} else {
setLaunchConfigurationWorkingCopy(getLaunchConfiguration().getWorkingCopy());
}
wc = getLaunchConfigurationWorkingCopy();
} catch (CoreException e) {
return;
}
}
if (initDefaults()) {
getDynamicTab().setDefaults(wc);
}
setInitializeDefault(false);
getDynamicTab().initializeFrom(wc);
}
}
/**
* Show the contributed piece of UI that was registered for the debugger id
* of the currently selected debugger.
*/
protected void loadDynamicDebugArea() {
// Dispose of any current child widgets in the tab holder area
Control[] children = getDynamicTabHolder().getChildren();
for (int i = 0; i < children.length; i++) {
children[i].dispose();
}
// Retrieve the dynamic UI for the current Debugger
ICDebugConfiguration debugConfig = getConfigForCurrentDebugger();
if (debugConfig == null) {
setDynamicTab(null);
} else {
ICDebuggerPage tab = null;
try {
tab = CDebugUIPlugin.getDefault().getDebuggerPage(debugConfig.getID());
} catch (CoreException e) {
LaunchUIPlugin.errorDialog(LaunchMessages.AbstractCDebuggerTab_ErrorLoadingDebuggerPage, e.getStatus());
}
setDynamicTab(tab);
}
setDebugConfig(debugConfig);
if (getDynamicTab() == null) {
return;
}
// Ask the dynamic UI to create its Control
getDynamicTab().setLaunchConfigurationDialog(getLaunchConfigurationDialog());
getDynamicTab().createControl(getDynamicTabHolder());
Control control = getDynamicTab().getControl();
if (control != null) {
control.setVisible(true);
}
getDynamicTabHolder().layout(true);
contentsChanged();
}
/**
* Called whenever the controls within the Debugger tab has changed.
*/
protected void contentsChanged() {
}
abstract public void createControl(Composite parent);
public void activated(ILaunchConfigurationWorkingCopy workingCopy) {
ICDebuggerPage dynamicTab = getDynamicTab();
if (dynamicTab != null) {
dynamicTab.activated(workingCopy);
}
}
public void initializeFrom(ILaunchConfiguration config) {
setLaunchConfiguration(config);
ICDebuggerPage dynamicTab = getDynamicTab();
if (dynamicTab != null) {
dynamicTab.initializeFrom(config);
}
}
public void performApply(ILaunchConfigurationWorkingCopy config) {
if (getDebugConfig() != null) {
config.setAttribute(ICDTLaunchConfigurationConstants.ATTR_DEBUGGER_ID, getDebugConfig().getID());
ICDebuggerPage dynamicTab = getDynamicTab();
if (dynamicTab == null) {
config.setAttribute(ICDTLaunchConfigurationConstants.ATTR_DEBUGGER_SPECIFIC_ATTRS_MAP, (Map<String, String>) null);
} else {
dynamicTab.performApply(config);
}
}
}
public void setDefaults(ILaunchConfigurationWorkingCopy config) {
setLaunchConfigurationWorkingCopy(config);
ICDebuggerPage dynamicTab = getDynamicTab();
if (dynamicTab != null) {
dynamicTab.setDefaults(config);
setInitializeDefault(false);
}
}
public boolean isValid(ILaunchConfiguration config) {
setErrorMessage(null);
setMessage(null);
if (getDebugConfig() == null) {
setErrorMessage(LaunchMessages.AbstractCDebuggerTab_No_debugger_available);
return false;
}
ICDebuggerPage dynamicTab = getDynamicTab();
if (dynamicTab != null) {
return dynamicTab.isValid(config);
}
return true;
}
protected void setInitializeDefault(boolean init) {
fInitDefaults = init;
}
protected boolean initDefaults() {
return fInitDefaults;
}
public Image getImage() {
return LaunchImages.get(LaunchImages.IMG_VIEW_DEBUGGER_TAB);
}
public String getName() {
return LaunchMessages.AbstractCDebuggerTab_Debugger;
}
protected void createDebuggerCombo(Composite parent, int colspan) {
Composite comboComp = new Composite(parent, SWT.NONE);
GridLayout layout = new GridLayout(2, false);
comboComp.setLayout(layout);
GridData gd = new GridData(GridData.FILL_HORIZONTAL);
gd.horizontalSpan = colspan;
comboComp.setLayoutData(gd);
Label dlabel = new Label(comboComp, SWT.NONE);
dlabel.setText(LaunchMessages.Launch_common_DebuggerColon);
fDCombo = new Combo(comboComp, SWT.READ_ONLY | SWT.DROP_DOWN);
fDCombo.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
fDCombo.addSelectionListener(new SelectionListener() {
public void widgetSelected(SelectionEvent e) {
if (!isInitializing()) {
setInitializeDefault(true);
updateComboFromSelection();
}
}
public void widgetDefaultSelected(SelectionEvent e) {
}
});
}
protected void loadDebuggerCombo(ICDebugConfiguration[] debugConfigs, String current) {
fDCombo.removeAll();
int select = -1;
for (int i = 0; i < debugConfigs.length; i++) {
fDCombo.add(debugConfigs[i].getName());
fDCombo.setData(Integer.toString(i), debugConfigs[i]);
if (debugConfigs[i].getID().equalsIgnoreCase(current)) {
select = i;
}
}
fPageUpdated = false;
if (select != -1) {
fDCombo.select(select);
}
//The behaviour is undefined for if the callbacks should be triggered
// for this,
//so force page update if needed.
if (!fPageUpdated) {
updateComboFromSelection();
}
fPageUpdated = false;
getControl().getParent().layout(true);
}
protected void createDebuggerGroup(Composite parent, int colspan) {
Group debuggerGroup = new Group(parent, SWT.SHADOW_ETCHED_IN);
debuggerGroup.setText(LaunchMessages.CDebuggerTab_Debugger_Options);
setDynamicTabHolder(debuggerGroup);
GridLayout tabHolderLayout = new GridLayout();
tabHolderLayout.marginHeight = 0;
tabHolderLayout.marginWidth = 0;
tabHolderLayout.numColumns = 1;
getDynamicTabHolder().setLayout(tabHolderLayout);
GridData gd = new GridData(GridData.FILL_BOTH);
gd.horizontalSpan = colspan;
getDynamicTabHolder().setLayoutData(gd);
}
protected void updateComboFromSelection() {
fPageUpdated = true;
handleDebuggerChanged();
updateLaunchConfigurationDialog();
}
protected boolean isInitializing() {
return fIsInitializing;
}
protected void setInitializing(boolean isInitializing) {
fIsInitializing = isInitializing;
}
/**
* Return the class that implements <code>ICDebuggerPage</code>
* that is registered against the debugger id of the currently selected
* debugger.
*/
protected ICDebugConfiguration getConfigForCurrentDebugger() {
int selectedIndex = fDCombo.getSelectionIndex();
return (ICDebugConfiguration)fDCombo.getData(Integer.toString(selectedIndex));
}
}