/*=============================================================================#
 # Copyright (c) 2012, 2019 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.ecommons.emf.ui.forms;

import org.eclipse.core.databinding.DataBindingContext;
import org.eclipse.core.databinding.observable.IObservable;
import org.eclipse.core.databinding.observable.Realm;
import org.eclipse.core.databinding.observable.value.IObservableValue;
import org.eclipse.emf.ecore.EClass;
import org.eclipse.emf.ecore.EStructuralFeature;
import org.eclipse.emf.edit.domain.EditingDomain;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Control;
import org.eclipse.ui.PlatformUI;
import org.eclipse.ui.swt.IFocusService;

import org.eclipse.statet.ecommons.emf.core.databinding.IEMFEditContext;
import org.eclipse.statet.ecommons.emf.core.databinding.IEMFEditPropertyContext;


public class EFProperty implements IEMFEditPropertyContext {
	
	
	protected static void register(final Control control, final String id) {
		final IFocusService service= PlatformUI.getWorkbench().getService(IFocusService.class);
		if (service != null) {
			service.addFocusTracker(control, id);
		}
	}
	
	
	private final String label;
	private final String tooltip;
	
	private final EClass eClass;
	private final EStructuralFeature eFeature;
	
	private IEMFEditContext context;
	
	
	public EFProperty(final String label, final String tooltip,
			final EClass eClass, final EStructuralFeature eFeature) {
		this.label= label;
		this.tooltip= tooltip;
		
		this.eClass= eClass;
		this.eFeature= eFeature;
	}
	
	
	public String getLabel() {
		return this.label;
	}
	
	public String getTooltip() {
		return this.tooltip;
	}
	
	@Override
	public EClass getEClass() {
		return this.eClass;
	}
	
	@Override
	public EStructuralFeature getEFeature() {
		return this.eFeature;
	}
	
	
	public void create(final Composite parent, final IEFFormPage page) {
	}
	
	public Control getControl() {
		return null;
	}
	
	
	public void bind(final IEMFEditContext context) {
		this.context= context;
	}
	
	@Override
	public IObservable getPropertyObservable() {
		return null;
	}
	
	@Override
	public EditingDomain getEditingDomain() {
		return this.context.getEditingDomain();
	}
	
	@Override
	public DataBindingContext getDataBindingContext() {
		return this.context.getDataBindingContext();
	}
	
	@Override
	public Realm getRealm() {
		return this.context.getRealm();
	}
	
	@Override
	public IObservableValue getBaseObservable() {
		return this.context.getBaseObservable();
	}
	
	@Override
	@SuppressWarnings("unchecked")
	public <T> T getAdapter(final Class<T> adapterType) {
		if (adapterType.isInstance(this)) {
			return (T) this;
		}
		return this.context.getAdapter(adapterType);
	}
	
}
