/*******************************************************************************
 * Copyright (c) 2016 Ericsson AB.
 * 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:
 *     Ericsson - initial API and implementation
 *******************************************************************************/

package org.eclipse.egerrit.internal.ui.tabs;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.Iterator;
import java.util.List;

import org.eclipse.core.runtime.Assert;
import org.eclipse.jface.text.Document;
import org.eclipse.jface.text.IDocument;
import org.eclipse.jface.text.IRegion;
import org.eclipse.jface.text.ITextSelection;
import org.eclipse.jface.text.ITextViewer;
import org.eclipse.jface.text.Region;
import org.eclipse.jface.text.TextViewer;
import org.eclipse.jface.text.hyperlink.HyperlinkManager;
import org.eclipse.jface.text.hyperlink.IHyperlink;
import org.eclipse.jface.text.hyperlink.IHyperlinkDetector;
import org.eclipse.jface.text.hyperlink.IHyperlinkDetectorExtension2;
import org.eclipse.jface.text.hyperlink.IHyperlinkPresenter;
import org.eclipse.jface.text.hyperlink.IHyperlinkPresenterExtension;
import org.eclipse.jface.text.hyperlink.IHyperlinkPresenterExtension2;
import org.eclipse.swt.SWT;
import org.eclipse.swt.custom.StyledText;
import org.eclipse.swt.events.FocusEvent;
import org.eclipse.swt.events.MouseEvent;

/**
 * @author lmcbout Note: this class is a copy of the class HyperlinkManager
 */
class EGerritHyperlinkManager extends HyperlinkManager {
	/**
	 * Text operation code for requesting to open the hyperlink at the caret position.
	 *
	 * @see #openHyperlink()
	 * @since 3.6
	 */

	/** The text viewer on which this hyperlink manager works. */
	private ITextViewer fTextViewer;

	/** The session is active. */
	private boolean fActive;

	/** The key modifier mask of the default hyperlink modifier. */
	private int fHyperlinkStateMask;

	/**
	 * The active key modifier mask.
	 *
	 * @since 3.3
	 */
	private int fActiveHyperlinkStateMask;

	/** The active hyperlinks. */
	private IHyperlink[] fActiveHyperlinks;

	/** The hyperlink detectors. */
	private IHyperlinkDetector[] fHyperlinkDetectors;

	/** The hyperlink presenter. */
	private IHyperlinkPresenter fHyperlinkPresenter;

	/** The detection strategy. */
	private final org.eclipse.jface.text.hyperlink.HyperlinkManager.DETECTION_STRATEGY fDetectionStrategy;

	/**
	 * Creates a new hyperlink manager.
	 *
	 * @param all2
	 *            the detection strategy one of {{@link #ALL}, {@link #FIRST}, {@link #LONGEST_REGION_ALL},
	 *            {@link #LONGEST_REGION_FIRST}}
	 * @param detectionStrategy
	 */
	EGerritHyperlinkManager(DETECTION_STRATEGY detectionStrategy) {
		super(detectionStrategy);
		Assert.isNotNull(detectionStrategy);
		fDetectionStrategy = detectionStrategy;
	}

	/**
	 * Installs this hyperlink manager with the given arguments.
	 *
	 * @param textViewer
	 *            the text viewer
	 * @param hyperlinkPresenter
	 *            the hyperlink presenter
	 * @param hyperlinkDetectors
	 *            the array of hyperlink detectors, must not be empty
	 * @param eventStateMask
	 *            the SWT event state mask to activate hyperlink mode
	 */
	@Override
	public void install(ITextViewer textViewer, IHyperlinkPresenter hyperlinkPresenter,
			IHyperlinkDetector[] hyperlinkDetectors, int eventStateMask) {
		super.install(textViewer, hyperlinkPresenter, hyperlinkDetectors, eventStateMask);
		Assert.isNotNull(textViewer);
		Assert.isNotNull(hyperlinkPresenter);
		fTextViewer = textViewer;
		//Create a document
		if (fTextViewer.getDocument() == null) {
			IDocument document = new Document(fTextViewer.getTextWidget().getText());
			fTextViewer.setDocument(document);
		}
		fHyperlinkPresenter = hyperlinkPresenter;
		fTextViewer.addTextListener(this);

		fHyperlinkPresenter.install(fTextViewer);
	}

	/**
	 * Sets the hyperlink detectors for this hyperlink manager.
	 * <p>
	 * It is allowed to call this method after this hyperlink manger has been installed.
	 * </p>
	 *
	 * @param hyperlinkDetectors
	 *            and array of hyperlink detectors, must not be empty
	 */
	@Override
	public void setHyperlinkDetectors(IHyperlinkDetector[] hyperlinkDetectors) {
		Assert.isTrue(hyperlinkDetectors != null && hyperlinkDetectors.length > 0);
		super.setHyperlinkDetectors(hyperlinkDetectors.clone());
		if (fHyperlinkDetectors == null) {
			fHyperlinkDetectors = hyperlinkDetectors.clone();
		} else {
			synchronized (fHyperlinkDetectors) {
				fHyperlinkDetectors = hyperlinkDetectors.clone();
			}
		}
	}

	/**
	 * Deactivates the currently shown hyperlinks.
	 */
	@Override
	protected void deactivate() {
		fActive = false;
	}

	/**
	 * Finds hyperlinks at the current offset.
	 *
	 * @return the hyperlinks or <code>null</code> if none.
	 */
	@Override
	protected IHyperlink[] findHyperlinks() {
		int offset = getCurrentTextOffset();
		if (offset == -1) {
			return null;
		}

		IRegion region = new Region(offset, 0);
		return findHyperlinks(region);
	}

	/**
	 * Returns the hyperlinks in the given region or <code>null</code> if none.
	 *
	 * @param region
	 *            the selection region
	 * @return the array of hyperlinks found or <code>null</code> if none
	 * @since 3.7
	 */
	private IHyperlink[] findHyperlinks(IRegion region) {
		List<IHyperlink> allHyperlinks = new ArrayList<>(fHyperlinkDetectors.length * 2);
		synchronized (fHyperlinkDetectors) {
			for (IHyperlinkDetector detector : fHyperlinkDetectors) {
				if (detector == null) {
					continue;
				}

				if (detector instanceof IHyperlinkDetectorExtension2) {
					int stateMask = ((IHyperlinkDetectorExtension2) detector).getStateMask();
					if (stateMask != -1 && (stateMask != fActiveHyperlinkStateMask
							|| fActiveHyperlinkStateMask != fHyperlinkStateMask)) {
						continue;
					}
				} else if (fActiveHyperlinkStateMask != fHyperlinkStateMask) {
					continue;
				}

				boolean canShowMultipleHyperlinks = fHyperlinkPresenter.canShowMultipleHyperlinks();
				if (fTextViewer.getDocument() == null) {
					IDocument document = new Document(fTextViewer.getTextWidget().getText());
					fTextViewer.setDocument(document);
				}
				IHyperlink[] hyperlinks = detector.detectHyperlinks(fTextViewer, region, canShowMultipleHyperlinks);
				if (hyperlinks == null) {
					continue;
				}

				Assert.isLegal(hyperlinks.length > 0);

				if (fDetectionStrategy == FIRST) {
					if (hyperlinks.length == 1) {
						return hyperlinks;
					}
					return new IHyperlink[] { hyperlinks[0] };
				}
				allHyperlinks.addAll(Arrays.asList(hyperlinks));
			}
		}

		if (allHyperlinks.isEmpty()) {
			return null;
		}

		if (fDetectionStrategy != ALL) {
			int maxLength = computeLongestHyperlinkLength(allHyperlinks);
			Iterator<IHyperlink> iter = new ArrayList<>(allHyperlinks).iterator();
			while (iter.hasNext()) {
				IHyperlink hyperlink = iter.next();
				if (hyperlink.getHyperlinkRegion().getLength() < maxLength) {
					allHyperlinks.remove(hyperlink);
				}
			}
		}

		if (fDetectionStrategy == LONGEST_REGION_FIRST) {
			return new IHyperlink[] { allHyperlinks.get(0) };
		}

		return allHyperlinks.toArray(new IHyperlink[allHyperlinks.size()]);

	}

/*
* @see org.eclipse.swt.events.MouseListener#mouseDown(org.eclipse.swt.events.MouseEvent)
*/
	@Override
	public void mouseDown(MouseEvent event) {
		if (fHyperlinkPresenter instanceof IHyperlinkPresenterExtension2 && fActiveHyperlinks != null) {

			StyledText source = (StyledText) event.getSource();

			((HyperLinkPresenter) fHyperlinkPresenter).setOffset(source.getCaretOffset());

			((IHyperlinkPresenterExtension2) fHyperlinkPresenter).showHyperlinks(fActiveHyperlinks, fActive);

		}
		if (fHyperlinkPresenter instanceof IHyperlinkPresenterExtension
				&& !((IHyperlinkPresenterExtension) fHyperlinkPresenter).canHideHyperlinks()) {
			return;
		}

		if (!isLocalRegisteredStateMask(event.stateMask)) {
			if (fActive) {
				deactivate();
			}

			return;
		}

		if (event.button != 1) {
			deactivate();
			return;
		}

		fActive = true;
		fActiveHyperlinkStateMask = event.stateMask & SWT.MODIFIER_MASK;

		StyledText text = fTextViewer.getTextWidget();
		if (text == null || text.isDisposed()) {
			deactivate();
			return;
		}

		if (text.isTextSelected()) {
			deactivate();
			return;
		}

		fActiveHyperlinks = findHyperlinks();
	}

/*
* @see org.eclipse.swt.events.MouseListener#mouseUp(org.eclipse.swt.events.MouseEvent)
*/
	@Override
	public void mouseUp(MouseEvent e) {

		int cursorOffset = ((StyledText) e.getSource()).getCaretOffset();
		if (!fActive) {
			fActiveHyperlinks = null;
			return;
		}

		if (e.button != 1) {
			fActiveHyperlinks = null;
		}

		deactivate();
		IHyperlink currentHyperlink = null;
		if (fActiveHyperlinks == null) {
			fActiveHyperlinks = findHyperlinks();
		}
		if (fActiveHyperlinks != null) {
			for (IHyperlink fActiveHyperlink : fActiveHyperlinks) {
				IRegion region = fActiveHyperlink.getHyperlinkRegion();
				if (region.getOffset() < cursorOffset && cursorOffset < (region.getOffset() + region.getLength())) {
					currentHyperlink = fActiveHyperlink;
					break;
				}
			}

			if (currentHyperlink != null) {
				localShowHyperlinks(true);
			}

		}
	}

	/*
	* @see org.eclipse.swt.events.MouseMoveListener#mouseMove(org.eclipse.swt.events.MouseEvent)
	*/
	@Override
	public void mouseMove(MouseEvent event) {
	}

	/**
	 * Checks whether the given state mask is registered.
	 *
	 * @param stateMask
	 *            the state mask
	 * @return <code>true</code> if a detector is registered for the given state mask
	 * @since 3.3
	 */
	private boolean isLocalRegisteredStateMask(int stateMask) {
		if (stateMask == fHyperlinkStateMask) {
			return true;
		}

		synchronized (fHyperlinkDetectors) {
			for (IHyperlinkDetector fHyperlinkDetector : fHyperlinkDetectors) {
				if ((fHyperlinkDetector instanceof IHyperlinkDetectorExtension2)
						&& stateMask == ((IHyperlinkDetectorExtension2) fHyperlinkDetector).getStateMask()) {
					return true;
				}
			}
		}
		return false;
	}

/*
* @see org.eclipse.swt.events.FocusListener#focusGained(org.eclipse.swt.events.FocusEvent)
*/
	@Override
	public void focusGained(FocusEvent e) {
		showAllLinks();
	}

	/**
	 *
	 */
	private void showAllLinks() {
		//Set all hyperlinks visible
		if (fActiveHyperlinks == null && fTextViewer != null && !fTextViewer.getTextWidget().getText().isEmpty()) {
			if (fTextViewer.getDocument() == null) {
				return;
			}
			IRegion region = new Region(0, ((TextViewer) fTextViewer).getBottomIndexEndOffset());
			fActiveHyperlinks = findHyperlinks(region);
			if (fActiveHyperlinks != null && fActiveHyperlinks.length > 1) {
				localShowHyperlinks(true);
			} else {
				//Do not trigger the open
				localShowHyperlinks(false);
			}
		}
	}

	/**
	 * Opens the hyperlink at the current caret location directly if there's only one link, else opens the hyperlink
	 * control showing all the hyperlinks at that location.
	 *
	 * @param takesFocusWhenVisible
	 *            <code>true</code> if the control takes focus when visible, <code>false</code> otherwise
	 * @return <code>true</code> if at least one hyperlink has been found at the caret location, <code>false</code>
	 *         otherwise
	 * @since 3.7
	 */
	private boolean localShowHyperlinks(boolean takesFocusWhenVisible) {

		if (fActiveHyperlinks == null || fActiveHyperlinks.length == 0) {
			return false;
		}
		if (fActiveHyperlinks.length == 1 && takesFocusWhenVisible) {
			fActiveHyperlinks[0].open();
		} else {
			fHyperlinkPresenter.showHyperlinks(fActiveHyperlinks);
		}
		return true;

	}

	/**
	 * Opens the hyperlink at the caret location or opens a chooser if more than one hyperlink is available.
	 *
	 * @return <code>true</code> if at least one hyperlink has been found at the caret location, <code>false</code>
	 *         otherwise
	 * @see #OPEN_HYPERLINK
	 * @since 3.6
	 */
	@Override
	public boolean openHyperlink() {
		fActiveHyperlinkStateMask = fHyperlinkStateMask;

		if (fHyperlinkPresenter instanceof IHyperlinkPresenterExtension
				&& !((IHyperlinkPresenterExtension) fHyperlinkPresenter).canHideHyperlinks()) {
			return false;
		}
		ITextSelection sel = (ITextSelection) ((TextViewer) fTextViewer).getSelection();
		int offset = sel.getOffset();
		if (offset == -1) {
			return false;
		}

		IRegion region = new Region(offset, 0);
		fActiveHyperlinks = findHyperlinks(region);
		return localShowHyperlinks(true);
	}
}