/**
 *  Copyright (c)2020 CEA LIST, Committer Name, and others.
 * 
 *  All rights reserved. This program and the accompanying materials
 *  are made available under the terms of the Eclipse Public License 2.0
 *  which accompanies this distribution, and is available at
 *  https://www.eclipse.org/legal/epl-2.0/
 * 
 *  SPDX-License-Identifier: EPL-2.0
 * 
 *  Contributors:
 *  CEA LIST - Initial API and implementation
 *  Patrick Tessier (CEA LIST) Patrick.tessier@cea.fr 
 *  Gabriel Pedroza (CEA LIST) gabriel.pedroza@cea.fr 
 * 
 */
package org.eclipse.papyrus.pdp4eng.req.profile.pdp4engReqGDPR.impl;

import org.eclipse.emf.common.notify.Notification;

import org.eclipse.emf.ecore.EClass;
import org.eclipse.emf.ecore.InternalEObject;

import org.eclipse.emf.ecore.impl.ENotificationImpl;

import org.eclipse.papyrus.pdp4eng.common.profile.pdp4engCommonGDPR.VitalInterest;

import org.eclipse.papyrus.pdp4eng.req.profile.pdp4engReqGDPR.LawfulByVitalInterest;
import org.eclipse.papyrus.pdp4eng.req.profile.pdp4engReqGDPR.pdp4engReqGDPRPackage;

/**
 * <!-- begin-user-doc -->
 * An implementation of the model object '<em><b>Lawful By Vital Interest</b></em>'.
 * <!-- end-user-doc -->
 * <p>
 * The following features are implemented:
 * </p>
 * <ul>
 *   <li>{@link org.eclipse.papyrus.pdp4eng.req.profile.pdp4engReqGDPR.impl.LawfulByVitalInterestImpl#getVitalInterest <em>Vital Interest</em>}</li>
 * </ul>
 *
 * @generated
 */
public class LawfulByVitalInterestImpl extends LawfulImpl implements LawfulByVitalInterest {
	/**
	 * The cached value of the '{@link #getVitalInterest() <em>Vital Interest</em>}' reference.
	 * <!-- begin-user-doc -->
	 * <!-- end-user-doc -->
	 * @see #getVitalInterest()
	 * @generated
	 * @ordered
	 */
	protected VitalInterest vitalInterest;

	/**
	 * <!-- begin-user-doc -->
	 * <!-- end-user-doc -->
	 * @generated
	 */
	protected LawfulByVitalInterestImpl() {
		super();
	}

	/**
	 * <!-- begin-user-doc -->
	 * <!-- end-user-doc -->
	 * @generated
	 */
	@Override
	protected EClass eStaticClass() {
		return pdp4engReqGDPRPackage.Literals.LAWFUL_BY_VITAL_INTEREST;
	}

	/**
	 * <!-- begin-user-doc -->
	 * <!-- end-user-doc -->
	 * @generated
	 */
	@Override
	public VitalInterest getVitalInterest() {
		if (vitalInterest != null && vitalInterest.eIsProxy()) {
			InternalEObject oldVitalInterest = (InternalEObject)vitalInterest;
			vitalInterest = (VitalInterest)eResolveProxy(oldVitalInterest);
			if (vitalInterest != oldVitalInterest) {
				if (eNotificationRequired())
					eNotify(new ENotificationImpl(this, Notification.RESOLVE, pdp4engReqGDPRPackage.LAWFUL_BY_VITAL_INTEREST__VITAL_INTEREST, oldVitalInterest, vitalInterest));
			}
		}
		return vitalInterest;
	}

	/**
	 * <!-- begin-user-doc -->
	 * <!-- end-user-doc -->
	 * @generated
	 */
	public VitalInterest basicGetVitalInterest() {
		return vitalInterest;
	}

	/**
	 * <!-- begin-user-doc -->
	 * <!-- end-user-doc -->
	 * @generated
	 */
	@Override
	public void setVitalInterest(VitalInterest newVitalInterest) {
		VitalInterest oldVitalInterest = vitalInterest;
		vitalInterest = newVitalInterest;
		if (eNotificationRequired())
			eNotify(new ENotificationImpl(this, Notification.SET, pdp4engReqGDPRPackage.LAWFUL_BY_VITAL_INTEREST__VITAL_INTEREST, oldVitalInterest, vitalInterest));
	}

	/**
	 * <!-- begin-user-doc -->
	 * <!-- end-user-doc -->
	 * @generated
	 */
	@Override
	public Object eGet(int featureID, boolean resolve, boolean coreType) {
		switch (featureID) {
			case pdp4engReqGDPRPackage.LAWFUL_BY_VITAL_INTEREST__VITAL_INTEREST:
				if (resolve) return getVitalInterest();
				return basicGetVitalInterest();
		}
		return super.eGet(featureID, resolve, coreType);
	}

	/**
	 * <!-- begin-user-doc -->
	 * <!-- end-user-doc -->
	 * @generated
	 */
	@Override
	public void eSet(int featureID, Object newValue) {
		switch (featureID) {
			case pdp4engReqGDPRPackage.LAWFUL_BY_VITAL_INTEREST__VITAL_INTEREST:
				setVitalInterest((VitalInterest)newValue);
				return;
		}
		super.eSet(featureID, newValue);
	}

	/**
	 * <!-- begin-user-doc -->
	 * <!-- end-user-doc -->
	 * @generated
	 */
	@Override
	public void eUnset(int featureID) {
		switch (featureID) {
			case pdp4engReqGDPRPackage.LAWFUL_BY_VITAL_INTEREST__VITAL_INTEREST:
				setVitalInterest((VitalInterest)null);
				return;
		}
		super.eUnset(featureID);
	}

	/**
	 * <!-- begin-user-doc -->
	 * <!-- end-user-doc -->
	 * @generated
	 */
	@Override
	public boolean eIsSet(int featureID) {
		switch (featureID) {
			case pdp4engReqGDPRPackage.LAWFUL_BY_VITAL_INTEREST__VITAL_INTEREST:
				return vitalInterest != null;
		}
		return super.eIsSet(featureID);
	}

} //LawfulByVitalInterestImpl
