/*******************************************************************************
 * Copyright (c) 2004, 2010 Tasktop Technologies 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:
 *     Xiaoyang Guan - initial API and implementation
 *******************************************************************************/

package org.eclipse.mylyn.internal.trac.wiki.editor;

import java.util.Iterator;

import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.core.runtime.IStatus;
import org.eclipse.core.runtime.Status;
import org.eclipse.core.runtime.jobs.IJobChangeEvent;
import org.eclipse.core.runtime.jobs.Job;
import org.eclipse.core.runtime.jobs.JobChangeAdapter;
import org.eclipse.jface.dialogs.InputDialog;
import org.eclipse.jface.dialogs.MessageDialog;
import org.eclipse.jface.layout.GridDataFactory;
import org.eclipse.jface.text.Document;
import org.eclipse.jface.text.TextViewer;
import org.eclipse.jface.text.source.AnnotationModel;
import org.eclipse.jface.text.source.IAnnotationAccess;
import org.eclipse.jface.text.source.SourceViewer;
import org.eclipse.jface.window.Window;
import org.eclipse.mylyn.commons.core.StatusHandler;
import org.eclipse.mylyn.commons.net.AuthenticationType;
import org.eclipse.mylyn.commons.ui.CommonImages;
import org.eclipse.mylyn.internal.tasks.ui.editors.RepositoryTextViewerConfiguration;
import org.eclipse.mylyn.internal.tasks.ui.util.TasksUiInternal;
import org.eclipse.mylyn.internal.trac.core.TracCorePlugin;
import org.eclipse.mylyn.internal.trac.core.model.TracWikiPage;
import org.eclipse.mylyn.internal.trac.ui.editor.TracRenderingEngine;
import org.eclipse.mylyn.internal.trac.wiki.TracWikiPlugin;
import org.eclipse.mylyn.tasks.core.TaskRepository;
import org.eclipse.mylyn.tasks.ui.TasksUiImages;
import org.eclipse.mylyn.tasks.ui.editors.AbstractRenderingEngine;
import org.eclipse.mylyn.tasks.ui.editors.BrowserFormPage;
import org.eclipse.swt.SWT;
import org.eclipse.swt.browser.Browser;
import org.eclipse.swt.browser.LocationAdapter;
import org.eclipse.swt.browser.LocationEvent;
import org.eclipse.swt.custom.StyledText;
import org.eclipse.swt.events.DisposeEvent;
import org.eclipse.swt.events.DisposeListener;
import org.eclipse.swt.events.ModifyEvent;
import org.eclipse.swt.events.ModifyListener;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Button;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Event;
import org.eclipse.swt.widgets.Listener;
import org.eclipse.ui.PartInitException;
import org.eclipse.ui.PlatformUI;
import org.eclipse.ui.editors.text.EditorsUI;
import org.eclipse.ui.editors.text.TextSourceViewerConfiguration;
import org.eclipse.ui.forms.IManagedForm;
import org.eclipse.ui.forms.editor.FormEditor;
import org.eclipse.ui.forms.editor.FormPage;
import org.eclipse.ui.forms.events.ExpansionEvent;
import org.eclipse.ui.forms.events.IExpansionListener;
import org.eclipse.ui.forms.widgets.ExpandableComposite;
import org.eclipse.ui.forms.widgets.FormToolkit;
import org.eclipse.ui.forms.widgets.ScrolledForm;
import org.eclipse.ui.forms.widgets.Section;
import org.eclipse.ui.texteditor.AnnotationPreference;
import org.eclipse.ui.texteditor.DefaultMarkerAnnotationAccess;
import org.eclipse.ui.texteditor.MarkerAnnotationPreferences;
import org.eclipse.ui.texteditor.SourceViewerDecorationSupport;

/**
 * @author Xiaoyang Guan
 */
public class TracWikiPageEditor extends FormEditor {

	public static final String ID_EDITOR = "org.eclipse.mylyn.trac.ui.editor.wikipage";

	private TaskRepository repository;

	private TracWikiPage page;

	private final WikiSourceEditor wikiSourceEditor;

	private final BrowserFormPage browserPage;

	private class WikiSourceEditor extends FormPage {

		private static final String ID = "org.eclipse.mylyn.trac.ui.editor.wikisource";

		private static final String TITLE = "Wiki Page Source";

		private static final String LABEL_PREVIEW = "Page Preview";

		private static final String LABEL_SOURCE = "Page Source";

		private static final String LABEL_BUTTON_PREVIEW = "Preview";

		private static final String LABEL_BUTTON_SUBMIT = "Submit";

		private static final int PREVIEW_BROWSER_HEIGHT = 10 * 14;

		private static final int DEFAULT_WIDTH = 79 * 7; // 500;

		private ScrolledForm form;

		private FormToolkit toolkit;

		private Composite editorComposite;

		private Section previewSection;

		private Browser previewBrowser;

		private TextViewer sourceEditor;

		private Button previewButton;

		private Button submitButton;

		protected boolean isDirty;

		public WikiSourceEditor(FormEditor editor) {
			super(editor, ID, TITLE);

		}

		@Override
		protected void createFormContent(IManagedForm managedForm) {
			super.createFormContent(managedForm);
			form = managedForm.getForm();
			toolkit = managedForm.getToolkit();

			editorComposite = form.getBody();
			GridLayout editorLayout = new GridLayout();
			editorComposite.setLayout(editorLayout);
			editorComposite.setLayoutData(new GridData(GridData.FILL_BOTH));

			createPreviewSection(editorComposite);
			createSourceSection(editorComposite);
		}

		private void createPreviewSection(Composite parent) {
			previewSection = toolkit.createSection(parent, ExpandableComposite.TITLE_BAR | ExpandableComposite.TWISTIE);
			previewSection.setText(LABEL_PREVIEW);
			previewSection.setExpanded(false);
			previewSection.setLayout(new GridLayout());
			previewSection.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
			previewSection.addExpansionListener(new IExpansionListener() {
				public void expansionStateChanging(ExpansionEvent e) {
					form.reflow(true);
				}

				public void expansionStateChanged(ExpansionEvent e) {
					form.reflow(true);
				}
			});

			Composite container = toolkit.createComposite(previewSection);
			previewSection.setClient(container);
			container.setLayout(new GridLayout());
			container.setLayoutData(new GridData(GridData.FILL_BOTH));

			previewBrowser = addBrowser(container, SWT.NONE);
			previewBrowser.setData(FormToolkit.KEY_DRAW_BORDER, FormToolkit.TEXT_BORDER);
			GridData previewBrowserData = new GridData(GridData.FILL_BOTH);
			previewBrowserData.heightHint = PREVIEW_BROWSER_HEIGHT;
			previewBrowser.setLayoutData(previewBrowserData);

			toolkit.paintBordersFor(container);
		}

		private void createSourceSection(Composite parent) {
			Section section = toolkit.createSection(parent, ExpandableComposite.TITLE_BAR);
			section.setText(LABEL_SOURCE);
			section.setExpanded(true);
			section.setLayout(new GridLayout());
			section.setLayoutData(new GridData(GridData.FILL_BOTH));
			section.addExpansionListener(new IExpansionListener() {
				public void expansionStateChanging(ExpansionEvent e) {
					form.reflow(true);
				}

				public void expansionStateChanged(ExpansionEvent e) {
					form.reflow(true);
				}
			});

			Composite container = toolkit.createComposite(section);
			section.setClient(container);
			container.setLayout(new GridLayout());
			container.setLayoutData(new GridData(GridData.FILL_BOTH));

			sourceEditor = new SourceViewer(container, null, SWT.FLAT | SWT.MULTI | SWT.WRAP | SWT.V_SCROLL);
			sourceEditor.getControl().setLayoutData(new GridData(GridData.FILL_BOTH));
			sourceEditor.getControl().setData(FormToolkit.KEY_DRAW_BORDER, FormToolkit.TEXT_BORDER);
			sourceEditor.setEditable(true);

			sourceEditor.getTextWidget().addModifyListener(new ModifyListener() {

				public void modifyText(ModifyEvent e) {
					if (!isDirty()) {
						markDirty(true);
						setSubmitEnabled(true);
					}
				}
			});

			StyledText styledText = sourceEditor.getTextWidget();
			GridDataFactory.fillDefaults().hint(DEFAULT_WIDTH, SWT.DEFAULT).grab(true, true).applyTo(styledText);

			IAnnotationAccess annotationAccess = new DefaultMarkerAnnotationAccess();

			final SourceViewerDecorationSupport support = new SourceViewerDecorationSupport(
					(SourceViewer) sourceEditor, null, annotationAccess, EditorsUI.getSharedTextColors());

			Iterator<?> e = new MarkerAnnotationPreferences().getAnnotationPreferences().iterator();
			while (e.hasNext()) {
				support.setAnnotationPreference((AnnotationPreference) e.next());
			}

			support.install(EditorsUI.getPreferenceStore());

			styledText.addDisposeListener(new DisposeListener() {
				public void widgetDisposed(DisposeEvent e) {
					support.uninstall();
				}
			});

			TextSourceViewerConfiguration viewerConfig = new RepositoryTextViewerConfiguration(repository, null, true);
			((SourceViewer) sourceEditor).configure(viewerConfig);
			Document document = new Document(page.getContent());
			((SourceViewer) sourceEditor).setDocument(document, new AnnotationModel());

			createActionsLayout(container);
			toolkit.paintBordersFor(container);
		}

		private void createActionsLayout(Composite parent) {
			Composite buttonComposite = toolkit.createComposite(parent);
			GridLayout buttonLayout = new GridLayout();
			buttonLayout.numColumns = 2;
			buttonComposite.setLayout(buttonLayout);
			buttonComposite.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
			addActionButtons(buttonComposite);

		}

		private void addActionButtons(Composite buttonComposite) {
			previewButton = toolkit.createButton(buttonComposite, LABEL_BUTTON_PREVIEW, SWT.NONE);
			GridData previewButtonData = new GridData(GridData.HORIZONTAL_ALIGN_BEGINNING);
			previewButtonData.widthHint = 100;
			previewButton.setLayoutData(previewButtonData);
			previewButton.addListener(SWT.Selection, new Listener() {
				public void handleEvent(Event e) {
					previewSection.setExpanded(true);
					setText(previewBrowser, "loading preview...");
					previewWiki(previewBrowser, sourceEditor.getTextWidget().getText());
				}
			});

			submitButton = toolkit.createButton(buttonComposite, LABEL_BUTTON_SUBMIT, SWT.NONE);
			GridData submitButtonData = new GridData(GridData.HORIZONTAL_ALIGN_BEGINNING);
			submitButtonData.widthHint = 100;
			submitButton.setImage(CommonImages.getImage(TasksUiImages.REPOSITORY_SUBMIT));
			submitButton.setLayoutData(submitButtonData);
			submitButton.addListener(SWT.Selection, new Listener() {
				public void handleEvent(Event e) {
					InputDialog commentDialog = new InputDialog(null, "Page Comment",
							"Enter a Comment for the page (or cancel the submit):", null, null);
					// cancel the comment dialog will cancel the submit
					if (commentDialog.open() == Window.OK) {
						page.getPageInfo().setComment(commentDialog.getValue());
						boolean isAnonymouse = repository.getCredentials(AuthenticationType.REPOSITORY) == null;
						page.getPageInfo().setAuthor(isAnonymouse ? "anonymous" : repository.getUserName());
						page.setContent(sourceEditor.getTextWidget().getText());

						submitToRepository();
					}
				}
			});

			setSubmitEnabled(false);
		}

		/**
		 * Copied from AbstractRepositoryTaskEditor
		 * 
		 * @param enabled
		 */
		private void setSubmitEnabled(boolean enabled) {
			if (submitButton != null && !submitButton.isDisposed()) {
				submitButton.setEnabled(enabled);
				if (enabled) {
					submitButton.setToolTipText("Submit to " + repository.getRepositoryUrl());
				}
			}
		}

		public void submitToRepository() {
			class SubmitPageJob extends Job {
				private IStatus jobStatus;

				public SubmitPageJob() {
					super("upload wiki page");
				}

				public IStatus getStatus() {
					return jobStatus;
				}

				@Override
				protected IStatus run(IProgressMonitor monitor) {
					try {
						monitor.beginTask("Uploading wiki page", IProgressMonitor.UNKNOWN);
						TracCorePlugin.getDefault()
								.getConnector()
								.getWikiHandler()
								.postWikiPage(repository, page, monitor);
						jobStatus = Status.OK_STATUS;
					} catch (CoreException e) {
						TasksUiInternal.displayStatus("Submit failed", e.getStatus());
						jobStatus = e.getStatus();
					} finally {
						monitor.done();
					}
					return Status.OK_STATUS;
				}

			}

			final SubmitPageJob submitJob = new SubmitPageJob();
			submitJob.addJobChangeListener(new JobChangeAdapter() {

				@Override
				public void done(IJobChangeEvent event) {

					// refresh editor only if uploading the wiki page succeeded
					if (submitJob.getStatus().isOK()) {
						updateWikiPage();
						PlatformUI.getWorkbench().getDisplay().asyncExec(new Runnable() {
							public void run() {
								if (browserPage.getBrowser() != null) {
									browserPage.getBrowser().refresh();
								}
								setActivePage(BrowserFormPage.ID_EDITOR);
								markDirty(false);
								setSubmitEnabled(false);
							}
						});
					}
				}
			});
			submitJob.schedule();
		}

		@Override
		public boolean isDirty() {
			return isDirty;
		}

		protected void markDirty(boolean dirty) {
			isDirty = dirty;
			getManagedForm().dirtyStateChanged();
		}

		/*====== Copied/modified from AbstractRepositoryTaskEditor ======*/

		private boolean ignoreLocationEvents = false;

		private Browser addBrowser(Composite parent, int style) {
			Browser browser = new Browser(parent, style);
			// intercept links to open tasks in rich editor and urls in separate browser
			browser.addLocationListener(new LocationAdapter() {
				@Override
				public void changing(LocationEvent event) {
					// ignore events that are caused by manually setting the contents of the browser
					if (ignoreLocationEvents) {
						return;
					}

					if (event.location != null) {
						event.doit = false;
						// TODO: add open link support when this editor is moved into ..mylyn.tasks.ui.editors
						//IHyperlink link = new TaskUrlHyperlink(
						//		new Region(0, 0)/* a fake region just to make constructor happy */, event.location);
						//link.open();
					}
				}

			});

			return browser;
		}

		private void setText(Browser browser, String html) {
			try {
				ignoreLocationEvents = true;
				browser.setText((html != null) ? html : "");
			} finally {
				ignoreLocationEvents = false;
			}

		}

		private void previewWiki(final Browser browser, String sourceText) {
			final class PreviewWikiJob extends Job {
				private final String sourceText;

				private String htmlText;

				private IStatus jobStatus;

				public PreviewWikiJob(String sourceText) {
					super("Formatting Wiki Text");

					if (sourceText == null) {
						throw new IllegalArgumentException("source text must not be null");
					}

					this.sourceText = sourceText;
				}

				@Override
				protected IStatus run(IProgressMonitor monitor) {
					AbstractRenderingEngine htmlRenderingEngine = new TracRenderingEngine();

					jobStatus = Status.OK_STATUS;
					try {
						htmlText = htmlRenderingEngine.renderAsHtml(repository, sourceText, monitor);
					} catch (CoreException e) {
						jobStatus = e.getStatus();
					}
					return Status.OK_STATUS;
				}

				public String getHtmlText() {
					return htmlText;
				}

				public IStatus getStatus() {
					return jobStatus;
				}

			}

			final PreviewWikiJob job = new PreviewWikiJob(sourceText);

			job.addJobChangeListener(new JobChangeAdapter() {

				@Override
				public void done(final IJobChangeEvent event) {
					if (!form.isDisposed()) {
						if (job.getStatus().isOK()) {
							getPartControl().getDisplay().asyncExec(new Runnable() {
								public void run() {
									WikiSourceEditor.this.setText(browser, job.getHtmlText());
									//parentEditor.setMessage(null, IMessageProvider.NONE);
								}
							});
						} else {
							getPartControl().getDisplay().asyncExec(new Runnable() {
								public void run() {
									//parentEditor.setMessage(job.getStatus().getMessage(), IMessageProvider.ERROR);
								}
							});
						}
					}
					super.done(event);
				}
			});

			job.setUser(true);
			job.schedule();
		}

	}

	public TracWikiPageEditor() {
		super();
		wikiSourceEditor = new WikiSourceEditor(this);
		browserPage = new BrowserFormPage(this, "Browser") {
			@Override
			protected String getUrl() {
				return ((TracWikiPageEditorInput) getEditorInput()).getPageUrl();
			}
		};
	}

	protected void initializeEditor() {
		TracWikiPageEditorInput editorInput = (TracWikiPageEditorInput) getEditorInput();
		page = editorInput.getPage();
		repository = editorInput.getRepository();
	}

	@Override
	protected void addPages() {
		initializeEditor();
		try {
			addPage(wikiSourceEditor);
			addPage(browserPage);
			setPartName(getEditorInput().getName());
			setActivePage(BrowserFormPage.ID_EDITOR);
		} catch (PartInitException e) {
			StatusHandler.fail(new Status(IStatus.ERROR, TracWikiPlugin.ID_PLUGIN,
					"Cannot create Trac Wiki page editor pages"));
		}
	}

	@Override
	public void doSave(IProgressMonitor monitor) {
		MessageDialog.openInformation(getSite().getShell(), "Changes cannot be saved",
				"Offline editting on wiki pages not supported yet.");
		monitor.setCanceled(true);
	}

	@Override
	public void doSaveAs() {
	}

	@Override
	public boolean isSaveAsAllowed() {
		return false;
	}

	protected void updateWikiPage() {
		Job updatePageJob = new Job("Update wiki page") {

			@Override
			protected IStatus run(IProgressMonitor monitor) {
				try {
					monitor.beginTask("Downloading wiki page", IProgressMonitor.UNKNOWN);
					TracWikiPage newPage = TracCorePlugin.getDefault()
							.getConnector()
							.getWikiHandler()
							.getWikiPage(repository, page.getPageInfo().getPageName(), monitor);
					if (newPage != null) {
						((TracWikiPageEditorInput) getEditorInput()).setPage(newPage);
					} else {
						TasksUiInternal.displayStatus("Download failed", new Status(IStatus.ERROR,
								TracCorePlugin.ID_PLUGIN, "Unable to retrieve wiki page "
										+ page.getPageInfo().getPageName()));
					}
				} catch (CoreException e) {
					TasksUiInternal.displayStatus("Download failed", e.getStatus());
				} finally {
					monitor.done();
				}
				return Status.OK_STATUS;
			}

		};
		updatePageJob.schedule();
	}

}
