//------------------------------------------------------------------------------
// Copyright (c) 2005, 2006 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 implementation
//------------------------------------------------------------------------------
package org.eclipse.epf.authoring.ui.forms;

import java.io.File;
import java.io.IOException;
import java.net.URI;
import java.text.MessageFormat;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Date;
import java.util.Iterator;
import java.util.List;

import org.eclipse.draw2d.ColorConstants;
import org.eclipse.emf.common.command.Command;
import org.eclipse.emf.common.notify.Notification;
import org.eclipse.emf.ecore.resource.Resource;
import org.eclipse.emf.edit.ui.provider.AdapterFactoryContentProvider;
import org.eclipse.emf.edit.ui.provider.AdapterFactoryLabelProvider;
import org.eclipse.epf.authoring.ui.AuthoringUIHelpContexts;
import org.eclipse.epf.authoring.ui.AuthoringUIImages;
import org.eclipse.epf.authoring.ui.AuthoringUIPlugin;
import org.eclipse.epf.authoring.ui.AuthoringUIResources;
import org.eclipse.epf.authoring.ui.AuthoringUIText;
import org.eclipse.epf.authoring.ui.actions.MethodElementDeleteAction;
import org.eclipse.epf.authoring.ui.dialogs.ChangeHistoryDialog;
import org.eclipse.epf.authoring.ui.dialogs.ItemsFilterDialog;
import org.eclipse.epf.authoring.ui.editors.EditorChooser;
import org.eclipse.epf.authoring.ui.editors.MethodElementEditor;
import org.eclipse.epf.authoring.ui.filters.ContentFilter;
import org.eclipse.epf.authoring.ui.richtext.IMethodRichText;
import org.eclipse.epf.authoring.ui.richtext.IMethodRichTextEditor;
import org.eclipse.epf.authoring.ui.util.EditorsContextHelper;
import org.eclipse.epf.authoring.ui.util.UIHelper;
import org.eclipse.epf.authoring.ui.views.LibraryView;
import org.eclipse.epf.common.serviceability.MsgBox;
import org.eclipse.epf.common.utils.FileUtil;
import org.eclipse.epf.common.utils.NetUtil;
import org.eclipse.epf.common.utils.StrUtil;
import org.eclipse.epf.library.LibraryService;
import org.eclipse.epf.library.edit.IFilter;
import org.eclipse.epf.library.edit.TngAdapterFactory;
import org.eclipse.epf.library.edit.command.DeleteMethodElementCommand;
import org.eclipse.epf.library.edit.command.IActionManager;
import org.eclipse.epf.library.edit.itemsfilter.FilterConstants;
import org.eclipse.epf.library.edit.util.TngUtil;
import org.eclipse.epf.library.edit.validation.IValidator;
import org.eclipse.epf.library.edit.validation.IValidatorFactory;
import org.eclipse.epf.library.ui.LibraryUIText;
import org.eclipse.epf.library.util.ConvertGuidanceType;
import org.eclipse.epf.persistence.MethodLibraryPersister;
import org.eclipse.epf.richtext.RichTextListener;
import org.eclipse.epf.uma.ContentCategory;
import org.eclipse.epf.uma.ContentDescription;
import org.eclipse.epf.uma.Guidance;
import org.eclipse.epf.uma.MethodElement;
import org.eclipse.epf.uma.MethodPlugin;
import org.eclipse.epf.uma.SupportingMaterial;
import org.eclipse.epf.uma.UmaPackage;
import org.eclipse.epf.uma.VariabilityElement;
import org.eclipse.epf.uma.VariabilityType;
import org.eclipse.epf.uma.util.ContentDescriptionFactory;
import org.eclipse.epf.uma.util.UmaUtil;
import org.eclipse.jface.viewers.ComboViewer;
import org.eclipse.jface.viewers.ILabelProvider;
import org.eclipse.jface.viewers.ISelectionChangedListener;
import org.eclipse.jface.viewers.IStructuredContentProvider;
import org.eclipse.jface.viewers.IStructuredSelection;
import org.eclipse.jface.viewers.SelectionChangedEvent;
import org.eclipse.jface.viewers.StructuredSelection;
import org.eclipse.jface.viewers.TableViewer;
import org.eclipse.swt.SWT;
import org.eclipse.swt.events.ControlEvent;
import org.eclipse.swt.events.ControlListener;
import org.eclipse.swt.events.FocusAdapter;
import org.eclipse.swt.events.FocusEvent;
import org.eclipse.swt.events.ModifyListener;
import org.eclipse.swt.events.PaintEvent;
import org.eclipse.swt.events.PaintListener;
import org.eclipse.swt.events.SelectionAdapter;
import org.eclipse.swt.events.SelectionEvent;
import org.eclipse.swt.graphics.Image;
import org.eclipse.swt.graphics.ImageData;
import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Button;
import org.eclipse.swt.widgets.Canvas;
import org.eclipse.swt.widgets.Combo;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Display;
import org.eclipse.swt.widgets.Event;
import org.eclipse.swt.widgets.FileDialog;
import org.eclipse.swt.widgets.Label;
import org.eclipse.swt.widgets.Listener;
import org.eclipse.swt.widgets.Table;
import org.eclipse.swt.widgets.TableItem;
import org.eclipse.swt.widgets.Text;
import org.eclipse.ui.IEditorInput;
import org.eclipse.ui.IEditorSite;
import org.eclipse.ui.PlatformUI;
import org.eclipse.ui.forms.IManagedForm;
import org.eclipse.ui.forms.editor.FormEditor;
import org.eclipse.ui.forms.events.HyperlinkAdapter;
import org.eclipse.ui.forms.events.HyperlinkEvent;
import org.eclipse.ui.forms.widgets.FormToolkit;
import org.eclipse.ui.forms.widgets.ImageHyperlink;
import org.eclipse.ui.forms.widgets.Section;
import org.eclipse.ui.forms.widgets.TableWrapData;
import org.eclipse.ui.forms.widgets.TableWrapLayout;

import com.ibm.icu.text.DateFormat;


/**
 * The base class for all Description pages in the Method editors.
 * 
 * @author Jeff Hardy
 * @author Kelvin Low
 * @author Shashidhar Kannoori
 * @author Shilpa Toraskar
 * @since 1.0
 */
public abstract class DescriptionFormPage extends BaseFormPage implements IRefreshable {

	protected static final String NOT_APPLICABLE_TEXT = AuthoringUIResources.notApplicable_text; //$NON-NLS-1$

	protected static final String CONTRIBUTES_TEXT = AuthoringUIResources.contributes_text; //$NON-NLS-1$
	
	private static final String LOCAL_CONTRIBUTES_TEXT = AuthoringUIResources.localContributes_text;  //$NON-NLS-1$

	protected static final String EXTENDS_TEXT = AuthoringUIResources.extends_text; //$NON-NLS-1$

	protected static final String REPLACES_TEXT = AuthoringUIResources.replaces_text; //$NON-NLS-1$
	
	protected static final String LOCAL_REPLACES_TEXT = AuthoringUIResources.localReplaces_text; //$NON-NLS-1$

	protected static final ILabelProvider labelProvider = new AdapterFactoryLabelProvider(
			TngUtil.umaItemProviderAdapterFactory);

	// Composites and sections.
	protected Section formSection;

	protected Composite sectionComposite;

	protected Composite expandedComposite;

	protected Section generalSection;

	protected Section variabilitySection;

	protected Composite generalComposite;

	protected Composite variabilityComposite;

	protected Section versionSection;

	protected Composite versionComposite;

	protected Section iconSection;

	protected Composite iconComposite;

	private Canvas pane1;

	private Canvas pane3;

	protected Section detailSection;

	protected Composite detailComposite;

	protected Section notationSection;

	protected Composite notationComposite;

	protected Section tailoringSection;

	protected Composite tailoringComposite;

	// Edit controls.
	protected Text ctrl_name;

	protected Text ctrl_presentation_name;

	protected Label ctrl_type_label;

	protected Button ctrl_type_button;

	protected Text ctrl_brief_desc;

	protected IMethodRichText ctrl_full_desc;

	protected IMethodRichText ctrl_key;

	protected IMethodRichTextEditor ctrl_expanded;

	protected ComboViewer viewer_variability;

	protected Combo ctrl_variability;

	protected Label label_base;

	protected TableViewer base_viewer;

	protected Table ctrl_base;

	protected Button ctrl_base_button;

	private IMethodRichText activeControl;

	private Text ctrl_authors;

	private Text ctrl_change_date;

	private Text ctrl_change_desc;

	private Button view_history_button;

	private Text ctrl_version;

	protected Label label_copyright;

	protected TableViewer copyright_viewer;

	protected Table ctrl_copyright;

	private Button copyright_button;

	private Button copyright_button_deselect;

	protected ImageHyperlink expandDetailLink;

	protected Label expandDetailLabel;

	protected ImageHyperlink expandNotationLink;

	protected Label expandNotationLabel;

	protected ImageHyperlink expandTailoringLink;

	protected Label expandTailoringLabel;

	protected IMethodRichText ctrl_purpose;

	protected Text ctrl_external_id;

	private Image shapeImage;

	private Image nodeImage;

	protected Button ctrl_select_shapeIcon_button;

	protected Button ctrl_clear_shapeIcon_button;

	protected Button ctrl_select_nodeIcon_button;

	protected Button ctrl_clear_nodeIcon_button;

	protected ImageHyperlink expandVersionLink;

	protected Label expandVersionLabel;

	protected ImageHyperlink expandLink;

	protected Label expandLabel;

	private String lastChangeHistory = "";

	protected IStructuredContentProvider contentProviderVariability;

	protected IStructuredContentProvider contentProviderBase;

	protected ILabelProvider labelProviderVariability = new AdapterFactoryLabelProvider(
			TngAdapterFactory.INSTANCE
					.getNavigatorView_ComposedAdapterFactory()) {
		public String getText(Object object) {
			VariabilityType varObject = (VariabilityType) object;
			if (varObject == VariabilityType.NA_LITERAL)
				return NOT_APPLICABLE_TEXT;
			if (varObject == VariabilityType.CONTRIBUTES_LITERAL)
				return CONTRIBUTES_TEXT;
			if (varObject == VariabilityType.LOCAL_CONTRIBUTION_LITERAL)
				return LOCAL_CONTRIBUTES_TEXT;
			if (varObject == VariabilityType.EXTENDS_LITERAL)
				return EXTENDS_TEXT;
			if (varObject == VariabilityType.REPLACES_LITERAL)
				return REPLACES_TEXT;
			if (varObject == VariabilityType.LOCAL_REPLACEMENT_LITERAL)
				return LOCAL_REPLACES_TEXT;
			return null;
		}
	};

	protected ILabelProvider labelProviderBase = new AdapterFactoryLabelProvider(
			TngAdapterFactory.INSTANCE
					.getNavigatorView_ComposedAdapterFactory()) {
		public String getColumnText(Object object, int columnIndex) {
			return TngUtil.getLabelWithPath(object);
		}
	};

	protected IActionManager actionMgr;

	protected IStructuredContentProvider copyrightContentProvider;

	private ILabelProvider copyrightLabelProviderBase = new AdapterFactoryLabelProvider(
			TngAdapterFactory.INSTANCE
					.getNavigatorView_ComposedAdapterFactory());

	protected ModifyListener modelModifyListener;

	protected ModifyListener contentModifyListener;

	// Editing and display flags.
	protected boolean descExpandFlag = false;

	protected boolean generalSectionExpandFlag = false;

	protected boolean detailSectionExpandFlag = false;

	protected boolean notationSectionExpandFlag = false;

	protected boolean tailoringSectionExpandFlag = false;

	protected boolean versionSectionExpandFlag = false;

	protected boolean elementSectionExpandFlag = false;

	protected boolean iconSectionExpandFlag = false;

	protected boolean fullDescOn = true;

	protected boolean keyConsiderationOn = true;

	protected boolean briefDescOn = true;

	protected boolean elementTypeOn = false;

	protected boolean contentFieldOn = false;

	protected boolean versionSectionOn = true;

	protected boolean anyAttributeModified = false;

	protected boolean generalSectionOn = true;

	protected boolean notationSectionOn = false;

	protected boolean detailSectionOn = true;

	protected boolean tailoringSectionOn = false;

	protected boolean variabilitySectionOn = true;

	protected boolean purposeOn = false;

	protected boolean externalIdOn = false;

	protected boolean iconSectionOn = false;

	// commented because these variables are not in use
	// protected String variabilityTypeNone = NOT_APPLICABLE_TEXT;
	// protected String variabilityTypeContributes = CONTRIBUTES_TEXT;
	// protected String variabilityTypeExtends = EXTENDS_TEXT;
	// protected String variabilityTypeReplaces = REPLACES_TEXT;

	// Internal IDs for the sections.
	protected static final int GENERAL_SECTION_ID = 1;

	protected static final int DETAIL_SECTION_ID = 2;

	protected static final int VERSION_SECTION_ID = 3;

	protected static final int NOTATION_SECTION_ID = 4;

	protected static final int TAILORING_SECTION_ID = 5;

	private int warningCount = 1;

	private int SECTIONS = 0;

	private static int SHAPEICON_WIDTH_MAX = 32;

	private static int SHAPEICON_HEIGHT_MAX = 32;

	private static int NODEICON_WIDTH_MAX = 16;

	private static int NODEICON_HEIGHT_MAX = 16;

	protected IFilter filter;

	private boolean disposed;

	// To handle the i118n properly and avoid string concatenation.
	public String generalSectionDescription;
	public String detailSectionDescription;
	public String tailoringSectionDescription;
	public String notationSectionDescription;
	public String variabilitySectionDescription;
	public String iconSectionDescription;
	public String versionSectionDescription;

	/**
	 * Returns the Content filter associated with this page.
	 */
	protected IFilter getFilter() {
		return filter;
	}

	/**
	 * Returns the Content element associated with this page.
	 */
	protected Object getContentElement() {
		return null;
	}

	protected void initContentProviderBase() {
		contentProviderBase = new AdapterFactoryContentProvider(
				TngAdapterFactory.INSTANCE
						.getNavigatorView_ComposedAdapterFactory()) {
			public Object[] getElements(Object object) {
				ArrayList base_selected_list = new ArrayList();
				if (contentElement.getVariabilityBasedOnElement() != null)
					base_selected_list.add(contentElement
							.getVariabilityBasedOnElement());
				return base_selected_list.toArray();
			}

			public void notifyChanged(Notification notification) {
				switch (notification.getFeatureID(VariabilityElement.class)) {
				case UmaPackage.VARIABILITY_ELEMENT__VARIABILITY_BASED_ON_ELEMENT:
					super.notifyChanged(notification);
				}
			}
		};
		base_viewer.setContentProvider(contentProviderBase);
	}

	/**
	 * Creates a new instance.
	 * 
	 * @param editor
	 *            The parent form editor.
	 * @param id
	 *            The unique ID for the form page.
	 * @param title
	 *            The title for the form page.
	 */
	public DescriptionFormPage(FormEditor editor, String id, String title) {
		super(editor, id, title);
	}

	/**
	 * @see org.eclipse.ui.forms.editor.init(IEditorSite, IEditorInput)
	 */
	public void init(IEditorSite site, IEditorInput input) {
		super.init(site, input);

		if (contentElement instanceof ContentCategory) {
			contentProviderVariability = new AdapterFactoryContentProvider(
					TngAdapterFactory.INSTANCE
							.getNavigatorView_ComposedAdapterFactory()) {
				public Object[] getElements(Object object) {
					List variabilityTypesList = new ArrayList();
					variabilityTypesList.add(VariabilityType.NA_LITERAL);
					variabilityTypesList
							.add(VariabilityType.CONTRIBUTES_LITERAL);
					variabilityTypesList.add(VariabilityType.REPLACES_LITERAL);
					return variabilityTypesList.toArray();
				}
			};
		} else {
			contentProviderVariability = new AdapterFactoryContentProvider(
					TngAdapterFactory.INSTANCE
							.getNavigatorView_ComposedAdapterFactory()) {
				public Object[] getElements(Object object) {
					List variabilityTypesList = new ArrayList();
					variabilityTypesList.add(VariabilityType.NA_LITERAL);
					variabilityTypesList
							.add(VariabilityType.CONTRIBUTES_LITERAL);
					variabilityTypesList.add(VariabilityType.EXTENDS_LITERAL);
					variabilityTypesList.add(VariabilityType.REPLACES_LITERAL);
					return variabilityTypesList.toArray();
				}
			};
		}
	}

	/**
	 * @see org.eclipse.ui.forms.editor.createFormContent(IManagedForm)
	 */
	protected void createFormContent(IManagedForm managedForm) {
		super.createFormContent(managedForm);
		createEditorContent(toolkit);
		setContextHelp();
		setFormTextWithVariableInfo();
		loadData();
		addListeners();
	}

	private void setFormTextWithVariableInfo() {
		UIHelper.setFormText(form, contentElement);
	}

	/**
	 * @deprecated
	 * @see TngUtil#getLabel Code moved to TngUtil.getLabel(below more specific
	 *      method)returns label with variabilityInfo
	 *      <code>TngUtil.getLabel(VariabilityElement object, String alternativeLabel, boolean preferBase)</code>
	 * 
	 */
	public String getLabel(VariabilityElement object, String alternativeLabel,
			boolean preferBase) {
		String label = TngUtil.getLabel(object, alternativeLabel);
		if (preferBase && object.getVariabilityBasedOnElement() != null) {
			VariabilityType type = object.getVariabilityType();
			String variabilityTxt = null;
			if (type == VariabilityType.CONTRIBUTES_LITERAL) {
				variabilityTxt = AuthoringUIResources
						.contributes_to_text; //$NON-NLS-1$
			} else if (type == VariabilityType.LOCAL_CONTRIBUTION_LITERAL) {
				variabilityTxt = AuthoringUIResources
					.localContributes_text; //$NON-NLS-1$			
			} else if (type == VariabilityType.EXTENDS_LITERAL) {					
				variabilityTxt = AuthoringUIResources
						.extends_text; //$NON-NLS-1$
			} else if (type == VariabilityType.REPLACES_LITERAL) {
				variabilityTxt = AuthoringUIResources
						.replaces_text; //$NON-NLS-1$
			} else if (type == VariabilityType.LOCAL_REPLACEMENT_LITERAL) {
				variabilityTxt = AuthoringUIResources
						.localReplaces_text; //$NON-NLS-1$
			}
			if (variabilityTxt != null) {
				StringBuffer strBuf = new StringBuffer(label)
						.append(" (").append(variabilityTxt).append(" '") //$NON-NLS-1$ //$NON-NLS-2$
						.append(
								TngUtil.getLabel(object
										.getVariabilityBasedOnElement(),
										alternativeLabel)).append("'"); //$NON-NLS-1$
				MethodPlugin basePlugin = UmaUtil.getMethodPlugin(object
						.getVariabilityBasedOnElement());
				if (basePlugin != null) {
					strBuf
							.append(" in '").append(basePlugin.getName()).append("')"); //$NON-NLS-1$ //$NON-NLS-2$
				}
				label = strBuf.toString();
			}
		}

		return label;
	}

	/**
	 * Creates the editor tab content
	 * 
	 * @param toolkit
	 *            The form toolkit.
	 */
	protected void createEditorContent(FormToolkit toolkit) {
		createFormComposites(toolkit);
		loadSectionDescription();
		// Create the General section.
		if (generalSectionOn) {
			createGeneralSection(toolkit);
			SECTIONS++;
		}

		// Create the Detail section.
		if (detailSectionOn) {
			createDetailSection(toolkit);
			SECTIONS++;
		}

		// Create the Notation section.
		if (notationSectionOn) {
			createNotationSection(toolkit);
			SECTIONS++;
		}

		// Create the Tailoring Section.
		if (tailoringSectionOn) {
			createTailoringSection(toolkit);
			SECTIONS++;
		}

		// Create the Version section.
		if (versionSectionOn) {
			createVersionSection(toolkit);
			createVersionSectionContent();
			SECTIONS++;
		}

		if (variabilitySectionOn) {
			createVariabilitySection(toolkit);
			SECTIONS++;
		}

		// Icon Section
		if (iconSectionOn) {
			createIconSection(toolkit);
			createIconSectionContent();
			SECTIONS++;
		}

		toolkit.paintBordersFor(variabilityComposite);
		toolkit.paintBordersFor(expandedComposite);
		toolkit.paintBordersFor(generalComposite);
		toolkit.paintBordersFor(versionComposite);
	}

	private void createFormComposites(FormToolkit toolkit) {
		// Create the main section (used for swapping display of
		// sectionComposite and expandedComposite).
		formSection = toolkit.createSection(form.getBody(), Section.NO_TITLE);
		{
			TableWrapData td = new TableWrapData(TableWrapData.FILL_GRAB);
			formSection.setLayoutData(td);
			formSection.setLayout(new TableWrapLayout());
		}

		// Create the composite for the sections.
		sectionComposite = toolkit.createComposite(formSection, SWT.NONE);
		sectionComposite.setLayoutData(new TableWrapData());
		sectionComposite.setLayout(new TableWrapLayout());
		formSection.setClient(sectionComposite);

		// Create the composite for the RichTextEditor.
		expandedComposite = toolkit.createComposite(formSection, SWT.NONE);
		{
			TableWrapData td = new TableWrapData(TableWrapData.FILL_GRAB);
			expandedComposite.setLayoutData(td);
			expandedComposite.setLayout(new GridLayout(2, false));
			expandedComposite.setVisible(false);
		}

		// Add the expand/collapse hyperlink image.
		expandLink = toolkit.createImageHyperlink(expandedComposite, SWT.NONE);
		expandLink.setImage(AuthoringUIImages.IMG_EXPANDED);
		expandLink.setToolTipText(AuthoringUIResources.closeRTE);
		expandLink.setUnderlined(false);
		expandLink.addHyperlinkListener(new HyperlinkAdapter() {
			public void linkActivated(HyperlinkEvent e) {
				toggle(e);
			}
		});

		// Add the expand/collapse hyperlink text.
		expandLabel = createLabel(toolkit, expandedComposite, ""); //$NON-NLS-1$
	}

	/**
	 * Creates the General section.
	 */
	protected void createGeneralSection(FormToolkit toolkit) {
		generalSection = createSection(toolkit, sectionComposite,
				AuthoringUIText.GENERAL_INFO_SECTION_NAME,
				getGeneralSectionDescription());
		generalComposite = createComposite(toolkit, generalSection);
		((GridLayout) generalComposite.getLayout()).numColumns = 4;
		createGeneralSectionContent();
	}

	/**
	 * Creates the General section content.
	 */
	private void createGeneralSectionContent() {
		// Add the Name label and text control.
		ctrl_name = createTextEditWithLabel3(toolkit, generalComposite,
				AuthoringUIText.NAME_TEXT, SWT.DEFAULT, SWT.SINGLE);

		// Add the Presentation name label and text control.
		ctrl_presentation_name = createTextEditWithLabel3(toolkit,
				generalComposite, AuthoringUIText.PRESENTATION_NAME_TEXT,
				SWT.DEFAULT, SWT.SINGLE);

		if (elementTypeOn) {
			createLabel(toolkit, generalComposite, AuthoringUIText.TYPE_TEXT, 2);
			ctrl_type_label = createLabel(toolkit, generalComposite, ""); //$NON-NLS-1$
			{
				GridData gridData = new GridData(GridData.BEGINNING);
				gridData.horizontalSpan = 1;
				ctrl_type_label.setBackground(Display.getCurrent()
						.getSystemColor(19));
				ctrl_type_label.setLayoutData(gridData);
			}
			if (contentElement instanceof Guidance) {
				ctrl_type_button = toolkit.createButton(generalComposite,
						AuthoringUIText.CHANGE_TYPE_BUTTON_TEXT, SWT.PUSH);
				{
					GridData gridData = new GridData(GridData.BEGINNING);
					gridData.horizontalSpan = 1;
					ctrl_type_button.setLayoutData(gridData);
				}
				if (ConvertGuidanceType
						.getValidNewGuidanceTypes((Guidance) contentElement) == null) {
					ctrl_type_button.setVisible(false);
				}
			}
		}

		if (externalIdOn) {
			ctrl_external_id = createTextEditWithLabel3(toolkit,
					generalComposite, AuthoringUIText.UNIQUE_ID_TEXT,
					SWT.DEFAULT, SWT.SINGLE);
		}

		if (briefDescOn) {
			ctrl_brief_desc = createTextEditWithLabel3(toolkit,
					generalComposite, AuthoringUIText.BRIEF_DESCRIPTION_TEXT,
					40, SWT.MULTI | SWT.TRAVERSE_TAB_NEXT);
		}
	}

	/**
	 * Creates the Content Variability section.
	 */
	protected void createVariabilitySection(FormToolkit toolkit) {
		variabilitySection = createSection(toolkit, sectionComposite,
				AuthoringUIText.VARIABILITY_SECTION_NAME,
				getVariabilitySectionDescription());
		variabilityComposite = createComposite(toolkit, variabilitySection);

		ctrl_variability = createComboWithLabel(toolkit, variabilityComposite,
				AuthoringUIText.VARIABILITY_TYPE_TEXT);

		viewer_variability = new ComboViewer(ctrl_variability);
		viewer_variability.getCombo().setLayoutData(new GridData(1));
		viewer_variability.setContentProvider(contentProviderVariability);
		viewer_variability.setLabelProvider(labelProviderVariability);
		viewer_variability.setInput(contentElement);

		toolkit.createLabel(variabilityComposite, "", SWT.NONE); //$NON-NLS-1$

		//String baseElement = LibraryUIText.getUITextLower(methodElement);
		label_base = createLabel(toolkit, variabilityComposite,
				AuthoringUIText.BASE_ELEMENT_TEXT);
		ctrl_base = createTable(toolkit, variabilityComposite, SWT.SINGLE
				| SWT.READ_ONLY, GridData.FILL_HORIZONTAL, 5, 300, 1, 1);
		{
			GridData gridData = new GridData(GridData.FILL_HORIZONTAL);
			gridData.horizontalSpan = 1;
			gridData.heightHint = 24;
			ctrl_base.setLayoutData(gridData);
		}

		base_viewer = new TableViewer(ctrl_base);
		initContentProviderBase();
		base_viewer.setLabelProvider(labelProviderBase);
		base_viewer.setInput(contentElement);

		ctrl_base_button = toolkit.createButton(variabilityComposite,
				AuthoringUIText.SELECT_BUTTON_TEXT, SWT.SIMPLE);

		// Set focus on the Name text control.
		Display display = form.getBody().getDisplay();
		if (!(display == null || display.isDisposed())) {
			display.asyncExec(new Runnable() {
				public void run() {
					if(ctrl_name.isDisposed()) return;
					
					ctrl_name.setFocus();
					ContentDescription contentDescription = contentElement
							.getPresentation();
					if (contentDescription.getChangeDate() == null)
						ctrl_name.setSelection(0, ctrl_name.getText().length());
				}
			});
		}
	}

	protected void refresh(boolean editable) {
		ctrl_name.setEditable(editable);
		ctrl_presentation_name.setEditable(editable);

		if (briefDescOn) {
			ctrl_brief_desc.setEditable(editable);
		}
		if (purposeOn) {
			ctrl_purpose.setEditable(editable);
		}
		if (fullDescOn) {
			ctrl_full_desc.setEditable(editable);
		}
		if (keyConsiderationOn) {
			ctrl_key.setEditable(editable);
		}
		if (externalIdOn) {
			ctrl_external_id.setEditable(editable);
		}
		if (elementTypeOn) {
			ctrl_type_button.setEnabled(editable);
		}
		if (variabilitySectionOn) {
			ctrl_variability.setEnabled(editable);
			ctrl_base_button.setEnabled(editable);
			if (((IStructuredSelection) viewer_variability.getSelection())
					.getFirstElement() == VariabilityType.NA_LITERAL) {
				ctrl_base_button.setEnabled(false);
			}
		}
		if (versionSectionOn) {
			ctrl_change_date.setEditable(false);
			ctrl_change_desc.setEditable(editable);
			ctrl_authors.setEditable(editable);
			ctrl_version.setEditable(editable);
			copyright_button.setEnabled(editable);
			setCopyrightButtonDeselect();
		}
		if (iconSectionOn) {
			ctrl_select_shapeIcon_button.setEnabled(editable);
			ctrl_clear_shapeIcon_button.setEnabled(editable
					&& contentElement.getShapeicon() != null);
			ctrl_select_nodeIcon_button.setEnabled(editable);
			ctrl_clear_nodeIcon_button.setEnabled(editable
					&& contentElement.getNodeicon() != null);
		}
		if (ctrl_expanded != null) {
			ctrl_expanded.setEditable(editable);
		}
	}

	/**
	 * Create the Detail section.
	 */
	protected void createDetailSection(FormToolkit toolkit) {
		detailSection = createSection(toolkit, sectionComposite,
				AuthoringUIText.DETAIL_SECTION_NAME,
				getDetailSectionDescription());
		detailComposite = createComposite(toolkit, detailSection);
		createDetailSectionContent();
		toolkit.paintBordersFor(detailComposite);
	}

	/**
	 * Creates the Detail section content.
	 */
	private void createDetailSectionContent() {
		if (purposeOn) {
			ctrl_purpose = createRichTextEditWithLinkForSection(toolkit,
					detailComposite, AuthoringUIText.PURPOSE_TEXT, 40, 400,
					DETAIL_SECTION_ID);
		}

		if (fullDescOn) {
			ctrl_full_desc = createRichTextEditWithLinkForSection(toolkit,
					detailComposite, AuthoringUIText.MAIN_DESCRIPTION_TEXT,
					100, 400, DETAIL_SECTION_ID);

		}

		if (keyConsiderationOn) {
			ctrl_key = createRichTextEditWithLinkForSection(toolkit,
					detailComposite, AuthoringUIText.KEY_CONSIDERATIONS_TEXT,
					40, 400, DETAIL_SECTION_ID);
		}
	}

	/**
	 * Creates the Notation section.
	 */
	protected void createNotationSection(FormToolkit toolkit) {
		notationSection = createSection(toolkit, sectionComposite,
				AuthoringUIText.NOTATION_SECTION_NAME,
				getNotationSectionDescription());
		notationComposite = createComposite(toolkit, notationSection);
		createNotationSectionContent();
		toolkit.paintBordersFor(notationComposite);
	}

	/**
	 * Creates the Notation section content.
	 */
	protected void createNotationSectionContent() {
	}

	/**
	 * Creates the Tailoring section.
	 */
	protected void createTailoringSection(FormToolkit toolkit) {
		tailoringSection = createSection(toolkit, sectionComposite,
				AuthoringUIText.TAILORING_SECTION_NAME,
				getTailoringSectionDescription());
		tailoringComposite = createComposite(toolkit, tailoringSection);
		createTailoringSectionContent();
		toolkit.paintBordersFor(tailoringComposite);

	}

	protected void createTailoringSectionContent() {
	}

	/**
	 * Add listeners to monitor focus and modification changes in the edit
	 * controls.
	 */
	protected void addListeners() {
		final MethodElementEditor editor = (MethodElementEditor) getEditor();

		modelModifyListener = editor.createModifyListener(contentElement);
		contentModifyListener = editor.createModifyListener(contentElement
				.getPresentation());
		actionMgr = editor.getActionManager();

		form.addControlListener(new ControlListener() {
			public void controlResized(ControlEvent e) {
				if (ctrl_expanded != null) {
					((GridData) ctrl_expanded.getLayoutData()).heightHint = getRichTextEditorHeight();
					((GridData) ctrl_expanded.getLayoutData()).widthHint = getRichTextEditorWidth();
				}
				formSection.layout(true, true);
			}

			public void controlMoved(ControlEvent e) {
			}
		});

		form.getParent().addListener(SWT.Activate, new Listener() {
			public void handleEvent(Event event) {
				if(disposed) {
					return;
				}
				
				refresh(!TngUtil.isLocked(contentElement));
				setFormTextWithVariableInfo();
				
				// do refresh variability and copyright viewer
				if(variabilitySectionOn)
					base_viewer.refresh();
				if(versionSectionOn)
					copyright_viewer.refresh();
			}
		});

		if (generalSectionOn) {
			addGeneralSectionListeners();
		}

		if (detailSectionOn) {
			addDetailSectionListeners();
		}

		if (versionSectionOn) {
			addVersionSectionListeners();
		}

		if (iconSectionOn) {
			addIconSectionListeners();
		}

		viewer_variability
				.addSelectionChangedListener(new ISelectionChangedListener() {
					public void selectionChanged(SelectionChangedEvent event) {
						IStructuredSelection selection = (IStructuredSelection) viewer_variability
								.getSelection();

						if (contentElement.getVariabilityBasedOnElement() != null) {
							boolean status = editor
									.getActionManager()
									.doAction(
											IActionManager.SET,
											contentElement,
											UmaPackage.eINSTANCE
													.getVariabilityElement_VariabilityType(),
											(VariabilityType) selection
													.getFirstElement(), -1);
							if (!status) {
								return;
							}
						}
						if (selection.getFirstElement() == VariabilityType.NA_LITERAL) {
							if (contentElement.getVariabilityBasedOnElement() != null) {
								boolean status = editor
										.getActionManager()
										.doAction(
												IActionManager.SET,
												contentElement,
												UmaPackage.eINSTANCE
														.getVariabilityElement_VariabilityBasedOnElement(),
												null, -1);
								if (!status) {
									return;
								}
							}
							ctrl_base_button.setEnabled(false);
							base_viewer.refresh();
						} else {
							List selectionBaseList = new ArrayList();
							VariabilityElement base = contentElement
									.getVariabilityBasedOnElement();
							selectionBaseList.add(base);
							ctrl_base_button.setEnabled(true);
							base_viewer.refresh();
						}
						setFormTextWithVariableInfo();
					}
				});

		ctrl_base_button.addSelectionListener(new SelectionAdapter() {
			public void widgetSelected(SelectionEvent e) {
				filter = getFilter();
				if (filter != null) {
					ItemsFilterDialog fd = new ItemsFilterDialog(PlatformUI
							.getWorkbench().getActiveWorkbenchWindow()
							.getShell(), filter, getContentElement(),
							LibraryUIText.getUIText(contentElement, true));
					fd.setViewerSelectionSingle(true);
					fd.setBlockOnOpen(true);
					fd.setTitle(LibraryUIText.getUIText(contentElement, true));
					fd.open();
					fd.getSelectedItems();
					if (fd.getSelectedItems().size() > 0) {
						boolean status = editor
								.getActionManager()
								.doAction(
										IActionManager.SET,
										contentElement,
										UmaPackage.eINSTANCE
												.getVariabilityElement_VariabilityBasedOnElement(),
										(VariabilityElement) fd
												.getSelectedItems().get(0), -1);
						if (!status) {
							return;
						}
						status = editor
								.getActionManager()
								.doAction(
										IActionManager.SET,
										contentElement,
										UmaPackage.eINSTANCE
												.getVariabilityElement_VariabilityType(),
										(VariabilityType) ((IStructuredSelection) viewer_variability
												.getSelection())
												.getFirstElement(), -1);
					}
				}
				setFormTextWithVariableInfo();
				if ((ctrl_base != null) && (!(ctrl_base.isDisposed())))
					ctrl_base.redraw();
				if ((base_viewer != null)
						&& (!(base_viewer.getControl().isDisposed())))
					base_viewer.refresh();
			}
		});
	}

	private void addGeneralSectionListeners() {
		ctrl_name.addModifyListener(modelModifyListener);
		ctrl_name.addFocusListener(new FocusAdapter() {
			public void focusGained(FocusEvent e) {
				((MethodElementEditor) getEditor()).setCurrentFeatureEditor(e.widget,
						UmaPackage.eINSTANCE.getNamedElement_Name());
			}

			public void focusLost(FocusEvent e) {
				String name = ctrl_name.getText().trim();
				if (((MethodElementEditor) getEditor()).mustRestoreValue(
						e.widget, contentElement.getName())) {
					return;
				}
				if (name.equals(contentElement.getName()))
					return;
				IValidator validator = IValidatorFactory.INSTANCE
						.createNameValidator(
								contentElement,
								TngAdapterFactory.INSTANCE
										.getNavigatorView_ComposedAdapterFactory());
				String msg = validator.isValid(name);
				if (msg == null) {
					name = StrUtil.makeValidFileName(ctrl_name.getText());
					if (!name.equals(contentElement.getName())) {
						boolean success = actionMgr.doAction(
								IActionManager.SET, contentElement,
								UmaPackage.eINSTANCE.getNamedElement_Name(),
								name, -1);
						if (!success) {
							return;
						}
						if (ContentDescriptionFactory
								.hasPresentation(contentElement)) {
							Resource contentResource = contentElement
									.getPresentation().eResource();
							if (contentResource != null) {
								((MethodElementEditor) getEditor())
										.addResourceToAdjustLocation(contentResource);
							}
						}
						setFormTextWithVariableInfo();
						ctrl_name.setText(name);
					}
				} else {
					AuthoringUIPlugin
							.getDefault()
							.getMsgDialog()
							.displayError(
									AuthoringUIResources.renameError_title, //$NON-NLS-1$
									msg);
					ctrl_name.setText(contentElement.getName());
					ctrl_name.getDisplay().asyncExec(new Runnable() {
						public void run() {
							ctrl_name.setFocus();
							ctrl_name.selectAll();
						}
					});
				}
			}
		});

		ctrl_presentation_name.addModifyListener(modelModifyListener);
		ctrl_presentation_name.addFocusListener(new FocusAdapter() {
			public void focusLost(FocusEvent e) {
				String oldContent = contentElement.getPresentationName();
				if (((MethodElementEditor) getEditor()).mustRestoreValue(
						e.widget, oldContent)) {
					return;
				}
				String newContent = StrUtil.getPlainText(ctrl_presentation_name
						.getText());
				if (!newContent.equals(oldContent)) {
					boolean success = actionMgr.doAction(IActionManager.SET,
							contentElement, UmaPackage.eINSTANCE
									.getDescribableElement_PresentationName(),
							newContent, -1);
					if (success) {
						ctrl_presentation_name.setText(newContent);
					}
				}
			}
			
			/* (non-Javadoc)
			 * @see org.eclipse.swt.events.FocusAdapter#focusGained(org.eclipse.swt.events.FocusEvent)
			 */
			public void focusGained(FocusEvent e) {
				((MethodElementEditor) getEditor()).setCurrentFeatureEditor(e.widget, UmaPackage.eINSTANCE.getDescribableElement_PresentationName());
			}
		});

		if (briefDescOn) {
			ctrl_brief_desc.addModifyListener(modelModifyListener);
			ctrl_brief_desc.addFocusListener(new FocusAdapter() {
				public void focusGained(FocusEvent e) {
					((MethodElementEditor) getEditor()).setCurrentFeatureEditor(e.widget,
							UmaPackage.eINSTANCE.getMethodElement_BriefDescription());
				}

				/* (non-Javadoc)
				 * @see org.eclipse.swt.events.FocusAdapter#focusLost(org.eclipse.swt.events.FocusEvent)
				 */
				public void focusLost(FocusEvent e) {
					String oldContent = contentElement.getBriefDescription();
					if (((MethodElementEditor) getEditor()).mustRestoreValue(
							e.widget, oldContent)) {
						return;
					}
					String newContent = StrUtil.getPlainText(ctrl_brief_desc
							.getText());
					if (!newContent.equals(oldContent)) {
						boolean success = actionMgr.doAction(
								IActionManager.SET, contentElement,
								UmaPackage.eINSTANCE
										.getMethodElement_BriefDescription(),
								newContent, -1);
						if (success) {
							ctrl_brief_desc.setText(newContent);
						}
					}
				}
			});
		}

		if (elementTypeOn) {
			if (contentElement instanceof Guidance) {
				ctrl_type_button.addListener(SWT.Selection, new Listener() {
					public void handleEvent(Event event) {
						final MethodElementEditor editor = (MethodElementEditor) getEditor();
						if (editor.isDirty()) {
							String title = AuthoringUIResources.descriptionTabGuidanceWarningDialog_title; //$NON-NLS-1$
							String message = AuthoringUIResources.descriptionTabGuidanceWarningDialog_message1; //$NON-NLS-1$
							AuthoringUIPlugin.getDefault().getMsgDialog()
									.displayWarning(title, message);
						} else if (contentElement instanceof Guidance) {
							MethodElementDeleteAction deleteAction = new MethodElementDeleteAction();
							deleteAction.setEditingDomain(LibraryView.getView()
									.getEditingDomain());
							deleteAction
									.selectionChanged(new StructuredSelection(
											contentElement));
							Command cmd = deleteAction
									.createCommand(Collections
											.singleton(contentElement));
							if (cmd instanceof DeleteMethodElementCommand) {
								Guidance newGuidance = ConvertGuidanceType
										.convertGuidance(
												(Guidance) contentElement,
												null,
												(DeleteMethodElementCommand) cmd);
								if (newGuidance != null) {
									EditorChooser.getInstance().closeEditor(
											contentElement);
									EditorChooser.getInstance().openEditor(
											newGuidance);
								}
							}
						} else if (editor.isDirty()) {
							String title = AuthoringUIResources.descriptionTabGuidanceWarningDialog_title; //$NON-NLS-1$
							String message = AuthoringUIResources.descriptionTabGuidanceWarningDialog_message2; //$NON-NLS-1$
							AuthoringUIPlugin.getDefault().getMsgDialog()
									.displayWarning(title, message);
						}
					}
				});
			}
		}
	}

	private void addDetailSectionListeners() {
		if (fullDescOn) {
			ctrl_full_desc.setModalObject(contentElement.getPresentation());
			ctrl_full_desc.setModalObjectFeature(UmaPackage.eINSTANCE
					.getContentDescription_MainDescription());
			ctrl_full_desc.addModifyListener(contentModifyListener);
			ctrl_full_desc.addListener(SWT.Deactivate, new Listener() {
				public void handleEvent(Event e) {
					IMethodRichText control = descExpandFlag ? ctrl_expanded
							: ctrl_full_desc;
					if (debug) {
						System.out
								.println("DescriptionFormPage.ctrl_full_desc.deactivateListener: control=" + control); //$NON-NLS-1$
					}
					if (!control.getModified()) {
						if (debug) {
							System.out
									.println("DescriptionFormPage.ctrl_full_desc.deactivateListener: content not modified, exit"); //$NON-NLS-1$
						}
						return;
					}
					String oldContent = contentElement.getPresentation()
							.getMainDescription();
					if (((MethodElementEditor) getEditor()).mustRestoreValue(
							control, oldContent)) {
						if (debug) {
							System.out
									.println("DescriptionFormPage.ctrl_full_desc.deactivateListener: restored old content, exit"); //$NON-NLS-1$
						}
						return;
					}
					String newContent = control.getText();
					if (!newContent.equals(oldContent)) {
						if (debug) {
							System.out
									.println("DescriptionFormPage.ctrl_full_desc.deactivateListener: saving modified content"); //$NON-NLS-1$
						}
						boolean success = actionMgr
								.doAction(
										IActionManager.SET,
										contentElement.getPresentation(),
										UmaPackage.eINSTANCE
												.getContentDescription_MainDescription(),
										newContent, -1);
						if (debug) {
							System.out
									.println("DescriptionFormPage.ctrl_full_desc.deactivateListener: saved status=" + success); //$NON-NLS-1$
						}
						if (success && isVersionSectionOn()) {
							updateChangeDate();
						}
					}
					if (debug) {
						System.out
								.println("DescriptionFormPage.ctrl_full_desc.deactivateListener: exit"); //$NON-NLS-1$
					}
				}
			});
		}

		if (keyConsiderationOn) {
			ctrl_key.setModalObject(contentElement.getPresentation());
			ctrl_key.setModalObjectFeature(UmaPackage.eINSTANCE
					.getContentDescription_KeyConsiderations());
			ctrl_key.addModifyListener(contentModifyListener);
			ctrl_key.addListener(SWT.Deactivate, new Listener() {
				public void handleEvent(Event e) {
					IMethodRichText control = descExpandFlag ? ctrl_expanded
							: ctrl_key;
					if (debug) {
						System.out
								.println("DescriptionFormPage.ctrl_key.deactivateListener: control=" + control); //$NON-NLS-1$
					}
					if (!control.getModified()) {
						if (debug) {
							System.out
									.println("DescriptionFormPage.ctrl_key.deactivateListener: content not modified, exit"); //$NON-NLS-1$
						}
						return;
					}
					String oldContent = contentElement.getPresentation()
							.getKeyConsiderations();
					if (((MethodElementEditor) getEditor()).mustRestoreValue(
							control, oldContent)) {
						if (debug) {
							System.out
									.println("DescriptionFormPage.ctrl_key.deactivateListener: restored old content, exit"); //$NON-NLS-1$
						}
						return;
					}
					String newContent = control.getText();
					if (!newContent.equals(oldContent)) {
						boolean success = actionMgr
								.doAction(
										IActionManager.SET,
										contentElement.getPresentation(),
										UmaPackage.eINSTANCE
												.getContentDescription_KeyConsiderations(),
										newContent, -1);
						if (debug) {
							System.out
									.println("DescriptionFormPage.ctrl_key.deactivateListener: saved status=" + success); //$NON-NLS-1$
						}
						if (success && isVersionSectionOn()) {
							updateChangeDate();
						}
					}
					if (debug) {
						System.out
								.println("DescriptionFormPage.ctrl_key.deactivateListener: exit"); //$NON-NLS-1$
					}
				}
			});
		}
	}

	/**
	 * Initializes the controls with data from the model.
	 */
	protected void loadData() {
		if (generalSectionOn) {
			loadGeneralSectionData();
		}
		if (detailSectionOn) {
			loadDetailSectionData();
		}
		if (notationSectionOn) {
			loadNotationSectionData();
		}
		if (tailoringSectionOn) {
			loadTailoringSectionData();
		}
		if (versionSectionOn) {
			loadVersionSectionData();
		}
		if (iconSectionOn) {
			loadIconSectionData();
		}
		if (variabilitySectionOn) {
			variabilitySectionData();
		}
		form.getBody().layout(true, true);
	}

	private void loadGeneralSectionData() {
		String name = contentElement.getName();
		String presentationName = (contentElement).getPresentationName();
		ctrl_name.setText(name == null ? "" : name); //$NON-NLS-1$
		ctrl_presentation_name
				.setText(presentationName == null ? "" : presentationName); //$NON-NLS-1$

		if (elementTypeOn) {
			// String type = contentElement.getType().getName();
			String type = LibraryUIText.getUIText(contentElement);
			ctrl_type_label.setText(type == null ? "" : type); //$NON-NLS-1$
		}
		if (briefDescOn) {
			String brief_desc = contentElement.getBriefDescription();
			ctrl_brief_desc.setText(brief_desc == null ? "" : brief_desc); //$NON-NLS-1$
		}
	}

	private void loadDetailSectionData() {
		if (fullDescOn) {
			String full_desc = (contentElement.getPresentation())
					.getMainDescription();
			ctrl_full_desc.setText(full_desc == null ? "" : full_desc); //$NON-NLS-1$
		}
		if (keyConsiderationOn) {
			String keyConsiderations = (contentElement.getPresentation())
					.getKeyConsiderations();
			ctrl_key
					.setText(keyConsiderations == null ? "" : keyConsiderations); //$NON-NLS-1$
		}
	}

	private void loadTailoringSectionData() {
	}

	private void loadNotationSectionData() {
	}

	private void variabilitySectionData() {
		VariabilityType variabilityType = contentElement.getVariabilityType();
		List selectionVariabilityList = new ArrayList();
		selectionVariabilityList.add(variabilityType);
		IStructuredSelection newVariabilitySelection = new StructuredSelection(
				selectionVariabilityList);
		viewer_variability.setSelection(newVariabilitySelection, true);
	}

	/**
	 * Toggle Description control to expand and control state.
	 */
	protected void toggle(HyperlinkEvent e) {
		if (ctrl_expanded == null) {
			ctrl_expanded = createRichTextEditor(toolkit, expandedComposite,
					SWT.MULTI | SWT.WRAP | SWT.V_SCROLL, GridData.FILL_BOTH,
					getRichTextEditorHeight(), getRichTextEditorWidth(), 2);
			ctrl_expanded.addModifyListener(contentModifyListener);
		}

		if (descExpandFlag) {
			expandedComposite.setVisible(false);
			sectionComposite.setVisible(true);
			formSection.setClient(sectionComposite);
			enableSections(true);
			IMethodRichText richText = getActiveRichTextControl();
			richText.setText(ctrl_expanded.getText());
			for (Iterator i = richText.getListeners(); i.hasNext();) {
				RichTextListener listener = (RichTextListener) i.next();
				ctrl_expanded.removeListener(listener.getEventType(), listener
						.getListener());
			}
			if (ctrl_expanded.getModified()) {
				((MethodElementEditor) getEditor())
						.saveModifiedRichText(ctrl_expanded);
			}
			richText.setFocus();
		} else {
			sectionComposite.setVisible(false);
			expandedComposite.setVisible(true);
			formSection.setClient(expandedComposite);
			enableSections(false);
			expandLabel.setText((String) ((ImageHyperlink) e.getSource())
					.getData("Title")); //$NON-NLS-1$
			IMethodRichText richText = (IMethodRichText) e.getHref();
			ctrl_expanded.setText(richText.getText());
			ctrl_expanded.setModalObject(richText.getModalObject());
			ctrl_expanded.setModalObjectFeature(richText
					.getModalObjectFeature());
			for (Iterator i = richText.getListeners(); i.hasNext();) {
				RichTextListener listener = (RichTextListener) i.next();
				ctrl_expanded.addListener(listener.getEventType(), listener
						.getListener());
			}
			boolean editable = !TngUtil.isLocked(contentElement);
			ctrl_expanded.setEditable(editable);
			if (editable) {
				ctrl_expanded.setFocus();
			}
			setActiveRichTextControl(richText);
		}
		form.getBody().layout(true, true);
		descExpandFlag = !descExpandFlag;
	}

	/**
	 * Set the active rich text control.
	 */
	private void setActiveRichTextControl(IMethodRichText ctrl) {
		activeControl = ctrl;
	}

	/**
	 * Returns the active rich text control.
	 */
	private IMethodRichText getActiveRichTextControl() {
		return activeControl;
	}

	public void setBriefDescOn(boolean briefDescOn) {
		this.briefDescOn = briefDescOn;
	}

	public void setFullDescOn(boolean fullDescOn) {
		this.fullDescOn = fullDescOn;
	}

	public void setKeyConsiderationOn(boolean keyConsiderationOn) {
		this.keyConsiderationOn = keyConsiderationOn;
	}

	/**
	 * @param elementTypeOn
	 *            The elementTypeOn to set.
	 */
	public void setElementTypeOn(boolean elementTypeOn) {
		this.elementTypeOn = elementTypeOn;
	}

	/**
	 * @return Returns the anyAttributeModified.
	 */
	public boolean isAnyAttributeModified() {
		return anyAttributeModified;
	}

	/**
	 * Set this if any attribute is modified. this is required for the change
	 * date field in version section.
	 * 
	 * @param anyAttributeModified
	 *            The anyAttributeModified to set.
	 */
	public void setAnyAttributeModified(boolean anyAttributeModified) {
		this.anyAttributeModified = anyAttributeModified;
	}

	/**
	 * @return Returns the versionSectionOn.
	 */
	public boolean isVersionSectionOn() {
		return versionSectionOn;
	}

	/**
	 * @param versionSectionOn
	 *            The versionSectionOn to set.
	 */
	public void setVersionSectionOn(boolean versionSectionOn) {
		this.versionSectionOn = versionSectionOn;
	}

	/**
	 * Creates the Version Information section.
	 */
	private void createVersionSection(FormToolkit toolkit) {
		versionSection = toolkit.createSection(sectionComposite,
				Section.DESCRIPTION | Section.TWISTIE | Section.EXPANDED
						| Section.TITLE_BAR);
		TableWrapData td = new TableWrapData(TableWrapData.FILL_GRAB);
		versionSection.setLayoutData(td);
		versionSection.setText(AuthoringUIText.VERSION_INFO_SECTION_NAME);
		versionSection.setDescription(getVersionSectionDescription());
		versionSection.setLayout(new GridLayout());

		versionComposite = toolkit.createComposite(versionSection);
		versionComposite.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
		versionComposite.setLayout(new GridLayout(4, false));
		versionSection.setClient(versionComposite);
	}

	/**
	 * Create the Version section content.
	 */
	private void createVersionSectionContent() {
		ctrl_version = createTextEditWithLabel3(toolkit, versionComposite,
				AuthoringUIText.VERSION_TEXT, SWT.DEFAULT, SWT.SINGLE);

		ctrl_change_date = createTextEditWithLabel3(toolkit, versionComposite,
				AuthoringUIText.CHANGE_DATE_TEXT, SWT.DEFAULT, SWT.SINGLE);
		ctrl_change_date.setEditable(false);

		ctrl_change_desc = createTextEditWithLabel2(toolkit, versionComposite,
				AuthoringUIText.CHANGE_DESCRIPTION_TEXT);
		{
			GridData gridData = new GridData(GridData.FILL_HORIZONTAL
					| GridData.BEGINNING);
			gridData.heightHint = 40;
			ctrl_change_desc.setLayoutData(gridData);
		}

		Composite viewHistoryButtonPane = createComposite(toolkit,
				versionComposite, GridData.HORIZONTAL_ALIGN_END, 1, 1, 2);
		{
			GridData gridData = new GridData(GridData.HORIZONTAL_ALIGN_END);
			viewHistoryButtonPane.setLayoutData(gridData);
		}
		view_history_button = toolkit.createButton(viewHistoryButtonPane,
				AuthoringUIText.VIEW_HISTORY_BUTTON_TEXT, SWT.PUSH);

		ctrl_authors = createTextEditWithLabel3(toolkit, versionComposite,
				AuthoringUIText.AUTHORS_TEXT, 40, SWT.MULTI);

		label_copyright = createLabel(toolkit, versionComposite,
				AuthoringUIText.COPYRIGHT_TEXT, 2);
		ctrl_copyright = createTable(toolkit, versionComposite, SWT.SINGLE
				| SWT.READ_ONLY, GridData.FILL_HORIZONTAL | GridData.BEGINNING,
				5, 400, 1, 1);
		{
			GridData gridData = new GridData(GridData.FILL_HORIZONTAL
					| GridData.BEGINNING);
			gridData.heightHint = 24;
			ctrl_copyright.setLayoutData(gridData);
		}

		copyright_viewer = new TableViewer(ctrl_copyright);
		initContentProviderCopyright();
		copyright_viewer.setLabelProvider(copyrightLabelProviderBase);
		copyright_viewer.setInput(contentElement);
		Composite buttonpane = createComposite(toolkit, versionComposite,
				GridData.HORIZONTAL_ALIGN_END, 1, 1, 2);
		{
			GridData gridData = new GridData(GridData.HORIZONTAL_ALIGN_END);

			buttonpane.setLayoutData(gridData);
		}
		copyright_button = toolkit.createButton(buttonpane,
				AuthoringUIText.SELECT_BUTTON_TEXT, SWT.SIMPLE);
		copyright_button_deselect = toolkit.createButton(buttonpane,
				AuthoringUIText.DESELECT_BUTTON_TEXT, SWT.SIMPLE);

		setCopyrightButtonDeselect();

		// Create the expanded composite.
		toolkit.paintBordersFor(versionComposite);
		toolkit.paintBordersFor(viewHistoryButtonPane);
		toolkit.paintBordersFor(buttonpane);
	}

	private void initContentProviderCopyright() {
		copyrightContentProvider = new AdapterFactoryContentProvider(
				TngAdapterFactory.INSTANCE
						.getNavigatorView_ComposedAdapterFactory()) {
			public Object[] getElements(Object object) {
				List list = new ArrayList();
				if (contentElement.getPresentation().getCopyrightStatement() != null) {
					list.add(contentElement.getPresentation()
							.getCopyrightStatement());
				}
				return list.toArray();
			}

			public void notifyChanged(Notification notification) {
			}
		};
		copyright_viewer.setContentProvider(copyrightContentProvider);
	}

	protected void addVersionSectionListeners() {
		ctrl_version.addModifyListener(contentModifyListener);
		ctrl_version.addFocusListener(new FocusAdapter() {
			public void focusGained(FocusEvent e) {
				((MethodElementEditor) getEditor()).setCurrentFeatureEditor(e.widget,
						UmaPackage.eINSTANCE.getMethodUnit_Version());
			}

			public void focusLost(FocusEvent e) {
				String oldContent = contentElement.getPresentation()
						.getVersion();
				if (((MethodElementEditor) getEditor()).mustRestoreValue(
						e.widget, oldContent)) {
					return;
				}
				String newContent = StrUtil
						.getPlainText(ctrl_version.getText());
				if (!newContent.equals(oldContent)) {
					boolean status = actionMgr.doAction(IActionManager.SET,
							contentElement.getPresentation(),
							UmaPackage.eINSTANCE.getMethodUnit_Version(),
							newContent, -1);
					if (status) {
						updateChangeDate();
					}
				}
			}
		});

		ctrl_authors.addModifyListener(contentModifyListener);
		ctrl_authors.addFocusListener(new FocusAdapter() {
			public void focusGained(FocusEvent e) {
				((MethodElementEditor) getEditor()).setCurrentFeatureEditor(e.widget,
						UmaPackage.eINSTANCE.getMethodUnit_Authors());
			}

			public void focusLost(FocusEvent e) {
				String oldContent = contentElement.getPresentation()
						.getAuthors();
				if (((MethodElementEditor) getEditor()).mustRestoreValue(
						e.widget, oldContent)) {
					return;
				}
				String newContent = StrUtil
						.getPlainText(ctrl_authors.getText());
				if (!newContent.equals(oldContent)) {
					boolean status = actionMgr.doAction(IActionManager.SET,
							contentElement.getPresentation(),
							UmaPackage.eINSTANCE.getMethodUnit_Authors(),
							newContent, -1);
					if (status) {
						updateChangeDate();
					}
				}
			}
		});

		copyright_button.addSelectionListener(new SelectionAdapter() {
			public void widgetSelected(SelectionEvent e) {
				IFilter filter = new ContentFilter() {
					protected boolean childAccept(Object obj) {
						if (obj instanceof Guidance) {
							return (obj instanceof SupportingMaterial);
						}
						return false;
					}
				};
				List alreadyExsting = new ArrayList();
				if (ctrl_copyright.getItemCount() > 0) {
					TableItem item = ctrl_copyright.getItems()[0];
					if (item.getData() != null)
						alreadyExsting.add(item.getData());
				}
				ItemsFilterDialog fd = new ItemsFilterDialog(PlatformUI
						.getWorkbench().getActiveWorkbenchWindow().getShell(),
						filter, contentElement,
						FilterConstants.SUPPORTING_MATERIALS, alreadyExsting);
				fd.setViewerSelectionSingle(true);
				fd.setBlockOnOpen(true);
				fd.setTitle(FilterConstants.SUPPORTING_MATERIALS);
				fd.open();
				fd.getSelectedItems();
				if (fd.getSelectedItems().size() > 0) {
					boolean status = actionMgr.doAction(IActionManager.SET,
							contentElement.getPresentation(),
							UmaPackage.eINSTANCE
									.getMethodUnit_CopyrightStatement(),
							(SupportingMaterial) fd.getSelectedItems().get(0),
							-1);
					if (!status) {
						return;
					}
				}
				copyright_viewer.refresh();
				setCopyrightButtonDeselect();
			}
		});

		ctrl_change_desc.addModifyListener(contentModifyListener);
		ctrl_change_desc.addFocusListener(new FocusAdapter() {
			public void focusGained(FocusEvent e) {
				((MethodElementEditor) getEditor()).setCurrentFeatureEditor(e.widget,
						UmaPackage.eINSTANCE.getMethodUnit_ChangeDescription());
			}

			public void focusLost(FocusEvent e) {
				String oldContent = contentElement.getPresentation()
						.getChangeDescription();
				char delimiter = AuthoringUIResources.ChangeHistoryDialog_delimiter.charAt(0); //$NON-NLS-1$
				if (((MethodElementEditor) getEditor()).mustRestoreValue(
						e.widget, oldContent)) {
					return;
				}
				String newContent = ctrl_change_desc.getText();

				newContent = newContent.replace(delimiter, ' '); //$NON-NLS-1$ //$NON-NLS-2$

				if (!newContent.equals(lastChangeHistory)) {
					lastChangeHistory = newContent;
					if ((oldContent != null)
							&& (!(StrUtil.isBlank(oldContent)))) {
						newContent = oldContent + delimiter + newContent;
					}

					actionMgr.doAction(IActionManager.SET, contentElement
							.getPresentation(), UmaPackage.eINSTANCE
							.getMethodUnit_ChangeDescription(), newContent, -1);
				}
			}
		});

		view_history_button.addSelectionListener(new SelectionAdapter() {
			public void widgetSelected(SelectionEvent e) {

				ChangeHistoryDialog dlg = new ChangeHistoryDialog(PlatformUI
						.getWorkbench().getActiveWorkbenchWindow().getShell(),
						contentElement);
				dlg.open();
			}
		});

		copyright_button_deselect.addSelectionListener(new SelectionAdapter() {
			public void widgetSelected(SelectionEvent e) {
				boolean status = actionMgr.doAction(IActionManager.SET,
						contentElement.getPresentation(), UmaPackage.eINSTANCE
								.getMethodUnit_CopyrightStatement(), null, -1);
				if (status) {
					copyright_viewer.refresh();
					setCopyrightButtonDeselect();
				}
			}
		});
	}

	/*
	 * update the change date if any attribute is modified.
	 */
	protected void updateChangeDate() {

		Date changeDate = contentElement.getPresentation().getChangeDate();
		DateFormat df = DateFormat.getDateInstance(DateFormat.FULL);

		String oldContent = ""; //$NON-NLS-1$
		if (changeDate != null) {
			oldContent = df.format(changeDate);
		}

		Date currentDate = new Date();
		String newContent = df.format(currentDate);
		if (!newContent.equals(oldContent)) {
			boolean status = actionMgr.doAction(IActionManager.SET,
					contentElement.getPresentation(), UmaPackage.eINSTANCE
							.getMethodUnit_ChangeDate(), currentDate, -1);
			if (!status) {
				return;
			} else {
				ctrl_change_date.setText(newContent);
			}
		}
	}

	protected void loadVersionSectionData() {

		ContentDescription contentDescription = contentElement
				.getPresentation();
		ctrl_version
				.setText(contentDescription.getVersion() == null ? "" : contentDescription.getVersion()); //$NON-NLS-1$
		ctrl_authors
				.setText(contentDescription.getAuthors() == null ? "" : contentDescription.getAuthors()); //$NON-NLS-1$
		ctrl_change_desc.setText(""); //$NON-NLS-1$
		ctrl_change_date
				.setText(contentDescription.getChangeDate() == null ? "" //$NON-NLS-1$
						: DateFormat.getDateInstance(DateFormat.FULL).format(
								contentDescription.getChangeDate()));
	}

	/**
	 * Toggle Description control to expand and control state
	 */
	protected void toggle(HyperlinkEvent e, int id) {
		// TODO- we should combine these methods into one. One way to do it,
		// dispoing
		// ctrl_expanded every time it collapses and creating it when we expand.
		// At present, there is no method to dispose
		toggle(e);
	}

	/**
	 * @return Returns the iconSectionOn.
	 */
	public boolean isIconSectionOn() {
		return iconSectionOn;
	}

	/**
	 * @param iconSectionOn
	 *            The iconSectionOn to set.
	 */
	public void setIconSectionOn(boolean iconSectionOn) {
		this.iconSectionOn = iconSectionOn;
	}

	/**
	 * Creates the Icon section.
	 */
	protected void createIconSection(FormToolkit toolkit) {
		iconSection = toolkit.createSection(sectionComposite,
				Section.DESCRIPTION | Section.TWISTIE | Section.EXPANDED
						| Section.TITLE_BAR);
		TableWrapData td = new TableWrapData(TableWrapData.FILL_GRAB);
		iconSection.setLayoutData(td);
		iconSection.setText(AuthoringUIText.ICON_SECTION_NAME);
		iconSection.setDescription(getIconSectionDescription());
		iconSection.setLayout(new GridLayout());

		iconComposite = toolkit.createComposite(iconSection);
		iconComposite.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
		iconComposite.setLayout(new GridLayout(3, true));
		iconSection.setClient(iconComposite);
	}
	private void createIconSectionContent() {
		Composite shapeIconComposite = createComposite(toolkit, iconComposite,
				1);
		shapeIconComposite.setLayoutData(new GridData());
		shapeIconComposite.setLayout(new GridLayout(2, true));
		createLabel(
				toolkit,
				shapeIconComposite,
				AuthoringUIResources.DescriptionFormPage_ShapeIconPreview_Label, 2); //$NON-NLS-1$
		pane1 = new Canvas(shapeIconComposite, SWT.BORDER);
		{
			GridData gridData = new GridData(GridData.BEGINNING);

			gridData.heightHint = 60;
			gridData.widthHint = 60;
			gridData.verticalSpan = 1;
			gridData.horizontalSpan = 1;
			pane1.setLayoutData(gridData);
			pane1.setBackground(ColorConstants.lightGray);
		}
		// pane1.setSize(30,30);
		Composite pane2 = createCompositeForButtons(toolkit, shapeIconComposite);
		ctrl_select_shapeIcon_button = toolkit
				.createButton(
						pane2,
						AuthoringUIResources.DescriptionFormPage_ShapeIconPreview_SelectButtonLabel, SWT.NONE); //$NON-NLS-1$
		ctrl_clear_shapeIcon_button = toolkit
				.createButton(
						pane2,
						AuthoringUIResources.DescriptionFormPage_ShapeIconPreview_ClearButtonLabel, SWT.NONE); //$NON-NLS-1$
		if (contentElement.getShapeicon() == null)
			ctrl_clear_shapeIcon_button.setEnabled(false);
		else
			ctrl_clear_shapeIcon_button.setEnabled(true);

		Composite nodeIconComposite = createComposite(toolkit, iconComposite, 1);
		nodeIconComposite.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
		nodeIconComposite.setLayout(new GridLayout(2, false));
		createLabel(
				toolkit,
				nodeIconComposite,
				AuthoringUIResources.DescriptionFormPage_NodeIconPreview_Label, 2); //$NON-NLS-1$
		pane3 = new Canvas(nodeIconComposite, SWT.BORDER);
		{
			GridData gridData = new GridData(GridData.BEGINNING);

			gridData.heightHint = 40;
			gridData.widthHint = 40;
			gridData.verticalSpan = 1;
			gridData.horizontalSpan = 1;
			pane3.setLayoutData(gridData);
			pane3.setBackground(ColorConstants.lightGray);
		}
		Composite pane4 = createCompositeForButtons(toolkit, nodeIconComposite);
		ctrl_select_nodeIcon_button = toolkit
				.createButton(
						pane4,
						AuthoringUIResources.DescriptionFormPage_NodeIconPreview_SelectButtonLabel, SWT.NONE); //$NON-NLS-1$
		ctrl_clear_nodeIcon_button = toolkit
				.createButton(
						pane4,
						AuthoringUIResources.DescriptionFormPage_NodeIconPreview_ClearButtonLabel, SWT.NONE); //$NON-NLS-1$
		if (contentElement.getNodeicon() == null)
			ctrl_clear_nodeIcon_button.setEnabled(false);
		else
			ctrl_clear_nodeIcon_button.setEnabled(true);

		toolkit.paintBordersFor(pane1);
		toolkit.paintBordersFor(pane2);
		toolkit.paintBordersFor(pane3);
		toolkit.paintBordersFor(pane4);
	}

	protected void addIconSectionListeners() {

		ctrl_select_shapeIcon_button
				.addSelectionListener(new SelectionAdapter() {
					File libDirFile = new File(LibraryService.getInstance()
							.getCurrentMethodLibraryPath());

					public void widgetSelected(SelectionEvent e) {
						java.net.URI shapeIconUri = null;
						FileDialog fileChooser = new FileDialog(Display
								.getCurrent().getActiveShell(), SWT.OPEN);
						fileChooser
								.setText(AuthoringUIResources.DescriptionFormPage_IconFileChooserDialog_title); //$NON-NLS-1$
						fileChooser
								.setFilterExtensions(new String[] { "*.gif; *.jpg; *.png; *.ico; *.bmp" }); //$NON-NLS-1$
						fileChooser.setFilterNames(new String[] { "Image" //$NON-NLS-1$
								+ " (gif, jpeg, png, ico, bmp)" }); //$NON-NLS-1$
						String imageFile = null;
						String filename = null;
						while (true) {
							imageFile = fileChooser.open();
							filename = fileChooser.getFileName();
							if (imageFile != null) {
								if (new File(imageFile).exists()) {
									ImageData imageData = new ImageData(
											imageFile);
									if (imageData.width > SHAPEICON_WIDTH_MAX
											|| imageData.height > SHAPEICON_HEIGHT_MAX) {
										// msg user - image too big
										AuthoringUIPlugin
												.getDefault()
												.getMsgDialog()
												.displayError(
														AuthoringUIResources.forms_DescriptionFormPage_imageTooBigDialog_title, //$NON-NLS-1$ 
														MessageFormat
																.format(
																		AuthoringUIResources.forms_DescriptionFormPage_imageTooBigDialog_template, //$NON-NLS-1$
																		new Object[] {
																				imageFile,
																				new Integer(
																						SHAPEICON_WIDTH_MAX),
																				new Integer(
																						SHAPEICON_HEIGHT_MAX) }));
									} else {
										break;
									}
								} else {
									// msg user - file doesn't exist
									AuthoringUIPlugin
											.getDefault()
											.getMsgDialog()
											.displayError(
													AuthoringUIResources.forms_DescriptionFormPage_imageNotFoundDialog_title, //$NON-NLS-1$ 
													MessageFormat
															.format(
																	AuthoringUIResources.forms_DescriptionFormPage_imageNotFoundDialog_template, //$NON-NLS-1$ 
																	new Object[] { imageFile }));
								}
							} else {
								return;
							}
						}
						if (imageFile != null && imageFile.length() > 0) {
							try {
								String url = copyResourceToLib(filename,
										fileChooser.getFilterPath(),
										contentElement);
								File file = new File(url);
								shapeIconUri = new URI(NetUtil
										.encodeFileURL(FileUtil
												.getRelativePath(file,
														libDirFile)));
								if (shapeIconUri != null) {
									boolean status = actionMgr
											.doAction(
													IActionManager.SET,
													contentElement,
													UmaPackage.eINSTANCE
															.getDescribableElement_Shapeicon(),
													shapeIconUri, -1);
									if (!status)
										return;
								}
								shapeImage = new Image(Display.getCurrent(),
										file.getAbsolutePath());
							} catch (Exception ex) {
								shapeIconUri = null;
								shapeImage = null;
								AuthoringUIPlugin.getDefault().getLogger()
										.logError(ex);
								if (ex instanceof IOException) {
									AuthoringUIPlugin
											.getDefault()
											.getMsgDialog()
											.displayError(
													AuthoringUIResources.err_copying_file_title, //$NON-NLS-1$
													AuthoringUIResources.err_copying_file_error, //$NON-NLS-1$
													AuthoringUIResources.err_copying_file_reason, //$NON-NLS-1$
													ex.getMessage());
								} else {
									AuthoringUIPlugin
											.getDefault()
											.getMsgDialog()
											.displayError(
													AuthoringUIResources.err_processing_file_title, //$NON-NLS-1$
													AuthoringUIResources.err_processing_file_description, ex); //$NON-NLS-1$
								}
							}
						}
						if (shapeImage != null) {
							pane1.redraw();
							ctrl_clear_shapeIcon_button.setEnabled(true);
						} else {
							ctrl_clear_shapeIcon_button.setEnabled(false);
						}

					}
				});

		ctrl_clear_shapeIcon_button
				.addSelectionListener(new SelectionAdapter() {
					public void widgetSelected(SelectionEvent e) {
						boolean status = actionMgr.doAction(IActionManager.SET,
								contentElement, UmaPackage.eINSTANCE
										.getDescribableElement_Shapeicon(),
								null, -1);
						if (!status)
							return;
						pane1.redraw();
						ctrl_clear_shapeIcon_button.setEnabled(false);
					}
				});

		ctrl_select_nodeIcon_button
				.addSelectionListener(new SelectionAdapter() {
					File libDirFile = new File(LibraryService.getInstance()
							.getCurrentMethodLibraryPath());

					public void widgetSelected(SelectionEvent e) {
						java.net.URI nodeIconUri = null;
						FileDialog fileChooser = new FileDialog(Display
								.getCurrent().getActiveShell(), SWT.OPEN);
						fileChooser
								.setText(AuthoringUIResources.DescriptionFormPage_IconFileChooserDialog_title); //$NON-NLS-1$
						fileChooser
								.setFilterExtensions(new String[] { "*.gif; *.jpg; *.png; *.ico; *.bmp" }); //$NON-NLS-1$
						fileChooser.setFilterNames(new String[] { "Image" //$NON-NLS-1$
								+ " (gif, jpeg, png, ico, bmp)" }); //$NON-NLS-1$
						String imageFile = null;
						String filename = null;
						while (true) {
							imageFile = fileChooser.open();
							filename = fileChooser.getFileName();
							if (imageFile != null) {
								if (new File(imageFile).exists()) {
									ImageData imageData = new ImageData(
											imageFile);
									if (imageData.width > NODEICON_WIDTH_MAX
											|| imageData.height > NODEICON_HEIGHT_MAX) {
										// msg user - image too big
										AuthoringUIPlugin
												.getDefault()
												.getMsgDialog()
												.displayError(
														AuthoringUIResources.forms_DescriptionFormPage_imageTooBigDialog_title, //$NON-NLS-1$ 
														MessageFormat
																.format(
																		AuthoringUIResources.forms_DescriptionFormPage_imageTooBigDialog_template, //$NON-NLS-1$
																		new Object[] {
																				imageFile,
																				new Integer(
																						NODEICON_WIDTH_MAX),
																				new Integer(
																						NODEICON_HEIGHT_MAX) }));
									} else {
										break;
									}
								} else {
									// msg user - file doesn't exist
									AuthoringUIPlugin
											.getDefault()
											.getMsgDialog()
											.displayError(
													AuthoringUIResources.forms_DescriptionFormPage_imageNotFoundDialog_title, //$NON-NLS-1$
													MessageFormat
															.format(
																	AuthoringUIResources.forms_DescriptionFormPage_imageNotFoundDialog_template, //$NON-NLS-1$
																	new Object[] { imageFile }));
								}
							} else {
								return;
							}
						}
						if (imageFile != null && imageFile.length() > 0) {
							try {
								String url = copyResourceToLib(filename,
										fileChooser.getFilterPath(),
										contentElement);
								File file = new File(url);
								nodeIconUri = new URI(NetUtil
										.encodeFileURL(FileUtil
												.getRelativePath(file,
														libDirFile)));
								if (nodeIconUri != null) {
									boolean status = actionMgr
											.doAction(
													IActionManager.SET,
													contentElement,
													UmaPackage.eINSTANCE
															.getDescribableElement_Nodeicon(),
													nodeIconUri, -1);
									if (!status)
										return;
								}
								nodeImage = new Image(Display.getCurrent(),
										file.getAbsolutePath());
							} catch (Exception ex) {
								nodeIconUri = null;
								nodeImage = null;
								AuthoringUIPlugin.getDefault().getLogger()
										.logError(ex);
								if (ex instanceof IOException) {
									AuthoringUIPlugin
											.getDefault()
											.getMsgDialog()
											.displayError(
													AuthoringUIResources.err_copying_file_title, //$NON-NLS-1$
													AuthoringUIResources.err_copying_file_error, //$NON-NLS-1$
													AuthoringUIResources.err_copying_file_reason, //$NON-NLS-1$
													ex.getMessage());

								} else {
									AuthoringUIPlugin
											.getDefault()
											.getMsgDialog()
											.displayError(
													AuthoringUIResources.err_processing_file_title, //$NON-NLS-1$
													AuthoringUIResources.err_processing_file_description, ex); //$NON-NLS-1$
								}
							}
						}
						if (nodeImage != null) {
							pane3.redraw();
							ctrl_clear_nodeIcon_button.setEnabled(true);
						} else {
							ctrl_clear_nodeIcon_button.setEnabled(false);
						}
					}
				});

		ctrl_clear_nodeIcon_button.addSelectionListener(new SelectionAdapter() {
			public void widgetSelected(SelectionEvent e) {
				boolean status = actionMgr.doAction(IActionManager.SET,
						contentElement, UmaPackage.eINSTANCE
								.getDescribableElement_Nodeicon(), null, -1);
				if (!status)
					return;
				pane3.redraw();
				ctrl_clear_nodeIcon_button.setEnabled(false);
			}
		});
	}

	protected String copyResourceToLib(String sFileName, String sFilePath,
			MethodElement methodElement) throws IOException {
		File libDirs = new File(LibraryService.getInstance().getCurrentMethodLibraryPath());
		String resourceLoc = libDirs.getAbsolutePath() + File.separator
				+ MethodLibraryPersister.getResourcePath(methodElement);

		File sFile = new File(sFilePath + File.separator + sFileName);
		StringBuffer resourceFile = new StringBuffer(resourceLoc).append(
				File.separator).append(sFileName);
		File formatFile = new File(resourceFile.toString());

		FileUtil.copyfile(sFile, formatFile);

		return resourceFile.toString();
	}

	protected void loadIconSectionData() {
		pane1.addPaintListener(new PaintListener() {
			public void paintControl(PaintEvent e) {
				// paint the grey background
				Rectangle clientRect = pane1.getClientArea();
				e.gc.setClipping(clientRect);
				e.gc.setBackground(Display.getCurrent().getSystemColor(15));
				e.gc.fillRectangle(clientRect);

				java.net.URI uri = contentElement.getShapeicon();
				if (uri != null) {
					String path = contentElement.getShapeicon().getPath();
					if (path != null) {
						try {
							File file = new File(path);
							if (file.exists()) {
							} else {
								if (!file.isAbsolute()) {
									path = LibraryService.getInstance()
											.getCurrentMethodLibraryPath()
											+ File.separator + path;
								}
								file = new File(path);
							}
							if (file.exists()) {
								if (shapeImage == null) {
									shapeImage = new Image(
											Display.getCurrent(), path);
								}
								clientRect = pane1.getClientArea();
								e.gc.setClipping(clientRect);
								e.gc.setBackground(Display.getCurrent()
										.getSystemColor(15));
								e.gc.fillRectangle(clientRect);
								e.gc.drawImage(shapeImage, shapeImage
										.getBounds().x,
										shapeImage.getBounds().y, shapeImage
												.getBounds().width, shapeImage
												.getBounds().height, pane1
												.getClientArea().x, pane1
												.getClientArea().y, pane1
												.getClientArea().width, pane1
												.getClientArea().height);
							} else {
								if (warningCount == 1) {
									String msg = AuthoringUIResources.bind(AuthoringUIResources.DescriptionFormPage_LoadShapeIconWarning, (new Object[] { contentElement.getName(), path })); //$NON-NLS-1$
									MsgBox.showWarning(msg);
									warningCount++;
								}

							}
						} catch (Exception ex) {
							AuthoringUIPlugin
									.getDefault()
									.getLogger()
									.logError(
											AuthoringUIResources.bind(AuthoringUIResources.DescriptionFormPage_LoadShapeIconError, (new Object[] { ex.getMessage() }))); //$NON-NLS-1$
						}
					}
				}
			}

		});
		pane1.redraw();

		pane3.addPaintListener(new PaintListener() {
			public void paintControl(PaintEvent e) {
				// paint the grey background
				Rectangle clientRect = pane3.getClientArea();
				e.gc.setClipping(clientRect);
				e.gc.setBackground(Display.getCurrent().getSystemColor(15));
				e.gc.fillRectangle(clientRect);

				java.net.URI uri = contentElement.getNodeicon();
				if (uri != null) {
					String path = contentElement.getNodeicon().getPath();
					if (path != null) {
						try {
							File file = new File(path);
							if (file.exists()) {
							} else {
								if (!file.isAbsolute()) {
									path = LibraryService.getInstance()
											.getCurrentMethodLibraryPath()
											+ File.separator + path;
								}
								file = new File(path);
							}
							if (file.exists()) {
								if (nodeImage == null) {
									nodeImage = new Image(Display.getCurrent(),
											path);
								}
								clientRect = pane3.getClientArea();
								e.gc.setClipping(clientRect);
								e.gc.setBackground(Display.getCurrent()
										.getSystemColor(15));
								e.gc.fillRectangle(clientRect);
								e.gc.drawImage(nodeImage,
										nodeImage.getBounds().x, nodeImage
												.getBounds().y, nodeImage
												.getBounds().width, nodeImage
												.getBounds().height, pane3
												.getClientArea().x, pane3
												.getClientArea().y, pane3
												.getClientArea().width, pane3
												.getClientArea().height);
							} else {
								if (warningCount == 1) {
									String msg = AuthoringUIResources.bind(AuthoringUIResources.DescriptionFormPage_LoadNodeIconWarning, (new Object[] { contentElement.getName(), path })); //$NON-NLS-1$
									MsgBox.showWarning(msg);
									warningCount++;
								}

							}
						} catch (Exception ex) {
							AuthoringUIPlugin
									.getDefault()
									.getLogger()
									.logError(
											AuthoringUIResources.bind(AuthoringUIResources.DescriptionFormPage_LoadNodeIconError, (new Object[] { ex.getMessage() }))); //$NON-NLS-1$
						}
					}
				}
			}

		});
		pane3.redraw();

	}

	protected void enableSections(boolean enable) {
		if (generalSectionOn) {
			generalSection.setVisible(enable);
			if (enable) {
				generalSection.setExpanded(generalSectionExpandFlag);
			} else {
				generalSectionExpandFlag = generalSection.isExpanded();
				generalSection.setExpanded(enable);
			}
		}

		if (detailSectionOn) {
			detailSection.setVisible(enable);
			if (enable) {
				detailSection.setExpanded(detailSectionExpandFlag);
			} else {
				detailSectionExpandFlag = detailSection.isExpanded();
				detailSection.setExpanded(enable);
			}
		}
		if (notationSectionOn) {
			notationSection.setVisible(enable);
			if (enable) {
				notationSection.setExpanded(notationSectionExpandFlag);
			} else {
				notationSectionExpandFlag = notationSection.isExpanded();
				notationSection.setExpanded(enable);
			}
		}
		if (tailoringSectionOn) {
			tailoringSection.setVisible(enable);
			if (enable) {
				tailoringSection.setExpanded(tailoringSectionExpandFlag);
			} else {
				tailoringSectionExpandFlag = tailoringSection.isExpanded();
				tailoringSection.setExpanded(enable);
			}
		}
		if (versionSectionOn) {
			versionSection.setVisible(enable);
			if (enable) {
				versionSection.setExpanded(versionSectionExpandFlag);
			} else {
				versionSectionExpandFlag = versionSection.isExpanded();
				versionSection.setExpanded(enable);
			}
		}
		if (iconSectionOn) {
			iconSection.setVisible(enable);
			if (enable) {
				iconSection.setExpanded(iconSectionExpandFlag);
			} else {
				iconSectionExpandFlag = iconSection.isExpanded();
				iconSection.setExpanded(enable);
			}
		}
		if (variabilitySectionOn) {
			variabilitySection.setVisible(enable);
			if (enable) {
				variabilitySection.setExpanded(elementSectionExpandFlag);
			} else {
				elementSectionExpandFlag = variabilitySection.isExpanded();
				variabilitySection.setExpanded(enable);
			}
		}
	}

	public void dispose() {
		if (shapeImage != null) {
			shapeImage.dispose();
		}
		if (nodeImage != null) {
			nodeImage.dispose();
		}
		if (labelProviderVariability != null) {
			labelProviderVariability.dispose();
		}
		if (contentProviderVariability != null) {
			contentProviderVariability.dispose();
		}
		if (labelProviderBase != null) {
			labelProviderBase.dispose();
		}
		if (copyrightLabelProviderBase != null) {
			copyrightLabelProviderBase.dispose();
		}
		super.dispose();
		
		disposed = true;
	}		

	public int getRichTextEditorHeight() {
		return form.getBounds().height - 3 * 32;
	}

	public int getRichTextEditorWidth() {
		return Math.max(560, form.getBounds().width - 2 * 32);
	}

	private void setCopyrightButtonDeselect() {
		if (contentElement.getPresentation().getCopyrightStatement() != null) {
			copyright_button_deselect
					.setEnabled((contentElement.getPresentation()
							.getCopyrightStatement().getName() == null) ? false
							: true);
		} else
			copyright_button_deselect.setEnabled(false);
		if (TngUtil.isLocked(contentElement))
			copyright_button_deselect.setEnabled(false);
	}

	private void setContextHelp() {
		if (sectionComposite != null) {
			EditorsContextHelper.setHelp(sectionComposite.getParent(),
					getContentElement());
		}
		if (expandedComposite != null) {
			PlatformUI.getWorkbench().getHelpSystem().setHelp(
					expandedComposite,
					AuthoringUIHelpContexts.RICH_TEXT_EDITOR_CONTEXT_ID);
		}

	}

	/* (non-Javadoc)
	 * @see org.eclipse.epf.authoring.ui.forms.IRefreshable#refreshName(java.lang.String)
	 */
	public void refreshName(String newName) {
		if (newName != null) {
			if ((ctrl_name != null) && !(ctrl_name.isDisposed())) {
				ctrl_name.removeModifyListener(modelModifyListener);
				ctrl_name.setText(newName);
				ctrl_name.addModifyListener(modelModifyListener);
				setFormTextWithVariableInfo();
			}
		}
	}
	
	public void loadSectionDescription(){
		
	}
	protected String getDetailSectionDescription(){
		if(detailSectionDescription != null){
			return detailSectionDescription;
		}
		return AuthoringUIText.DETAIL_SECTION_DESC;
	}
	protected String getGeneralSectionDescription(){
		if(generalSectionDescription!= null){
			return generalSectionDescription;
		}
		return AuthoringUIText.GENERAL_INFO_SECTION_DESC;
	}
	protected String getTailoringSectionDescription(){
		if(tailoringSectionDescription != null){
			return tailoringSectionDescription;
		}
		return AuthoringUIText.TAILORING_SECTION_DESC;
	}
	protected String getNotationSectionDescription(){
		if(notationSectionDescription != null){
			return notationSectionDescription;
		}
		return AuthoringUIText.NOTATION_SECTION_DESC;
	}
	protected String getVariabilitySectionDescription(){
		if(variabilitySectionDescription != null){
			return variabilitySectionDescription;
		}
		return AuthoringUIText.VARIABILITY_SECTION_DESC;
	}
	
	private String getIconSectionDescription() {
		// TODO Auto-generated method stubs
		if(iconSectionDescription != null){
			return iconSectionDescription;
		}
		return AuthoringUIText.ICON_SECTION_DESC;
	}
	private String getVersionSectionDescription() {
		// TODO Auto-generated method stub
		if(versionSectionDescription != null){
			return versionSectionDescription;
		}
		return AuthoringUIText.VERSION_INFO_SECTION_DESC;
	}

	/** 
	 * Following methods below exposed public in order to allow 
	 * test automation to access the form objects through test objects
	 * of any automation tools.
	 */
	
	/**
	 * @return Returns the ctrl_brief_desc.
	 */
	public Text getCtrl_brief_desc() {
		return ctrl_brief_desc;
	}

	/**
	 * @param ctrl_brief_desc The ctrl_brief_desc to set.
	 */
	public void setCtrl_brief_desc(Text ctrl_brief_desc) {
		this.ctrl_brief_desc = ctrl_brief_desc;
	}

	/**
	 * @return Returns the ctrl_full_desc.
	 */
	public IMethodRichText getCtrl_full_desc() {
		return ctrl_full_desc;
	}

	/**
	 * @param ctrl_full_desc The ctrl_full_desc to set.
	 */
	public void setCtrl_full_desc(IMethodRichText ctrl_full_desc) {
		this.ctrl_full_desc = ctrl_full_desc;
	}

	/**
	 * @return Returns the ctrl_presentation_name.
	 */
	public Text getCtrl_presentation_name() {
		return ctrl_presentation_name;
	}

	/**
	 * @param ctrl_presentation_name The ctrl_presentation_name to set.
	 */
	public void setCtrl_presentation_name(Text ctrl_presentation_name) {
		this.ctrl_presentation_name = ctrl_presentation_name;
	}

	/**
	 * @return Returns the ctrl_expanded.
	 */
	public IMethodRichTextEditor getCtrl_expanded() {
		return ctrl_expanded;
	}

	/**
	 * @param ctrl_expanded The ctrl_expanded to set.
	 */
	public void setCtrl_expanded(IMethodRichTextEditor ctrl_expanded) {
		this.ctrl_expanded = ctrl_expanded;
	}

	/**
	 * @return Returns the ctrl_key.
	 */
	public IMethodRichText getCtrl_key() {
		return ctrl_key;
	}

	/**
	 * @param ctrl_key The ctrl_key to set.
	 */
	public void setCtrl_key(IMethodRichText ctrl_key) {
		this.ctrl_key = ctrl_key;
	}
}
