/*******************************************************************************
 * Copyright (c) 2009, 2011 SpringSource, a divison of VMware, Inc. 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:
 *     SpringSource, a division of VMware, Inc. - initial API and implementation
 *     SAP AG - moving to Eclipse Libra project and enhancements
 *******************************************************************************/
package org.eclipse.libra.framework.editor.ui.dependencies;

import java.lang.reflect.InvocationTargetException;
import java.util.Map;

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.Job;
import org.eclipse.jface.action.Action;
import org.eclipse.jface.action.IMenuListener;
import org.eclipse.jface.action.IMenuManager;
import org.eclipse.jface.action.IToolBarManager;
import org.eclipse.jface.action.MenuManager;
import org.eclipse.jface.action.Separator;
import org.eclipse.jface.dialogs.ProgressMonitorDialog;
import org.eclipse.jface.operation.IRunnableContext;
import org.eclipse.jface.operation.IRunnableWithProgress;
import org.eclipse.jface.resource.ImageDescriptor;
import org.eclipse.jface.viewers.DoubleClickEvent;
import org.eclipse.jface.viewers.IDoubleClickListener;
import org.eclipse.jface.viewers.IStructuredSelection;
import org.eclipse.jface.viewers.StructuredSelection;
import org.eclipse.jface.viewers.ViewerFilter;
import org.eclipse.libra.framework.editor.core.IOSGiFrameworkAdmin;
import org.eclipse.libra.framework.editor.core.model.IBundle;
import org.eclipse.libra.framework.editor.ui.internal.AbstractBundleEditorPage;
import org.eclipse.libra.framework.editor.ui.internal.EditorUIPlugin;
import org.eclipse.libra.framework.editor.ui.internal.SearchControl;
import org.eclipse.libra.framework.editor.ui.internal.SearchTextHistory;
import org.eclipse.libra.framework.editor.ui.internal.dependencies.BundleDependencyContentProvider;
import org.eclipse.libra.framework.editor.ui.internal.dependencies.BundleDependencyLabelProvider;
import org.eclipse.libra.framework.editor.ui.internal.dependencies.FocusedBundleDependencyLayoutAlgorithm;
import org.eclipse.libra.framework.editor.ui.overview.BundleInformationEditorPage;
import org.eclipse.swt.SWT;
import org.eclipse.swt.events.KeyAdapter;
import org.eclipse.swt.events.KeyEvent;
import org.eclipse.swt.events.ModifyEvent;
import org.eclipse.swt.events.ModifyListener;
import org.eclipse.swt.events.SelectionAdapter;
import org.eclipse.swt.events.SelectionEvent;
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.Display;
import org.eclipse.swt.widgets.Label;
import org.eclipse.swt.widgets.Menu;
import org.eclipse.swt.widgets.Spinner;
import org.eclipse.ui.IEditorInput;
import org.eclipse.ui.IEditorPart;
import org.eclipse.ui.IEditorSite;
import org.eclipse.ui.IWorkbenchActionConstants;
import org.eclipse.ui.IWorkbenchCommandConstants;
import org.eclipse.ui.commands.ICommandImageService;
import org.eclipse.ui.forms.IFormColors;
import org.eclipse.ui.forms.ManagedForm;
import org.eclipse.ui.forms.widgets.ExpandableComposite;
import org.eclipse.ui.forms.widgets.FormToolkit;
import org.eclipse.ui.forms.widgets.Section;
import org.eclipse.wst.server.ui.ServerUICore;
import org.eclipse.wst.server.ui.internal.editor.ServerEditorPartInput;
import org.eclipse.wst.server.ui.internal.editor.ServerResourceCommandManager;
import org.eclipse.zest.core.viewers.AbstractZoomableViewer;
import org.eclipse.zest.core.viewers.GraphViewer;
import org.eclipse.zest.core.viewers.IZoomableWorkbenchPart;
import org.eclipse.zest.core.viewers.ZoomContributionViewItem;
import org.eclipse.zest.core.widgets.ZestStyles;
import org.eclipse.zest.layouts.LayoutAlgorithm;
import org.eclipse.zest.layouts.LayoutStyles;
import org.eclipse.zest.layouts.algorithms.CompositeLayoutAlgorithm;
import org.eclipse.zest.layouts.algorithms.HorizontalShift;
import org.eclipse.zest.layouts.algorithms.RadialLayoutAlgorithm;


/**
 * @author Christian Dupuis
 * @author Kaloyan Raev
 */
@SuppressWarnings("restriction")
public class BundleDependencyEditorPage extends AbstractBundleEditorPage implements IZoomableWorkbenchPart {

	GraphViewer viewer;

	BundleDependencyContentProvider contentProvider;

	private BundleDependencyLabelProvider labelProvider;

	private ZoomContributionViewItem zoomContributionItem;

	SearchControl searchControl;

	private Action refreshAction;

	IToolBarManager toolBarManager;

	final SearchTextHistory history = new SearchTextHistory();

	Action forwardAction;

	Action backAction;

	private ServerResourceCommandManager commandManager;

	@Override
	protected void createBundleContent(Composite parent) {
		mform = new ManagedForm(parent);
		setManagedForm(mform);
		sform = mform.getForm();
		FormToolkit toolkit = mform.getToolkit();
		sform.setText("Bundle Dependency Graph");
		sform.setImage(ServerUICore.getLabelProvider().getImage(getServer()));
		sform.setExpandHorizontal(true);
		sform.setExpandVertical(true);
		toolkit.decorateFormHeading(sform.getForm());

		Composite body = sform.getBody();
		GridLayout layout = new GridLayout(2, false);
		layout.marginHeight = 0;
		layout.marginWidth = 0;
		body.setLayout(layout);

		Composite configComposite = toolkit.createComposite(body);
		layout.marginLeft = 6;
		layout.marginTop = 6;
		layout.numColumns = 2;
		configComposite.setLayoutData(new GridData(GridData.FILL_VERTICAL));
		configComposite.setLayout(layout);

		Section expandableComposite = toolkit.createSection(configComposite, ExpandableComposite.TITLE_BAR
				| ExpandableComposite.FOCUS_TITLE);
		layout = new GridLayout();
		expandableComposite.setLayout(layout);
		expandableComposite.setLayoutData(new GridData(GridData.VERTICAL_ALIGN_BEGINNING));
		expandableComposite.setFont(body.getFont());
		expandableComposite.setBackground(body.getBackground());
		expandableComposite.setText("Configuration");

		Composite composite = toolkit.createComposite(expandableComposite, SWT.NONE);
		layout = new GridLayout();
		layout.numColumns = 1;
		layout.marginHeight = 0;
		layout.marginRight = 0;
		composite.setLayout(layout);
		expandableComposite.setClient(composite);

		final Button servicesButton = toolkit.createButton(composite, "Services", SWT.RADIO);
		servicesButton.addSelectionListener(new SelectionAdapter() {
			@Override
			public void widgetSelected(SelectionEvent e) {
				contentProvider.setShowServices(servicesButton.getSelection());
				new BundleDependencyUpdateJob(false).schedule(200);
			}
		});

		final Button packagesButton = toolkit.createButton(composite, "Packages", SWT.RADIO);
		packagesButton.addSelectionListener(new SelectionAdapter() {
			@Override
			public void widgetSelected(SelectionEvent e) {
				contentProvider.setShowPackage(packagesButton.getSelection());
				new BundleDependencyUpdateJob(false).schedule(200);
			}
		});
		packagesButton.setSelection(true);

		toolkit.createLabel(composite, "", SWT.NONE);
		Label dependenciesLabel = toolkit.createLabel(composite, "Dependencies");
		dependenciesLabel.setForeground(toolkit.getColors().getColor(IFormColors.TITLE));

		toolkit.createLabel(composite, "Incoming");

		final Spinner incomingSpinner = new Spinner(composite, SWT.NONE);
		incomingSpinner.setMinimum(0);
		incomingSpinner.setIncrement(1);
		incomingSpinner.setMaximum(20);
		incomingSpinner.setSelection(1);
		GridData data = new GridData(GridData.HORIZONTAL_ALIGN_END);
//		data.widthHint = 20;
		incomingSpinner.setLayoutData(data);
		incomingSpinner.addModifyListener(new ModifyListener() {

			public void modifyText(ModifyEvent e) {
				contentProvider.setIncomingDependencyDegree(incomingSpinner.getSelection());
				new BundleDependencyUpdateJob(false).schedule(200);
			}
		});

		toolkit.createLabel(composite, "Outgoing");

		final Spinner outgoingSpinner = new Spinner(composite, SWT.NONE);
		outgoingSpinner.setMinimum(0);
		outgoingSpinner.setIncrement(1);
		outgoingSpinner.setMaximum(20);
		outgoingSpinner.setSelection(1);
		data = new GridData(GridData.HORIZONTAL_ALIGN_END);
//		data.widthHint = 20;
		outgoingSpinner.setLayoutData(data);
		outgoingSpinner.addModifyListener(new ModifyListener() {

			public void modifyText(ModifyEvent e) {
				contentProvider.setOutgoingDependencyDegree(outgoingSpinner.getSelection());
				new BundleDependencyUpdateJob(false).schedule(200);
			}
		});

		Label separator = new Label(configComposite, SWT.NONE);
		// separator.setBackground(toolkit.getColors().getColor(IFormColors.TB_BG));
		separator.setForeground(toolkit.getColors().getColor(IFormColors.H_BOTTOM_KEYLINE1));
		data = new GridData(GridData.HORIZONTAL_ALIGN_END | GridData.FILL_VERTICAL);
		data.widthHint = 1;
		separator.setLayoutData(data);

		toolkit.paintBordersFor(expandableComposite);

		layout = new GridLayout(2, false);
		layout.marginHeight = 0;
		layout.marginWidth = 0;
		body.setLayout(layout);

		viewer = new GraphViewer(body, SWT.NONE);
		viewer.getControl().setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
		viewer.setConnectionStyle(ZestStyles.CONNECTIONS_DIRECTED);

		CompositeLayoutAlgorithm layoutAlgorithm = new CompositeLayoutAlgorithm(LayoutStyles.NO_LAYOUT_NODE_RESIZING
				| LayoutStyles.ENFORCE_BOUNDS, //
				new LayoutAlgorithm[] { // 
				new RadialLayoutAlgorithm(LayoutStyles.NO_LAYOUT_NODE_RESIZING | LayoutStyles.ENFORCE_BOUNDS), //
						new HorizontalShift(LayoutStyles.NO_LAYOUT_NODE_RESIZING | LayoutStyles.ENFORCE_BOUNDS) });
		searchControl = new SearchControl("Find", getManagedForm());
		contentProvider = new BundleDependencyContentProvider(viewer, searchControl);

		FocusedBundleDependencyLayoutAlgorithm la = new FocusedBundleDependencyLayoutAlgorithm(
				LayoutStyles.NO_LAYOUT_NODE_RESIZING | LayoutStyles.ENFORCE_BOUNDS, layoutAlgorithm, contentProvider);
		viewer.setLayoutAlgorithm(la);

		viewer.setContentProvider(contentProvider);
		viewer.addSelectionChangedListener(contentProvider);
		viewer.setFilters(new ViewerFilter[] {});
		labelProvider = new BundleDependencyLabelProvider(contentProvider, toolkit);
		viewer.setLabelProvider(labelProvider);
		viewer.addDoubleClickListener(new IDoubleClickListener() {

			public void doubleClick(DoubleClickEvent event) {
				Object selection = ((IStructuredSelection) event.getSelection()).getFirstElement();
				if (selection instanceof IBundle) {
					IBundle bundle = (IBundle) selection;
					setSelection(bundle);
				}
			}
			
		});

		toolBarManager = sform.getToolBarManager();
		toolBarManager.add(searchControl);

		backAction = new Action("Back") {
			@Override
			public void run() {
				searchControl.getSearchText().setText(history.back());
				setEnabled(history.canBack());
				forwardAction.setEnabled(history.canForward());
				toolBarManager.update(true);
				new BundleDependencyUpdateJob(true).schedule();
			}
		};
		final ICommandImageService service = getSite().getWorkbenchWindow().getService(ICommandImageService.class);
		final ImageDescriptor imgDescBack = service.getImageDescriptor(IWorkbenchCommandConstants.NAVIGATE_BACK);
		backAction.setImageDescriptor(imgDescBack);
		backAction.setHoverImageDescriptor(imgDescBack);
		backAction.setDisabledImageDescriptor(imgDescBack);
		backAction.setEnabled(false);
		toolBarManager.add(backAction);

		forwardAction = new Action("Forward") {
			@Override
			public void run() {
				searchControl.getSearchText().setText(history.forward());
				setEnabled(history.canForward());
				backAction.setEnabled(history.canBack());
				toolBarManager.update(true);
				new BundleDependencyUpdateJob(true).schedule();
			}
		};
		ImageDescriptor imgDescFwd = service.getImageDescriptor(IWorkbenchCommandConstants.NAVIGATE_FORWARD);
		forwardAction.setImageDescriptor(imgDescFwd);
		forwardAction.setHoverImageDescriptor(imgDescFwd);
		forwardAction.setDisabledImageDescriptor(imgDescFwd);
		forwardAction.setEnabled(false);
		toolBarManager.add(forwardAction);

		refreshAction = new Action("Refresh from server", service.getImageDescriptor(IWorkbenchCommandConstants.FILE_REFRESH)) {

			@Override
			public void run() {
				IRunnableWithProgress runnable = new IRunnableWithProgress() {

					public void run(final IProgressMonitor monitor) throws InvocationTargetException, InterruptedException {
						monitor.beginTask("Updating bundle status from server", 1);
						Display.getDefault().asyncExec(new Runnable() {
							public void run() {
								clearStatus();
								
								IOSGiFrameworkAdmin admin = (IOSGiFrameworkAdmin) getServer().getOriginal()
										.loadAdapter(IOSGiFrameworkAdmin.class, monitor);
								
								if (admin == null) {
									IStatus status = EditorUIPlugin.newErrorStatus("Bundle Dependency Graph editor part is not integrated with the runtime.");
									EditorUIPlugin.log(status);
									setStatus(status);
									return ;
								}
								
								try {
									Map<Long, IBundle> allBundles = admin.getBundles(monitor);
									refresh(allBundles);
								} catch (CoreException e) {
									EditorUIPlugin.log(e);
									setStatus(e.getStatus());
								}
							}
						});
						monitor.worked(1);
					}
				};

				try {
					IRunnableContext context = new ProgressMonitorDialog(Display.getCurrent().getActiveShell());
					context.run(true, true, runnable);
				}
				catch (InvocationTargetException e1) {
					e1.printStackTrace();
				}
				catch (InterruptedException e2) {
					e2.printStackTrace();
				}
			}

		};
		toolBarManager.add(refreshAction);

		sform.updateToolBar();
		initPopupMenu();

		searchControl.getSearchText().addKeyListener(new KeyAdapter() {
			@Override
			public void keyPressed(KeyEvent e) {
				if (e.character == SWT.CR || e.character == SWT.LF) {
					if (!"type filter text".equals(searchControl.getSearchText().getText())) {
						history.add(searchControl.getSearchText().getText());
						forwardAction.setEnabled(history.canForward());
						backAction.setEnabled(history.canBack());
						toolBarManager.update(true);
						new BundleDependencyUpdateJob(true).schedule();
					}
				}
			}
		});

		searchControl.getSearchText().addModifyListener(new ModifyListener() {

			public void modifyText(ModifyEvent e) {
				if ("".equals(searchControl.getSearchText().getText())) {
					new BundleDependencyUpdateJob(true).schedule();
				}
			}
		});

	}
	
	void setSelection(IBundle bundle) {
		setSelection(bundle.getSymbolicName(), bundle.getVersion());
	}
	
	private void setSelection(String bundle, String version) {
		String filterText = bundle + " (" + version + ")";
		searchControl.getSearchText().setText(filterText);
		history.add(filterText);
		forwardAction.setEnabled(history.canForward());
		backAction.setEnabled(history.canBack());
		toolBarManager.update(true);
		new BundleDependencyUpdateJob(true).schedule();
	}

	public AbstractZoomableViewer getZoomableViewer() {
		return viewer;
	}

	private void initPopupMenu() {
		zoomContributionItem = new ZoomContributionViewItem(this);

		MenuManager menuMgr = new MenuManager("#PopupMenu");
		menuMgr.setRemoveAllWhenShown(true);
		menuMgr.addMenuListener(new IMenuListener() {
			public void menuAboutToShow(IMenuManager manager) {
				fillContextMenu(manager);
			}
		});

		Menu menu = menuMgr.createContextMenu(viewer.getControl());
		viewer.getControl().setMenu(menu);
		getSite().registerContextMenu(menuMgr, viewer);
	}

	void fillContextMenu(IMenuManager manager) {
		manager.add(new Separator(IWorkbenchActionConstants.MB_ADDITIONS));

		if (!viewer.getSelection().isEmpty()) {
			manager.add(new Action("Show Bundle Overview") {
				@Override
				public void run() {
					Object obj = ((IStructuredSelection) viewer.getSelection()).getFirstElement();
					if (obj instanceof IBundle) {
						openDependencyPage((IBundle) obj);
					}
				}
			});
			manager.add(new Separator());
		}
		manager.add(zoomContributionItem);
	}

	@Override
	public void init(IEditorSite site, IEditorInput input) {
		super.init(site, input);
		commandManager = ((ServerEditorPartInput) input).getServerCommandManager();
	}

	public void showDependenciesForBundle(String bundle, String version) {
		setSelection(bundle, version);
	}

	public void openDependencyPage(IBundle bundle) {
		BundleInformationEditorPage infoPage = openInformationPage();
		if (infoPage != null) {
			commandManager.getServerEditor().setActiveEditor(infoPage);
			infoPage.showOverviewForBundle(bundle);
		}
	}
	
	public void refresh(Map<Long, IBundle> bundles) {
		if (bundles != null && !bundles.equals(viewer.getInput())) {
			contentProvider.setBundles(bundles);
			viewer.setInput(bundles.values());
			
			BundleInformationEditorPage infoPage = openInformationPage();
			if (infoPage != null) {
				infoPage.refresh(bundles);
			}
		}
	}
	
	private BundleInformationEditorPage openInformationPage() {
		IEditorPart[] parts = commandManager.getServerEditor().findEditors(getEditorInput());
		for (IEditorPart part : parts) {
			if (part instanceof BundleInformationEditorPage) {
				return (BundleInformationEditorPage) part;
			}
		}
		return null;
	}

	@Override
	protected void enablePage() {
		super.enablePage();
		setInfoStatus("Click the 'Refresh' button for fetching data from server.");
	}

	class BundleDependencyUpdateJob extends Job {

		final boolean deleteSelection;

		public BundleDependencyUpdateJob(boolean deleteSelection) {
			super("Updating Bundle Dependency Graph");
			this.deleteSelection = deleteSelection;
		}

		@Override
		protected IStatus run(IProgressMonitor monitor) {
			Display.getDefault().asyncExec(new Runnable() {

				public void run() {
					contentProvider.clearSelection();
					if (deleteSelection) {
						viewer.setSelection(new StructuredSelection());
					}
					viewer.refresh(true);
					viewer.getGraphControl().applyLayout();
				}
			});
			return Status.OK_STATUS;
		}
	}
}
