/*******************************************************************************
 * Copyright (c) 2001, 2004 IBM Corporation and others.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 * 
 * Contributors:
 *     IBM Corporation - initial API and implementation
 *     Jens Lukowski/Innoopract - initial renaming/restructuring
 *     
 *******************************************************************************/
package org.eclipse.wst.sse.ui;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

import org.eclipse.core.resources.IResource;
import org.eclipse.jface.text.DefaultInformationControl;
import org.eclipse.jface.text.IInformationControl;
import org.eclipse.jface.text.IInformationControlCreator;
import org.eclipse.jface.text.IUndoManager;
import org.eclipse.jface.text.contentassist.ContentAssistant;
import org.eclipse.jface.text.contentassist.IContentAssistProcessor;
import org.eclipse.jface.text.contentassist.IContentAssistant;
import org.eclipse.jface.text.presentation.IPresentationReconciler;
import org.eclipse.jface.text.source.IAnnotationHover;
import org.eclipse.jface.text.source.ISourceViewer;
import org.eclipse.jface.text.source.SourceViewerConfiguration;
import org.eclipse.swt.SWT;
import org.eclipse.swt.widgets.Shell;
import org.eclipse.ui.IEditorPart;
import org.eclipse.ui.texteditor.AbstractDecoratedTextEditorPreferenceConstants;
import org.eclipse.ui.texteditor.ITextEditor;
import org.eclipse.wst.sse.core.text.IStructuredDocument;
import org.eclipse.wst.sse.ui.contentassist.IResourceDependentProcessor;
import org.eclipse.wst.sse.ui.extension.IExtendedConfiguration;
import org.eclipse.wst.sse.ui.internal.SSEUIPlugin;
import org.eclipse.wst.sse.ui.internal.editor.HTMLTextPresenter;
import org.eclipse.wst.sse.ui.internal.reconcile.validator.ValidatorBuilder;
import org.eclipse.wst.sse.ui.internal.reconcile.validator.ValidatorMetaData;
import org.eclipse.wst.sse.ui.internal.reconcile.validator.ValidatorStrategy;
import org.eclipse.wst.sse.ui.style.Highlighter;
import org.eclipse.wst.sse.ui.style.IHighlighter;
import org.eclipse.wst.sse.ui.taginfo.TextHoverManager;
import org.eclipse.wst.sse.ui.util.EditorUtility;


/**
 * Configuration for a TextViewer that shows Structured Text (XML)
 */
public class StructuredTextViewerConfiguration extends SourceViewerConfiguration implements IExtendedConfiguration {

	public static final String ID = "textviewerconfiguration"; //$NON-NLS-1$
	protected String[] configuredContentTypes;
	protected IEditorPart editorPart;
	private IAnnotationHover fAnnotationHover = null;
	protected IContentAssistant fContentAssistant;
	private List fContentAssistProcessors = null;
	protected IContentAssistant fCorrectionAssistant;
	private String fDeclaringID;
	protected IHighlighter fHighlighter;
	protected StructuredTextReconciler fReconciler;
	protected IResource fResource = null;
	protected final String SSE_EDITOR_ID = "org.eclipse.wst.sse.ui"; //$NON-NLS-1$
	protected final String SSE_MODEL_ID = "org.eclipse.wst.sse.core"; //$NON-NLS-1$

	/**
	 * Default constructor.
	 */
	public StructuredTextViewerConfiguration() {
		super();
		fContentAssistProcessors = new ArrayList();
	}

	/**
	 * use this constructor to have reconciler
	 */
	public StructuredTextViewerConfiguration(IEditorPart textEditor) {

		this();
		editorPart = textEditor;
	}

	/**
	 * Content assist processors should be added to the ContentAssistant via
	 * this method so that they are initialized/released properly.
	 * 
	 * @param ca
	 * @param processor
	 * @param partitionType
	 */
	public void addContentAssistProcessor(ContentAssistant ca, IContentAssistProcessor processor, String partitionType) {

		// save for reinit and release
		fContentAssistProcessors.add(processor);
		if (processor instanceof IResourceDependentProcessor)
			((IResourceDependentProcessor) processor).initialize(fResource);
		ca.setContentAssistProcessor(processor, partitionType);
	}

	public void configureOn(IResource resource) {

		fResource = resource;
		updateForResource();
	}

	protected ValidatorStrategy createValidatorStrategy(String contentTypeId) {

		ValidatorStrategy validatorStrategy = new ValidatorStrategy((ITextEditor) editorPart, contentTypeId);
		ValidatorBuilder vBuilder = new ValidatorBuilder();
		ValidatorMetaData[] vmds = vBuilder.getValidatorMetaData("org.eclipse.wst.sse.ui"); //$NON-NLS-1$
		for (int i = 0; i < vmds.length; i++) {
			if (vmds[i].canHandleContentType(contentTypeId))
				validatorStrategy.addValidatorMetaData(vmds[i]);
		}
		return validatorStrategy;
	}

	/**
	 * Returns the annotation hover which will provide the information to be
	 * shown in a hover popup window when requested for the given source
	 * viewer.
	 * 
	 * @param sourceViewer
	 *            the source viewer to be configured by this configuration
	 * @return an annotation hover or <code>null</code> if no hover support
	 *         should be installed
	 */
	public IAnnotationHover getAnnotationHover(ISourceViewer sourceViewer) {
		if (fAnnotationHover == null) {
			fAnnotationHover = new StructuredTextAnnotationHover();
		}
		return fAnnotationHover;
	}

	/**
	 * @param sourceViewer
	 * @return a Map of partition content types to java.util.List of
	 *         IAutoEditStrategy objects
	 */
	public Map getAutoEditStrategies(ISourceViewer sourceViewer) {
		return new HashMap();
	}
	
	/* (non-Javadoc)
	 * @see org.eclipse.jface.text.source.SourceViewerConfiguration#getConfiguredDocumentPartitioning(org.eclipse.jface.text.source.ISourceViewer)
	 */
	public String getConfiguredDocumentPartitioning(ISourceViewer sourceViewer) {
		return IStructuredDocument.DEFAULT_STRUCTURED_PARTITIONING;
	}

	/*
	 * @see SourceViewerConfiguration#getConfiguredTextHoverStateMasks(ISourceViewer,
	 *      String)
	 * @since 2.1
	 */
	public int[] getConfiguredTextHoverStateMasks(ISourceViewer sourceViewer, String contentType) {
		// content type does not matter when getting hover state mask
		TextHoverManager.TextHoverDescriptor[] hoverDescs = SSEUIPlugin.getDefault().getTextHoverManager().getTextHovers();
		int stateMasks[] = new int[hoverDescs.length];
		int stateMasksLength = 0;
		for (int i = 0; i < hoverDescs.length; i++) {
			if (hoverDescs[i].isEnabled()) {
				int j = 0;
				int stateMask = EditorUtility.computeStateMask(hoverDescs[i].getModifierString());
				while (j < stateMasksLength) {
					if (stateMasks[j] == stateMask)
						break;
					j++;
				}
				if (j == stateMasksLength)
					stateMasks[stateMasksLength++] = stateMask;
			}
		}
		if (stateMasksLength == hoverDescs.length)
			return stateMasks;

		int[] shortenedStateMasks = new int[stateMasksLength];
		System.arraycopy(stateMasks, 0, shortenedStateMasks, 0, stateMasksLength);
		return shortenedStateMasks;
	}

	/**
	 * @see ISourceViewerConfiguration#getContentAssistant
	 */
	public IContentAssistant getContentAssistant(ISourceViewer sourceViewer) {

		if (fContentAssistant == null) {
			// Ensure that only one assistant is ever returned. Creating a
			// second assistant
			// that is added to a viewer can cause odd key-eating by the wrong
			// one.
			ContentAssistant assistant = new ContentAssistant();
			// content assistant configurations
			assistant.setDocumentPartitioning(getConfiguredDocumentPartitioning(sourceViewer));
			assistant.enableAutoActivation(true);
			assistant.setAutoActivationDelay(500);
			assistant.setProposalPopupOrientation(IContentAssistant.PROPOSAL_OVERLAY);
			assistant.setContextInformationPopupOrientation(IContentAssistant.CONTEXT_INFO_ABOVE);
			assistant.setInformationControlCreator(getInformationControlCreator(sourceViewer));
			fContentAssistant = assistant;
		}
		updateForResource();
		return fContentAssistant;
	}

	public IContentAssistant getCorrectionAssistant(ISourceViewer sourceViewer) {

		if (fCorrectionAssistant == null) {
			// Ensure that only one assistant is ever returned. Creating a
			// second assistant
			// that is added to a viewer can cause odd key-eating by the wrong
			// one.
			ContentAssistant assistant = new ContentAssistant();
			assistant.setDocumentPartitioning(getConfiguredDocumentPartitioning(sourceViewer));
			fCorrectionAssistant = assistant;
		}
		updateForResource();
		return fCorrectionAssistant;
	}

	/**
	 * @return Returns the declaringID.
	 */
	public String getDeclaringID() {

		return fDeclaringID;
	}

	/**
	 * @return Returns the editorPart.
	 */
	public IEditorPart getEditorPart() {

		return editorPart;
	}

	public IHighlighter getHighlighter(ISourceViewer viewer) {

		// assuming for now that only one highlighter is needed per
		// configuration,
		// and that its just configured for lots of different content types.
		// In the future, this may change, if its tied closer to the acutual
		// content
		// type (for example, made specifc for HTML vs. XML). I think it would
		// be little
		// imact to create a new instance each time.
		if (fHighlighter != null) {
			fHighlighter.uninstall();
		} else {
			fHighlighter = new Highlighter();
		}
		// allowed viewer to be null for easier unit testing,
		// but during normal use, would not be null
		if (viewer != null) {
			IStructuredDocument document = (IStructuredDocument) viewer.getDocument();
			fHighlighter.setDocument(document);
		}
		return fHighlighter;
	}

	/*
	 * @see SourceViewerConfiguration#getHoverControlCreator(ISourceViewer)
	 */
	public IInformationControlCreator getInformationControlCreator(ISourceViewer sourceViewer) {

		return getInformationControlCreator(sourceViewer, false);
	}

	private IInformationControlCreator getInformationControlCreator(ISourceViewer sourceViewer, final boolean cutDown) {

		return new IInformationControlCreator() {

			public IInformationControl createInformationControl(Shell parent) {

				//int style= cutDown ? SWT.NONE : (SWT.V_SCROLL |
				// SWT.H_SCROLL);
				int style = SWT.NONE;
				return new DefaultInformationControl(parent, style, new HTMLTextPresenter(cutDown));
			}
		};
	}

	/**
	 * Returns the information presenter control creator. The creator is a
	 * factory creating the presenter controls for the given source viewer.
	 * This implementation always returns a creator for
	 * <code>DefaultInformationControl</code> instances. (Copied from
	 * JavaSourceViewerConfiguration)
	 * 
	 * @param sourceViewer
	 *            the source viewer to be configured by this configuration
	 * @return an information control creator
	 */
	protected IInformationControlCreator getInformationPresenterControlCreator(ISourceViewer sourceViewer) {

		return new IInformationControlCreator() {

			public IInformationControl createInformationControl(Shell parent) {

				int shellStyle = SWT.RESIZE;
				int style = SWT.V_SCROLL | SWT.H_SCROLL;
				return new DefaultInformationControl(parent, shellStyle, style, new HTMLTextPresenter(false));
			}
		};
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.jface.text.source.SourceViewerConfiguration#getOverviewRulerAnnotationHover(org.eclipse.jface.text.source.ISourceViewer)
	 */
	public IAnnotationHover getOverviewRulerAnnotationHover(ISourceViewer arg0) {

		return new StructuredTextAnnotationHover();
	}

	public IPresentationReconciler getPresentationReconciler(ISourceViewer sourceViewer) {

		return null;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.jface.text.source.SourceViewerConfiguration#getTabWidth(org.eclipse.jface.text.source.ISourceViewer)
	 */
	public int getTabWidth(ISourceViewer sourceViewer) {
		return SSEUIPlugin.getDefault().getPreferenceStore().getInt(AbstractDecoratedTextEditorPreferenceConstants.EDITOR_TAB_WIDTH);
	}

	protected ITextEditor getTextEditor() {

		ITextEditor editor = null;
		if (editorPart instanceof ITextEditor)
			editor = (ITextEditor) editorPart;
		if (editor == null && editorPart != null)
			editor = (ITextEditor) editorPart.getAdapter(ITextEditor.class);
		return editor;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.jface.text.source.SourceViewerConfiguration#getUndoManager(org.eclipse.jface.text.source.ISourceViewer)
	 */
	public IUndoManager getUndoManager(ISourceViewer sourceViewer) {
		return new StructuredTextViewerUndoManager();
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.wst.sse.ui.extension.IExtendedConfiguration#setDeclaringID(java.lang.String)
	 */
	public void setDeclaringID(String targetID) {

		fDeclaringID = targetID;
	}

	/**
	 * @param editorPart
	 *            The editorPart to set.
	 */
	public void setEditorPart(IEditorPart editorPart) {

		this.editorPart = editorPart;
	}

	/**
	 * This method is allow any cleanup to take place that is not otherwise
	 * done in the viewer's unConfigure method. In some cases, things may be
	 * done "twice" ... so uninstall, release, etc., should be prepared.
	 */
	public void unConfigure(ISourceViewer viewer) {

		editorPart = null;
		// if there's any processor's we're hanging on to,
		// be sure they have a chance to clean themselves up.
		if (fHighlighter != null) {
			fHighlighter.uninstall();
		}
		if (fContentAssistant != null) {
			fContentAssistant.uninstall();
		}
		if (fReconciler != null) {
			fReconciler.uninstall();
		}
		if (fContentAssistant != null) {
			unconfigureContentAssistProcessors();
		}
		if (fAnnotationHover != null && fAnnotationHover instanceof IReleasable) {
			((IReleasable) fAnnotationHover).release();
		}
	}

	/**
	 *  
	 */
	private void unconfigureContentAssistProcessors() {

		if (!fContentAssistProcessors.isEmpty()) {
			Iterator it = fContentAssistProcessors.iterator();
			IContentAssistProcessor p = null;
			while (it.hasNext()) {
				p = (IContentAssistProcessor) it.next();
				if (p instanceof IReleasable)
					((IReleasable) p).release();
			}
		}
	}

	protected void updateForResource() {

		if (!fContentAssistProcessors.isEmpty()) {
			Iterator it = fContentAssistProcessors.iterator();
			IContentAssistProcessor p = null;
			while (it.hasNext()) {
				p = (IContentAssistProcessor) it.next();
				if (p instanceof IResourceDependentProcessor)
					((IResourceDependentProcessor) p).initialize(fResource);
			}
		}
	}
	
	/**
	 * Returns the text hovers available in StructuredTextEditors
	 * @return TextHoverManager.TextHoverDescriptor[]
	 */
	protected TextHoverManager.TextHoverDescriptor[] getTextHovers() {
		return SSEUIPlugin.getDefault().getTextHoverManager().getTextHovers();
	}
}
