/*=============================================================================#
 # Copyright (c) 2006, 2020 Stephan Wahlbrink and others.
 # 
 # This program and the accompanying materials are made available under the
 # terms of the Eclipse Public License 2.0 which is available at
 # https://www.eclipse.org/legal/epl-2.0, or the Apache License, Version 2.0
 # which is available at https://www.apache.org/licenses/LICENSE-2.0.
 # 
 # SPDX-License-Identifier: EPL-2.0 OR Apache-2.0
 # 
 # Contributors:
 #     Stephan Wahlbrink <sw@wahlbrink.eu> - initial API and implementation
 #=============================================================================*/

package org.eclipse.statet.nico.ui.views;

import org.eclipse.debug.core.DebugEvent;
import org.eclipse.debug.core.DebugPlugin;
import org.eclipse.debug.core.IDebugEventSetListener;
import org.eclipse.jface.action.Action;
import org.eclipse.jface.action.IMenuManager;
import org.eclipse.jface.action.IToolBarManager;
import org.eclipse.jface.viewers.IStructuredContentProvider;
import org.eclipse.jface.viewers.IStructuredSelection;
import org.eclipse.jface.viewers.ITableLabelProvider;
import org.eclipse.jface.viewers.LabelProvider;
import org.eclipse.jface.viewers.TableViewer;
import org.eclipse.jface.viewers.Viewer;
import org.eclipse.swt.SWT;
import org.eclipse.swt.custom.BusyIndicator;
import org.eclipse.swt.dnd.DND;
import org.eclipse.swt.dnd.DragSourceEvent;
import org.eclipse.swt.dnd.TableDragSourceEffect;
import org.eclipse.swt.dnd.Transfer;
import org.eclipse.swt.events.ControlAdapter;
import org.eclipse.swt.events.ControlEvent;
import org.eclipse.swt.graphics.Image;
import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Table;
import org.eclipse.swt.widgets.TableColumn;
import org.eclipse.ui.IActionBars;
import org.eclipse.ui.IMemento;
import org.eclipse.ui.IViewSite;
import org.eclipse.ui.PartInitException;
import org.eclipse.ui.actions.ActionFactory;
import org.eclipse.ui.menus.CommandContributionItem;
import org.eclipse.ui.menus.CommandContributionItemParameter;
import org.eclipse.ui.part.ViewPart;

import org.eclipse.statet.jcommons.collections.ImCollections;
import org.eclipse.statet.jcommons.collections.ImList;
import org.eclipse.statet.jcommons.ts.core.Tool;
import org.eclipse.statet.jcommons.ts.core.ToolRunnable;

import org.eclipse.statet.ecommons.ts.ui.workbench.WorkbenchToolRegistry;
import org.eclipse.statet.ecommons.ts.ui.workbench.WorkbenchToolRegistryListener;
import org.eclipse.statet.ecommons.ts.ui.workbench.WorkbenchToolSessionData;
import org.eclipse.statet.ecommons.ui.util.UIAccess;

import org.eclipse.statet.internal.nico.ui.LocalTaskTransfer;
import org.eclipse.statet.internal.nico.ui.Messages;
import org.eclipse.statet.nico.core.runtime.Queue;
import org.eclipse.statet.nico.core.runtime.ToolProcess;
import org.eclipse.statet.nico.ui.NicoUI;
import org.eclipse.statet.nico.ui.NicoUITools;
import org.eclipse.statet.nico.ui.util.ToolProgressGroup;


/**
 * A view for the queue of a tool process.
 * 
 * Usage: This class is not intended to be subclassed.
 */
public class QueueView extends ViewPart {
	
	
	private class ViewContentProvider implements IStructuredContentProvider, IDebugEventSetListener {
		
		private volatile boolean expectInfoEvent= false;
		private ImList<ToolRunnable> refreshData;
		
		@Override
		public void inputChanged(final Viewer viewer, final Object oldInput, final Object newInput) {
			if (oldInput != null && newInput == null) {
				unregister();
			}
			if (newInput != null) {
				final ToolProcess newProcess= (ToolProcess) newInput;
				
				final DebugPlugin manager= DebugPlugin.getDefault();
				if (manager != null) {
					manager.addDebugEventListener(this);
				}
			}
		}
		
		@Override
		public Object[] getElements(final Object inputElement) {
			ToolRunnable[] elements;
			if (this.refreshData != null) {
				elements= this.refreshData.toArray(new ToolRunnable[this.refreshData.size()]);
				this.refreshData= null;
			}
			else {
				elements= new ToolRunnable[0];
				final Queue queue= getQueue();
				if (queue != null) {
					this.expectInfoEvent= true;
					queue.sendElements();
				}
			}
			return elements;
		}
		
		private void unregister() {
			final DebugPlugin manager= DebugPlugin.getDefault();
			if (manager != null) {
				manager.removeDebugEventListener(this);
			}
		}
		
		@Override
		public void dispose() {
			unregister();
		}
		
		private void setElements(final ImList<ToolRunnable> elements) {
			UIAccess.getDisplay().syncExec(new Runnable() {
				@Override
				public void run() {
					if (!UIAccess.isOkToUse(QueueView.this.tableViewer)) {
						return;
					}
					ViewContentProvider.this.refreshData= elements;
					QueueView.this.tableViewer.refresh();
				}
			});
		}
		
		@Override
		public void handleDebugEvents(final DebugEvent[] events) {
			final ToolProcess process= QueueView.this.process;
			if (process == null) {
				return;
			}
			boolean updateProgress= false;
			final Queue queue= process.getQueue();
			EVENT: for (int i= 0; i < events.length; i++) {
				final DebugEvent event= events[i];
				final Object source= event.getSource();
				if (source == queue) {
					switch (event.getKind()) {
					
					case DebugEvent.CHANGE:
						if (event.getDetail() != DebugEvent.CONTENT) {
							continue EVENT;
						}
						final Queue.TaskDelta taskDelta= (Queue.TaskDelta) event.getData();
						switch (taskDelta.type) {
						case ToolRunnable.ADDING_TO:
						case ToolRunnable.MOVING_TO:
							if (!this.expectInfoEvent) {
								if (events.length > i + 1 && taskDelta.data.size() == 1) {
									// Added and removed in same set
									final DebugEvent next= events[i + 1];
									if (next.getSource() == queue
											&& next.getKind() == DebugEvent.CHANGE
											&& next.getDetail() == DebugEvent.CONTENT) {
										final Queue.TaskDelta nextDelta= (Queue.TaskDelta) next.getData();
										if (nextDelta.type == ToolRunnable.STARTING
												&& taskDelta.data.get(0) == nextDelta.data.get(0)) {
											updateProgress= true;
											i++;
											continue EVENT;
										}
									}
								}
								UIAccess.getDisplay().syncExec(new Runnable() {
									@Override
									public void run() {
										if (!UIAccess.isOkToUse(QueueView.this.tableViewer)) {
											return;
										}
										if (taskDelta.position >= 0) {
											for (int j= 0; j < taskDelta.data.size(); j++) {
												QueueView.this.tableViewer.insert(taskDelta.data.get(j), taskDelta.position + j);
											}
										}
										else {
											QueueView.this.tableViewer.add(taskDelta.data.toArray());
										}
									}
								});
							}
							continue EVENT;
						
						case ToolRunnable.STARTING:
							updateProgress= true;
							//$FALL-THROUGH$ continue with delete
						case ToolRunnable.REMOVING_FROM:
						case ToolRunnable.MOVING_FROM:
							if (!this.expectInfoEvent) {
								UIAccess.getDisplay().syncExec(new Runnable() {
									@Override
									public void run() {
										if (!UIAccess.isOkToUse(QueueView.this.tableViewer)) {
											return;
										}
										QueueView.this.tableViewer.remove(taskDelta.data.toArray());
									}
								});
							}
							continue EVENT;
						
//						case Queue.QUEUE_CHANGE:
//							if (!fExpectInfoEvent) {
//								setElements((IToolRunnable[]) event.getData());
//							}
//							continue EVENT;
						}
						continue EVENT;
						
					case DebugEvent.MODEL_SPECIFIC:
						if (event.getDetail() == Queue.QUEUE_INFO && this.expectInfoEvent) {
							this.expectInfoEvent= false;
							setElements((ImList<ToolRunnable>) event.getData());
						}
						continue EVENT;
						
					case DebugEvent.TERMINATE:
						disconnect(process);
						continue EVENT;
						
					default:
						continue EVENT;
					}
				}
			}
			if (updateProgress && QueueView.this.showProgress) {
				final ToolProgressGroup progress= QueueView.this.progressControl;
				if (progress != null) {
					progress.refresh(false);
				}
			}
		}
	}
	
	private class TableLabelProvider extends LabelProvider implements ITableLabelProvider {
		
		@Override
		public Image getColumnImage(final Object element, final int columnIndex) {
			if (columnIndex == 0) {
				return getImage(element);
			}
			return null;
		}
		
		@Override
		public Image getImage(final Object element) {
			return NicoUITools.getImage((ToolRunnable) element);
		}
		
		@Override
		public String getColumnText(final Object element, final int columnIndex) {
			if (columnIndex == 0) {
				return getText(element);
			}
			return ""; //$NON-NLS-1$
		}
		
		@Override
		public String getText(final Object element) {
			final ToolRunnable runnable= (ToolRunnable) element;
			return runnable.getLabel();
		}
	}
	
	private class ShowDescriptionAction extends Action {
		
		public ShowDescriptionAction() {
			setText(Messages.ShowToolDescription_name);
			setToolTipText(Messages.ShowToolDescription_tooltip);
			setChecked(QueueView.this.showDescription);
		}
		
		@Override
		public void run() {
			QueueView.this.showDescription= isChecked();
			updateContentDescription(QueueView.this.process);
		}
	}
	
	private class ShowProgressAction extends Action {
		
		public ShowProgressAction() {
			setText(Messages.ShowProgress_name);
			setToolTipText(Messages.ShowProgress_tooltip);
			setChecked(QueueView.this.showProgress);
		}
		
		@Override
		public void run() {
			QueueView.this.showProgress= isChecked();
			if (QueueView.this.showProgress) {
				createProgressControl();
				QueueView.this.progressControl.setTool(QueueView.this.process, true);
				QueueView.this.progressControl.getControl().moveAbove(QueueView.this.tableViewer.getControl());
			}
			else {
				if (QueueView.this.progressControl != null) {
					QueueView.this.progressControl.getControl().dispose();
					QueueView.this.progressControl= null;
				}
			}
			QueueView.this.composite.layout(true);
		}
	}
	
	
	private Composite composite;
	private ToolProgressGroup progressControl;
	private TableViewer tableViewer;
	
	private ToolProcess process;
	private WorkbenchToolRegistryListener toolRegistryListener;
	
	private static final String M_SHOW_DESCRIPTION= "QueueView.ShowDescription"; //$NON-NLS-1$
	private boolean showDescription;
	private Action showDescriptionAction;
	
	private static final String M_SHOW_PROGRESS= "QueueView.ShowProgress"; //$NON-NLS-1$
	private boolean showProgress;
	private Action showProgressAction;
	
	private Action selectAllAction;
	private Action deleteAction;
	
	
	public QueueView() {
	}
	
	
	@Override
	public void init(final IViewSite site, final IMemento memento) throws PartInitException {
		super.init(site, memento);
		
		final String showDescription= (memento != null) ? memento.getString(M_SHOW_DESCRIPTION) : null;
		if (showDescription == null || showDescription.equals("off")) { // default  //$NON-NLS-1$
			this.showDescription= false;
		} else {
			this.showDescription= true;
		}
		
		final String showProgress= (memento != null) ? memento.getString(M_SHOW_PROGRESS) : null;
		if (showProgress== null || showProgress.equals("on")) { // default  //$NON-NLS-1$
			this.showProgress= true;
		} else {
			this.showProgress= false;
		}
	}
	
	@Override
	public void saveState(final IMemento memento) {
		super.saveState(memento);
		
		memento.putString(M_SHOW_DESCRIPTION, (this.showDescription) ? "on" : "off"); //$NON-NLS-1$ //$NON-NLS-2$
		memento.putString(M_SHOW_PROGRESS, (this.showProgress) ? "on" : "off"); //$NON-NLS-1$ //$NON-NLS-2$
	}
	
	@Override
	public void createPartControl(final Composite parent) {
		updateContentDescription(null);
		
		this.composite= parent;
		final GridLayout layout= new GridLayout();
		layout.marginHeight= 0;
		layout.marginWidth= 0;
		layout.verticalSpacing= 0;
		parent.setLayout(layout);
		
		if (this.showProgress) {
			createProgressControl();
		}
		
		this.tableViewer= new TableViewer(parent, SWT.MULTI | SWT.V_SCROLL);
		this.tableViewer.getControl().setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
		this.tableViewer.getTable().setLinesVisible(false);
		this.tableViewer.getTable().setHeaderVisible(false);
		new TableColumn(this.tableViewer.getTable(), SWT.DEFAULT);
		this.tableViewer.getTable().addControlListener(new ControlAdapter() {
			@Override
			public void controlResized(final ControlEvent e) {
				// adapt the column width to the width of the table
				final Table table= QueueView.this.tableViewer.getTable();
				final Rectangle area= table.getClientArea();
				final TableColumn column= table.getColumn(0);
				column.setWidth(area.width-3); // it looks better with a small gap
			}
		});
		
		this.tableViewer.setContentProvider(new ViewContentProvider());
		this.tableViewer.setLabelProvider(new TableLabelProvider());
		
		createActions();
		contributeToActionBars();
		hookDND();
		
		// listen on console changes
		final WorkbenchToolRegistry toolRegistry= NicoUI.getToolRegistry();
		connect(toolRegistry.getActiveToolSession(getViewSite().getPage()).getTool());
		this.toolRegistryListener= new WorkbenchToolRegistryListener() {
			@Override
			public void toolSessionActivated(final WorkbenchToolSessionData sessionData) {
				final Tool tool= sessionData.getTool();
				UIAccess.getDisplay().syncExec(new Runnable() {
					@Override
					public void run() {
						connect(tool);
					}
				});
			}
			@Override
			public void toolTerminated(final WorkbenchToolSessionData sessionData) {
				// handled by debug events
			}
		};
		toolRegistry.addListener(this.toolRegistryListener, getViewSite().getPage());
	}
	
	
	private void createProgressControl() {
		this.progressControl= new ToolProgressGroup(this.composite);
		this.progressControl.getControl().setLayoutData(
				new GridData(SWT.FILL, SWT.FILL, true, false));
	}
	
	protected void updateContentDescription(final ToolProcess process) {
		if (this.showDescription) {
			setContentDescription(process != null ? process.getLabel(0) : " "); //$NON-NLS-1$
		}
		else {
			setContentDescription(""); //$NON-NLS-1$
		}
	}
	
	private void createActions() {
		this.showDescriptionAction= new ShowDescriptionAction();
		this.showProgressAction= new ShowProgressAction();
		
		this.selectAllAction= new Action() {
			@Override
			public void run() {
				QueueView.this.tableViewer.getTable().selectAll();
			}
		};
		this.deleteAction= new Action() {
			@Override
			public void run() {
				final Queue queue= getQueue();
				if (queue != null) {
					final IStructuredSelection selection= (IStructuredSelection) QueueView.this.tableViewer.getSelection();
					queue.remove(ImCollections.toList(selection.toList()));
				}
			}
		};
	}
	
	private void contributeToActionBars() {
		final IActionBars bars= getViewSite().getActionBars();
		
		bars.setGlobalActionHandler(ActionFactory.SELECT_ALL.getId(), this.selectAllAction);
		bars.setGlobalActionHandler(ActionFactory.DELETE.getId(), this.deleteAction);
		
		fillLocalPullDown(bars.getMenuManager());
		fillLocalToolBar(bars.getToolBarManager());
	}
	
	private void fillLocalPullDown(final IMenuManager manager) {
		manager.add(this.showDescriptionAction);
		manager.add(this.showProgressAction);
	}
	
	private void fillLocalToolBar(final IToolBarManager manager) {
		manager.add(new CommandContributionItem(new CommandContributionItemParameter(
				getSite(), null, NicoUI.PAUSE_COMMAND_ID, null,
				null, null, null,
				null, null, null,
				CommandContributionItem.STYLE_CHECK, null, false)));
	}
	
	private void hookDND() {
		this.tableViewer.addDragSupport(DND.DROP_MOVE,
				new Transfer[] { LocalTaskTransfer.getTransfer() },
				new TableDragSourceEffect(this.tableViewer.getTable()) {
			@Override
			public void dragStart(final DragSourceEvent event) {
				if (QueueView.this.tableViewer.getTable().getSelectionCount() > 0) {
					event.doit= true;
				} else {
					event.doit= false;
				}
				LocalTaskTransfer.getTransfer().init(QueueView.this.process);
				super.dragStart(event);
			}
			@Override
			public void dragSetData(final DragSourceEvent event) {
				super.dragSetData(event);
				final LocalTaskTransfer.Data data= LocalTaskTransfer.getTransfer().createData();
				if (data.process != QueueView.this.process) {
					event.doit= false;
					return;
				}
				data.runnables= ImCollections.toList(
						((IStructuredSelection) QueueView.this.tableViewer.getSelection()).toList() );
				event.data= data;
			}
			@Override
			public void dragFinished(final DragSourceEvent event) {
				super.dragFinished(event);
				LocalTaskTransfer.getTransfer().finished();
			}
		});
	}
	
	private void disconnect(final ToolProcess process) {
		UIAccess.getDisplay().syncExec(new Runnable() {
			@Override
			public void run() {
				if (QueueView.this.process != null && QueueView.this.process == process) {
					connect(null);
				}
			}
		});
	}
	
	/** May only be called in UI thread */
	private void connect(final Tool tool) {
		final ToolProcess process= (tool instanceof ToolProcess) ? (ToolProcess)tool : null;
		final Runnable runnable= new Runnable() {
			@Override
			public void run() {
				if (!UIAccess.isOkToUse(QueueView.this.tableViewer)) {
					return;
				}
				QueueView.this.process= process;
				updateContentDescription(process);
				if (QueueView.this.progressControl != null) {
					QueueView.this.progressControl.setTool(process, true);
				}
				QueueView.this.tableViewer.setInput(process);
			}
		};
		BusyIndicator.showWhile(UIAccess.getDisplay(), runnable);
	}
	
	/**
	 * Returns the tool process, which this view is connected to.
	 * 
	 * @return a tool process or <code>null</code>, if no process is connected.
	 */
	public ToolProcess getProcess() {
		return this.process;
	}
	
	public Queue getQueue() {
		if (this.process != null) {
			return this.process.getQueue();
		}
		return null;
	}
	
	
	@Override
	public void setFocus() {
		// Passing the focus request to the viewer's control.
		this.tableViewer.getControl().setFocus();
	}
	
	@Override
	public void dispose() {
		super.dispose();
	}
	
}
