/*******************************************************************************
 * Copyright (c) 2005, 2015 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
 *******************************************************************************/
package org.eclipse.ui.internal.ide;

import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;

import org.eclipse.core.resources.IProject;
import org.eclipse.core.resources.ProjectScope;
import org.eclipse.core.runtime.Platform;
import org.eclipse.core.runtime.preferences.DefaultScope;
import org.eclipse.core.runtime.preferences.InstanceScope;
import org.eclipse.osgi.util.NLS;
import org.eclipse.swt.SWT;
import org.eclipse.swt.events.SelectionAdapter;
import org.eclipse.swt.events.SelectionEvent;
import org.eclipse.swt.graphics.Font;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Button;
import org.eclipse.swt.widgets.Combo;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Control;
import org.eclipse.swt.widgets.Group;
import org.osgi.service.prefs.BackingStoreException;
import org.osgi.service.prefs.Preferences;

/**
 * A class to handle editing of the line delimiter preferences in core.
 *
 * @since 3.1
 */
public class LineDelimiterEditor {

	private Button defaultButton;

	private Button otherButton;

	private Combo choiceCombo;

	/**
	 * The project whose preferences should be set. In some cases this class
	 * will be used to edit project preferences. If project is null, then we
	 * are editing workspace preferences.
	 */
	private IProject project;

	private Group group;

	/**
	 * Creates a new line delimiter editor for workspace.
	 *
	 * @param composite
	 *            the parent of the field editor's control
	 */
	public LineDelimiterEditor(Composite composite) {
		this(composite, null);
	}

	/**
	 * Creates a new line delimiter editor for the given project.
	 *
	 * @param composite
	 *            the parent of the field editor's control
	 * @param project
	 *            the project to set preferences on
	 */
	public LineDelimiterEditor(Composite composite, IProject project) {
		this.project = project;
		createControl(composite);
	}

	/**
	 * Creates this field editor's main control containing all of its basic
	 * controls.
	 *
	 * @param parent
	 *            the parent control
	 */
	private void createControl(Composite parent) {
		Font font = parent.getFont();
		group = new Group(parent, SWT.NONE);
		GridData data = new GridData(GridData.FILL_HORIZONTAL);
		group.setLayoutData(data);
		GridLayout layout = new GridLayout();
		layout.numColumns = 2;
		group.setLayout(layout);
		group.setText(IDEWorkbenchMessages.IDEWorkspacePreference_fileLineDelimiter);
		group.setFont(font);

		SelectionAdapter buttonListener = new SelectionAdapter() {
			@Override
			public void widgetSelected(SelectionEvent e) {
				if (e.widget.equals(defaultButton)) {
					updateState(true);
				} else {
					updateState(false);
				}
			}
		};

		defaultButton = new Button(group, SWT.RADIO);
		String key = getKeyForValue(getDefaultValue());
		if (project == null) {
			defaultButton.setText(NLS.bind(IDEWorkbenchMessages.IDEWorkspacePreference_defaultLineDelim, key));
		} else {
			defaultButton.setText(NLS.bind(IDEWorkbenchMessages.IDEWorkspacePreference_defaultLineDelimProj, key));
		}

		data = new GridData();
		data.horizontalSpan = 2;
		defaultButton.setLayoutData(data);
		defaultButton.addSelectionListener(buttonListener);
		defaultButton.setFont(font);

		otherButton = new Button(group, SWT.RADIO);
		otherButton.setText(IDEWorkbenchMessages.IDEWorkspacePreference_otherLineDelim);
		otherButton.addSelectionListener(buttonListener);
		otherButton.setFont(font);

		choiceCombo = new Combo(group, SWT.NONE | SWT.READ_ONLY);
		data = new GridData();
		choiceCombo.setFont(font);
		choiceCombo.setLayoutData(data);
	}

	/**
	 * Load the list items from core and update the state of the buttons to
	 * match what the preference is currently set to.
	 */
	public void doLoad() {
		if (choiceCombo != null) {
			choiceCombo.setItems(getChoices());
			String resourcePreference = getStoredValue(getPreferences(project));
			selectChoice(getKeyForValue(resourcePreference));
			updateState(resourcePreference == null);
		}
	}

	/**
	 * Initializes this field editor with the preference default value.
	 */
	public void loadDefault() {
		if (choiceCombo != null) {
			updateState(true);
		}
	}

	private String getDefaultValue() {
		String value = null;
		if (project != null) {
			value = getStoredValue(getPreferences(null));
		}
		if (value == null) {
			value = getStoredValue(Platform.getPreferencesService().getRootNode().node(DefaultScope.SCOPE));
		}
		return value != null ? value : System.getProperty(Platform.PREF_LINE_SEPARATOR);
	}

	private String getKeyForValue(String value) {
		Map<String, String> knownValues = Platform.knownPlatformLineSeparators();
		for (Entry<String, String> entry : knownValues.entrySet()) {
			String key = entry.getKey();
			if (entry.getValue().equals(value)) {
				return key;
			}
		}
		return null;
	}

	/**
	 * Returns the value that is currently stored for the line delimiter.
	 *
	 * @param node
	 *            preferences node from which the value should be read
	 * @return the currently stored line delimiter
	 */
	private String getStoredValue(Preferences node) {
		try {
			// be careful looking up for our node so not to create any nodes as side effect
			if (node.nodeExists(Platform.PI_RUNTIME))
				return node.node(Platform.PI_RUNTIME).get(Platform.PREF_LINE_SEPARATOR, null);
		} catch (BackingStoreException e) {
			// ignore
		}
		return null;
	}

	/**
	 * Answer the <code>Preferences</code> for the receiver, this will be a
	 * project preferences if the receiver is editing project preferences,
	 * otherwise instance preferences.
	 *
	 * @param project
	 *            the project for which the line editor will be modified
	 * @return the preferences
	 */
	private Preferences getPreferences(IProject project) {
		if (project != null) {
			return Platform.getPreferencesService().getRootNode().node(ProjectScope.SCOPE).node(project.getName());
		}

		return Platform.getPreferencesService().getRootNode().node(InstanceScope.SCOPE);
	}

	/**
	 * Returns the default setting for the object being shown.
	 *
	 * @return the default setting for the object being shown
	 */
	private String[] getChoices() {
		Set keys = Platform.knownPlatformLineSeparators().keySet();
		String[] keyArray = new String[keys.size()];
		keys.toArray(keyArray);
		return keyArray;
	}

	private void updateState(boolean useDefault) {
		if (useDefault) {
			defaultButton.setSelection(true);
			otherButton.setSelection(false);
			choiceCombo.setEnabled(false);
			selectChoice(getKeyForValue(getDefaultValue()));
		} else {
			defaultButton.setSelection(false);
			otherButton.setSelection(true);
			choiceCombo.setEnabled(true);
		}
	}

	/**
	 * Select the item in the combo that matches the current preferences
	 * setting. NOTE: not handling the case where two platform line separators
	 * are defined with the same value. Assumption is that they are unique and
	 * the key will be modified to represent that. E.g. a key might be Mac OS
	 * 10/Linux if the same value is required for two platforms.
	 */
	private void selectChoice(String selection) {
		String[] items = choiceCombo.getItems();
		for (int i = 0; i < items.length; i++) {
			String item = items[i];
			if (item.equals(selection)) {
				choiceCombo.select(i);
				break;
			}
		}
	}

	/**
	 * Store the currently selected line delimiter value in the preference
	 * store.
	 */
	public void store() {
		String val;
		if (defaultButton.getSelection() || choiceCombo.getText().equals("")) { //$NON-NLS-1$
			val = null;
		} else {
			Map lineSeparators = Platform.knownPlatformLineSeparators();
			val = (String) lineSeparators.get(choiceCombo.getText());
		}

		Preferences node = getPreferences(project).node(Platform.PI_RUNTIME);
		if (val == null) {
			node.remove(Platform.PREF_LINE_SEPARATOR);
		} else {
			node.put(Platform.PREF_LINE_SEPARATOR, val);
		}
		try {
			node.flush();
		} catch (BackingStoreException e) {
			IDEWorkbenchPlugin.log(e.getMessage(), e);
		}
	}

	/**
	 * Set whether or not the controls in the field editor are enabled.
	 *
	 * @param enabled
	 *            The enabled state.
	 */
	public void setEnabled(boolean enabled) {
		group.setEnabled(enabled);
		for (Control child : group.getChildren()) {
			child.setEnabled(enabled);
		}
	}
}
